function svgMarkerSegments(projection, graph, dt, shouldReverse = () => false, bothDirections = () => false) {
    /**
     * @param {iD.OsmWay} entity
     * @returns {[{id: String, d: String}]} list of svg path segments corres
     */
    return function(entity) {
        let i = 0;
        let offset = dt / 2;
        const segments = [];

        const clip = paddedClipExtent(projection);

        const coordinates = graph.childNodes(entity).map(function(n) { return n.loc; });
        let a, b;

        const _shouldReverse = shouldReverse(entity);
        const _bothDirections = bothDirections(entity);

        d3_geoStream({
            type: 'LineString',
            coordinates: coordinates
        }, projection.stream(clip({
            lineStart: function() {},
            lineEnd: function() { a = null; },
            point: function(x, y) {
                b = [x, y];

                if (a) {
                    let span = geoVecLength(a, b) - offset;

                    if (span >= 0) {
                        const heading = geoVecAngle(a, b);
                        const dx = dt * Math.cos(heading);
                        const dy = dt * Math.sin(heading);
                        let p = [
                            a[0] + offset * Math.cos(heading),
                            a[1] + offset * Math.sin(heading)
                        ];

                        // gather coordinates
                        const coord = [a, p];
                        for (span -= dt; span >= 0; span -= dt) {
                            p = geoVecAdd(p, [dx, dy]);
                            coord.push(p);
                        }
                        coord.push(b);

                        // generate svg paths
                        let segment = '';

                        if (!_shouldReverse || _bothDirections) {
                            for (let j = 0; j < coord.length; j++) {
                                segment += (j === 0 ? 'M' : 'L') + coord[j][0] + ',' + coord[j][1];
                            }
                            segments.push({ id: entity.id, index: i++, d: segment });
                        }

                        if (_shouldReverse || _bothDirections) {
                            segment = '';
                            for (let j = coord.length - 1; j >= 0; j--) {
                                segment += (j === coord.length - 1 ? 'M' : 'L') + coord[j][0] + ',' + coord[j][1];
                            }
                            segments.push({ id: entity.id, index: i++, d: segment });
                        }
                    }

                    offset = -span;
                }

                a = b;
            }
        })));

        return segments;
    };
}
@param {iD.Projection} projection
@param {iD.Graph} graph
@param {Number} dt spacing between segments
@param {Function<Boolean>} [shouldReverse]
@param {Function<Boolean>} [bothDirections]