vector_salad 0.0.8 → 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (60) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +17 -5
  3. data/Rakefile +16 -0
  4. data/examples/birthday.png +0 -0
  5. data/examples/birthday.rb +5 -3
  6. data/examples/birthday.svg +273 -623
  7. data/examples/boolean_operations.png +0 -0
  8. data/examples/boolean_operations.svg +133 -5
  9. data/examples/bunny_card.png +0 -0
  10. data/examples/bunny_card.svg +110 -110
  11. data/examples/chill.png +0 -0
  12. data/examples/chill.rb +5 -6
  13. data/examples/chill.svg +82 -82
  14. data/examples/circles.png +0 -0
  15. data/examples/circles.rb +1 -1
  16. data/examples/circles.svg +1 -1
  17. data/examples/clip_operations.png +0 -0
  18. data/examples/clip_operations.svg +1 -1
  19. data/examples/cog_menu.png +0 -0
  20. data/examples/cog_menu.rb +1 -8
  21. data/examples/cog_menu.svg +1 -1
  22. data/examples/fox.png +0 -0
  23. data/examples/fox.svg +19 -19
  24. data/examples/pepsi_logo.png +0 -0
  25. data/examples/pepsi_logo.rb +7 -7
  26. data/examples/pepsi_logo.svg +2 -2
  27. data/examples/polygons.png +0 -0
  28. data/examples/polygons.rb +7 -8
  29. data/examples/polygons.svg +2 -2
  30. data/examples/quadratic_bezier_handle.rb +3 -3
  31. data/examples/simple_path.rb +7 -7
  32. data/examples/simple_path.svg +2 -2
  33. data/examples/space.png +0 -0
  34. data/examples/space.rb +11 -11
  35. data/examples/space.svg +5836 -46444
  36. data/examples/space_huge.png +0 -0
  37. data/examples/space_huge.svg +46453 -0
  38. data/examples/spiro_nodes.rb +5 -5
  39. data/examples/squares.svg +2 -2
  40. data/examples/transforms.png +0 -0
  41. data/examples/transforms.rb +16 -16
  42. data/examples/transforms.svg +47 -47
  43. data/examples/triangles.rb +3 -3
  44. data/lib/vector_salad/exporters/svg_exporter.rb +1 -11
  45. data/lib/vector_salad/mixins/at.rb +14 -6
  46. data/lib/vector_salad/monkeypatches.rb +19 -4
  47. data/lib/vector_salad/standard_shapes/basic_shape.rb +1 -0
  48. data/lib/vector_salad/standard_shapes/custom.rb +1 -1
  49. data/lib/vector_salad/standard_shapes/path.rb +13 -10
  50. data/lib/vector_salad/standard_shapes/square.rb +0 -1
  51. data/lib/vector_salad/version.rb +1 -1
  52. data/test/minitest_helper.rb +4 -0
  53. data/test/test_vector_salad.rb +23 -0
  54. metadata +9 -9
  55. data/examples/galaxies.png +0 -0
  56. data/examples/galaxies.rb +0 -60
  57. data/examples/galaxies.svg +0 -5806
  58. data/examples/stars.png +0 -0
  59. data/examples/stars.rb +0 -3
  60. data/examples/stars.svg +0 -30006
@@ -13,8 +13,8 @@ path(
13
13
  stroke_width: 4
14
14
  )
15
15
 
16
- circle(5, at: n1.at, fill: :green)
17
- circle(5, at: n2.at, fill: :green)
18
- circle(5, at: s1.at, fill: :blue)
19
- circle(5, at: s2.at, fill: :blue)
20
- circle(5, at: s3.at, fill: :blue)
16
+ circle(5, fill: :green)[*n1.at]
17
+ circle(5, fill: :green)[*n2.at]
18
+ circle(5, fill: :blue)[*s1.at]
19
+ circle(5, fill: :blue)[*s2.at]
20
+ circle(5, fill: :blue)[*s3.at]
data/examples/squares.svg CHANGED
@@ -3,8 +3,8 @@
3
3
  width="280"
4
4
  height="200">
5
5
 
6
- <path d="M 0 0 L 0 100 L 100 100 L 100 0 Z"/>
7
- <path d="M 200 100 L 200 150 L 250 150 L 250 100 Z"/>
6
+ <rect x="0" y="0" width="100" height="100"/>
7
+ <rect x="200" y="100" width="50" height="50"/>
8
8
  <path d="M 60 140 L 60 170 L 30 170 L 30 140 Z" fill="cyan" stroke="magenta" stroke-width="3"/>
9
9
  <path d="M 150 200 L 150 160 L 190 160 L 190 200 Z" fill="magenta"/>
10
10
  <path d="M 250 130 L 250 160 L 280 160 L 280 130 Z" fill="lightblue"/>
Binary file
@@ -1,6 +1,6 @@
1
1
  @width = 320.0
2
2
  # Background
3
- rect(@width, @width * 2, fill: 'tan')
3
+ rect(@width, @width * 2, fill: "tan")
4
4
 
