diff --git a/src/controls/instructions.js b/src/controls/instructions.js index 9f28434..98cf1fc 100644 --- a/src/controls/instructions.js +++ b/src/controls/instructions.js @@ -39,13 +39,76 @@ export default class Instructions { if (directions.length && shouldRender) { const direction = this.directions = directions[routeIndex]; - if (compile) { - direction.legs.forEach(function(leg) { - leg.steps.forEach(function(step) { + direction.legs.forEach(function(leg) { + leg.steps.forEach(function(step) { + step.lanes = stepToLanes(step); + if (compile) { step.maneuver.instruction = compile('en', step); - }); + } }); - } + }); + + function stepToLanes(step) { + var lanes = step.intersections[0].lanes; + + if (!lanes) return []; + + var maneuver = step.maneuver.modifier || ''; + + return lanes.map(function(lane, index) { + var classes = []; + if (!lane.valid) classes.push(['invalid']); + + // check maneuver direction matches this lane one(s) + var maneuverIndication = lane.indications.indexOf(maneuver); + if (maneuverIndication === -1) { + // check non-indicated lane to allow straight, right turn from last lane and left turn for first lane + if ((lane.indications[0] === 'none' || lane.indications[0] === '') && ( + maneuver === 'straight' || + (index === 0 && maneuver.slice(-4) === 'left') || + (index === (lanes.length - 1) && maneuver.slice(-5) === 'right'))) { + maneuverIndication = 0; + } else if (maneuver.slice(0, 7) === 'slight ' ) { + // try to exclude 'slight' modifier + maneuverIndication = lane.indications.indexOf(maneuver.slice(7)); + } + } + var indication = (maneuverIndication === -1) ? lane.indications[0] : maneuver; + + var icon; + switch (indication) { + case 'right': + icon = 'right'; + break; + case 'sharp right': + icon = 'sharp-right'; + break; + case 'slight right': + icon = 'slight-right'; + break; + case 'left': + icon = 'left'; + break; + case 'sharp left': + icon = 'sharp-left'; + break; + case 'slight left': + icon = 'slight-left'; + break; + case 'uturn': + icon = 'u-turn'; + break; + //case 'straight': + //case 'none': + default: + icon = 'straight'; + break; + } + classes.push('directions-icon-' + icon); + + return classes.join(' '); + }); + } this.container.innerHTML = instructionsTemplate({ routeIndex, diff --git a/src/mapbox-gl-directions.css b/src/mapbox-gl-directions.css index 3b9fcc5..0696673 100644 --- a/src/mapbox-gl-directions.css +++ b/src/mapbox-gl-directions.css @@ -354,7 +354,7 @@ } /* Instructions */ -.mapbox-directions-instructions .directions-icon { +.mapbox-directions-instructions .directions-maneuver-icon { position:absolute; left:12px; top:20px; @@ -459,6 +459,10 @@ speak:none; background-repeat:no-repeat; } + +.directions-icon.invalid { + opacity: 0.25; +} .directions-icon-arrive { background-image:url(data:image/svg+xml;base64,PHN2ZyB4bWxuczpzdmc9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIiB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIyMCIgaGVpZ2h0PSIyMCIgaWQ9InN2ZzUzMjciIHZlcnNpb249IjEuMSIgdmlld0JveD0iMCAwIDIwIDIwIj48ZGVmcyBpZD0iZGVmczUzMjkiLz48bWV0YWRhdGEgaWQ9Im1ldGFkYXRhNTMzMiIvPjxnIGlkPSJsYXllcjEiIHRyYW5zZm9ybT0idHJhbnNsYXRlKC0zMjAwLC05OTIuMzYyMTgpIj48ZyBpZD0iZzU5MzYiIHRyYW5zZm9ybT0ibWF0cml4KDEsMCwwLC0xLDEsMjAwNC43MjQ0KSIgb3BhY2l0eT0iMC41Ii8+PGcgaWQ9Imc1OTMyIiB0cmFuc2Zvcm09InRyYW5zbGF0ZSgxLC0yKSIvPjxnIHRyYW5zZm9ybT0ibWF0cml4KDEsMCwwLC0xLDEsMjAyNC43MjQ0KSIgaWQ9Imc2MDM4IiBmaWxsPSIjZmZmIi8+PGcgaWQ9InRleHQ2NjA2IiBzdHlsZT0iLWlua3NjYXBlLWZvbnQtc3BlY2lmaWNhdGlvbjonT3BlbiBTYW5zIEJvbGQnO2Jsb2NrLXByb2dyZXNzaW9uOnRiO2NvbG9yOiNGRkY7ZGlyZWN0aW9uOmx0cjtkaXNwbGF5OmlubGluZTtlbmFibGUtYmFja2dyb3VuZDphY2N1bXVsYXRlO2ZpbGwtcnVsZTpub256ZXJvO2ZpbGw6I0ZGRjtmb250LWZhbWlseTonT3BlbiBTYW5zJztmb250LXNpemU6MTYuODE7Zm9udC13ZWlnaHQ6Ym9sZDtsZXR0ZXItc3BhY2luZzpub3JtYWw7bGluZS1oZWlnaHQ6MTI1O292ZXJmbG93OnZpc2libGU7dGV4dC1hbGlnbjpjZW50ZXI7dGV4dC1hbmNob3I6bWlkZGxlO3RleHQtZGVjb3JhdGlvbi1saW5lOm5vbmU7dGV4dC1kZWNvcmF0aW9uOm5vbmU7dGV4dC1pbmRlbnQ6MDt0ZXh0LXRyYW5zZm9ybTpub25lO3dvcmQtc3BhY2luZzpub3JtYWw7d3JpdGluZy1tb2RlOmxyLXRiIj48cGF0aCBkPSJtMzIwNiA5OTYuMzYgMy43MyAwcTIuNTUgMCAzLjcgMC43MyAxLjE2IDAuNzIgMS4xNiAyLjMxIDAgMS4wOC0wLjUxIDEuNzYtMC41IDAuNjktMS4zNCAwLjgzbDAgMC4wOHExLjE0IDAuMjUgMS42NCAwLjk1IDAuNTEgMC43IDAuNTEgMS44NiAwIDEuNjQtMS4xOSAyLjU2LTEuMTggMC45Mi0zLjIyIDAuOTJsLTQuNDkgMCAwLTEyem0yLjU0IDQuNzUgMS40OCAwcTEuMDMgMCAxLjQ5LTAuMzIgMC40Ny0wLjMyIDAuNDctMS4wNiAwLTAuNjktMC41MS0wLjk4LTAuNS0wLjMtMS41OS0wLjNsLTEuMzQgMCAwIDIuNjd6bTAgMi4wMiAwIDMuMTMgMS42NiAwcTEuMDUgMCAxLjU1LTAuNCAwLjUtMC40IDAuNS0xLjIzIDAtMS40OS0yLjEzLTEuNDlsLTEuNTggMHoiIGlkPSJwYXRoMjcyMTIiLz48L2c+PC9nPjwvc3ZnPg==); } diff --git a/src/templates/instructions.html b/src/templates/instructions.html index caabeaa..2779e9f 100644 --- a/src/templates/instructions.html +++ b/src/templates/instructions.html @@ -35,10 +35,17 @@

<%- duration %>

data-lat='<%= lat %>' data-lng='<%= lng %>' class='mapbox-directions-step'> - +
<%= step.maneuver.instruction %>
+ <% if (step.lanes) { %> +
+ <% step.lanes.forEach(function(lane) { %> + + <% }); %> +
+ <% } %> <% if (distance) { %>
<%= distance %>