fill-path.js 3.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129
  1. "use strict";
  2. Object.defineProperty(exports, "__esModule", { value: true });
  3. function decasteljau(points, t) {
  4. var left = [];
  5. var right = [];
  6. function recurse(points, t) {
  7. if (points.length === 1) {
  8. left.push(points[0]);
  9. right.push(points[0]);
  10. }
  11. else {
  12. var middlePoints = [];
  13. for (var i = 0; i < points.length - 1; i++) {
  14. if (i === 0) {
  15. left.push(points[0]);
  16. }
  17. if (i === points.length - 2) {
  18. right.push(points[i + 1]);
  19. }
  20. middlePoints[i] = [(1 - t) * points[i][0] + t * points[i + 1][0], (1 - t) * points[i][1] + t * points[i + 1][1]];
  21. }
  22. recurse(middlePoints, t);
  23. }
  24. }
  25. if (points.length) {
  26. recurse(points, t);
  27. }
  28. return { left: left, right: right.reverse() };
  29. }
  30. function splitCurve(start, end, count) {
  31. var points = [[start[1], start[2]]];
  32. count = count || 2;
  33. var segments = [];
  34. if (end[0] === 'A') {
  35. points.push(end[6]);
  36. points.push(end[7]);
  37. }
  38. else if (end[0] === 'C') {
  39. points.push([end[1], end[2]]);
  40. points.push([end[3], end[4]]);
  41. points.push([end[5], end[6]]);
  42. }
  43. else if (end[0] === 'S' || end[0] === 'Q') {
  44. points.push([end[1], end[2]]);
  45. points.push([end[3], end[4]]);
  46. }
  47. else {
  48. points.push([end[1], end[2]]);
  49. }
  50. var leftSegments = points;
  51. var t = 1 / count;
  52. for (var i = 0; i < count - 1; i++) {
  53. var rt = t / (1 - t * i);
  54. var split = decasteljau(leftSegments, rt);
  55. segments.push(split.left);
  56. leftSegments = split.right;
  57. }
  58. segments.push(leftSegments);
  59. var result = segments.map(function (segment) {
  60. var cmd = [];
  61. if (segment.length === 4) {
  62. cmd.push('C');
  63. cmd = cmd.concat(segment[2]);
  64. }
  65. if (segment.length >= 3) {
  66. if (segment.length === 3) {
  67. cmd.push('Q');
  68. }
  69. cmd = cmd.concat(segment[1]);
  70. }
  71. if (segment.length === 2) {
  72. cmd.push('L');
  73. }
  74. cmd = cmd.concat(segment[segment.length - 1]);
  75. return cmd;
  76. });
  77. return result;
  78. }
  79. function splitSegment(start, end, count) {
  80. if (count === 1) {
  81. return [[].concat(start)];
  82. }
  83. var segments = [];
  84. if (end[0] === 'L' || end[0] === 'C' || end[0] === 'Q') {
  85. segments = segments.concat(splitCurve(start, end, count));
  86. }
  87. else {
  88. var temp = [].concat(start);
  89. if (temp[0] === 'M') {
  90. temp[0] = 'L';
  91. }
  92. for (var i = 0; i <= count - 1; i++) {
  93. segments.push(temp);
  94. }
  95. }
  96. return segments;
  97. }
  98. function fillPath(source, target) {
  99. if (source.length === 1) {
  100. return source;
  101. }
  102. var sourceLen = source.length - 1;
  103. var targetLen = target.length - 1;
  104. var ratio = sourceLen / targetLen;
  105. var segmentsToFill = [];
  106. if (source.length === 1 && source[0][0] === 'M') {
  107. for (var i = 0; i < targetLen - sourceLen; i++) {
  108. source.push(source[0]);
  109. }
  110. return source;
  111. }
  112. for (var i = 0; i < targetLen; i++) {
  113. var index = Math.floor(ratio * i);
  114. segmentsToFill[index] = (segmentsToFill[index] || 0) + 1;
  115. }
  116. var filled = segmentsToFill.reduce(function (filled, count, i) {
  117. if (i === sourceLen) {
  118. return filled.concat(source[sourceLen]);
  119. }
  120. return filled.concat(splitSegment(source[i], source[i + 1], count));
  121. }, []);
  122. filled.unshift(source[0]);
  123. if (target[targetLen] === 'Z' || target[targetLen] === 'z') {
  124. filled.push('Z');
  125. }
  126. return filled;
  127. }
  128. exports.default = fillPath;
  129. //# sourceMappingURL=fill-path.js.map