5
5
  # Draw a row of repeating shapes at a y position cycling through colors
6
6
  def row(shape, y)
@@ -17,25 +17,25 @@ row(Circle.new(5), 15)
17
17
 
18
18
  (1..7).each do |x| # Triangle snake
19
19
  if x.even?
20
- iso_tri(30, at: [x * 40, -60], fill: 'darkorange').flip_x
20
+ iso_tri(30, fill: "darkorange")[x * 40, -60].flip_x
21
21
  else
22
- iso_tri(30, at: [x * 40, 30], fill: 'firebrick')
22
+ iso_tri(30, fill: "firebrick")[x * 40, 30]
23
23
  end
24
24
  end
25
25
 
26
26
  row(Pentagon.new(6), 80)
27
27
 
28
28
  # Toothy face
29
- rect(320, 160, at: [0, 100], fill: 'saddlebrown')
29
+ rect(320, 160, fill: "saddlebrown")[0, 100]
30
30
 
31
31
  flip(:x) do # flip multiple shapes at once
32
- 6.times { |x| iso_tri(30, 100, at: [x * 30 + 85, -200], fill: 'white') }
33
- iso_tri(50, 20, at: [35, -145], fill: 'black')
34
- iso_tri(50, 20, at: [285, -145], fill: 'black')
35
- circle(7, at: [35, -160], fill: 'firebrick')
36
- circle(7, at: [285, -160], fill: 'firebrick')
32
+ 6.times { |x| iso_tri(30, 100, fill: "white")[x * 30 + 85, -200] }
33
+ iso_tri(50, 20, fill: "black")[35, -145]
34
+ iso_tri(50, 20, fill: "black")[285, -145]
35
+ circle(7, fill: "firebrick")[35, -160]
36
+ circle(7, fill: "firebrick")[285, -160]
37
37
  end
38
- 7.times { |x| iso_tri(30, 100, at: [x * 30 + 70, @width / 2], fill: 'white') }
38
+ 7.times { |x| iso_tri(30, 100, fill: "white")[x * 30 + 70, @width / 2] }
39
39
 
40
40
  row(Pentagon.new(6), 280)
41
41
 
@@ -45,14 +45,14 @@ n.times do |t|
45
45
  col1.rotate!
46
46
  col2.rotate!
47
47
  move(@width / 2, 450) do
48
- iso_tri(20, at: [0, -120], fill: col2[0]).rotate(360.0 / n * t)
49
- iso_tri(25, at: [0, 120], fill: col1[0]).rotate(360.0 / n * t + 180.0 / n)
48
+ iso_tri(20, fill: col2[0])[0, -120].rotate(360.0 / n * t)
49
+ iso_tri(25, fill: col1[0])[0, 120].rotate(360.0 / n * t + 180.0 / n)
50
50
  end
51
51
  end
52
52
  # "Diamond"
53
- intersection(fill: 'firebrick') do
54
- triangle(80, at: [0, 0]).flip_x
55
- pentagon(60, at: [0, 0])
56
- end.move(@width/2,450)
53
+ intersection(fill: "firebrick") do
54
+ triangle(80).flip_x
55
+ pentagon(60)
56
+ end.move(@width / 2, 450)
57
57
 
58
58
  row(Circle.new(5), 625)
@@ -4,20 +4,20 @@
4
4
  height="640.0">
5
5
 
6
6
  <rect x="0" y="0" width="320.0" height="640.0" fill="tan"/>
7
- <circle cx="20.0" cy="15" r="5" fill="black"/>
8
- <circle cx="40.0" cy="15" r="5" fill="saddlebrown"/>
7
+ <circle cx="20.0" cy="15" r="5" fill="darkorange"/>
8
+ <circle cx="40.0" cy="15" r="5" fill="black"/>
9
9
  <circle cx="60.0" cy="15" r="5" fill="firebrick"/>
10
- <circle cx="80.0" cy="15" r="5" fill="darkorange"/>
10
+ <circle cx="80.0" cy="15" r="5" fill="saddlebrown"/>
11
11
  <circle cx="100.0" cy="15" r="5" fill="white"/>
12
- <circle cx="120.0" cy="15" r="5" fill="black"/>
13
- <circle cx="140.0" cy="15" r="5" fill="saddlebrown"/>
12
+ <circle cx="120.0" cy="15" r="5" fill="darkorange"/>
13
+ <circle cx="140.0" cy="15" r="5" fill="black"/>
14
14
  <circle cx="160.0" cy="15" r="5" fill="firebrick"/>
15
- <circle cx="180.0" cy="15" r="5" fill="darkorange"/>
15
+ <circle cx="180.0" cy="15" r="5" fill="saddlebrown"/>
16
16
  <circle cx="200.0" cy="15" r="5" fill="white"/>
