rubysketch 0.3.6 → 0.3.11

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 1a40d65c055cc2baacd0a7489ec511a0db37b8e534f58fc02d5c095f78ecca66
4
- data.tar.gz: 9c8634c610e0df8201655809b82bc8e7dbc2adab8cad405e2033ecc321c09137
3
+ metadata.gz: f9d6862ce564503738c10d66ea1b76000d57ffa7100a0e47bf0b96c8083e02dd
4
+ data.tar.gz: 44825a802755cd03c1efa129ec0a0349872f330795433839f2232ef2b9b83a24
5
5
  SHA512:
6
- metadata.gz: 04d5e9096e7cef9ea5d6c16e3397d5965bc8da07f699fc3b241e91ad982c755fe7b4faf4296b6ce74612da690cc7d7cfd507612387f43276b0e2ab0d05566ddf
7
- data.tar.gz: 224f32277392e5b84c84b6ef13a437813859f960e47dce696f97dd547273d0d86a3e62685a171a7055981989fd99679e60b843e12b839bc2b501c4e9fbb7e622
6
+ metadata.gz: ed6efaf98ea1b9e816d337ebf82d57516f3f2fb30877d693f2a18c42d24d85eaf981fa804c1f1761ec0bd86ec73e8a5f88fcb50103c5bd5979e46bf58a2c0162
7
+ data.tar.gz: 5d8d25591fdbc056dc0f793d5a8c93cae50547731e10128c6ec27e9432491f238d5e547f9cc74701beb85903a39114da045cd320cf1903f235afa7975bef42ca
@@ -1,6 +1,38 @@
1
1
  # RubySketch ChangeLog
2
2
 
3
3
 
4
+ ## [0.3.11] - 2020-12-9
5
+
6
+ - add size(), createCanvas() and pixelDensity()
7
+
8
+
9
+ ## [0.3.10] - 2020-12-1
10
+
11
+ - invert angle parameter value for arc() to fix compatibility to processing API
12
+
13
+
14
+ ## [0.3.9] - 2020-11-30
15
+
16
+ - Graphics#beginDraw() can take block to call endDraw automatically
17
+ - Capture#start() always returns nil
18
+ - add delay_camera.rb
19
+
20
+
21
+ ## [0.3.8] - 2020-11-27
22
+
23
+ - Capture#initialize() can take requestWidth, requestHeight and cameraName
24
+ - add Capture#width and Capture#height
25
+
26
+
27
+ ## [0.3.7] - 2020-11-18
28
+
29
+ - add Capture class
30
+ - add log(), exp(), sqrt() and PI
31
+ - add examples/camera.rb
32
+ - add examples/breakout.rb
33
+ - fix error on calling image()
34
+
35
+
4
36
  ## [0.3.6] - 2020-08-02
5
37
 
6
38
  - random() can take array or nothing
data/README.md CHANGED
@@ -1,3 +1,11 @@
1
- # RubySketch - Processing like Creative Coding Framework
1
+ # RubySketch - Processing compatible Creative Coding Framework
2
2
 
3
3
  by xordog@gmail.com
4
+
5
+
6
+ # How to release
7
+
8
+ ```
9
+ $ rake version:bump:patch message="..."
10
+ $ git push origin --tags
11
+ ```
data/Rakefile CHANGED
@@ -23,3 +23,28 @@ generate_documents
23
23
  build_ruby_gem
24
24
 
25
25
  task :default => :test
