Author Topic: How to use the DrawVectors function?  (Read 8884 times)

0 Members and 1 Guest are viewing this topic.

sinc

  • Guest
Re: How to use the DrawVectors function?
« Reply #15 on: November 01, 2008, 03:36:28 PM »
I saw those, but didn't take the time to watch them, because they looked too "introductory".

Would they help with my current problem?

I'm trying to use the PointMonitor event, the way you indicated, and it's working fine with one exception.  It works fine the first time it is invoked.  But the second time it is invoked, it displays the geometry drawn during the first invocation until the user moves the mouse.  As soon as the user moves the mouse, it updates the geometry, and everything is drawn correctly.  But I can't figure out why it appears to be "remembering" the geometry from the last invocation...

Spike Wilbury

  • Guest
Re: How to use the DrawVectors function?
« Reply #16 on: November 01, 2008, 03:56:53 PM »
I saw those, but didn't take the time to watch them, because they looked too "introductory".

Would they help with my current problem?

I'm trying to use the PointMonitor event, the way you indicated, and it's working fine with one exception.  It works fine the first time it is invoked.  But the second time it is invoked, it displays the geometry drawn during the first invocation until the user moves the mouse.  As soon as the user moves the mouse, it updates the geometry, and everything is drawn correctly.  But I can't figure out why it appears to be "remembering" the geometry from the last invocation...

Below there are some of those functions:

Code: [Select]

[CommandMethod("newInput")]
public void NewInput()
{
// start our input point Monitor   
// get the editor object
Editor ed = acadApp.DocumentManager.MdiActiveDocument.Editor;
// now add the delegate to the events list
ed.PointMonitor += new PointMonitorEventHandler(this.MyInputMonitor);
ed.TurnForcedPickOn();
// now pick some point, this emulates a real world input that may be required
// pick the center point of the circle
PromptPointOptions getPointOptions = new PromptPointOptions("Pick A Point : ");
if (ed.GetPoint(getPointOptions).Status == PromptStatus.OK)
{
// do something
}

// now remove our point monitor as we are finished With it
ed.PointMonitor -= new PointMonitorEventHandler(this.MyInputMonitor);
}

public void MyInputMonitor(object sender, PointMonitorEventArgs e)
{
// first lets check what is under the Cursor
FullSubentityPath[] fullEntPath = e.Context.GetPickedEntities();
if (fullEntPath.Length > 0)
{
// start a transaction
Transaction trans = acadApp.DocumentManager.MdiActiveDocument.Database.TransactionManager.StartTransaction();
try
{
// open the Entity for read, it must be derived from Curve
Curve ent = (Curve)trans.GetObject(fullEntPath[0].GetObjectIds()[0], OpenMode.ForRead);
// ok, so if we are over something - then check to see if it has an extension dictionary
if (ent.ExtensionDictionary.IsValid)
{
// open it for read
DBDictionary extensionDict = (DBDictionary)trans.GetObject(ent.ExtensionDictionary, OpenMode.ForRead);
// find the entry
ObjectId entryId = extensionDict.GetAt("MyData");
// if we are here, then all is ok
// extract the xrecord
Xrecord myXrecord = (Xrecord) trans.GetObject(entryId, OpenMode.ForRead);
// now draw the positions
foreach (TypedValue value in myXrecord.Data)
{
// if the TypeCode is a distance value
if (value.TypeCode == 40)
{
// draw some temporary graphics along the Curve to show the distances

// first get the point along the curve
Point3d pnt = ent.GetPointAtDist((double)value.Value);
// next work out how many pixels are in a unit square - so we can keep the temporary graphics a set size
Point2d pixels = e.Context.DrawContext.Viewport.GetNumPixelsInUnitSquare(pnt);
// setup the constant distances
double xDist = 10 / pixels.X;
double yDist = 10 / pixels.Y;

// then draw the temporary Graphics
Circle circle = new Circle(pnt, Vector3d.ZAxis, xDist);
e.Context.DrawContext.Geometry.Draw(circle);
// more temporary graphics
DBText text = new DBText();
// always a good idea to set the Database defaults With things like text, dimensions etc
text.SetDatabaseDefaults();
// set the position of the text to the same point as the circle, but offset by the radius
text.Position = pnt + new Vector3d(xDist, yDist, 0);
text.TextString = value.Value.ToString();
text.Height = yDist;
e.Context.DrawContext.Geometry.Draw(text);
}
}
}
// all ok, commit it
trans.Commit();
}
catch
{
}
finally
{
// whatever happens, nuke the transaction
trans.Dispose();
}
}
}

Code: [Select]
[CommandMethod("pointmonitor")]
static public void pointmonitor()
{
// get the editor object
Editor ed = acadApp.DocumentManager.MdiActiveDocument.Editor;
// now add the delegate to the events list
ed.PointMonitor += new PointMonitorEventHandler(ed_PointMonitor);
}

