Page Index Toggle Pages: 1 Send TopicPrint
Normal Topic How to avoid the giagram be update? (Read 3645 times)
GoldyWang
YaBB Newbies
*
Offline


I Love MindFusion!

Posts: 34
Joined: May 7th, 2012
How to avoid the giagram be update?
May 10th, 2012 at 5:02am
Print Post  
Any such mechenism:

diagram.BeginUpdate()

diagram.Nodes.Add(node1);
....
diagram.Nodes.Add(noden);

diagram.EndUpdate()

so can used for:
1. bulk insert nodes and update just once.
2. when back-grand threading nodes, and avoid cross-thread operation with the Ui-thread.
« Last Edit: May 10th, 2012 at 7:49am by GoldyWang »  
Back to top
 
IP Logged
 
Stoyo
God Member
*****
Offline


MindFusion support

Posts: 13230
Joined: Jul 20th, 2005
Re: How to avoid the giagram be update?
Reply #1 - May 10th, 2012 at 6:10am
Print Post  
There isn't any built-in thread synchronization. However you could remove the Diagram from the DiagramView to make it safe to access from another thread:

Code
Select All
private Diagram d;
private void miViewThreadTest_Click(object sender, EventArgs e)
{
	d = diagramView.Diagram;
	diagramView.Diagram = new Diagram();
	diagramView.Diagram.BackgroundImage = d.CreateImage();
	BackgroundWorker w = new BackgroundWorker();
	w.DoWork += w_DoWork;
	w.RunWorkerAsync();
}

void w_DoWork(object sender, DoWorkEventArgs e)
{
	Random r = new Random();
	for (int i = 0; i < 100; i++)
	{
		d.Factory.CreateShapeNode(r.Next(200), r.Next(200), 10, 10);
		Thread.Sleep(10);
	}
	diagramView.Diagram = d;
} 



I hope that helps,
Stoyan
  
Back to top
 
IP Logged
 
GoldyWang
YaBB Newbies
*
Offline


I Love MindFusion!

Posts: 34
Joined: May 7th, 2012
Re: How to avoid the giagram be update?
Reply #2 - May 10th, 2012 at 8:24am
Print Post  
the idea of detaching the doc from view when threading seems work(I have not tried it yet), but it is just a trade-off?


  
Back to top
 
IP Logged
 
GoldyWang
YaBB Newbies
*
Offline


I Love MindFusion!

Posts: 34
Joined: May 7th, 2012
Re: How to avoid the giagram be update?
Reply #3 - May 10th, 2012 at 9:01am
Print Post  
I have such scenario:

//-----------------------------------------------------------
public delegate void TRefreshDelegate();
private TRefreshDelegate RefreshDelegate = new TRefreshDelegate(RefreshCore);
//-----------------------------------------------------------
public void Refresh()
{
if (this.InvokeRequired)
this.Invoke(RefreshDelegate, null);
else
RefreshCore();
}
//-----------------------------------------------------------
public void RefreshCore()
{
view.Refresh();
}

In a Dedicated thread ---
private static void ProberOp(Object state)
{
while (true)
{
.....
diagram.Nodes.Remove(node1); // ** Error point
diagram.Nodes.Add(node2);
Refresh();
Thread.Sleep(1000);
}
}

In my first predicate that the diagram is not control-ui -sensitive(just doc feature), so can ui-threading-free. and can safely run the 'diagram.Nodes.Remove()'.
and let Refresh() to Control.Invoke() the view.Refresh().
but the result is:
error message:"Cross-thread operation not valid: Control '' accessed from a thread other than the thread it was created on"

and error called stack show:
Source=System.Windows.Forms
StackTrace:
at System.Windows.Forms.Control.get_Handle()
at System.Windows.Forms.Control.SetVisibleCore(Boolean value)
at System.Windows.Forms.Control.set_Visible(Boolean value)
at MindFusion.Diagramming.WinForms.DiagramView.ResetScrollbars()
at MindFusion.Diagramming.WinForms.DiagramView.x115588a415d2dbd9(Object xe0292b9ed559da7d, EventArgs xfbf34718e704c6bc)
at MindFusion.Diagramming.Diagram.ResetDocSize()
at MindFusion.Diagramming.Diagram.xaf4db0d26185109c()
at MindFusion.Diagramming.Diagram.RemoveItem(DiagramItem item)
at MindFusion.Diagramming.Commands.RemoveItemCmd.Execute(Boolean undoEnabled)
at MindFusion.Diagramming.UndoManager.xdf8cd2685f83d9b7(Command x61b060a94340c4fc)
at MindFusion.Diagramming.Diagram.x7d877b7264517b49(DiagramItem xccb63ca5f63dc470)
at MindFusion.Diagramming.Diagram.xba535330911dfd91(Object xe0292b9ed559da7d, ItemEventArgs xfbf34718e704c6bc)
at MindFusion.Diagramming.ItemCollectionBase.RaiseRemoving(DiagramItem item)
at MindFusion.Diagramming.DiagramNodeCollection.x52b190e626f65140(DiagramNode xda5bf54deb817e37, Boolean x808547253555a9ba)
at MindFusion.Diagramming.DiagramNodeCollection.Remove(DiagramNode node)
at Pn.Doc.TPlace.RemoveToken(Int32 cnt) in E:\myProjects\0801_Cy\03_Code\Cy2011\Pn\Pn\Place.cs:line 72
at Pn.Doc.TTransition.ProberOp(Object state) in E:\myProjects\0801_Cy\03_Code\Cy2011\Pn\Pn\Transition.cs:line 85
at System.Threading.ThreadHelper.ThreadStart_Context(Object state)
at System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state, Boolean preserveSyncCtx)
at System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state)
at System.Threading.ThreadHelper.ThreadStart(Object obj)