17
- <circle cx="220.0" cy="15" r="5" fill="black"/>
18
- <circle cx="240.0" cy="15" r="5" fill="saddlebrown"/>
17
+ <circle cx="220.0" cy="15" r="5" fill="darkorange"/>
18
+ <circle cx="240.0" cy="15" r="5" fill="black"/>
19
19
  <circle cx="260.0" cy="15" r="5" fill="firebrick"/>
20
- <circle cx="280.0" cy="15" r="5" fill="darkorange"/>
20
+ <circle cx="280.0" cy="15" r="5" fill="saddlebrown"/>
21
21
  <circle cx="300.0" cy="15" r="5" fill="white"/>
22
22
  <path d="M 40 30 L 10 60 L 70 60 Z" fill="firebrick"/>
23
23
  <path d="M 80 60 L 50 30 L 110 30 Z" fill="darkorange"/>
@@ -26,21 +26,21 @@
26
26
  <path d="M 200 30 L 170 60 L 230 60 Z" fill="firebrick"/>
27
27
  <path d="M 240 60 L 210 30 L 270 30 Z" fill="darkorange"/>
28
28
  <path d="M 280 30 L 250 60 L 310 60 Z" fill="firebrick"/>
29
- <path d="M 16.47328848624516 84.85410196624969 L 14.293660902229078 78.14589803375031 L 20.0 74.0 L 25.706339097770922 78.14589803375031 L 23.52671151375484 84.85410196624969 Z" fill="darkorange"/>
30
- <path d="M 36.47328848624516 84.85410196624969 L 34.29366090222908 78.14589803375031 L 40.0 74.0 L 45.70633909777092 78.14589803375031 L 43.52671151375484 84.85410196624969 Z" fill="firebrick"/>
29
+ <path d="M 16.47328848624516 84.85410196624969 L 14.293660902229078 78.14589803375031 L 20.0 74.0 L 25.706339097770922 78.14589803375031 L 23.52671151375484 84.85410196624969 Z" fill="white"/>
30
+ <path d="M 36.47328848624516 84.85410196624969 L 34.29366090222908 78.14589803375031 L 40.0 74.0 L 45.70633909777092 78.14589803375031 L 43.52671151375484 84.85410196624969 Z" fill="black"/>
31
31
  <path d="M 56.47328848624516 84.85410196624969 L 54.29366090222908 78.14589803375031 L 60.0 74.0 L 65.70633909777092 78.14589803375031 L 63.52671151375484 84.85410196624969 Z" fill="saddlebrown"/>
32
- <path d="M 76.47328848624517 84.85410196624969 L 74.29366090222908 78.14589803375031 L 80.0 74.0 L 85.70633909777092 78.14589803375031 L 83.52671151375483 84.85410196624969 Z" fill="black"/>
33
- <path d="M 96.47328848624517 84.85410196624969 L 94.29366090222908 78.14589803375031 L 100.0 74.0 L 105.70633909777092 78.14589803375031 L 103.52671151375483 84.85410196624969 Z" fill="white"/>
34
- <path d="M 116.47328848624517 84.85410196624969 L 114.29366090222908 78.14589803375031 L 120.0 74.0 L 125.70633909777092 78.14589803375031 L 123.52671151375483 84.85410196624969 Z" fill="darkorange"/>
35
- <path d="M 136.47328848624517 84.85410196624969 L 134.29366090222908 78.14589803375031 L 140.0 74.0 L 145.70633909777092 78.14589803375031 L 143.52671151375483 84.85410196624969 Z" fill="firebrick"/>
32
+ <path d="M 76.47328848624517 84.85410196624969 L 74.29366090222908 78.14589803375031 L 80.0 74.0 L 85.70633909777092 78.14589803375031 L 83.52671151375483 84.85410196624969 Z" fill="darkorange"/>
33
+ <path d="M 96.47328848624517 84.85410196624969 L 94.29366090222908 78.14589803375031 L 100.0 74.0 L 105.70633909777092 78.14589803375031 L 103.52671151375483 84.85410196624969 Z" fill="firebrick"/>
34
+ <path d="M 116.47328848624517 84.85410196624969 L 114.29366090222908 78.14589803375031 L 120.0 74.0 L 125.70633909777092 78.14589803375031 L 123.52671151375483 84.85410196624969 Z" fill="white"/>
35
+ <path d="M 136.47328848624517 84.85410196624969 L 134.29366090222908 78.14589803375031 L 140.0 74.0 L 145.70633909777092 78.14589803375031 L 143.52671151375483 84.85410196624969 Z" fill="black"/>
36
36
  <path d="M 156.47328848624517 84.85410196624969 L 154.29366090222908 78.14589803375031 L 160.0 74.0 L 165.70633909777092 78.14589803375031 L 163.52671151375483 84.85410196624969 Z" fill="saddlebrown"/>
