Articulated Line

Started by Hey Ken, June 13, 2018, 09:47:33 PM

Previous topic - Next topic

0 Members and 1 Guest are viewing this topic.

Hey Ken

Folks:

    Attached is a rough draft of a new shape I'm working on, an articulated line, and I need some help.

    The way It works is that you can add or remove additional line segments, with the location of each vertex managed by moving a control point.  That was fairly easy to accomplish, but the place it got difficult is where I added moveable arrowheads to the first line segment.  My question is: How can I add a similar pair of moveable arrowheads to the second and third line segments?   I've wasted far too much time trying to get the beast to work, but to no avail.  Any suggestions? 

    Thanks in advance,

    - Ken


Ken V. Krawchuk
Author
No Dogs on Mars - A Starship Story
http://astarshipstory.com

wapperdude

Oh, I see.  I thought you were talking about a highly educated, proper line.  Just kidding.

Not sure this will do what you want, but here's a variation.  The arrowheads remain at the end of each segment.  I only did two segments.  Note, geometry1 defines the beginning and end points, and all segments would fit within these limits.  Geometry1 is not visible.  Best I could come up with at this late hour.

Cheers.
Wapperdude
Visio 2019 Pro

wapperdude

#2
Doh!.  Never mind.  You  can control the appearance of the arrowheads by turning the fill on or off.  So, the construct for the other line segments just needs to be similar to the first.  You end up with one section that has full length line with no arrowheads, and then a 2nd line with arrowheads that overlays the first.  Gives the illusion of moving arrowheads.  That was my quick and dirty after looking at what you did.

Here's updated file to give you the idea.  If you have newer version of Visio, I think it's not too difficult to make the arrowhead control points stay on the lines.  Otherwise, I'll leave the math and gory details to you.

Anyway, HTH
Wapperdude
Visio 2019 Pro

Hey Ken

Mr. Dude:

    Thanks for taking the time to play around with the inarticulate articulated line. 

Quote

I think it's not too difficult to make the arrowhead control points stay on the lines.


   LOL!  That is precisely the issue I've been grappling with!

    Some brief background: I've been using the simple, single-segment version of that line for years, adjusting the arrowheads as artistically necessary.  There are times where I need to connect multiple single-segment lines into one longer, articulated line—I've found they are much better behaved than Visio's native self-routing lines—but connecting multiple lines has its own foibles (accidentally disconnecting, losing right angles, issues with innie/outtie connection points, etc.), so laziness dictated that I try to build a better-behaved, multi-segment version of my classic single-segment arrowed line.  Which brings us to the issue at hand.

    As I mentioned, supporting multiple segments is no big deal; the issue is keeping those pesky arrowheads on top of their line on the additional segments.  Obviously it has to begin with a row in the Controls section so that you can move the arrowheads to suit, but how do you limit things to keeping their endpoints on the host line segment?  I tried several approaches, but it seems a true solution would be contradictory.  You can't GUARD the X and Y on the Controls; that defeats the purpose of the control.  Nor can you use GUARD on the GEOMETRY section because the control points will still be free to go where they may.  BOUND was handy to keep the arrowheads from exceeding the X-endpoints of the host line segment, but it's constraining the control point itself that's stumping me. 

    Having the arrowheads constrained to the line is important to me, because if it does not behave itself automatically, then I have to go in there and manually align things.  That's a cure worse than the disease.

    One option I expected to hear was to use a group, but that has even more problems.  You can hide the group-ness easily enough, but if you move the wrong line segment, the connection is broken.  GUARDing the connection does not stop that if you move the unGUARDed side.

    So I'm stumped.  And I do not want a VBA solution.  That'd be cheating.  ;- )

    - Ken


Ken V. Krawchuk
Author
No Dogs on Mars - A Starship Story
http://astarshipstory.com

wapperdude

Briefly thought about grouping, and just as quickly dismissed it.  My initial reaction says this can be done in shapesheet alone.  Seems like it's close.

