From: Steve Bennett Date: Sun, 6 Feb 2011 13:55:38 +0000 (+0000) Subject: ADD 'arrows-reversed' line decoration rendering solely to cater for "highway=*, onewa... X-Git-Tag: 2.0~99 X-Git-Url: https://git.openstreetmap.org/potlatch2.git/commitdiff_plain/cd28227a95afc4821e940e2545a06a63b3e071fb ADD 'arrows-reversed' line decoration rendering solely to cater for "highway=*, oneway=-1". This fixes trac.openstreetmap.org/ticket/3384 . ADD oneway=-1 feature to core_ways.css SPEEDUP dash and arrow rendering by removing all trig functions --- diff --git a/net/systemeD/halcyon/WayUI.as b/net/systemeD/halcyon/WayUI.as index 0e903793..3da196e5 100644 --- a/net/systemeD/halcyon/WayUI.as +++ b/net/systemeD/halcyon/WayUI.as @@ -1,15 +1,14 @@ package net.systemeD.halcyon { import flash.display.*; + import flash.events.*; import flash.geom.Matrix; - import flash.geom.Point; import flash.geom.Rectangle; import flash.text.TextField; import flash.text.TextFormat; - import flash.events.*; + + import net.systemeD.halcyon.connection.*; import net.systemeD.halcyon.styleparser.*; - import net.systemeD.halcyon.connection.*; - import net.systemeD.halcyon.Globals; /** The graphical representation of a Way. */ public class WayUI extends EntityUI { @@ -405,43 +404,59 @@ package net.systemeD.halcyon { private function dashedLine(g:Graphics,dashes:Array):Array { var way:Way=entity as Way; - var segments:Array=[]; - var draw:Boolean=false, dashleft:Number=0, dc:Array=new Array(); - var a:Number, xc:Number, yc:Number; - var curx:Number, cury:Number; - var dx:Number, dy:Number, segleft:Number=0; - var i:int=indexStart; + var segments:Array=[]; // array of dash locations being constructed for later arrow drawing + var draw:Boolean=false; // are we drawing or marking empty space till next dash + var dashleft:Number=0; // how much of current dash is left + var dc:Array=new Array(); // copy of dashes, gets consumed then replaced + var xc:Number, yc:Number; // normalised vector coordinates of direction to next node + var curx:Number, cury:Number; // current drawing location + var dx:Number, dy:Number, segleft:Number=0; // distance remaining until next node + var i:int=indexStart; // node index + var dashstartx:int, dashstarty:int; // needed to draw reverse arrows + var dashstartxc: Number, dashstartyc: Number; var node:Node = way.getNode(i); var nextNode:Node = way.getNode(i); g.moveTo(paint.map.lon2coord(node.lon), paint.map.latp2coord(node.latp)); while (i < indexEnd-1 || segleft>0) { if (dashleft<=0) { // should be ==0 + // finished drawing current dash, pop another one off the pattern, looping if necessary if (dc.length==0) { dc=dashes.slice(0); } dashleft=dc.shift(); - if (draw) { segments.push([curx,cury,dx,dy]); } + if (draw) { segments.push([curx,cury,xc,yc, dashstartx, dashstarty, dashstartxc, dashstartyc]); } draw=!draw; + // record start of each dash, if we need to draw a reverse arrow head later + dashstartx = curx; dashstarty = cury; + dashstartxc = xc; dashstartyc = yc; } if (i==drawExcept || i==drawExcept+1) { draw=false; } if (segleft<=0) { // should be ==0 + // arrived at target node. calculate direction to next node. node = way.getNode(i); nextNode = way.getNode(i+1); curx=paint.map.lon2coord(node.lon); dx=paint.map.lon2coord(nextNode.lon)-curx; cury=paint.map.latp2coord(node.latp); dy=paint.map.latp2coord(nextNode.latp)-cury; - a=Math.atan2(dy,dx); xc=Math.cos(a); yc=Math.sin(a); + //a=Math.atan2(dy,dx); xc=Math.cos(a); yc=Math.sin(a); segleft=Math.sqrt(dx*dx+dy*dy); + xc = dx/segleft; + yc = dy/segleft; + if (i==0) { + // record start location of very first dash + dashstartx = curx; dashstarty = cury; + dashstartxc = xc; dashstartyc = yc; + } i++; } if (segleft<=dashleft) { - // the path segment is shorter than the dash + // the path segment is shorter than the dash: draw to end of segment curx+=dx; cury+=dy; moveLine(g,curx,cury,draw); dashleft-=segleft; segleft=0; } else { - // the path segment is longer than the dash + // draw whole dash, then loop curx+=dashleft*xc; dx-=dashleft*xc; cury+=dashleft*yc; dy-=dashleft*yc; moveLine(g,curx,cury,draw); @@ -462,22 +477,25 @@ package net.systemeD.halcyon { var c:int=s.color ? s.color : 0; switch (s.line_style.toLowerCase()) { - case 'arrows': - var w:Number=s.width*1.5; // width of arrow - var l:Number=s.width*2; // length of arrow - var angle0:Number, angle1:Number, angle2:Number; + case 'arrows':; case 'arrows-reversed': + var w:Number=s.width*1.5; // width of arrow + var l:Number=s.width*2; // length of arrow g.lineStyle(1,c); for each (var seg:Array in segments) { g.beginFill(c); - angle0= Math.atan2(seg[3],seg[2]); - angle1=-Math.atan2(seg[3],seg[2]); - angle2=-Math.atan2(seg[3],seg[2])-Math.PI; - g.moveTo(seg[0]+l*Math.cos(angle0), - seg[1]+l*Math.sin(angle0)); - g.lineTo(seg[0]+w*Math.sin(angle1), - seg[1]+w*Math.cos(angle1)); - g.lineTo(seg[0]+w*Math.sin(angle2), - seg[1]+w*Math.cos(angle2)); + // seg: {dashendx, dashendy, dx, dy, dashstartx, dashstarty, dashstartdx, dashstartdy} + // where dx is normalised x component of direction vector + // note that a dash can go around a corner, so the info is not redundant + + if (s.line_style.toLowerCase() == "arrows-reversed") { + g.moveTo(seg[4]-l*seg[6], seg[5]-l*seg[7]); // note reversed arrow head + g.lineTo(seg[4]-w*seg[7], seg[5]+w*seg[6]); + g.lineTo(seg[4]+w*seg[7], seg[5]-w*seg[6]); + } else { + g.moveTo(seg[0]+l*seg[2], seg[1]+l*seg[3]); + g.lineTo(seg[0]-w*seg[3], seg[1]+w*seg[2]); + g.lineTo(seg[0]+w*seg[3], seg[1]-w*seg[2]); + } g.endFill(); } break; @@ -486,8 +504,8 @@ package net.systemeD.halcyon { g.lineStyle(1,c); for each (seg in segments) { g.beginFill(c); - angle0 = -Math.atan2(seg[3], seg[2]) + Math.PI / 2; //0 - angle1 = -Math.atan2(seg[3], seg[2]) - Math.PI/6; //60 + var angle0:Number = -Math.atan2(seg[3], seg[2]) + Math.PI / 2; //0 + var angle1:Number = -Math.atan2(seg[3], seg[2]) - Math.PI/6; //60 g.moveTo(seg[0], seg[1]);//start 0,0 g.lineTo(seg[0] - w * Math.sin(angle0), seg[1] - w * Math.cos(angle0)); g.lineTo(seg[0] + w * Math.sin(angle1), seg[1] + w * Math.cos(angle1)); @@ -496,7 +514,6 @@ package net.systemeD.halcyon { break; } } - /** Find point partway (0-1) along a path * @return (x,y,angle) diff --git a/resources/stylesheets/core_ways.css b/resources/stylesheets/core_ways.css index 469aec8c..b14ecdb5 100644 --- a/resources/stylesheets/core_ways.css +++ b/resources/stylesheets/core_ways.css @@ -121,3 +121,4 @@ way[tunnel=yes][!waterway] /* Attribute decoration */ way[oneway=yes], way[junction=roundabout] { z-index: 15; color: #444444; width: 2; dashes: 15,35; line-style: arrows; } +way[oneway=-1] { z-index: 15; color: #444444; width: 2; dashes: 15,35; line-style: arrows-reversed; }