37
- <path d="M 176.47328848624517 84.85410196624969 L 174.29366090222908 78.14589803375031 L 180.0 74.0 L 185.70633909777092 78.14589803375031 L 183.52671151375483 84.85410196624969 Z" fill="black"/>
38
- <path d="M 196.47328848624517 84.85410196624969 L 194.29366090222908 78.14589803375031 L 200.0 74.0 L 205.70633909777092 78.14589803375031 L 203.52671151375483 84.85410196624969 Z" fill="white"/>
39
- <path d="M 216.47328848624517 84.85410196624969 L 214.29366090222908 78.14589803375031 L 220.0 74.0 L 225.70633909777092 78.14589803375031 L 223.52671151375483 84.85410196624969 Z" fill="darkorange"/>
40
- <path d="M 236.47328848624517 84.85410196624969 L 234.29366090222908 78.14589803375031 L 240.0 74.0 L 245.70633909777092 78.14589803375031 L 243.52671151375483 84.85410196624969 Z" fill="firebrick"/>
37
+ <path d="M 176.47328848624517 84.85410196624969 L 174.29366090222908 78.14589803375031 L 180.0 74.0 L 185.70633909777092 78.14589803375031 L 183.52671151375483 84.85410196624969 Z" fill="darkorange"/>
38
+ <path d="M 196.47328848624517 84.85410196624969 L 194.29366090222908 78.14589803375031 L 200.0 74.0 L 205.70633909777092 78.14589803375031 L 203.52671151375483 84.85410196624969 Z" fill="firebrick"/>
39
+ <path d="M 216.47328848624517 84.85410196624969 L 214.29366090222908 78.14589803375031 L 220.0 74.0 L 225.70633909777092 78.14589803375031 L 223.52671151375483 84.85410196624969 Z" fill="white"/>
40
+ <path d="M 236.47328848624517 84.85410196624969 L 234.29366090222908 78.14589803375031 L 240.0 74.0 L 245.70633909777092 78.14589803375031 L 243.52671151375483 84.85410196624969 Z" fill="black"/>
41
41
  <path d="M 256.47328848624517 84.85410196624969 L 254.29366090222908 78.14589803375031 L 260.0 74.0 L 265.7063390977709 78.14589803375031 L 263.52671151375483 84.85410196624969 Z" fill="saddlebrown"/>
42
- <path d="M 276.47328848624517 84.85410196624969 L 274.2936609022291 78.14589803375031 L 280.0 74.0 L 285.7063390977709 78.14589803375031 L 283.52671151375483 84.85410196624969 Z" fill="black"/>
43
- <path d="M 296.47328848624517 84.85410196624969 L 294.2936609022291 78.14589803375031 L 300.0 74.0 L 305.7063390977709 78.14589803375031 L 303.52671151375483 84.85410196624969 Z" fill="white"/>
42
+ <path d="M 276.47328848624517 84.85410196624969 L 274.2936609022291 78.14589803375031 L 280.0 74.0 L 285.7063390977709 78.14589803375031 L 283.52671151375483 84.85410196624969 Z" fill="darkorange"/>
43
+ <path d="M 296.47328848624517 84.85410196624969 L 294.2936609022291 78.14589803375031 L 300.0 74.0 L 305.7063390977709 78.14589803375031 L 303.52671151375483 84.85410196624969 Z" fill="firebrick"/>
44
44
  <rect x="0" y="100" width="320" height="160" fill="saddlebrown"/>
45
45
  <path d="M 85 200 L 70 100 L 100 100 Z" fill="white"/>
46
46
  <path d="M 115 200 L 100 100 L 130 100 Z" fill="white"/>
@@ -50,8 +50,8 @@
50
50
  <path d="M 235 200 L 220 100 L 250 100 Z" fill="white"/>
51
51
  <path d="M 35 145 L 10 125 L 60 125 Z" fill="black"/>
52
52
  <path d="M 285 145 L 260 125 L 310 125 Z" fill="black"/>
53
- <path d="M 42 160 C 42 156.136594828542, 38.863405171458 153, 35 153 C 31.136594828542002 153, 28 156.136594828542, 28 160 C 28 163.863405171458, 31.136594828542002 167, 35 167 C 38.863405171458 167, 42 163.863405171458, 42 160" fill="firebrick"/>
54
- <path d="M 292 160 C 292 156.136594828542, 288.863405171458 153, 285 153 C 281.136594828542 153, 278 156.136594828542, 278 160 C 278 163.863405171458, 281.136594828542 167, 285 167 C 288.863405171458 167, 292 163.863405171458, 292 160" fill="firebrick"/>
53
+ <path d="M 42 160 C 42 156.136594828542, 38.863405171458 153, 35 153 C 31.136594828542002 153, 28 156.136594828542, 28 160 C 28 163.863405171458, 31.136594828542002 167, 35 167 C 38.863405171458 167, 42 163.863405171458, 42 160 Z" fill="firebrick"/>
54
+ <path d="M 292 160 C 292 156.136594828542, 288.863405171458 153, 285 153 C 281.136594828542 153, 278 156.136594828542, 278 160 C 278 163.863405171458, 281.136594828542 167, 285 167 C 288.863405171458 167, 292 163.863405171458, 292 160 Z" fill="firebrick"/>
55
55
  <path d="M 70 160.0 L 55 260.0 L 85 260.0 Z" fill="white"/>
