none
Problem with labeled edges

    Question

  • Hi,

     

    I'm working on a graph that have nodes and Labeled Edges. In the Viewer I have enabled the Layout Algorithm settings button. When I change the Layout Method to "MDS" or "Ranking" the graph is drawn without Labels. Then I try to drag some node I get an unhandled NullReferenceException. This only occurs if I try to drag a node linked to a edge labeled.

    Next I paste the stacktrace:

     


    System.NullReferenceException was unhandled
      Message="Object reference not set to an instance of an object."
      Source="Microsoft.Msagl.GraphViewerGdi"
      StackTrace:
           at Microsoft.Msagl.GraphViewerGdi.DGraph.RebuildBBHierarchyUnderObject(DObject dObj)
           at Microsoft.Msagl.GraphViewerGdi.DGraph.UpdateBBoxHierarchy(IEnumerable`1 movedObjects)
           at Microsoft.Msagl.GraphViewerGdi.GViewer.OnDragEnd(IEnumerable`1 changedObjects)
           at Microsoft.Msagl.Drawing.DrawingLayoutEditor.viewer_MouseUp(Object sender, MsaglMouseEventArgs args)
           at Microsoft.Msagl.GraphViewerGdi.GViewer.RaiseMouseUpEvent(MsaglMouseEventArgs iArgs)
           at Microsoft.Msagl.GraphViewerGdi.DrawingPanel.OnMouseUp(MouseEventArgs args)
           at System.Windows.Forms.Control.WmMouseUp(Message& m, MouseButtons button, Int32 clicks)
           at System.Windows.Forms.Control.WndProc(Message& m)
           at System.Windows.Forms.Control.ControlNativeWindow.OnMessage(Message& m)
           at System.Windows.Forms.Control.ControlNativeWindow.WndProc(Message& m)
           at System.Windows.Forms.NativeWindow.DebuggableCallback(IntPtr hWnd, Int32 msg, IntPtr wparam, IntPtr lparam)
           at System.Windows.Forms.UnsafeNativeMethods.DispatchMessageW(MSG& msg)
           at System.Windows.Forms.Application.ComponentManager.System.Windows.Forms.UnsafeNativeMethods.IMsoComponentManager.FPushMessageLoop(Int32 dwComponentID, Int32 reason, Int32 pvLoopData)
           at System.Windows.Forms.Application.ThreadContext.RunMessageLoopInner(Int32 reason, ApplicationContext context)
           at System.Windows.Forms.Application.ThreadContext.RunMessageLoop(Int32 reason, ApplicationContext context)
           at System.Windows.Forms.Application.Run(Form mainForm)
           at TestMSAGL.Program.Main() in C:\Users\dcaicedo\Documents\Visual Studio 2008\Projects\TestMSAGL\TestMSAGL\Program.cs:line 18
           at System.AppDomain._nExecuteAssembly(Assembly assembly, String[] args)
           at System.AppDomain.ExecuteAssembly(String assemblyFile, Evidence assemblySecurity, String[] args)
           at Microsoft.VisualStudio.HostingProcess.HostProc.RunUsersAssembly()
           at System.Threading.ThreadHelper.ThreadStart_Context(Object state)
           at System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state)
           at System.Threading.ThreadHelper.ThreadStart()
      InnerException:

     

    Thanks in advance,

     

    Daniel

    Wednesday, September 17, 2008 8:14 PM

Answers