this mean the diagram access the view when diagram.Nodes.Add(node).

so my question is: is there any switch function, when I do not want the view be update in some case? (switch off the refreshing the view)


  
Back to top
 
IP Logged
 
Stoyo
God Member
*****
Offline


MindFusion support

Posts: 13230
Joined: Jul 20th, 2005
Re: How to avoid the giagram be update?
Reply #4 - May 10th, 2012 at 9:07am
Print Post  
There isn't such function, you will have to remove the diagram from this view, or use Control.Invoke to add nodes from the UI thread.
  
Back to top
 
IP Logged
 
GoldyWang
YaBB Newbies
*
Offline


I Love MindFusion!

Posts: 34
Joined: May 7th, 2012
Re: How to avoid the giagram be update?
Reply #5 - May 10th, 2012 at 9:14am
Print Post  
so, the code logic will seems confusion when multi-threading.
how about WPF version of Diagramming?

will the next version deal with it?
  
Back to top
 
IP Logged
 
GoldyWang
YaBB Newbies
*
Offline


I Love MindFusion!

Posts: 34
Joined: May 7th, 2012
Re: How to avoid the giagram be update?
Reply #6 - May 10th, 2012 at 10:31am
Print Post  
Now I try as following, and it seems work now.

    public class TDiagram : Diagram
    {
        public DiagramView View { get; set; }
        //---------------------------------------------------------------------
        public delegate void TRemoveNodeDelegate(ShapeNode node);
        private TRemoveNodeDelegate m_RemoveNodeDelegate;
        [
        Browsable(false),
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden),
        ]
        protected TRemoveNodeDelegate RemoveNodeDelegate
        {
            get
            {
                if (m_RemoveNodeDelegate == null)
                    m_RemoveNodeDelegate = new TRemoveNodeDelegate(RemoveNodeCore);
                return m_RemoveNodeDelegate;
            }
        }
        //--------------------------------------------------------------------
        public void RemoveNode(ShapeNode node)
        {
            if (View.InvokeRequired)
                View.Invoke(RemoveNodeDelegate, new object[] { node });
            else
                RemoveNodeCore(node);
        }
        //--------------------------------------------------------------------
        public void RemoveNodeCore(ShapeNode node)
        {
            this.Nodes.Remove(node);
        }

        //---------------------------------------------------------------------
        public delegate void TAddNodeDelegate(ShapeNode node);
        private TAddNodeDelegate m_AddNodeDelegate;
        [
        Browsable(false),
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden),
        ]
        protected TAddNodeDelegate AddNodeDelegate
        {
            get
            {
                if (m_AddNodeDelegate == null)
                    m_AddNodeDelegate = new TAddNodeDelegate(AddNodeCore);
                return m_AddNodeDelegate;
            }
        }
        //--------------------------------------------------------------------
        public void AddNode(ShapeNode node)
        {
            if (View.InvokeRequired)
                View.Invoke(AddNodeDelegate, new object[] { node });
            else
                AddNodeCore(node);
        }
        //--------------------------------------------------------------------
        public void AddNodeCore(ShapeNode node)
        {
            this.Nodes.Add(node);
        }
        //--------------------------------------------------------------------

    }
  
Back to top
 
IP Logged
 
Stoyo
God Member
*****
Offline


MindFusion support

Posts: 13230
Joined: Jul 20th, 2005
Re: How to avoid the giagram be update?
Reply #7 - May 10th, 2012 at 11:58am
Print Post  
The WPF version isn't thread-safe either. I'm afraid we don't have plans to add thread-safety at this time.
  
Back to top
 
IP Logged
 
Page Index Toggle Pages: 1
Send TopicPrint