static void ed_PointMonitor(object sender, PointMonitorEventArgs e)
{
// first let's check what's under the cursor
FullSubentityPath[] fullEntPath = e.Context.GetPickedEntities();

if (fullEntPath.Length > 0)
{
// display a tooltip
// start a transaction
Transaction trans = acadApp.DocumentManager.MdiActiveDocument.Database.TransactionManager.StartTransaction();
try
{
// open the entity for read
Entity ent = (Entity) trans.GetObject(fullEntPath[0].GetObjectIds()[0], OpenMode.ForRead);
e.AppendToolTipText("The Entity is a " + ent.GetType().ToString());

// ok, so if we are over something - then lets highlight it in the palette Window
// find the tag we want in the tree
Font fontRegular = new Font("Microsoft Sans Serif", 8f, FontStyle.Regular);
Font fontBold = new Font("Microsoft Sans Serif", 8f, FontStyle.Bold);

// wait until after we have processed the whole tree before we handle the different sized text
myPalette.treeView1.SuspendLayout();
foreach (TreeNode node in myPalette.treeView1.Nodes)
{
// if it's the one we want
if (ent.ObjectId == (ObjectId)node.Tag)
{
if (!fontBold.Equals(node.NodeFont))
{
node.NodeFont = fontBold;
node.Text = node.Text;
}
}
else if (!fontRegular.Equals(node.NodeFont))
{
node.NodeFont = fontRegular;
}
}

// now it's time to recalc the layout of the treeview
myPalette.treeView1.ResumeLayout();
myPalette.treeView1.Refresh();
myPalette.treeView1.Update();

// all ok, commit it
trans.Commit();
}
catch
{
// Explicit catch all here as we're monitoring cursor movement
}
finally
{
trans.Dispose();
}
}

// ok, so now lets do something really pointless! space invaders!
if ((e.Context.History & PointHistoryBits.NotDigitizer) > PointHistoryBits.DidNotPick)
{
// this means the mouse has been clicked... so...
// create a Circle
Circle circle = new Circle(e.Context.RawPoint, Vector3d.ZAxis, 10);
// draw it
e.Context.DrawContext.Geometry.Draw(circle);
// wait for a while
System.Threading.Thread.Sleep(50);
// draw
circle.Radius = 20;
e.Context.DrawContext.Geometry.Draw(circle);
// wait for a while
System.Threading.Thread.Sleep(50);
// draw it
circle.Radius = 40;
e.Context.DrawContext.Geometry.Draw(circle);
// wait for a while
System.Threading.Thread.Sleep(50);
// draw it
circle.Radius = 80;
e.Context.DrawContext.Geometry.Draw(circle);
// wait for a while
System.Threading.Thread.Sleep(50);
}

}

I am not doing nothing lately with C#... so, cannot be of much help  :-(

sinc

  • Guest
Re: How to use the DrawVectors function?
« Reply #17 on: November 01, 2008, 04:11:33 PM »
I'll take a look through that later, just to see what all is in it.

But I figured out the problem.  It was related to the fact that I was already using an EntityJig, and I tried to save some processing by using a calculation from the EntityJig.  The call to PointMonitor was happening before the required data was being updated by the EntityJig, so that wasn't working.

I redid the code, so that the PointMonitor handler performs the required calculation, and it works fine now.

In the process, it seems as though the EntityJig is no longer necessary.  I was having problems with the EntityJig, in that I wanted to draw a series of objects, and I couldn't figure out any good way of doing that with a Jig.  However, it seems quite easy to do it with PointMonitor instead.  So I suspect I may want to redo this code, and possibly eliminate the Jig entirely.

Kerry

  • Mesozoic relic
  • Seagull
  • Posts: 11654
  • class keyThumper<T>:ILazy<T>
Re: How to use the DrawVectors function?
« Reply #18 on: November 01, 2008, 06:10:55 PM »
And I'd like to thank Glenn for the translation Luis posted ...

Just thought I should post the solution as well because of the UserControl.
< link to zip. >
http://www.theswamp.org/index.php?topic=19780.msg243411#msg243411

kdub, kdub_nz in other timelines.
Perfection is not optional.
Everything will work just as you expect it to, unless your expectations are incorrect.
Discipline: None at all.

TonyT

  • Guest
Re: How to use the DrawVectors function?
« Reply #19 on: November 01, 2008, 10:41:59 PM »
Do you mean Editor.PointMonitor?  How do you use that, Tony?  What methods do we use to draw the temporary graphics, and how do the temporary graphics get removed when we're finished with them?

Sorry, yes I meant PointMonitor (the native method is monitorInputPoint).

It's also a good thing to not leave the handler attached to the event any
longer than needed (e.g., only when you want the graphics to be drawn).

The temporary graphics are erased and redrawn every time the mouse
moves or any other 'input' occurs, so you don't have to worry about
removing it, but you do have to be mindful of excessive processing in
the event handler, for the same reason.


« Last Edit: November 01, 2008, 10:45:13 PM by TonyT »