26
+
27
+
28
+ namespace :version do
29
+
30
+ namespace :bump do
31
+
32
+ task :major do
33
+ update_and_tag_version 0
34
+ end
35
+
36
+ task :minor do
37
+ update_and_tag_version 1
38
+ end
39
+
40
+ task :patch do
41
+ update_and_tag_version 2
42
+ end
43
+
44
+ task :build do
45
+ update_and_tag_version 3
46
+ end
47
+
48
+ end# bump
49
+
50
+ end# version
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.3.6
1
+ 0.3.11
@@ -0,0 +1,212 @@
1
+ %w[xot rays reflex rubysketch]
2
+ .map {|s| File.expand_path "../../#{s}/lib", __dir__}
3
+ .each {|s| $:.unshift s if !$:.include?(s) && File.directory?(s)}
4
+
5
+ require 'rubysketch-processing'
6
+
7
+
8
+ PADDING = 50
9
+ BRICK_COUNT = 10
10
+
11
+ $objs = []
12
+ $bar = nil
13
+ $gameover = false
14
+
15
+ setup do
16
+ addWalls
17
+ addBricks
18
+
19
+ colorMode HSB, 360, 100, 100
20
+ ellipseMode CORNER
21
+ background 0
22
+ noStroke
23
+ fill 0, 0, 100
24
+ end
25
+
26
+ draw do
27
+ background 0
28
+ $objs.each do |o|
29
+ o.update
30
+ o.draw
31
+ end
32
+ drawTexts
33
+ end
34
+
35
+ mousePressed do
36
+ start unless started?
37
+ end
38
+
39
+ mouseDragged do
40
+ $bar.pos.x = mouseX - $bar.w / 2 if $bar
41
+ end
42
+
43
+ def start()
44
+ $bar = Bar.new
45
+ $objs += [$bar, Ball.new($bar)]
46
+ end
47
+
48
+ def started?()
49
+ $bar
50
+ end
51
+
52
+ def gameover?()
53
+ started? &&
54
+ $objs.count {|o| o.kind_of? Ball} == 0
55
+ end
56
+
57
+ def cleared?()
58
+ started? && !gameover? &&
59
+ $objs.count {|o| o.kind_of? Brick} == 0
60
+ end
61
+
62
+ def addWalls()
63
+ left = Obj.new 0, 0, 10, height
64
+ top = Obj.new 0, 0, width, 10
65
+ right = Obj.new width - 10, 0, 10, height
66
+ bottom = Bottom.new 0, height - 10, width, 10
67
+ $objs += [top, bottom, left, right]
68
+ end
69
+
70
+ def addBricks()
71
+ brickW = (width - PADDING * 2) / BRICK_COUNT
72
+ 5.times do |y|
73
+ BRICK_COUNT.times do |x|
74
+ xx = PADDING + brickW * x
75
+ yy = PADDING + 30 * y
76
+ $objs.push Brick.new(xx, yy, brickW - 5, 20, y * 60)
77
+ end
78
+ end
79
+ end
80
+
81
+ def drawTexts()
82
+ push do
83
+ textAlign CENTER, CENTER
84
+
85
+ if !started?
86
+ fill 50, 100, 100
87
+ textSize 50
88
+ text "BREAKOUT", 0, 0, width, height
89
+ textSize 20
90
+ translate 0, 100
91
+ text "Tap to start!", 0, 0, width, height
92
+ elsif cleared?
93
+ fill 100, 80, 100
94
+ textSize 50
95
+ text "CLEAR!", 0, 0, width, height
96
+ elsif gameover?
97
+ fill 0, 20, 100
98
+ textSize 50
99
+ text "GAMEOVER", 0, 0, width, height
100
+ end
101
+ end
102
+ end
103
+
104
+ class Obj
105
+ attr_reader :pos, :w, :h, :vel
106
+
107
+ def initialize(x, y, w, h, vx = 0, vy = 0)
108
+ @pos = createVector x, y
109
+ @w, @h = w, h
110
+ @vel = createVector vx, vy
111
+ end
112
+
113
+ def update()
114
+ @pos.add @vel
115
+ end
116
+
117
+ def draw()
118
+ rect @pos.x, @pos.y, @w, @h
119
+ end
120
+
121
+ def bounds()
122
+ x, y = @pos.x, @pos.y
123
+ return x, y, x + @w, y + @h
124
+ end
125
+
126
+ def center()
127
+ createVector @pos.x + @w / 2, @pos.y + @h / 2
128
+ end
129
+ end
130
+
131
+ class Ball < Obj
132
+ def initialize(bar)
133
+ super bar.pos.x, bar.pos.y - bar.h, 20, 20
134
+ self.vel = createVector random(-1, 1), -1
135
+ end
136
+
137
+ def vel=(v)
138
+ @vel = v.dup.normalize.mult 8
139
+ end
140
+
141
+ def update()
142
+ b = bounds.dup
143
+ super
144
+ checkHit b
145
+ end
146
+
147
+ def checkHit(prevBounds)
148
+ x1, y1, x2, y2 = prevBounds
149
+ hitH = hitV = false
150
+ hits = []
151
+ $objs.each do |o|
152
+ next if o == self
153
+ next unless intersect? o
154
+ hits.push o
155
+ ox1, oy1, ox2, oy2 = o.bounds
156
+ hitH ||= !overlap?(x1, x2, ox1, ox2)
157
+ hitV ||= !overlap?(y1, y2, oy1, oy2)
158
+ end
159
+ vel.x *= -1 if hitH
160
+ vel.y *= -1 if hitV
161
+
162
+ hits.each {|o| hit o}
163
+ end
164
+
165
+ def intersect?(o)
166
+ x1, y1, x2, y2 = bounds
167
+ ox1, oy1, ox2, oy2 = o.bounds
168
+ overlap?(x1, x2, ox1, ox2) && overlap?(y1, y2, oy1, oy2)
169
+ end
170
+
171
+ def overlap?(a1, a2, b1, b2)
172
+ a1 <= b2 && b1 <= a2
173
+ end
174
+
175
+ def hit(o)
176
+ case o
177
+ when Bar then self.vel = center.sub o.center
178
+ when Brick then $objs.delete o
179
+ when Bottom then $objs.delete self unless cleared?
180
+ end
181
+ end
182
+ end
183
+
184
+ class Bar < Obj
185
+ def initialize()
186
+ w = 100
187
+ super (width - w) / 2, height - 50, w, 20
188
+ end
189
+ end
190
+
191
+ class Brick < Obj
192
+ def initialize(x, y, w, h, hue)
193
+ super x, y, w, h
194
+ @hue = hue
195
+ end
196
+
197
+ def draw()
198
+ push do
199
+ fill @hue, 50, 100
200
+ super
201
+ end
202
+ end
203
+ end
204
+
205
+ class Bottom < Obj
206
+ def draw()
207
+ push do
208
+ fill 0, 0, 50
209
+ super
210
+ end
211
+ end
212
+ end
@@ -0,0 +1,14 @@
1
+ %w[xot rays reflex rubysketch]
2
+ .map {|s| File.expand_path "../../#{s}/lib", __dir__}
3
+ .each {|s| $:.unshift s if !$:.include?(s) && File.directory?(s)}
4
+
5
+ require 'rubysketch-processing'
6
+
7
+
8
+ cam = Capture.new 300, 300
9
+ cam.start
10
+
11
+ draw do
12
+ background 0
13
+ image cam, 0, 0
14
+ end
@@ -0,0 +1,33 @@
1
+ %w[xot rays reflex rubysketch]
2
+ .map {|s| File.expand_path "../../#{s}/lib", __dir__}
3
+ .each {|s| $:.unshift s if !$:.include?(s) && File.directory?(s)}
4
+
5
+ require 'rubysketch-processing'
6
+
7
+
8
+ w, h = width, height
9
+
10
+ cam = Capture.new w, h, Capture.list.last
11
+ cam.start
12
+
13
+ images = 60.times.map {
14
+ Graphics.new w, h
15
+ }
16
+
17
+ draw do
18
+ if frameCount % 2 == 0
19
+ images.unshift images.pop
20
+ images.first.tap do |image|
21
+ image.beginDraw {
22
+ image.image cam, 0, 0
23
+ }
24
+ end
25
+ end
26
+
27
+ background 0
28
+ segment_h= h / images.size
29
+ images.each.with_index do |image, i|
30
+ y = i * segment_h
31
+ copy image, 0, y, w, segment_h, 0, y, w, segment_h
32
+ end
33
+ end
@@ -2,10 +2,18 @@ require 'rubysketch'
2
2
 
3
3
 
4
4
  begin
5
- include RubySketch::Processing::Context
5
+ window = RubySketch::Window.new {start}
6
+ context = RubySketch::Processing::Context.new window
6
7
 
7
- window = RubySketch::Window.new {start}
8
- setup__ window
8
+ (context.methods - Object.instance_methods).each do |method|
9
+ define_method method do |*args, &block|
10
+ context.__send__ method, *args, &block
11
+ end
12
+ end
13
+
14
+ context.class.constants.each do |const|
15
+ self.class.const_set const, context.class.const_get(const)
16
+ end
9
17
 
10
18
  window.__send__ :begin_draw
11
19
  at_exit do
@@ -141,9 +141,9 @@ module RubySketch
141
141
  #
142
142
  def lerp (*args, amount)
143
143
  v = toVector__ *args
144
- self.x = Context.lerp x, v.x, amount
145
- self.y = Context.lerp y, v.y, amount
146
- self.z = Context.lerp z, v.z, amount
144
+ self.x = x + (v.x - x) * amount
145
+ self.y = y + (v.y - y) * amount
146
+ self.z = z + (v.z - z) * amount
147
147
  self
148
148
  end
149
149
 
@@ -728,27 +728,127 @@ module RubySketch
728
728
  end# Touch
729
729
 
730
730
 
731
+ # Camera object.
732
+ #
733
+ class Capture
734
+
735
+ # Returns a list of available camera device names
736
+ #
737
+ # @return [Array] device name list
738
+ #
739
+ def self.list ()
740
+ Rays::Camera.device_names
741
+ end
742
+
743
+ # Initialize camera object.
744
+ #
745
+ # @overload Capture.new()
746
+ # @overload Capture.new(cameraName)
747
+ # @overload Capture.new(requestWidth, requestHeight)
748
+ # @overload Capture.new(requestWidth, requestHeight, cameraName)
749
+ #
750
+ # @param requestWidth [Integer] captured image width
751
+ # @param requestHeight [Integer] captured image height
752
+ # @param cameraName [String] camera device name
753
+ #
754
+ def initialize (*args)
755
+ width, height, name =
756
+ if args.empty?
757
+ [-1, -1, nil]
758
+ elsif args[0].kind_of?(String)
759
+ [-1, -1, args[0]]
760
+ elsif args[0].kind_of?(Numeric) && args[1].kind_of?(Numeric)
761
+ [args[0], args[1], args[2]]
762
+ else
763
+ raise ArgumentError
764
+ end
765
+ @camera = Rays::Camera.new width, height, device_name: name
766
+ end
767
+
768
+ # Start capturing.
769
+ #
770
+ # @return [nil] nil
771
+ #
772
+ def start ()
773
+ raise "Failed to start capture" unless @camera.start
774
+ nil
775
+ end
776
+
777
+ # Stop capturing.
778
+ #
779
+ # @return [nil] nil
780
+ #
781
+ def stop ()
782
+ @camera.stop
783
+ nil
784
+ end
785
+
786
+ # Returns is the next captured image available?
787
+ #
788
+ # @return [Boolean] true means object has next frame
789
+ #
790
+ def available ()
791
+ @camera.active?
792
+ end
793
+
794
+ # Reads next frame image
795
+ #
796
+ def read ()
797
+ @camera.image
798
+ end
799
+
800
+ # Returns the width of captured image
801
+ #
802
+ # @return [Numeric] the width of captured image
803
+ #
804
+ def width ()
805
+ @camera.image&.width || 0
806
+ end
807
+
808
+ # Returns the height of captured image
809
+ #
810
+ # @return [Numeric] the height of captured image
811
+ #
812
+ def height ()
813
+ @camera.image&.height || 0
814
+ end
815
+
816
+ # @private
817
+ def getInternal__ ()
818
+ @camera.image || dummyImage__
819
+ end
820
+
821
+ # @private
822
+ private def dummyImage__ ()
823
+ @dummy ||= Rays::Image.new 1, 1
824
+ end
825
+
826
+ end# Capture
827
+
828
+
731
829
  # Drawing context
732
830
  #
733
831
  module GraphicsContext
734
832
 
735
- Vector = Processing::Vector
833
+ # PI
834
+ #
835
+ PI = Math::PI
736
836
 
737
837
  # PI / 2
738
838
  #
739
- HALF_PI = Math::PI / 2
839
+ HALF_PI = PI / 2
740
840
 
741
841
  # PI / 4
742
842
  #
743
- QUARTER_PI = Math::PI / 4
843
+ QUARTER_PI = PI / 4
744
844
 
745
845
  # PI * 2
746
846
  #
747
- TWO_PI = Math::PI * 2
847
+ TWO_PI = PI * 2
748
848
 
749
849
  # PI * 2
750
850
  #
751
- TAU = Math::PI * 2
851
+ TAU = PI * 2
752
852
 
753
853
  # RGB mode for colorMode().
754
854
  #
@@ -813,11 +913,8 @@ module RubySketch
813
913
  #
814
914
  SQUARE = :square
815
915
 
816
- def setup__ (painter)
817
- @painter__ = painter
818
- @painter__.miter_limit = 10
819
-
820
- @drawing = false
916
+ def init__ (image, painter)
917
+ @drawing__ = false
821
918
  @hsbColor__ = false
822
919
  @colorMaxes__ = [1.0] * 4
823
920
  @angleScale__ = 1.0
@@ -829,6 +926,8 @@ module RubySketch
829
926
  @matrixStack__ = []
830
927
  @styleStack__ = []
831
928
 
929
+ updateCanvas__ image, painter
930
+
832
931
  colorMode RGB, 255
833
932
  angleMode RADIANS
834
933
  rectMode CORNER
@@ -840,14 +939,20 @@ module RubySketch
840
939
  stroke 0
841
940
  end
842
941
 
843
- def beginDraw ()
942
+ def updateCanvas__ (image, painter)
943
+ @image__, @painter__ = image, painter
944
+ end
945
+
946
+ # @private
947
+ def beginDraw__ ()
844
948
  @matrixStack__.clear
845
949
  @styleStack__.clear
846
- @drawing = true
950
+ @drawing__ = true
847
951
  end
848
952
 
849
- def endDraw ()
850
- @drawing = false
953
+ # @private
954
+ def endDraw__ ()
955
+ @drawing__ = false
851
956
  end
852
957
 
853
958
  def width ()
@@ -1267,8 +1372,8 @@ module RubySketch
1267
1372
  def arc (a, b, c, d, start, stop)
1268
1373
  assertDrawing__
1269
1374
  x, y, w, h = toXYWH__ @ellipseMode__, a, b, c, d
1270
- start = toAngle__ start
1271
- stop = toAngle__ stop
1375
+ start = toAngle__ -start
1376
+ stop = toAngle__ -stop
1272
1377
  @painter__.ellipse x, y, w, h, from: start, to: stop
1273
1378
  nil
1274
1379
  end
@@ -1411,8 +1516,9 @@ module RubySketch
1411
1516
  #
1412
1517
  def image (img, a, b, c = nil, d = nil)
1413
1518
  assertDrawing__
1414
- x, y, w, h = toXYWH__ @imageMode__, a, b, c || img.width, d || img.height
1415
- @painter__.image img.getInternal__, x, y, w, h
1519
+ i = img.getInternal__
1520
+ x, y, w, h = toXYWH__ @imageMode__, a, b, c || i.width, d || i.height
1521
+ @painter__.image i, x, y, w, h
1416
1522
  nil
1417
1523
  end
1418
1524
 
@@ -1588,13 +1694,13 @@ module RubySketch
1588
1694
  end
1589
1695
 
1590
1696
  # @private
1591
- private def getInternal__ ()
1697
+ def getInternal__ ()
1592
1698
  @image__
1593
1699
  end
1594
1700
 
1595
1701
  # @private
1596
1702
  private def assertDrawing__ ()
1597
- raise "call beginDraw() before drawing" unless @drawing
1703
+ raise "call beginDraw() before drawing" unless @drawing__
1598
1704
  end
1599
1705
 
1600
1706
  end# GraphicsContext
@@ -1606,20 +1712,30 @@ module RubySketch
1606
1712
 
1607
1713
  include GraphicsContext
1608
1714
 
1715
+ # Initialize graphics object.
1716
+ #
1609
1717
  def initialize (width, height)
1610
- @image__ = Rays::Image.new width, height
1611
- setup__ @image__.painter
1718
+ image = Rays::Image.new width, height
1719
+ init__ image, image.painter
1612
1720
  end
1613
1721
 
1614
- def beginDraw ()
1722
+ # Start drawing.
1723
+ #
1724
+ def beginDraw (&block)
1615
1725
  @painter__.__send__ :begin_paint
1616
- super
1726
+ beginDraw__
1617
1727
  push
1728
+ if block
1729
+ block.call
1730
+ endDraw
1731
+ end
1618
1732
  end
1619
1733
 
1734
+ # End drawing.
1735
+ #
1620
1736
  def endDraw ()
1621
1737
  pop
1622
- super
1738
+ endDraw__
1623
1739
  @painter__.__send__ :end_paint
1624
1740
  end
1625
1741
 
@@ -1628,38 +1744,42 @@ module RubySketch
1628
1744
 
1629
1745
  # Processing context
1630
1746
  #
1631
- module Context
1747
+ class Context
1748
+
1749
+ include GraphicsContext
1632
1750
 
1633
- include GraphicsContext, Math
1751
+ Vector = Processing::Vector
1752
+ Capture = Processing::Capture
1753
+ Graphics = Processing::Graphics
1634
1754
 
1755
+ # @private
1635
1756
  @@context__ = nil
1636
1757
 
1758
+ # @private
1637
1759
  def self.context__ ()
1638
1760
  @@context__
1639
1761
  end
1640
1762
 
1641
1763
  # @private
1642
- def setup__ (window)
1764
+ def initialize (window)
1643
1765
  @@context__ = self
1644
1766
 
1645
1767
  @window__ = window
1646
- @image__ = @window__.canvas
1647
- super @window__.canvas_painter.paint {background 0.8}
1768
+ init__ @window__.canvas, @window__.canvas_painter.paint {background 0.8}
1648
1769
 
1649
1770
  @loop__ = true
1650
1771
  @redraw__ = false
1651
1772
  @frameCount__ = 0
1652
1773
  @mousePos__ =
1653
- @mousePrevPos__ = Rays::Point.new 0
1774
+ @mousePrevPos__ = [0, 0]
1654
1775
  @mousePressed__ = false
1655
1776
  @touches__ = []
1656
1777
 
1657
- @window__.before_draw = proc {beginDraw}
1658
- @window__.after_draw = proc {endDraw}
1778
+ @window__.before_draw = proc {beginDraw__}
1779
+ @window__.after_draw = proc {endDraw__}
1659
1780
 
1660
1781
  drawFrame = -> {
1661
- @image__ = @window__.canvas
1662
- @painter__ = @window__.canvas_painter
1782
+ updateCanvas__ @window__.canvas, @window__.canvas_painter
1663
1783
  begin
1664
1784
  push
1665
1785
  @drawBlock__.call if @drawBlock__
@@ -1678,9 +1798,11 @@ module RubySketch
1678
1798
  end
1679
1799
 
1680
1800
  updatePointerStates = -> event, pressed = nil {
1681
- @mousePos__ = event.pos
1801
+ @mousePos__ = @window__.to_canvas_coord event.pos.x, event.pos.y
1682
1802
  @mousePressed__ = pressed if pressed != nil
1683
- @touches__ = event.positions.map {|pos| Touch.new pos.x, pos.y}
1803
+ @touches__ = event.positions.map {|pos|
1804
+ Touch.new *@window__.to_canvas_coord(pos.x, pos.y)
1805
+ }
1684
1806
  }
1685
1807
 
1686
1808
  @window__.pointer_down = proc do |e|
@@ -1758,15 +1880,59 @@ module RubySketch
1758
1880
  nil
1759
1881
  end
1760
1882
 
1883
+ # Changes canvas size.
1884
+ #
1885
+ # @param width [Integer] new width
1886
+ # @param height [Integer] new height
1887
+ #
1888
+ # @return [nil] nil
1889
+ #
1890
+ def size (width, height)
1891
+ resizeCanvas__ :size, width, height, pixelDensity
1892
+ nil
1893
+ end
1894
+
1895
+ # Changes canvas size.
1896
+ #
1897
+ # @param width [Integer] new width
1898
+ # @param height [Integer] new height
1899
+ #
1900
+ # @return [nil] nil
1901
+ #
1902
+ def createCanvas (width, height)
1903
+ resizeCanvas__ :createCanvas, width, height, pixelDensity
1904
+ nil
1905
+ end
1906
+
1907
+ # Changes and returns canvas pixel density.
1908
+ #
1909
+ # @param density [Numeric] new pixel density
1910
+ #
1911
+ # @return [Numeric] current pixel density
1912
+ #
1913
+ def pixelDensity (density = nil)
1914
+ resizeCanvas__ :pixelDensity, width, height, density if density
1915
+ @painter__.pixel_density
1916
+ end
1917
+
1761
1918
  # @private
1762
- private def size__ (width, height)
1763
- raise 'size() must be called on startup or setup block' if @started__
1919
+ def resizeCanvas__ (name, width, height, pixelDensity)
1920
+ raise '#{name}() must be called on startup or setup block' if @started__
1764
1921
 
1765
1922
  @painter__.__send__ :end_paint
1766
- @window__.__send__ :reset_canvas, width, height
1923
+ @window__.__send__ :resize_canvas, width, height, pixelDensity
1924
+ updateCanvas__ @window__.canvas, @window__.canvas_painter
1767
1925
  @painter__.__send__ :begin_paint
1768
1926
 
1769
- @auto_resize__ = false
1927
+ @window__.auto_resize = false
1928
+ end
1929
+
1930
+ # Returns pixel density of display.
1931
+ #
1932
+ # @return [Numeric] pixel density
1933
+ #
1934
+ def displayDensity ()
1935
+ @window__.painter.pixel_density
1770
1936
  end
1771
1937
 
1772
1938
  def windowWidth ()
@@ -1793,20 +1959,12 @@ module RubySketch
1793
1959
  @window__.event.fps
1794
1960
  end
1795
1961
 
1796
- # Returns pixel density
1797
- #
1798
- # @return [Numeric] pixel density
1799
- #
1800
- def displayDensity ()
1801
- @painter__.pixel_density
1802
- end
1803
-
1804
1962
  # Returns mouse x position
1805
1963
  #
1806
1964
  # @return [Numeric] horizontal position of mouse
1807
1965
  #
1808
1966
  def mouseX ()
1809
- @mousePos__.x
1967
+ @mousePos__[0]
1810
1968
  end
1811
1969
 
1812
1970
  # Returns mouse y position
@@ -1814,7 +1972,7 @@ module RubySketch
1814
1972
  # @return [Numeric] vertical position of mouse
1815
1973
  #
1816
1974
  def mouseY ()
1817
- @mousePos__.y
1975
+ @mousePos__[1]
1818
1976
  end
1819
1977
 
1820
1978
  # Returns mouse x position in previous frame
@@ -1822,7 +1980,7 @@ module RubySketch
1822
1980
  # @return [Numeric] horizontal position of mouse
1823
1981
  #
1824
1982
  def pmouseX ()
1825
- @mousePrevPos__.x
1983
+ @mousePrevPos__[0]
1826
1984
  end
1827
1985
 
1828
1986
  # Returns mouse y position in previous frame
@@ -1830,7 +1988,7 @@ module RubySketch
1830
1988
  # @return [Numeric] vertical position of mouse
1831
1989
  #
1832
1990
  def pmouseY ()
1833
- @mousePrevPos__.y
1991
+ @mousePrevPos__[1]
1834
1992
  end
1835
1993
 
1836
1994
  # Returns array of touches
@@ -1865,7 +2023,9 @@ module RubySketch
1865
2023
  @redraw__ = true
1866
2024
  end
1867
2025
 
1868
- module_function
2026
+ #
2027
+ # Utilities
2028
+ #
1869
2029
 
1870
2030
  # Returns the absolute number of the value.
1871
2031
  #
@@ -1907,6 +2067,26 @@ module RubySketch
1907
2067
  value.round
1908
2068
  end
1909
2069
 
2070
+ # Returns the natural logarithm (the base-e logarithm) of a number.
2071
+ #
2072
+ # @param value [Numeric] number (> 0.0)
2073
+ #
2074
+ # @return [Numeric] result number
2075
+ #
2076
+ def log (n)
2077
+ Math.log n
2078
+ end
2079
+
2080
+ # Returns Euler's number e raised to the power of value.
2081
+ #
2082
+ # @param value [Numeric] number
2083
+ #
2084
+ # @return [Numeric] result number
2085
+ #
2086
+ def exp (n)
2087
+ Math.exp n
2088
+ end
2089
+
1910
2090
  # Returns value raised to the power of exponent.
1911
2091
  #
1912
2092
  # @param value [Numeric] base number
@@ -1928,6 +2108,16 @@ module RubySketch
1928
2108
  value * value
1929
2109
  end
1930
2110
 
2111
+ # Returns squared value.
2112
+ #
2113
+ # @param value [Numeric] number
2114
+ #
2115
+ # @return [Numeric] squared value
2116
+ #
2117
+ def sqrt (value)
2118
+ Math.sqrt value
2119
+ end
2120
+
1931
2121
  # Returns the magnitude (or length) of a vector.
1932
2122
  #
1933
2123
  # @overload mag(x, y)
@@ -2202,6 +2392,14 @@ module RubySketch
2202
2392
  Vector.new *args
2203
2393
  end
2204
2394
 
2395
+ # Creates a camera object as a video input device.
2396
+ #
2397
+ # @return [Capture] camera object
2398
+ #
2399
+ def createCapture (*args)
2400
+ Capture.new *args
2401
+ end
2402
+
2205
2403
  # Creates a new off-screen graphics context object.
2206
2404
  #
2207
2405
  # @param width [Numeric] width of graphics image
@@ -16,7 +16,8 @@ module RubySketch
16
16
  @auto_resize = true
17
17
  @error = nil
18
18
 
19
- reset_canvas 1, 1
19
+ painter.miter_limit = 10
20
+ resize_canvas 1, 1
20
21
 
21
22
  super *args, size: [width, height], &block
22
23
  end
@@ -43,7 +44,9 @@ module RubySketch
43
44
 
44
45
  def on_draw (e)
45
46
  draw_canvas {call_block @draw, e} if @draw
46
- e.painter.image @canvas
47
+
48
+ x, y, w, h = coord_converter
49
+ e.painter.image @canvas, x, y, @canvas.width * w, @canvas.height * h
47
50
  end
48
51
 
49
52
  def on_key (e)
@@ -64,27 +67,45 @@ module RubySketch
64
67
  end
65
68
 
66
69
  def on_resize (e)
67
- reset_canvas e.width, e.height if @auto_resize
70
+ resize_canvas e.width, e.height if @auto_resize
68
71
  draw_canvas {call_block @resize, e} if @resize
69
72
  end
70
73
 
74
+ def to_canvas_coord (x, y)
75
+ xx, yy, ww, hh = coord_converter
76
+ return (x - xx) / ww, (y - yy) / hh
77
+ end
78
+
71
79
  private
72
80
 
73
- def reset_canvas (width, height)
74
- return if width * height == 0
75
- return if width == @canvas&.width && height == @canvas&.height
81
+ def resize_canvas (width, height, pixel_density = nil)
82
+ return nil if width * height == 0
76
83
 
77
- old_canvas = @canvas
78
- old_painter = @canvas_painter
84
+ unless width == @canvas&.width &&
85
+ height == @canvas&.height &&
86
+ pixel_density == @canvas_painter&.pixel_density
79
87
 
80
- cs = old_canvas&.color_space || Rays::RGBA
81
- @canvas = Rays::Image.new width, height, cs, painter.pixel_density
82
- @canvas_painter = @canvas.painter
88
+ old_canvas = @canvas
89
+ old_painter = @canvas_painter
83
90
 
84
- if old_canvas
85
- @canvas_painter.paint {image old_canvas}
86
- copy_painter_attributes old_painter, @canvas_painter
91
+ cs = old_canvas&.color_space || Rays::RGBA
92
+ pd = pixel_density || painter.pixel_density
93
+ @canvas = Rays::Image.new width, height, cs, pd
94
+ @canvas_painter = @canvas.painter
95
+
96
+ if old_canvas
97
+ @canvas_painter.paint {image old_canvas}
98
+ copy_painter_attributes old_painter, @canvas_painter
99
+ end
100
+
101
+ resize_window width, height
87
102
  end
103
+
104
+ @canvas_painter
105
+ end
106
+
107
+ def resize_window (width, height)
108
+ size width, height
88
109
  end
89
110
 
90
111
  def copy_painter_attributes (from, to)
@@ -97,6 +118,21 @@ module RubySketch
97
118
  to.font = from.font
98
119
  end
99
120
 
121
+ def coord_converter ()
122
+ ww, wh = width.to_f, height.to_f
123
+ cw, ch = @canvas.width.to_f, @canvas.height.to_f
124
+ return [0, 0, 1, 1] if ww == 0 || wh == 0 || cw == 0 || ch == 0
125
+
126
+ wratio, cratio = ww / wh, cw / ch
127
+ if wratio >= cratio
128
+ scaled_w = wh * cratio
129
+ return (ww - scaled_w) / 2, 0, scaled_w / cw, wh / ch
130
+ else
131
+ scaled_h = ww / cratio
132
+ return 0, (wh - scaled_h) / 2, ww / cw, scaled_h / ch
133
+ end
134
+ end
135
+
100
136
  def draw_canvas (&block)
101
137
  begin_draw
102
138
  block.call
@@ -12,11 +12,6 @@ require 'rubysketch'
12
12
  include Xot::Test
13
13
 
14
14
 
15
- unless $RAYS_NOAUTOINIT
16
- #def Rays.fin! () end
17
- end
18
-
19
-
20
15
  def assert_equal_vector (v1, v2, delta = 0.000001)
21
16
  assert_in_delta v1.x, v2.x, delta
22
17
  assert_in_delta v1.y, v2.y, delta
@@ -6,27 +6,31 @@ require_relative '../helper'
6
6
 
7
7
  class TestProcessingUtility < Test::Unit::TestCase
8
8
 
9
- C = RubySketch::Processing::Context
9
+ class Context
10
+ include RubySketch::Processing::Context
11
+ end
10
12
 
11
- def setup ()
12
-
13
+ def context
14
+ Context.new
13
15
  end
14
16
 
15
17
  def test_random ()
16
- assert_equal Float, C.random(1).class
17
- assert_equal Float, C.random(1.0).class
18
- assert_equal Symbol, C.random((:a..:z).to_a).class
18
+ c = context
19
+
20
+ assert_equal Float, c.random(1).class
21
+ assert_equal Float, c.random(1.0).class
22
+ assert_equal Symbol, c.random((:a..:z).to_a).class
19
23
 
20
- assert_not_equal C.random, C.random
24
+ assert_not_equal c.random, c.random
21
25
 
22
26
  10000.times do
23
- n = C.random
27
+ n = c.random
24
28
  assert 0 <= n && n < 1
25
29
 
26
- n = C.random 1
30
+ n = c.random 1
27
31
  assert 0 <= n && n < 1
28
32
 
29
- n = C.random 1, 2
33
+ n = c.random 1, 2
30
34
  assert 1.0 <= n && n < 2.0
31
35
  end
32
36
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: rubysketch
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.3.6
4
+ version: 0.3.11
5
5
  platform: ruby
6
6
  authors:
7
7
  - xordog
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2020-08-05 00:00:00.000000000 Z
11
+ date: 2020-12-09 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: reflexion
@@ -40,7 +40,10 @@ files:
40
40
  - README.md
41
41
  - Rakefile
42
42
  - VERSION
43
+ - examples/breakout.rb
44
+ - examples/camera.rb
43
45
  - examples/clock.rb
46
+ - examples/delay_camera.rb
44
47
  - examples/glsl.rb
45
48
  - examples/hello.rb
46
49
  - examples/image.rb