56
56
  <path d="M 100 160.0 L 85 260.0 L 115 260.0 Z" fill="white"/>
57
57
  <path d="M 130 160.0 L 115 260.0 L 145 260.0 Z" fill="white"/>
@@ -59,21 +59,21 @@
59
59
  <path d="M 190 160.0 L 175 260.0 L 205 260.0 Z" fill="white"/>
60
60
  <path d="M 220 160.0 L 205 260.0 L 235 260.0 Z" fill="white"/>
61
61
  <path d="M 250 160.0 L 235 260.0 L 265 260.0 Z" fill="white"/>
62
- <path d="M 16.47328848624516 284.8541019662497 L 14.293660902229078 278.1458980337503 L 20.0 274.0 L 25.706339097770922 278.1458980337503 L 23.52671151375484 284.8541019662497 Z" fill="darkorange"/>
63
- <path d="M 36.47328848624516 284.8541019662497 L 34.29366090222908 278.1458980337503 L 40.0 274.0 L 45.70633909777092 278.1458980337503 L 43.52671151375484 284.8541019662497 Z" fill="white"/>
64
- <path d="M 56.47328848624516 284.8541019662497 L 54.29366090222908 278.1458980337503 L 60.0 274.0 L 65.70633909777092 278.1458980337503 L 63.52671151375484 284.8541019662497 Z" fill="saddlebrown"/>
62
+ <path d="M 16.47328848624516 284.8541019662497 L 14.293660902229078 278.1458980337503 L 20.0 274.0 L 25.706339097770922 278.1458980337503 L 23.52671151375484 284.8541019662497 Z" fill="saddlebrown"/>
63
+ <path d="M 36.47328848624516 284.8541019662497 L 34.29366090222908 278.1458980337503 L 40.0 274.0 L 45.70633909777092 278.1458980337503 L 43.52671151375484 284.8541019662497 Z" fill="darkorange"/>
64
+ <path d="M 56.47328848624516 284.8541019662497 L 54.29366090222908 278.1458980337503 L 60.0 274.0 L 65.70633909777092 278.1458980337503 L 63.52671151375484 284.8541019662497 Z" fill="black"/>
65
65
  <path d="M 76.47328848624517 284.8541019662497 L 74.29366090222908 278.1458980337503 L 80.0 274.0 L 85.70633909777092 278.1458980337503 L 83.52671151375483 284.8541019662497 Z" fill="firebrick"/>
66
- <path d="M 96.47328848624517 284.8541019662497 L 94.29366090222908 278.1458980337503 L 100.0 274.0 L 105.70633909777092 278.1458980337503 L 103.52671151375483 284.8541019662497 Z" fill="black"/>
67
- <path d="M 116.47328848624517 284.8541019662497 L 114.29366090222908 278.1458980337503 L 120.0 274.0 L 125.70633909777092 278.1458980337503 L 123.52671151375483 284.8541019662497 Z" fill="darkorange"/>
68
- <path d="M 136.47328848624517 284.8541019662497 L 134.29366090222908 278.1458980337503 L 140.0 274.0 L 145.70633909777092 278.1458980337503 L 143.52671151375483 284.8541019662497 Z" fill="white"/>
69
- <path d="M 156.47328848624517 284.8541019662497 L 154.29366090222908 278.1458980337503 L 160.0 274.0 L 165.70633909777092 278.1458980337503 L 163.52671151375483 284.8541019662497 Z" fill="saddlebrown"/>
66
+ <path d="M 96.47328848624517 284.8541019662497 L 94.29366090222908 278.1458980337503 L 100.0 274.0 L 105.70633909777092 278.1458980337503 L 103.52671151375483 284.8541019662497 Z" fill="white"/>
67
+ <path d="M 116.47328848624517 284.8541019662497 L 114.29366090222908 278.1458980337503 L 120.0 274.0 L 125.70633909777092 278.1458980337503 L 123.52671151375483 284.8541019662497 Z" fill="saddlebrown"/>
68
+ <path d="M 136.47328848624517 284.8541019662497 L 134.29366090222908 278.1458980337503 L 140.0 274.0 L 145.70633909777092 278.1458980337503 L 143.52671151375483 284.8541019662497 Z" fill="darkorange"/>
69
+ <path d="M 156.47328848624517 284.8541019662497 L 154.29366090222908 278.1458980337503 L 160.0 274.0 L 165.70633909777092 278.1458980337503 L 163.52671151375483 284.8541019662497 Z" fill="black"/>
70
70
  <path d="M 176.47328848624517 284.8541019662497 L 174.29366090222908 278.1458980337503 L 180.0 274.0 L 185.70633909777092 278.1458980337503 L 183.52671151375483 284.8541019662497 Z" fill="firebrick"/>