All replies

  • Hi Daniel,

    Thank you for reporting the bug.  The problem will be fixed and the sources of the viewer with the fix will be availabe but  not immediately.  Please for the time being,  as a workaround, remove the edge labels before using layout others than the Sugiyama scheme.

    Lev

    Wednesday, September 24, 2008 9:10 AM
    Owner
  • Hi Lev,

    just purchased MSAGL and while I am quite impressed by the ease of graph handling over Glee, the above issue is still present.
    I need to visualize RDF-based graph structures so both MDS and edge-labels (for predicates) combined are a necessity for whichever graph visualization is used.

    MSAGL allowing edge labels was the major feature which made me go for your solution instead of some scenario involving Graphviz/Dot2Wpf after all.


    Thank you for the otherwise very nice Library,
    Hinnerk


    edit:
    Sorry if I am somehow blind here, but your post http://social.msdn.microsoft.com/Forums/en-US/automaticgraphlayout/thread/29d15b24-b1ae-4cf8-b60b-023880686c25 gave the impression sources for the viewer would be available in the package on Windows Store, but I see only /bin and /samples in the version I got.
    Is there a difference in the European (which I used) and US download?
    Saturday, March 07, 2009 6:34 PM
  • Hi Hinnerk,
    It seems that only today the new version with the viewer sources and with your problem solved has appeared at the UK store. Sorry for the confusion. Can you try to download the MSI again?
    Thanks,
    Lev
    Lev Nachmanson
    Tuesday, March 10, 2009 11:36 PM
    Owner
  • Hi Lev,

    thank you for your fast and helpful reply.
    I ended up having to retour and reorder MSAGL to get the 2.1 version but now everything works fine as you described.

    Again thanks a bunch,
    Hinnerk
    Friday, March 20, 2009 8:08 PM

  • hi,

    i have MSAGL 2.1 version only but still i have the problem with labeled edges

    if i drag some node I get an unhandled NullReferenceException .

    any one can help how to solve it ..............

     

    Thanks in Advance,

    Aravinda

     

     

     

     

     

    Monday, January 25, 2010 6:37 AM
  • hi LEV,


    In  MSAGL 2.1 version, how to enable label display for edges  while using MDSLayoutSettings.


    Plz reply as soon as possible.


    Thanks In Advance

     

    Wednesday, March 10, 2010 10:05 AM
  • Hi Aravindabe,
    The labels for MDS layouts are not supported, sorry.
    Thanks,
    Lev
    Lev Nachmanson
    Wednesday, March 10, 2010 4:11 PM
    Owner
  • Hi Lev,

         Thanks for ur immediate reply.


    Thursday, March 11, 2010 10:04 AM
  • Hi again Lev,

    Is there a reasonably easy/quick way to put edge labels for MDS in the code, just the same as with the mds layout problem with no viewer.  Could you just give us some input where to look in the code for it etc.  Thanks a lot.

     

    Dino

     

    Wednesday, January 25, 2012 8:55 PM
  • Hi Dino,

    Not rendering of labels in MDS layout is pretty much hard coded. You can try the following hack that seems working for me. It draws each label on the center of its edge.

    edit: C:\dev\MSAGL_RTMJune2008\GraphViewerGDI\DGraph.cs
    File: GraphViewerGDI\DGraph.cs
    ===================================================================
    308a309,328
    >             //hack for MDS label start - it is the very end of  DGraph.DrawEdge
    >             if (dEdge.Label != null) {
    >                 var geomEdge = drawingEdge.Attr.GeometryEdge;
    >                 var center = 0.5 * (geomEdge.Source.Center + geomEdge.Target.Center);
    >                 using (SolidBrush sb = new SolidBrush(Draw.MsaglColorToDrawingColor(dEdge.Label.DrawingLabel.FontColor)))
    >                 {
    >                     double w;
    >                     double h;
    >                     var font = dEdge.Label.Font;
    >                     StringMeasure.MeasureWithFont(dEdge.Label.DrawingLabel.Text, font, out w, out h);
    >
    >                     Draw.DrawStringInRectCenter(graphics, sb,
    >                     font, dEdge.Label.DrawingLabel.Text,
    >                                                            new RectangleF((float)(center.X-w/2), (float)(center.Y-h/2),
    >                                                                           (float)w, (float)h));
    >                 }
    >
    >             }
    >             //hack for MDS labels end
    >
    ===================================================================
    edit: C:\dev\MSAGL_RTMJune2008\GraphViewerGDI\Draw.cs
    File: GraphViewerGDI\Draw.cs
    ===================================================================
    570c570
    <         static void DrawStringInRectCenter(Graphics g, Brush brush, Font f, string s, RectangleF r /*, double rectLineWidth*/) {
    ---
    >         static internal void DrawStringInRectCenter(Graphics g, Brush brush, Font f, string s, RectangleF r /*, double rectLineWidth*/) {
    ===================================================================
    edit: C:\dev\MSAGL_RTMJune2008\Samples\WindowsApplicationSample\Form1.cs
    File: Samples\WindowsApplicationSample\Form1.cs
    ===================================================================
    8a9,10
    > using Microsoft.Msagl.GraphViewerGdi;
    > using Microsoft.Msagl.Mds;
    171c173,174
    <
    ---
    >             gViewer.CurrentLayoutMethod= LayoutMethod.UseSettingsOfTheGraph; //testing that the hack works
    >             graph.LayoutAlgorithmSettings = new MdsLayoutSettings();
    ===================================================================


    Lev Nachmanson

    Wednesday, January 25, 2012 10:45 PM
    Owner
  • Hi,

    that was quick... thanks a lot, I will try it out.


    Dino
    Wednesday, January 25, 2012 11:43 PM
  • Hi again,

    and thanks again Lev for your snippet, it works nice.  Here is only a little enhancement which introduces offset to the Label position:

                //hack for MDS label start - it is the very end of  DGraph.DrawEdge
                if (dEdge.Label != null)
                {
                    var geomEdge = drawingEdge.Attr.GeometryEdge;
                    var srcCenter = geomEdge.Source.Center;
                    var trgCenter = geomEdge.Target.Center;
                    var center = 0.5 * (srcCenter + trgCenter);
                    
                    //To control the offset for differently inclined edges
                    double Xoffset =  Math.Abs(srcCenter.X - trgCenter.X);
                    double gradient = Xoffset > 0.1 ?  Math.Abs(srcCenter.Y - trgCenter.Y) / Math.Abs(srcCenter.X - trgCenter.X) : 0;

                    using (SolidBrush sb = new SolidBrush(Draw.MsaglColorToDrawingColor(dEdge.Label.DrawingLabel.FontColor)))
                    {
                        double w;
                        double h;
                        var font = dEdge.Label.Font;
                        StringMeasure.MeasureWithFont(dEdge.Label.DrawingLabel.Text, font, out w, out h);

                        RectangleF rct;

                        //Specially handle small angle or incline
                        if (gradient < 0.2)
                        {
                            var y = center.Y;

                            if (srcCenter.X < trgCenter.X )
                               y += 3;
                            else
                              y -= h ;

                            rct = new RectangleF((float)(center.X - w / 2), (float)y, (float)w, (float)h);

                        }

                        else if ((srcCenter.X < trgCenter.X &&  srcCenter.Y < trgCenter.Y) ||
                                 (srcCenter.X > trgCenter.X && srcCenter.Y > trgCenter.Y))
                            rct = new RectangleF((float)(center.X - w - 3), (float)(center.Y + 3), (float)w, (float)h);                      

                        else if ((srcCenter.X < trgCenter.X && srcCenter.Y > trgCenter.Y) ||
                                (srcCenter.X > trgCenter.X && srcCenter.Y < trgCenter.Y))
                            rct = new RectangleF((float)(center.X + 3), (float)(center.Y + 3), (float)w, (float)h);
                        else
                            rct = new RectangleF((float)(center.X - w / 2), (float)(center.Y - h/2), (float)w, (float)h);

                        Draw.DrawStringInRectCenter(graphics, sb, font, dEdge.Label.DrawingLabel.Text, rct);
                    }

                }
                //hack for MDS labels end

    Dino
    Saturday, January 28, 2012 5:57 PM