| 4427 | #endif |
| 4428 | |
| 4429 | int PSL_plotcurve (struct PSL_CTRL *PSL, double *x, double *y, int n, int type) { |
| 4430 | /* Plot a (portion of a) Bezier curve. This can be a line from start to finish, or a portion of it, depending |
| 4431 | * on the type argument. Optionally, the line can be stroked (using the current pen), closed. |
| 4432 | * Type is a combination of the following: |
| 4433 | * PSL_DRAW (0) : Draw a line segment |
| 4434 | * PSL_MOVE (1) : Move to a new anchor point (x[0], y[0]) first [REQUIRED] |
| 4435 | * PSL_STROKE (2) : Stroke the line |
| 4436 | * PSL_CLOSE (8) : Close the line back to the beginning of this segment, this is done automatically |
| 4437 | * when the first and last point are the same and PSL_MOVE is on. |
| 4438 | */ |
| 4439 | int i = 0, *ix = NULL, *iy = NULL; |
| 4440 | double *Px1 = NULL, *Py1 = NULL, *Px2 = NULL, *Py2 = NULL; |
| 4441 | |
| 4442 | if (n < 1) return (PSL_NO_ERROR); /* Cannot deal with empty lines */ |
| 4443 | if (type < 0) type = -type; /* Should be obsolete now */ |
| 4444 | |
| 4445 | psl_computeBezierControlPoints (PSL, x, n, &Px1, &Px2); |
| 4446 | psl_computeBezierControlPoints (PSL, y, n, &Py1, &Py2); |
| 4447 | |
| 4448 | /* First convert knots to integers */ |
| 4449 | |
| 4450 | ix = PSL_memory (PSL, NULL, n, int); |
| 4451 | iy = PSL_memory (PSL, NULL, n, int); |
| 4452 | |
| 4453 | n = psl_convert_path (PSL, x, y, n, ix, iy, PSL_CONVERT_PATH); |
| 4454 | |
| 4455 | /* If first and last point are the same, close the polygon and drop the last point |
| 4456 | * (but only if this segment runs start to finish) |
| 4457 | */ |
| 4458 | |
| 4459 | if (n > 1 && (type & PSL_MOVE) && (ix[0] == ix[n-1] && iy[0] == iy[n-1])) type |= PSL_CLOSE; |
| 4460 | |
| 4461 | /* Move to (and set) currentpoint */ |
| 4462 | PSL_command (PSL, "%d %d M\n", ix[0], iy[0]); |
| 4463 | n--; |
| 4464 | while (i < n) { |
| 4465 | PSL_command (PSL, "%d %d ", psl_ix (PSL, Px1[i]), psl_iy (PSL, Py1[i])); |
| 4466 | PSL_command (PSL, "%d %d ", psl_ix (PSL, Px2[i]), psl_iy (PSL, Py2[i])); |
| 4467 | i++; /* Go to end point of segment */ |
| 4468 | PSL_command (PSL, "%d %d curveto\n", ix[i], iy[i]); |
| 4469 | } |
| 4470 | PSL_free (Px1); PSL_free (Py1); PSL_free (Px2); PSL_free (Py2); |
| 4471 | i--; /* ID of last point */ |
| 4472 | PSL->internal.ix = ix[i]; |
| 4473 | PSL->internal.iy = iy[i]; |
| 4474 | if (type & PSL_STROKE && type & PSL_CLOSE) |
| 4475 | PSL_command (PSL, "P S\n"); /* Close and stroke the path */ |
| 4476 | else if (type & PSL_CLOSE) |
| 4477 | PSL_command (PSL, "P\n"); /* Close the path */ |
| 4478 | else if (type & PSL_STROKE) |
| 4479 | PSL_command (PSL, "S\n"); /* Stroke the path */ |
| 4480 | |
| 4481 | PSL_free (ix); |
| 4482 | PSL_free (iy); |
| 4483 | |
| 4484 | return (PSL_NO_ERROR); |
| 4485 | } |
| 4486 |
no test coverage detected