71
- <path d="M 196.47328848624517 284.8541019662497 L 194.29366090222908 278.1458980337503 L 200.0 274.0 L 205.70633909777092 278.1458980337503 L 203.52671151375483 284.8541019662497 Z" fill="black"/>
72
- <path d="M 216.47328848624517 284.8541019662497 L 214.29366090222908 278.1458980337503 L 220.0 274.0 L 225.70633909777092 278.1458980337503 L 223.52671151375483 284.8541019662497 Z" fill="darkorange"/>
73
- <path d="M 236.47328848624517 284.8541019662497 L 234.29366090222908 278.1458980337503 L 240.0 274.0 L 245.70633909777092 278.1458980337503 L 243.52671151375483 284.8541019662497 Z" fill="white"/>
74
- <path d="M 256.47328848624517 284.8541019662497 L 254.29366090222908 278.1458980337503 L 260.0 274.0 L 265.7063390977709 278.1458980337503 L 263.52671151375483 284.8541019662497 Z" fill="saddlebrown"/>
71
+ <path d="M 196.47328848624517 284.8541019662497 L 194.29366090222908 278.1458980337503 L 200.0 274.0 L 205.70633909777092 278.1458980337503 L 203.52671151375483 284.8541019662497 Z" fill="white"/>
72
+ <path d="M 216.47328848624517 284.8541019662497 L 214.29366090222908 278.1458980337503 L 220.0 274.0 L 225.70633909777092 278.1458980337503 L 223.52671151375483 284.8541019662497 Z" fill="saddlebrown"/>
73
+ <path d="M 236.47328848624517 284.8541019662497 L 234.29366090222908 278.1458980337503 L 240.0 274.0 L 245.70633909777092 278.1458980337503 L 243.52671151375483 284.8541019662497 Z" fill="darkorange"/>
74
+ <path d="M 256.47328848624517 284.8541019662497 L 254.29366090222908 278.1458980337503 L 260.0 274.0 L 265.7063390977709 278.1458980337503 L 263.52671151375483 284.8541019662497 Z" fill="black"/>
75
75
  <path d="M 276.47328848624517 284.8541019662497 L 274.2936609022291 278.1458980337503 L 280.0 274.0 L 285.7063390977709 278.1458980337503 L 283.52671151375483 284.8541019662497 Z" fill="firebrick"/>
76
- <path d="M 296.47328848624517 284.8541019662497 L 294.2936609022291 278.1458980337503 L 300.0 274.0 L 305.7063390977709 278.1458980337503 L 303.52671151375483 284.8541019662497 Z" fill="black"/>
76
+ <path d="M 296.47328848624517 284.8541019662497 L 294.2936609022291 278.1458980337503 L 300.0 274.0 L 305.7063390977709 278.1458980337503 L 303.52671151375483 284.8541019662497 Z" fill="white"/>
77
77
  <path d="M 160.0 330.0 L 140.0 350.0 L 180.0 350.0 Z" fill="black"/>
78
78
  <path d="M 133.29748792524228 566.9913494618188 L 103.36126677178882 585.8015239174565 L 152.10766238088002 596.9275706152723 Z" fill="white"/>
79
79
  <path d="M 212.06604869410697 341.88373585170973 L 185.36899655370743 351.2254384274069 L 221.40775126980418 368.58078799210926 Z" fill="darkorange"/>
@@ -103,19 +103,19 @@
103
103
  <path d="M 107.933951305893 341.88373585170973 L 98.59224873019579 368.58078799210926 L 134.63100344629254 351.2254384274069 Z" fill="darkorange"/>
104
104
  <path d="M 186.70251207475786 566.9913494618188 L 167.89233761912016 596.9275706152723 L 216.63873322821132 585.8015239174565 Z" fill="firebrick"/>
105
105
  <path d=" M 141.83714962005615 498.54101943969727 L 103.05687046051025 431.3716058731079 L 132.47236156463623 410.0 L 187.5276393890381 410.0000009536743 L 216.94313049316406 431.3716058731079 L 178.16285133361816 498.54101943969727 Z" fill="firebrick"/>
106
- <circle cx="20.0" cy="625" r="5" fill="saddlebrown"/>
106
+ <circle cx="20.0" cy="625" r="5" fill="firebrick"/>
107
107
  <circle cx="40.0" cy="625" r="5" fill="darkorange"/>
108
- <circle cx="60.0" cy="625" r="5" fill="black"/>
109
- <circle cx="80.0" cy="625" r="5" fill="white"/>
110
- <circle cx="100.0" cy="625" r="5" fill="firebrick"/>
111
- <circle cx="120.0" cy="625" r="5" fill="saddlebrown"/>
108
+ <circle cx="60.0" cy="625" r="5" fill="white"/>
109
+ <circle cx="80.0" cy="625" r="5" fill="black"/>
110
+ <circle cx="100.0" cy="625" r="5" fill="saddlebrown"/>
111
+ <circle cx="120.0" cy="625" r="5" fill="firebrick"/>
112
112
  <circle cx="140.0" cy="625" r="5" fill="darkorange"/>
113
- <circle cx="160.0" cy="625" r="5" fill="black"/>
114
- <circle cx="180.0" cy="625" r="5" fill="white"/>
115
- <circle cx="200.0" cy="625" r="5" fill="firebrick"/>
116
- <circle cx="220.0" cy="625" r="5" fill="saddlebrown"/>
113
+ <circle cx="160.0" cy="625" r="5" fill="white"/>
114
+ <circle cx="180.0" cy="625" r="5" fill="black"/>
115
+ <circle cx="200.0" cy="625" r="5" fill="saddlebrown"/>
116
+ <circle cx="220.0" cy="625" r="5" fill="firebrick"/>
117
117
  <circle cx="240.0" cy="625" r="5" fill="darkorange"/>
118
- <circle cx="260.0" cy="625" r="5" fill="black"/>
119
- <circle cx="280.0" cy="625" r="5" fill="white"/>
120
- <circle cx="300.0" cy="625" r="5" fill="firebrick"/>
118
+ <circle cx="260.0" cy="625" r="5" fill="white"/>
119
+ <circle cx="280.0" cy="625" r="5" fill="black"/>
120
+ <circle cx="300.0" cy="625" r="5" fill="saddlebrown"/>
121
121
  </svg>
@@ -1,8 +1,8 @@
1
1
  # Isoscelese right-angle triangle
2
- iso_tri(50, at: [100, 50])
2
+ iso_tri(50)[100, 50]
3
3
 
4
4
  # Simple equilateral triangle
5
- triangle(50, at: [100,220], fill: '#666')
5
+ triangle(50, fill: "#666")[100,220]
6
6
 
7
7
  # Isoscelese triangle
8
- iso_tri(50, 100, at: [100, 300], fill: 'lightgrey')
8
+ iso_tri(50, 100, fill: "lightgrey")[100, 300]
@@ -117,17 +117,7 @@ module VectorSalad
117
117
  end
118
118
  end
119
119
 
120
- class Square
121
- # Export the shape to an svg string
122
- def to_svg
123
- svg = "<rect x=\"#{at[0]}\" y=\"#{at[1]}\""
124
- svg << " width=\"#{size}\" height=\"#{size}\""
125
- svg << VectorSalad::Exporters::SvgExporter.options(@options)
126
- svg << "/>"
127
- end
128
- end
129
-
130
- class Rect
120
+ class Rect # and Square subclass
131
121
  # Export the shape to an svg string
132
122
  def to_svg
133
123
  svg = "<rect x=\"#{at[0]}\" y=\"#{at[1]}\""
@@ -4,11 +4,12 @@ module VectorSalad
4
4
  module At
5
5
  include Contracts
6
6
 
7
- # Change the absolute x, y coordinates of the shape.
8
- Contract Num, Num => Any
7
+ # Set the x, y coordinates of the shape.
8
+ Contract Coord, Coord => Any
9
9
  def [](x, y)
10
- @x, @y = x, y
11
- self
10
+ shape = clone
11
+ shape.at = [x, y]
12
+ shape
12
13
  end
13
14
 
14
15
  # Get the x, y coordinates of the shape.
@@ -17,11 +18,18 @@ module VectorSalad
17
18
  [@x, @y]
18
19
  end
19
20
 
21
+ # Set the x, y coordinates of the shape directly.
22
+ Contract Coords => Any
23
+ def at=(at)
24
+ @x, @y = *at
25
+ self
26
+ end
27
+
20
28
  # Move the shape relatively.
21
- Contract Num, Num => Any
29
+ Contract Coord, Coord => Any
22
30
  def move(x, y)
23
31
  shape = clone
24
- shape[shape.at[0] + x, shape.at[1] + y]
32
+ shape.at = [shape.at[0] + x, shape.at[1] + y]
25
33
  shape
26
34
  end
27
35
  end
@@ -1,15 +1,30 @@
1
+ # Monkeypatches to core Ruby Fixnum class
2
+ class Numeric
3
+ # Get unit value
4
+ def unit
5
+ @@unit ||= 1
6
+ end
7
+
8
+ # Set the global unit value
9
+ # for multiplying numbers by using tilde (~)
10
+ # to scale designs
11
+ def self.unit=(unit)
12
+ @@unit = unit
13
+ end
14
+ end
15
+
1
16
  # Monkeypatches to core Ruby Fixnum class
2
17
  class Fixnum
3
- # Multiply number self by UNIT constant
18
+ # Multiply number self by unit
4
19
  def ~
5
- self * UNIT
20
+ self * unit
6
21
  end
7
22
  end
8
23
 
9
24
  # Monkeypatches to core Ruby Float class
10
25
  class Float
11
- # Multiply number self by UNIT constant
26
+ # Multiply number self by unit
12
27
  def ~
13
- self * UNIT
28
+ self * unit
14
29
  end
15
30
  end
@@ -24,6 +24,7 @@ module VectorSalad
24
24
  def_instance_delegator :to_path, :flip_x
25
25
  def_instance_delegator :to_path, :flip_y
26
26
  def_instance_delegator :to_path, :rotate
27
+ def_instance_delegator :to_path, :[]
27
28
  def_instance_delegator :to_path, :move
28
29
  def_instance_delegator :to_path, :jitter
29
30
  def_instance_delegator :to_path, :scale
@@ -24,7 +24,7 @@ module VectorSalad
24
24
  # donut(100)
25
25
  #
26
26
  # @param name The name of your shape in snake_case
27
- Contract Symbol, {}, Proc => Custom
27
+ Contract Symbol, {}, Proc => Any
28
28
  def initialize(name, **options, &block)
29
29
  ::VectorSalad::StandardShapes.const_set(name.to_s.capitalize.to_sym, Class.new(BasicShape) do
30
30
  include VectorSalad::DSL
@@ -44,7 +44,7 @@ module VectorSalad
44
44
 
45
45
  dx = pivot.x - source.x
46
46
  dy = pivot.y - source.y
47
- node[pivot.x + dx, pivot.y + dy]
47
+ node.at = [pivot.x + dx, pivot.y + dy]
48
48
 
49
49
  node.type = source.type
50
50
  else
@@ -62,16 +62,19 @@ module VectorSalad
62
62
  end
63
63
 
64
64
  # Move the path absolutely.
65
- Contract Num, Num => Path
65
+ Contract Coord, Coord => Path
66
66
  def [](x, y)
67
- @nodes.map do |node|
68
- node[x, y]
69
- end
70
- self
67
+ Path.new(
68
+ *to_path.nodes.map do |node|
69
+ node[x, y]
70
+ end,
71
+ closed: @closed,
72
+ **@options
73
+ )
71
74
  end
72
75
 
73
76
  # Move the path relatively.
74
- Contract Num, Num => Path
77
+ Contract Coord, Coord => Path
75
78
  def move(x, y)
76
79
  Path.new(
77
80
  *to_path.nodes.map do |node|
@@ -117,7 +120,7 @@ module VectorSalad
117
120
  # rotate(90)
118
121
  # @example
119
122
  # rotate(-45)
120
- Contract Num => Path
123
+ Contract Coord => Path
121
124
  def rotate(angle)
122
125
  theta = angle / 180.0 * Math::PI
123
126
 
@@ -140,7 +143,7 @@ module VectorSalad
140
143
  # to stretch or squash the axies.
141
144
  #
142
145
  # @param x_multiplier 1 is no change, 2 is double size, 0.5 is half, etc.
143
- Contract Num, Maybe[Num] => Path
146
+ Contract Coord, Maybe[Coord] => Path
144
147
  def scale(x_multiplier, y_multiplier = x_multiplier)
145
148
  Path.new(
146
149
  *to_path.nodes.map do |n|
@@ -158,7 +161,7 @@ module VectorSalad
158
161
  # @param max The maximum offset
159
162
  # @param min The minimum offset (default 0)
160
163
  # @param fn The quantization number of sides
161
- Contract Num, { min: Maybe[Num], fn: Maybe[Fixnum] } => Path
164
+ Contract Coord, { min: Maybe[Coord], fn: Maybe[Fixnum] } => Path
162
165
  def jitter(max, min: 0, fn: nil)
163
166
  Path.new(
164
167
  *to_simple_path(fn).nodes.map do |n|
@@ -1,5 +1,4 @@
1
1
  require "vector_salad/standard_shapes/rect"
2
- require "vector_salad/mixins/at"
3
2
 
4
3
  module VectorSalad
5
4
  module StandardShapes
@@ -1,3 +1,3 @@
1
1
  module VectorSalad
2
- VERSION = "0.0.8" # Version of VectorSalad
2
+ VERSION = "0.1.0" # Version of VectorSalad
3
3
  end
@@ -0,0 +1,4 @@
1
+ $LOAD_PATH.unshift File.expand_path("../../lib", __FILE__)
2
+ require "vector_salad/export_with_magic"
3
+
4
+ require "minitest/autorun"
@@ -0,0 +1,23 @@
1
+ require "minitest_helper"
2
+ require "ostruct"
3
+
4
+ class TestVectorSalad < Minitest::Test
5
+ EXAMPLES = "#{__dir__}/../examples"
6
+
7
+ # Integration tests
8
+ # Run VectorSalad on each example to
9
+ # test that the output is still the same
10
+ Dir.glob("#{EXAMPLES}/*.rb").each do |file|
11
+ example = File.basename(file, ".rb")
12
+
13
+ define_method("test_example_#{example}".to_sym) do
14
+ srand 1 # seed random to keep example tests constant
15
+ exporter = VectorSalad::ExportWithMagic.new OpenStruct.new(
16
+ file: "#{EXAMPLES}/#{example}.rb"
17
+ )
18
+ svg = File.read("#{EXAMPLES}/#{example}.svg")
19
+
20
+ assert_equal svg, exporter.export
21
+ end
22
+ end
23
+ end