I forgot which version of Visio you have.  With newer versions, I think that point along a curve, or whatever it's called, would do the necessary positional constraints.  Then, add the bound fcn to keep each narrowband within the limits of its line segment.

Alas, I only have V2007, so cannot pursue that thinking any further.  If you're still old school like me, then I'll have a go at the formulas.  I may actually have that solved...need to rummage about a bit.

Visio 2019 Pro

vojo

2 cents to consider

1)  you can use loctoloc to lock the arrow the end of the line.  something like
     guard(loctoloc(pnt(<line x coord>,<line y coord>),<line ref point - width or similar>,<arrow ref point - idth or similar>)
     no groups needed

2) as in June's stuff, his primary and shadow lines track to a control point of the group.  Where ever you move the
    control, June's math makes the appropriate bends to make sure the line end point (or begin point) line up with the control
    points

no VBA involved with either...use shape data to assist in usage

Some examples attached

wapperdude

Well, several dead cats later, and just having sooooo much fun, here is an imperfect solution, old school style.

1) Major break-thru was to use the SETATREF family fcns.  This "slaved" the arrowhead points to the section control points.
2) The first section from width*0 was easy.  The second section, in this case, only two sections, had to handle issues with the section control exceeding the total width.  Not an issue if it is less than the zero, as that seems to work favorably.
3) Main issue has to do with the exact, 90 deg cases.  These are special cases as they result in divide by 0 scenarios.  Obviously, not good.
4) Did not add bound function.   This gets really messy as the limits change when either section control is less than 0 width or greater than 1 width.

Well, here's a step.  This is a lot of work to be lazy.  I kinda like the idea of just a single segment, and gluing segments together as needed.  Yeah, they can pull apart, but, at this point, there's no weird cases to handle.

Wapperdude
Visio 2019 Pro

Hey Ken


Wapperdude:

   I feel your pain.  But between the two of us looking for a solution, the cats never stood a chance.  ;- )

   Never considered the SETATREF functions—and I mean never.  Didn't even know what they did!  But that's one of the reasons I hang out here; ya learn new stuff all the time, and here's yet another opportunity.

   Seeing how there are still a few cats out there, let me take your fine example and expand it to three or four segments that can be turned on or off at will.  Thanks for showing it's possible.

   - Ken

Ken V. Krawchuk
Author
No Dogs on Mars - A Starship Story
http://astarshipstory.com

wapperdude

I made an attempt to do an in-depth, but understandable exploration of the SETATREF fcns:  http://visguy.com/vgforum/index.php?topic=6383.msg26308#msg26308

Wapperdude
Visio 2019 Pro

Hey Ken


    So I managed to get the arrows married to their respective lines, but not for all permutations.  Still, it's solid progress.

    The first thing I did was jettison Visio's opinion of what the line is, so I nailed the standard line endpoints on top of each other thereby making the Width, Height, and related cells meaningless.  The only lines are the ones I draw, each with their own Geometry.  That's what I access instead.

    The trick to taming the arrowheads wasn't SETATREF (although I did learn quite a bit about that by playing with Wapperdude's clever examples), but rather a permutation of the calculations he did.  I started Pythagorean, but realized all you need to identify where to nail the arrow endpoints is the ratio of how far along you are between the line endpoints.  That made it easy, except that it still blows apart under too many circumstances.

    Regardless, it is a new approach and it does work (sort of) so I thought I'd post it.  I agree that there's an all-shapesheet solution to this somewhere down the line; it's just not there yet. 

    I also added the right-click actions I'd like to see in the final product: adding and subtracting line segments, and turning arrowheads on and off; trivial stuff in light of the bigger headaches.  But at least that part works.

    More as it happens, in my copious free time.

    - Ken

Ken V. Krawchuk
Author
No Dogs on Mars - A Starship Story
http://astarshipstory.com

wapperdude

Interesting concept.  Ah, I see what you meant by changing arrowheads.  Cool.

I'll look at this some more, see if it's possible to tame some of the wilder behaviors.  While this seems like a easy task, as you've discovered, it is fraught with perils. 
Visio 2019 Pro

Hey Ken

   Quick update: I've spent far too much time on this; "a lot of work to be lazy", as Wapperdude so aptly put it.  I'd like to say "close but no cigar", except I'm not close, and there's still no cigar.

   I came at it fresh several different times, but all of them depend on the same foundation:
  • Nailing the start and end points of the line on the same spot.  That makes all lines under my direct control.  Still seems like a winning approach.

  • Using that nailed spot as the starting point of the line.  I tried using a control point as the starting point to allow for adjusting the start, but the nailed start/end point ended up in odd locations, especially after moving segments around, and I was unable to hide it.  Idea abandoned.

  • Using the ratio of height to width to nail the arrow line on top of the line segment rather than using Pythagoras.  However, I suspect this approach is the cause of wild behavior requiring BOUNDs.  Might have to abandon it.

  • Focusing on getting one line segment to work before adding additional segments.  That simplified things immensely because the difficulty is not in creating multiple segments; the problem is taming the arrowheads.  Get it to work for one segment, it should be trivial to get it to work for all.

  • One promising item that simplified things was to use two lines each with a single arrowhead rather than one line with an arrowhead on each end.  That eliminated the issue of arrowheads crossing each other and inverting themselves.
   That said, attached is the latest effort.  I added BOUNDs to keep the arrowheads within the scope of the line and not cross over each other, but other than that it displays all the unruly behaviors of its predecessors.  The problem here is fundamental; however, I just don't see it.

   Bottom line: I'm ready for a grouped solution.  I played around with one, and it's pretty trivial.  Segments can be turned on and off, locked against deletion (except with the entire group), connection points GUARDed, and arrowheads easily tamed using the Width shapesheet cell rather than playing around with my own geometries.  The only downside is when I link the line (doubleclick or hyperlink): the linking needs to be duplicated across all line segments and to the group itself.  Not a big deal; all the segments and group can link via the destination page name stored in the group's user cell.  However, it contradicts how I currently handle linking in my macros; I'd need to handle that special case too.  More work!  But less work, considering the unruly alternative of a single, ungrouped shape that continues to not work.

   More as it happens, albeit slowly.

   - Ken





Ken V. Krawchuk
Author
No Dogs on Mars - A Starship Story
http://astarshipstory.com

vojo

RE link links or macros to segments:  Could do one of the following
   -select child within group then bind the link
   -set behavior to show children first (one less click at group level
   -at group level, could get into a more complex scenario
      - actions to identify the child in play (this would allow a simpler way to have multiple segments use 1 link...
            a default perhaps???)
      - sets an index in some sort of user.index at group level
      - each child watches (DEPENDSON) index to do some sort of SETF(GETREF(<link cell>), <link>) to set link

wapperdude

Well, here's perhaps, 98% of desired.  The tough parts are the 2nd and latter segments.  This shows solution for 2 segments.  There's still the case of vertical 2nd segment not performing as desired, but doesn't go crazy.

HTH
Wapperdude
Visio 2019 Pro

wapperdude

#14
@Hey Ken
Well, all righty now!  I think this is 99.9% of what you were after.  Again, this is for just 2 segments.  But, I think the pattern is understandable.  I've tried to eliminate unnecessary calcs from the shapesheet.  The 2nd segment has the number "2" imbedded in the User and Control names.  So, for each additional segment, those lines would need to be replicated.  I did not do anything to hide the unused segment or its control points.  Figured you had that under control.

The trick was the to break for formulas as determined by the slope of the line segments, namely, the 45 deg point.  This shifts the arrowhead control to be either dependent upon its Xpos or its Ypos.  The dependent calculation then shifts between the Ypos or the Xpos respectively.  The ArrowHead will move proportionally to length of its line segment as determined by either the beginning or ending locations.

I've tried to thoroughly test this.  There does seem to be some minor calculation round off error right around the 50% arrowhead location on the 2nd line segment.  Hence, not 100%.

Enjoy.

Interesting problem.

Wapperdude

Visio 2019 Pro