8

In asymptote, I would like to draw arbitrary paths as in the following image, but with multiple colors. In the example, the path shown in black is also drawn with two parallel red lines. I would like to do the same thing but with green on the inner diameter and red on the outer diameter. I need it to also work for arbitrary paths.

enter image description here

In the next image, I've created two pens using the makepen function. The pen nibs are offset vertically in this example. However, I want a solution where the distance between the red and green curves is constant regardless of the path slope (as in the above image).

unitsize(1inch);
path path1 = arc((0,0), 0.6, 0, 180);
path path2 = (-0.5,0){E}..{S}(0.5,0);
pen pen1 = makepen(shift(-0.5,-2)*unitsquare)+green;
pen pen2 = makepen(shift(-0.5,+1)*unitsquare)+red;
draw(path1, pen1);
draw(path1, pen2);
draw(path1, black);
draw(path2, pen1);
draw(path2, pen2);
draw(path2, black);

enter image description here

Do you have an idea for how to keep the constant distance between the red and green curves for arbitrary paths?

FYI - The first image is produced in asymptote by drawing a thick red line, then drawing a thin white line over it.

1

2 Answers 2

3

Thank you @CharlesStaats for the link to your cool example code! That's a nice usage of the graph package. Adapting your example to my need gives the following result. Hopefully I'm not breaking etiquette by answering my own question.

I'm still interested in an alternate simple solution using pen definitions.

unitsize(1inch);
import graph;
path pathA = (0,0){E}..{S}(1.0,0);
real offset = 0.05;
pair offsetPoint(real t) { return point(pathA, t) + offset*(rotate(90)*dir(pathA,t)); }
path pathB = graph(offsetPoint, 0, length(pathA), operator ..);
offset = -0.05;
path pathC = graph(offsetPoint, 0, length(pathA), operator ..);
draw(pathA);
draw(pathB, red);
draw(pathC, green);

enter image description here

2
  • 1
    You're not breaking etiquette; there's even a badge for that, and I was hoping you would. One minor quibble--it's not a great idea to call a variable path3 since that's the type of a three-dimensional path. May 22, 2015 at 17:14
  • Great point, I've edited the path names.
    – James
    May 22, 2015 at 17:28
1

Building on James's solution, I've modified the code using a higher order function such that the path is not hard coded in the offset function.

unitsize(1inch);
import graph;
path pathA = (0,0){E}..{S}(1.0,0);
typedef pair offsetFunction(real);
offsetFunction offsetPoint(path original_path, real d) {return new pair(real t) {return point(original_path, t) + d*(rotate(90)*dir(original_path,t));};};
path pathB = graph(offsetPoint(pathA, 0.05), 0, length(pathA), operator ..);
path pathC = graph(offsetPoint(pathA, -0.05), 0, length(pathA), operator ..);
draw(pathA);
draw(pathB, red);
draw(pathC, green);

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .