picrate 0.0.2-java → 0.0.3-java
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/README.md +5 -4
- data/Rakefile +1 -1
- data/docs/_classes/aabb/aabb.md +28 -0
- data/docs/_classes/app/app.md +38 -0
- data/docs/_classes/app_render/app_render.md +93 -0
- data/docs/_classes/arc_ball/arc_ball.md +33 -0
- data/docs/_classes/chooser/chooser.md +56 -0
- data/docs/_classes/deglut/deglut.md +20 -0
- data/docs/_classes/library_proxy/library_proxy.md +76 -0
- data/docs/_classes/vec2d/vec2d.md +53 -0
- data/docs/_classes/vec3d/vec3d.md +53 -0
- data/docs/_config.yml +36 -7
- data/docs/_editors/vim.md +63 -0
- data/docs/_gems/gems/gems.md +29 -0
- data/docs/_gems/other_gems/other_gems.md +198 -0
- data/docs/_layouts/post.html +6 -6
- data/docs/_libraries/control_panel.md +137 -0
- data/docs/_libraries/custom.md +126 -0
- data/docs/_libraries/custom_java.md +162 -0
- data/docs/_libraries/gems.md +57 -0
- data/docs/_libraries/library_proxy.md +9 -0
- data/docs/_libraries/picrate.md +511 -0
- data/docs/_libraries/processing.md +126 -0
- data/docs/_libraries/vector_utils.md +126 -0
- data/docs/_magic/java.md +30 -0
- data/docs/_magic/jruby.md +105 -0
- data/docs/_magic/processing.md +297 -0
- data/docs/_magic/ruby.md +31 -0
- data/docs/_methods/alternative_methods.md +66 -0
- data/docs/_methods/color.md +109 -0
- data/docs/_methods/data_path.md +109 -0
- data/docs/_methods/draw.md +20 -0
- data/docs/_methods/key_pressed.md +27 -0
- data/docs/_methods/library_loader.md +49 -0
- data/docs/_methods/map1d.md +77 -0
- data/docs/_methods/methods_summary.md +103 -0
- data/docs/_methods/mouse_pressed.md +25 -0
- data/docs/_methods/post_initialize.md +9 -0
- data/docs/_methods/processing_api.md +46 -0
- data/docs/_methods/settings.md +48 -0
- data/docs/_methods/setup.md +36 -0
- data/docs/_methods/sketch_title.md +24 -0
- data/docs/_modules/custom.md +61 -0
- data/docs/_modules/helper_methods.md +10 -0
- data/docs/_modules/interface.md +66 -0
- data/docs/_modules/processing.md +7 -0
- data/docs/_modules/processing_proxy.md +28 -0
- data/docs/_objects/class/class.md +7 -0
- data/docs/_objects/global/global.md +7 -0
- data/docs/_objects/instance/instance.md +74 -0
- data/docs/_objects/numeric/numeric.md +37 -0
- data/docs/_posts/2018-05-06-getting_started.md +60 -0
- data/docs/_posts/2018-05-06-processing-api.md +68 -0
- data/docs/_posts/2018-05-11-arch-linux-arm.md +17 -0
- data/docs/about.md +7 -1
- data/docs/classes.md +10 -0
- data/docs/editors.md +10 -0
- data/docs/gems.md +11 -0
- data/docs/libraries.md +20 -0
- data/docs/magic.md +11 -0
- data/docs/methods.md +10 -0
- data/docs/modules.md +12 -0
- data/docs/objects.md +9 -0
- data/lib/picrate/version.rb +1 -1
- data/lib/picrate-0.0.3.jar +0 -0
- data/picrate.gemspec +2 -2
- data/pom.rb +1 -1
- data/pom.xml +7 -7
- data/src/main/java/monkstone/MathToolModule.java +2 -2
- data/src/main/java/monkstone/videoevent/VideoInterface.java +1 -1
- data/src/main/java/processing/core/PApplet.java +3 -3
- data/src/main/java/processing/javafx/PGraphicsFX2D.java +1 -1
- data/test/respond_to_test.rb +4 -4
- data/test/sketches/key_event.rb +3 -3
- data/vendors/Rakefile +1 -1
- metadata +61 -4
- data/lib/picrate-0.0.2.jar +0 -0
@@ -0,0 +1,198 @@
|
|
1
|
+
---
|
2
|
+
layout: post
|
3
|
+
title: 'Using Gems in picrate'
|
4
|
+
keywords: gem, library, picrate
|
5
|
+
permalink: gems/other_gems.html
|
6
|
+
---
|
7
|
+
```ruby
|
8
|
+
#####################################################################
|
9
|
+
# Using the ai4r gem in picrate.
|
10
|
+
# A simple example that demonstrates using
|
11
|
+
# a back-propagation neural network. Use the drop box menu to
|
12
|
+
# select a pre-built shape. To draw a test shape tick drawing check-box,
|
13
|
+
# release the mouse when drawing a discontinuous shape eg cross.
|
14
|
+
# Clear the sketch with clear button.
|
15
|
+
# Press evaluate and result is printed to the console....
|
16
|
+
####################################################################
|
17
|
+
|
18
|
+
require 'ai4r'
|
19
|
+
require 'json'
|
20
|
+
|
21
|
+
#....................
|
22
|
+
|
23
|
+
load_library :control_panel
|
24
|
+
|
25
|
+
attr_reader :img, :img_pixels, :ci_input, :cr_input, :tr_input, :sq_input, :net, :points, :panel, :hide, :drawing, :source_string
|
26
|
+
|
27
|
+
def settings
|
28
|
+
size(320, 320)
|
29
|
+
end
|
30
|
+
|
31
|
+
def setup
|
32
|
+
sketch_title 'AI4R Sketch'
|
33
|
+
control_panel do |c|
|
34
|
+
c.title'control'
|
35
|
+
c.look_feel 'Nimbus'
|
36
|
+
c.checkbox :drawing
|
37
|
+
c.button :clear
|
38
|
+
c.button :evaluate
|
39
|
+
c.menu :shape, ['CIRCLE', 'CROSS', 'CROSS_WITH_NOISE', 'SQUARE', 'SQUARE_WITH_NOISE', 'TRIANGLE', 'DEFAULT']
|
40
|
+
@panel = c
|
41
|
+
end
|
42
|
+
@hide = false
|
43
|
+
@source_string = open(data_path('data.json'), 'r'){ |file| file.read }
|
44
|
+
triangle = JSON.parse(source_string)['TRIANGLE']
|
45
|
+
square = JSON.parse(source_string)['SQUARE']
|
46
|
+
cross = JSON.parse(source_string)['CROSS']
|
47
|
+
circle = JSON.parse(source_string)['CIRCLE']
|
48
|
+
@points = []
|
49
|
+
srand 1
|
50
|
+
@net = Ai4r::NeuralNetwork::Backpropagation.new([256, 3])
|
51
|
+
@tr_input = triangle.flatten.collect { |input| input.to_f / 127.0}
|
52
|
+
@sq_input = square.flatten.collect { |input| input.to_f / 127.0}
|
53
|
+
@cr_input = cross.flatten.collect { |input| input.to_f / 127.0}
|
54
|
+
@ci_input = circle.flatten.collect { |input| input.to_f / 127.0}
|
55
|
+
train
|
56
|
+
background 255
|
57
|
+
end
|
58
|
+
|
59
|
+
|
60
|
+
def draw
|
61
|
+
# only make control_panel visible once, or again when hide is false
|
62
|
+
unless hide
|
63
|
+
@hide = true
|
64
|
+
panel.set_visible(hide)
|
65
|
+
end
|
66
|
+
if drawing
|
67
|
+
stroke_weight 32
|
68
|
+
stroke 127
|
69
|
+
points.each_cons(2) { |ps, pe| line ps.x, ps.y, pe.x, pe.y}
|
70
|
+
else
|
71
|
+
no_fill
|
72
|
+
stroke_weight(32)
|
73
|
+
stroke(127)
|
74
|
+
case @shape
|
75
|
+
when 'CIRCLE'
|
76
|
+
background(255)
|
77
|
+
draw_circle
|
78
|
+
@shape = 'DEFAULT'
|
79
|
+
when 'CROSS'
|
80
|
+
background(255)
|
81
|
+
draw_cross
|
82
|
+
@shape = 'DEFAULT'
|
83
|
+
when 'CROSS_WITH_NOISE','SQUARE_WITH_NOISE'
|
84
|
+
background(255)
|
85
|
+
draw_shape @shape
|
86
|
+
@shape = 'DEFAULT'
|
87
|
+
when 'SQUARE'
|
88
|
+
background(255)
|
89
|
+
draw_square
|
90
|
+
@shape = 'DEFAULT'
|
91
|
+
when 'TRIANGLE'
|
92
|
+
background(255)
|
93
|
+
draw_triangle
|
94
|
+
@shape = 'DEFAULT'
|
95
|
+
end
|
96
|
+
end
|
97
|
+
end
|
98
|
+
|
99
|
+
def draw_shape shp
|
100
|
+
shape = JSON.parse(source_string)[shp]
|
101
|
+
background(255)
|
102
|
+
no_stroke
|
103
|
+
(0 ... width / 20).each do |i|
|
104
|
+
(0 ... height / 20).each do |j|
|
105
|
+
col = 255 - shape[i][j]
|
106
|
+
fill(col)
|
107
|
+
rect(i * 20, j * 20, 20, 20)
|
108
|
+
end
|
109
|
+
end
|
110
|
+
end
|
111
|
+
|
112
|
+
def train
|
113
|
+
puts 'Training Network Please Wait'
|
114
|
+
101.times do |i|
|
115
|
+
error = net.train(tr_input, [1.0, 0, 0])
|
116
|
+
error = net.train(sq_input, [0, 1.0, 0])
|
117
|
+
error = net.train(cr_input, [0, 0, 1.0])
|
118
|
+
error = net.train(ci_input, [0, 1.0, 1.0])
|
119
|
+
puts "Error after iteration #{i}:\t#{format('%0.5f', error)}" if i%20 == 0
|
120
|
+
end
|
121
|
+
end
|
122
|
+
|
123
|
+
def result_label(result)
|
124
|
+
if result.reduce(0, :+).between?(1.9, 2.1)
|
125
|
+
if result[0] < 0.01 && result[1].between?(0.99, 1.0) && result[2].between?(0.99, 1.0)
|
126
|
+
return 'CIRCLE'
|
127
|
+
else
|
128
|
+
return 'UNKNOWN'
|
129
|
+
end
|
130
|
+
elsif result.reduce(0, :+).between?(0.95, 1.1)
|
131
|
+
if result[0].between?(0.95, 1.0) && (result[1] + result[2]) < 0.01
|
132
|
+
return 'TRIANGLE'
|
133
|
+
elsif result[1].between?(0.95, 1.0) && (result[0] + result[2]) < 0.01
|
134
|
+
return 'SQUARE'
|
135
|
+
elsif result[2].between?(0.95, 1.0) && (result[1] + result[0]) < 0.01
|
136
|
+
return 'CROSS'
|
137
|
+
else
|
138
|
+
return 'UNKNOWN'
|
139
|
+
end
|
140
|
+
end
|
141
|
+
return 'UNKNOWN'
|
142
|
+
end
|
143
|
+
|
144
|
+
def mouse_dragged
|
145
|
+
points << Vec2D.new(mouse_x, mouse_y)
|
146
|
+
end
|
147
|
+
|
148
|
+
def mouse_released
|
149
|
+
points.clear
|
150
|
+
end
|
151
|
+
|
152
|
+
def draw_circle
|
153
|
+
ellipse(width / 2, height / 2, 320 - 32, 320 - 32)
|
154
|
+
end
|
155
|
+
|
156
|
+
def draw_square
|
157
|
+
rect(16, 16, 320 - 32, 320 - 32)
|
158
|
+
end
|
159
|
+
|
160
|
+
def draw_cross
|
161
|
+
line(width / 2, 0, width / 2, 320)
|
162
|
+
line(0, height / 2, 320 , height / 2)
|
163
|
+
end
|
164
|
+
|
165
|
+
def draw_triangle
|
166
|
+
triangle(width / 2, 32, 24, height - 16, width - 24, height - 16)
|
167
|
+
end
|
168
|
+
|
169
|
+
def clear
|
170
|
+
background 255
|
171
|
+
end
|
172
|
+
|
173
|
+
def evaluate
|
174
|
+
load_pixels
|
175
|
+
img_pixels = []
|
176
|
+
(0...height).step(20) do |y|
|
177
|
+
row = []
|
178
|
+
(0...width).step(20) do |x|
|
179
|
+
row << 255 - brightness(pixels[(y + 10) * width + x + 10])
|
180
|
+
end
|
181
|
+
img_pixels << row
|
182
|
+
end
|
183
|
+
puts "#{net.eval(img_pixels.flatten).inspect} => #{result_label(net.eval(img_pixels.flatten))}"
|
184
|
+
end
|
185
|
+
```
|
186
|
+
data.json
|
187
|
+
```json
|
188
|
+
|
189
|
+
{"TRIANGLE":[[0,0,0,0,0,0,0,127,127,0,0,0,0,0,0,0],[0,0,0,0,0,0,25,229,229,25,0,0,0,0,0,0],[0,0,0,0,0,0,127,127,127,127,0,0,0,0,0,0],[0,0,0,0,0,25,229,25,25,229,25,0,0,0,0,0],[0,0,0,0,0,127,127,0,0,127,127,0,0,0,0,0],[0,0,0,0,25,229,25,0,0,25,229,25,0,0,0,0],[0,0,0,0,127,127,0,0,0,0,127,127,0,0,0,0],[0,0,0,25,229,25,0,0,0,0,25,229,25,0,0,0],[0,0,0,127,127,0,0,0,0,0,0,127,127,0,0,0],[0,0,25,229,25,0,0,0,0,0,0,25,229,25,0,0],[0,0,127,127,0,0,0,0,0,0,0,0,127,127,0,0],[0,25,229,25,0,0,0,0,0,0,0,0,25,229,25,0],[0,127,127,0,0,0,0,0,0,0,0,0,0,127,127,0],[25,229,25,0,0,0,0,0,0,0,0,0,0,25,229,25],[127,127,0,0,0,0,0,0,0,0,0,0,0,0,127,127],[255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255]]
|
190
|
+
,"SQUARE":[[255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255],[255,0,0,0,0,0,0,0,0,0,0,0,0,0,0,255],[255,0,0,0,0,0,0,0,0,0,0,0,0,0,0,255],[255,0,0,0,0,0,0,0,0,0,0,0,0,0,0,255],[255,0,0,0,0,0,0,0,0,0,0,0,0,0,0,255],[255,0,0,0,0,0,0,0,0,0,0,0,0,0,0,255],[255,0,0,0,0,0,0,0,0,0,0,0,0,0,0,255],[255,0,0,0,0,0,0,0,0,0,0,0,0,0,0,255],[255,0,0,0,0,0,0,0,0,0,0,0,0,0,0,255],[255,0,0,0,0,0,0,0,0,0,0,0,0,0,0,255],[255,0,0,0,0,0,0,0,0,0,0,0,0,0,0,255],[255,0,0,0,0,0,0,0,0,0,0,0,0,0,0,255],[255,0,0,0,0,0,0,0,0,0,0,0,0,0,0,255],[255,0,0,0,0,0,0,0,0,0,0,0,0,0,0,255],[255,0,0,0,0,0,0,0,0,0,0,0,0,0,0,255],[255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255]]
|
191
|
+
,"CROSS":[[0,0,0,0,0,0,0,127,127,0,0,0,0,0,0,0],[0,0,0,0,0,0,0,127,127,0,0,0,0,0,0,0],[0,0,0,0,0,0,0,127,127,0,0,0,0,0,0,0],[0,0,0,0,0,0,0,127,127,0,0,0,0,0,0,0],[0,0,0,0,0,0,0,127,127,0,0,0,0,0,0,0],[0,0,0,0,0,0,0,127,127,0,0,0,0,0,0,0],[0,0,0,0,0,0,0,127,127,0,0,0,0,0,0,0],[127,127,127,127,127,127,127,127,127,127,127,127,127,127,127,127],[127,127,127,127,127,127,127,127,127,127,127,127,127,127,127,127],[0,0,0,0,0,0,0,127,127,0,0,0,0,0,0,0],[0,0,0,0,0,0,0,127,127,0,0,0,0,0,0,0],[0,0,0,0,0,0,0,127,127,0,0,0,0,0,0,0],[0,0,0,0,0,0,0,127,127,0,0,0,0,0,0,0],[0,0,0,0,0,0,0,127,127,0,0,0,0,0,0,0],[0,0,0,0,0,0,0,127,127,0,0,0,0,0,0,0],[0,0,0,0,0,0,0,127,127,0,0,0,0,0,0,0]]
|
192
|
+
,"CIRCLE":[[0,0,0,0,32,64,64,80,80,64,64,32,0,0,0,0],[0,0,32,64,96,103,64,64,64,64,96,96,64,32,0,0],[0,32,96,128,96,32,0,0,0,0,32,89,128,96,32,0],[0,64,128,96,18,0,0,0,0,0,0,0,64,128,64,0],[32,96,96,18,0,0,0,0,0,0,0,0,0,82,101,32],[64,103,32,0,0,0,0,0,0,0,0,0,0,32,96,64],[64,64,0,0,0,0,0,0,0,0,0,0,0,0,64,68],[80,64,0,0,0,0,0,0,0,0,0,0,0,0,64,104],[80,64,0,0,0,0,0,0,0,0,0,0,0,0,64,106],[64,64,0,0,0,0,0,0,0,0,0,0,0,0,64,70],[64,96,32,0,0,0,0,0,0,0,0,0,0,32,96,64],[32,96,88,0,0,0,0,0,0,0,0,0,0,64,119,32],[0,64,128,64,0,0,0,0,0,0,0,0,32,113,70,0],[0,32,96,128,81,32,0,0,0,0,32,64,113,96,32,0],[0,0,32,64,102,96,64,64,64,64,96,119,70,32,0,0],[0,0,0,0,32,64,69,105,106,70,64,32,0,0,0,0]]
|
193
|
+
,"TRIANGLE_WITH_NOISE":[[25,0,0,0,0,0,0,25,127,0,0,25,0,0,0,0],[0,0,0,0,76,0,25,229,229,25,0,0,0,0,76,0],[0,76,0,0,0,0,127,25,127,76,0,0,0,0,0,178],[0,0,0,178,0,25,229,25,25,229,25,0,0,0,76,0],[0,0,0,0,0,76,127,0,76,127,127,0,0,0,0,0],[0,25,0,0,25,229,25,0,25,25,229,25,0,0,0,0],[25,0,0,0,127,127,0,0,0,0,127,127,178,0,0,76],[0,0,76,76,229,25,0,0,25,0,25,229,25,0,0,0],[0,0,0,127,127,0,76,178,0,0,0,127,127,0,0,0],[0,0,25,229,25,0,0,0,0,0,0,25,229,25,0,0],[0,0,127,127,0,0,0,0,76,0,0,0,127,127,0,0],[0,25,229,25,0,0,0,0,0,0,0,0,25,229,25,0],[0,127,127,0,76,0,0,76,0,0,0,0,0,127,127,0],[25,229,25,0,0,76,0,0,0,25,0,0,0,25,229,25],[127,127,0,0,0,0,0,0,0,0,0,0,0,0,127,127],[255,255,255,255,25,255,255,255,255,255,25,255,255,255,255,255]]
|
194
|
+
,"SQUARE_WITH_NOISE":[[255,76,255,255,255,153,255,255,255,255,255,102,255,255,255,255],[255,0,0,0,0,178,0,0,0,0,0,0,0,0,0,255],[255,0,76,0,0,0,0,178,0,153,25,0,0,0,0,0],[255,0,0,0,0,0,0,0,0,0,0,0,0,0,0,255],[255,0,102,0,102,0,0,0,25,0,76,0,0,102,0,255],[255,0,0,0,0,0,0,25,0,0,0,0,0,0,0,0],[255,0,0,0,76,153,0,0,25,0,0,0,0,0,0,255],[255,0,0,0,0,0,0,102,0,0,0,0,178,0,0,255],[255,102,102,0,0,0,0,0,0,0,0,0,0,0,0,255],[255,0,178,0,0,76,0,0,0,0,0,0,0,0,0,255],[255,0,0,0,0,0,0,0,76,0,0,0,0,0,178,255],[255,0,76,0,102,0,0,0,0,153,0,0,0,0,0,255],[255,0,0,0,0,0,0,0,0,0,0,0,25,0,0,255],[255,0,0,153,0,0,0,178,0,0,0,178,0,0,0,255],[255,0,0,0,0,0,0,0,0,0,0,0,0,0,0,255],[255,255,255,255,76,255,255,255,255,0,255,255,25,255,25,255]]
|
195
|
+
,"CROSS_WITH_NOISE":[[0,0,0,0,0,0,76,76,127,0,76,0,0,0,25,0],[0,25,0,0,0,25,0,127,127,0,0,0,0,0,0,0],[0,0,0,0,0,0,0,127,127,0,0,0,76,0,0,0],[0,0,25,204,0,0,0,127,127,0,102,0,0,0,25,0],[0,0,0,0,0,76,0,127,0,0,0,0,25,0,0,0],[0,0,0,204,0,0,0,127,127,0,0,0,0,0,0,25],[0,0,0,0,0,0,0,127,127,0,76,0,0,0,0,0],[127,127,127,204,127,76,127,127,127,127,127,127,127,127,0,5],[127,127,127,127,127,127,127,127,25,127,127,127,127,25,0,0],[0,0,0,204,0,0,0,102,127,0,0,0,0,0,0,0],[0,0,0,0,0,0,0,127,127,102,0,0,0,0,0,0],[0,0,0,0,0,102,0,127,127,0,0,0,0,0,0,0],[102,0,0,102,0,0,0,127,127,0,0,0,25,0,0,0],[0,0,0,0,0,25,0,127,102,102,76,0,0,0,0,0],[0,0,0,0,0,0,0,127,127,0,0,0,255,0,0,0],[0,0,0,0,0,0,0,127,127,0,0,0,0,0,0,0]]
|
196
|
+
,"CIRCLE_WITH_NOISE":[[0,0,0,0,21,0,21,128,128,21,0,21,0,0,0,0],[0,0,8,17,128,128,110,0,0,21,128,128,98,21,0,0],[0,8,21,128,21,21,0,0,0,0,21,21,128,21,21,0],[0,0,128,21,0,0,0,0,0,0,0,0,21,128,2,0],[21,128,21,0,0,0,0,0,0,0,0,0,0,21,128,21],[0,128,42,0,0,0,0,0,0,0,0,0,0,31,128,0],[0,25,0,0,0,0,0,0,0,0,0,0,0,0,21,21],[128,0,0,0,0,0,0,0,0,0,0,0,0,0,89,128],[23,0,0,0,0,0,0,0,0,0,0,0,0,0,0,128],[21,24,12,0,0,0,0,0,0,0,0,0,0,0,128,21],[0,128,21,0,0,0,0,0,0,0,0,0,0,32,128,0],[21,42,21,21,0,0,0,0,0,0,0,0,0,21,128,27],[0,13,128,21,21,0,0,0,0,0,0,0,21,128,86,0],[0,3,21,128,21,31,0,0,0,0,21,21,128,21,0,0],[0,0,0,88,128,128,128,3,89,128,128,128,21,0,0,0],[0,0,0,0,21,0,21,128,128,21,0,21,0,0,0,0]]}
|
197
|
+
#......
|
198
|
+
```
|
data/docs/_layouts/post.html
CHANGED
@@ -1,15 +1,15 @@
|
|
1
1
|
---
|
2
2
|
layout: default
|
3
3
|
---
|
4
|
-
<
|
4
|
+
<div class="post">
|
5
5
|
|
6
6
|
<header class="post-header">
|
7
|
-
<h1 class="post-title"
|
8
|
-
<p class="post-meta"
|
7
|
+
<h1 class="post-title">{{ page.title }}</h1>
|
8
|
+
<p class="post-meta">{{ page.date | date: "%b %-d, %Y" }}{% if page.author %} • {{ page.author }}{% endif %}{% if page.meta %} • {{ page.meta }}{% endif %}</p>
|
9
9
|
</header>
|
10
10
|
|
11
|
-
<
|
11
|
+
<article class="post-content">
|
12
12
|
{{ content }}
|
13
|
-
</
|
13
|
+
</article>
|
14
14
|
|
15
|
-
</
|
15
|
+
</div>
|
@@ -0,0 +1,137 @@
|
|
1
|
+
---
|
2
|
+
layout: post
|
3
|
+
title: "Control Panel<sup>2</sup>"
|
4
|
+
keywords: library, framework, gui, processing
|
5
|
+
permalink: libraries/control_panel.html
|
6
|
+
---
|
7
|
+
Inspired by Nodebox, picrate (copied from ruby-processing) provides a way to control the instance variables of your sketch with a control panel. You can create sliders, buttons, menus and checkboxes that set instance variables on your sketch. Since ruby-processing-2.0 you need to explicitly set the panel visible from the processing sketch (see included examples). Start by loading in the `control_panel` library, and then define your panel like so:-
|
8
|
+
NB: revised version for picrate-2.7.2+
|
9
|
+
|
10
|
+
__Simple Buttons Example__
|
11
|
+
|
12
|
+
```ruby
|
13
|
+
require 'picrate'
|
14
|
+
|
15
|
+
class SimpleButton < Processing::App
|
16
|
+
load_library :control_panel
|
17
|
+
|
18
|
+
attr_reader :back
|
19
|
+
|
20
|
+
def setup
|
21
|
+
sketch_title 'Simple Button'
|
22
|
+
control_panel do |c|
|
23
|
+
c.look_feel 'Nimbus'
|
24
|
+
c.title 'Control Button'
|
25
|
+
c.button :color_background # needs a defined :color_background method
|
26
|
+
c.button :exit { exit } # button with optional block
|
27
|
+
end
|
28
|
+
color_mode RGB, 1
|
29
|
+
@back = [0, 0, 1.0]
|
30
|
+
end
|
31
|
+
|
32
|
+
def color_background
|
33
|
+
@back = [rand, rand, rand]
|
34
|
+
end
|
35
|
+
|
36
|
+
def draw
|
37
|
+
background *back
|
38
|
+
end
|
39
|
+
|
40
|
+
def settings
|
41
|
+
size 300, 300
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
45
|
+
SimpleButton.new
|
46
|
+
|
47
|
+
```
|
48
|
+
__More Complete Example__
|
49
|
+
|
50
|
+
```ruby
|
51
|
+
|
52
|
+
require 'picrate'
|
53
|
+
|
54
|
+
class ControlPanelExample < Processing::App
|
55
|
+
load_library :control_panel
|
56
|
+
|
57
|
+
def settings
|
58
|
+
size(200, 200)
|
59
|
+
end
|
60
|
+
|
61
|
+
def setup
|
62
|
+
sketch_title 'Control Panel Example'
|
63
|
+
control_panel do |c|
|
64
|
+
c.look_feel "Nimbus"
|
65
|
+
c.slider :opacity
|
66
|
+
c.slider(:app_width, 5..60, 20) { reset! } # see reset! method
|
67
|
+
c.menu(:options, ['one', 'two', 'three'], 'two') { |m| load_menu_item(m) }
|
68
|
+
c.checkbox :paused
|
69
|
+
c.button :reset!
|
70
|
+
end
|
71
|
+
end
|
72
|
+
|
73
|
+
def draw
|
74
|
+
# Rest of the code follows
|
75
|
+
end
|
76
|
+
|
77
|
+
# eg
|
78
|
+
def reset!
|
79
|
+
# some action you want performed on button pressed
|
80
|
+
end
|
81
|
+
end
|
82
|
+
|
83
|
+
ControlPanelExample.new
|
84
|
+
|
85
|
+
```
|
86
|
+
|
87
|
+
This code will create a sketch with a control panel for adjusting the value of the `@opacity`, `@app_width`, `@options`, and `@paused` instance variables. The button will call the `reset!` method when clicked (a method defined by you in your sketch). The `app_width` slider will range from 5 to 60 instead of (the default) 0 to 100. The instance variable will be initialized at 20 when the sketch is loaded. The `app_width` and `options` controls have had callbacks attached to them. The callbacks will run, passing in the value of the control, any time the control changes. It all looks like this:
|
88
|
+
|
89
|
+
![control panel](http://s3.amazonaws.com/jashkenas/images/control_panel.png)
|
90
|
+
|
91
|
+
Here is the classic ruby-processing JWishy sketch translated for picrate, basically you enter the control_panel items in a block, to experiment just add a single item at a time and check that it works (eg :button or :checkbox)
|
92
|
+
|
93
|
+
Start by loading in the control_panel library, and then define your panel in setup like so:
|
94
|
+
|
95
|
+
```ruby
|
96
|
+
require 'picrate'
|
97
|
+
|
98
|
+
class JWishy < Processing::App
|
99
|
+
load_library :control_panel
|
100
|
+
attr_reader :panel
|
101
|
+
|
102
|
+
def settings
|
103
|
+
size 600, 600
|
104
|
+
end
|
105
|
+
|
106
|
+
def setup
|
107
|
+
sketch_title 'Wishy Worm'
|
108
|
+
control_panel do |c|
|
109
|
+
c.title 'Control Panel'
|
110
|
+
c.look_feel 'Nimbus'
|
111
|
+
c.slider :bluish, 0.0..1.0, 0.5
|
112
|
+
c.slider :alpha, 0.0..1.0, 0.5
|
113
|
+
c.checkbox :go_big
|
114
|
+
c.button :reset
|
115
|
+
c.menu :shape, %w(oval square triangle)
|
116
|
+
end
|
117
|
+
@hide = false
|
118
|
+
@shape = 'oval'
|
119
|
+
@go_big = false
|
120
|
+
@x_wiggle, @y_wiggle = 10.0, 0
|
121
|
+
@magnitude = 8.15
|
122
|
+
@back_color = [0.06, 0.03, 0.18]
|
123
|
+
color_mode RGB, 1
|
124
|
+
ellipse_mode CORNER
|
125
|
+
smooth
|
126
|
+
end
|
127
|
+
|
128
|
+
#....rest of code
|
129
|
+
|
130
|
+
def draw
|
131
|
+
#.... rest of draw
|
132
|
+
end
|
133
|
+
|
134
|
+
```
|
135
|
+
![JWishy]({{site.github.url}}/assets/jwishy.png)
|
136
|
+
|
137
|
+
See also [penrose](https://github.com/ruby-processing/picrate-examples/blob/master/library/vecmath/vec2d/penrose.rb) and [bezier playground](https://github.com/ruby-processing/picrate-examples/blob/master/contributed/bezier_playground.rb) sketches. See ruby code [here](https://github.com/ruby-processing/picrate/blob/master/library/control_panel/control_panel.rb).
|
@@ -0,0 +1,126 @@
|
|
1
|
+
---
|
2
|
+
layout: post
|
3
|
+
title: "custom ruby library<sup>3</sup>"
|
4
|
+
keywords: library, ruby, custom
|
5
|
+
permalink: libraries/custom.html
|
6
|
+
---
|
7
|
+
<sup>3</sup><i>A custom ruby library</i>
|
8
|
+
|
9
|
+
The custom ruby library `library/palette/palette.rb`
|
10
|
+
|
11
|
+
```ruby
|
12
|
+
class Palette
|
13
|
+
include Processing::Proxy # needed to access 'color' and 'map1d'
|
14
|
+
attr_reader :palette
|
15
|
+
|
16
|
+
def initialize
|
17
|
+
@palette = make_palette
|
18
|
+
end
|
19
|
+
|
20
|
+
def make_palette
|
21
|
+
(0..256).map do |i|
|
22
|
+
# Create the bands of colour for the palette (256 is the maximum colour))
|
23
|
+
case i
|
24
|
+
when 0..64 # Range of reds
|
25
|
+
color(*[map1d(i, 0..64, 1..255), 0, 0])
|
26
|
+
when 64..128 # Range of orange
|
27
|
+
color(*[255, map1d(i, 64..128, 1..255), 0])
|
28
|
+
when 128..172 # range of yellow
|
29
|
+
color(*[255, 255, map1d(i, 128..172, 1..255)])
|
30
|
+
else
|
31
|
+
color(*[180, 0, 0])
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
35
|
+
|
36
|
+
def self.create_palette
|
37
|
+
Palette.new.palette
|
38
|
+
end
|
39
|
+
end
|
40
|
+
```
|
41
|
+
|
42
|
+
A sketch using the custom palette library:-
|
43
|
+
|
44
|
+
```ruby
|
45
|
+
require 'picrate'
|
46
|
+
|
47
|
+
# After original by Alex Young https://github.com/alexyoung/fire-p5r
|
48
|
+
|
49
|
+
# Algorithm:
|
50
|
+
# 1. Create an indexed palette of red, orange and yellows
|
51
|
+
# 2. Loop:
|
52
|
+
# 3. Draw a random set of colours from the palette at the bottom of the screen
|
53
|
+
# 4. Loop through each pixel and average the colour index value around it
|
54
|
+
# 5. Reduce the average by a fire intensity factor
|
55
|
+
|
56
|
+
# jruby fire.rb
|
57
|
+
class Fire < Processing::App
|
58
|
+
load_library :palette
|
59
|
+
|
60
|
+
def settings
|
61
|
+
size 320, 240
|
62
|
+
end
|
63
|
+
|
64
|
+
def setup
|
65
|
+
sketch_title 'Fire'
|
66
|
+
frame_rate 30
|
67
|
+
@palette = Palette.create_palette
|
68
|
+
@fire = []
|
69
|
+
@scale = 8
|
70
|
+
@width = width / @scale
|
71
|
+
@height = height / @scale
|
72
|
+
@intensity = 2
|
73
|
+
end
|
74
|
+
|
75
|
+
def draw
|
76
|
+
background 0
|
77
|
+
update_fire
|
78
|
+
end
|
79
|
+
|
80
|
+
def update_fire
|
81
|
+
random_line @height - 1
|
82
|
+
(0..@height - 2).each do |y|
|
83
|
+
(0..@width).each do |x|
|
84
|
+
# Wrap
|
85
|
+
left = x.zero? ? fire_data(@width - 1, y) : fire_data(x - 1, y)
|
86
|
+
right = (x == @width - 1) ? fire_data(0, y) : fire_data(x + 1, y)
|
87
|
+
below = fire_data(x, y + 1)
|
88
|
+
# Get the average pixel value
|
89
|
+
average = (left.to_i + right.to_i + (below.to_i * 2)) / 4
|
90
|
+
# Fade the flames
|
91
|
+
average -= @intensity if average > @intensity
|
92
|
+
set_fire_data x, y, average
|
93
|
+
fill @palette[average]
|
94
|
+
stroke @palette[average]
|
95
|
+
rect x * @scale, (y + 1) * @scale, @scale, @scale
|
96
|
+
end
|
97
|
+
end
|
98
|
+
end
|
99
|
+
|
100
|
+
def fire_data(x, y)
|
101
|
+
@fire[offset(x, y)]
|
102
|
+
end
|
103
|
+
|
104
|
+
def set_fire_data(x, y, value)
|
105
|
+
@fire[offset(x, y)] = value.to_i
|
106
|
+
end
|
107
|
+
|
108
|
+
def random_offset
|
109
|
+
rand(0..@palette.size)
|
110
|
+
end
|
111
|
+
|
112
|
+
def random_line(y)
|
113
|
+
(0...@width).each do |x|
|
114
|
+
@fire[offset(x, y)] = random_offset
|
115
|
+
end
|
116
|
+
end
|
117
|
+
|
118
|
+
def offset(x, y)
|
119
|
+
(y * @width) + x
|
120
|
+
end
|
121
|
+
end
|
122
|
+
|
123
|
+
Fire.new
|
124
|
+
```
|
125
|
+
|
126
|
+
See also this [example](https://github.com/ruby-processing/picrate-examples/blob/master/topics/vectors/cubes_in_cube.rb), makes most sense when you might re-use your library for several sketches.
|
@@ -0,0 +1,162 @@
|
|
1
|
+
---
|
2
|
+
layout: post
|
3
|
+
title: "custom java library<sup>4</sup>"
|
4
|
+
keywords: library, ruby, custom
|
5
|
+
permalink: libraries/custom_java.html
|
6
|
+
---
|
7
|
+
<sup>4</sup><i>A custom java library</i>
|
8
|
+
|
9
|
+
See [github](https://github.com/ruby-processing/picrate-examples/tree/master/nature-of-code/xor) for the java source that gets compiled to `nn.jar`, where the `nn.jar` is nested in `library/nn` folder. Here is the sketch that uses the custom nn library:-
|
10
|
+
|
11
|
+
__xor.rb__
|
12
|
+
|
13
|
+
```ruby
|
14
|
+
require 'picrate'
|
15
|
+
# The Nature of Code
|
16
|
+
# Daniel Shiffman
|
17
|
+
# https://natureofcode.com
|
18
|
+
# XOR Multi-Layered Neural Network Example
|
19
|
+
# Neural network code is all in the 'code' folder
|
20
|
+
class Xor < Processing::App
|
21
|
+
load_library :nn
|
22
|
+
|
23
|
+
require_relative './landscape'
|
24
|
+
include_package 'nn'
|
25
|
+
|
26
|
+
ITERATIONS_PER_FRAME = 5
|
27
|
+
|
28
|
+
attr_reader :inputs, :nn, :count, :land, :theta, :f, :result, :known
|
29
|
+
|
30
|
+
def setup
|
31
|
+
sketch_title 'XOR'
|
32
|
+
@theta = 0.0
|
33
|
+
# Create a landscape object
|
34
|
+
@land = Landscape.new(20, 300, 300)
|
35
|
+
@f = create_font('Courier', 12, true)
|
36
|
+
@nn = Network.new(2, 4)
|
37
|
+
@count = 0
|
38
|
+
# Create a list of 4 training inputs
|
39
|
+
@inputs = []
|
40
|
+
inputs << [1.0, 0]
|
41
|
+
inputs << [0, 1.0]
|
42
|
+
inputs << [1.0, 1.0]
|
43
|
+
inputs << [0, 0.0]
|
44
|
+
end
|
45
|
+
|
46
|
+
def draw
|
47
|
+
lights
|
48
|
+
ITERATIONS_PER_FRAME.times do
|
49
|
+
inp = inputs.sample
|
50
|
+
# Compute XOR
|
51
|
+
@known = ((inp[0] > 0.0 && inp[1] > 0.0) || (inp[0] < 1.0 && inp[1] < 1.0)) ? 0 : 1.0
|
52
|
+
# Train that sucker!
|
53
|
+
@result = nn.train(inp, known)
|
54
|
+
@count += 1
|
55
|
+
end
|
56
|
+
# Ok, visualize the solution space
|
57
|
+
background(175)
|
58
|
+
push_matrix
|
59
|
+
translate(width / 2, height / 2 + 20, -160)
|
60
|
+
rotate_x(Math::PI / 3)
|
61
|
+
rotate_z(theta)
|
62
|
+
# Put a little BOX on screen
|
63
|
+
push_matrix
|
64
|
+
stroke(50)
|
65
|
+
no_fill
|
66
|
+
translate(-10, -10, 0)
|
67
|
+
box(280)
|
68
|
+
land.calculate(nn)
|
69
|
+
land.render
|
70
|
+
# Draw the landscape
|
71
|
+
pop_matrix
|
72
|
+
@theta += 0.0025
|
73
|
+
pop_matrix
|
74
|
+
# Display overal neural net stats
|
75
|
+
network_status
|
76
|
+
end
|
77
|
+
|
78
|
+
def network_status
|
79
|
+
mse = 0.0
|
80
|
+
text_font(f)
|
81
|
+
fill(0)
|
82
|
+
text('Your friendly neighborhood neural network solving XOR.', 10, 20)
|
83
|
+
text(format('Total iterations: %d', count), 10, 40)
|
84
|
+
mse += (result - known) * (result - known)
|
85
|
+
rmse = Math.sqrt(mse / 4.0)
|
86
|
+
out = format('Root mean squared error: %.5f', rmse)
|
87
|
+
hint DISABLE_DEPTH_SORT
|
88
|
+
text(out, 10, 60)
|
89
|
+
hint ENABLE_DEPTH_SORT
|
90
|
+
end
|
91
|
+
|
92
|
+
def settings
|
93
|
+
size(400, 400, P3D)
|
94
|
+
end
|
95
|
+
end
|
96
|
+
|
97
|
+
Xor.new
|
98
|
+
```
|
99
|
+
__landscape.rb__
|
100
|
+
|
101
|
+
```ruby
|
102
|
+
# The Nature of Code
|
103
|
+
# Daniel Shiffman
|
104
|
+
# https://natureofcode.com
|
105
|
+
|
106
|
+
# "Landscape" example
|
107
|
+
class Landscape
|
108
|
+
include Processing::Proxy
|
109
|
+
|
110
|
+
attr_reader :scl, :w, :h, :rows, :cols, :z, :zoff
|
111
|
+
|
112
|
+
def initialize(scl, w, h)
|
113
|
+
@scl, @w, @h = scl, w, h
|
114
|
+
@cols = w / scl
|
115
|
+
@rows = h / scl
|
116
|
+
@z = Array.new(cols, Array.new(rows, 0.0))
|
117
|
+
@zoff = 0
|
118
|
+
end
|
119
|
+
|
120
|
+
# Calculate height values (based off a neural network)
|
121
|
+
def calculate(nn)
|
122
|
+
val = lambda do |curr, net, x, y|
|
123
|
+
curr * 0.95 + 0.05 * (net.feed_forward([x, y]) * 280.0 - 140.0)
|
124
|
+
end
|
125
|
+
@z = (0...cols).map do |i|
|
126
|
+
(0...rows).map do |j|
|
127
|
+
val.call(z[i][j], nn, i * 1.0 / cols, j * 1.0 / cols)
|
128
|
+
end
|
129
|
+
end
|
130
|
+
end
|
131
|
+
|
132
|
+
# Render landscape as grid of quads
|
133
|
+
def render
|
134
|
+
# Every cell is an individual quad
|
135
|
+
# (could use quad_strip here, but produces funny results, investigate this)
|
136
|
+
(0...z.size - 1).each do |x|
|
137
|
+
(0...z[0].size - 1).each do |y|
|
138
|
+
# one quad at a time
|
139
|
+
# each quad's color is determined by the height value at each vertex
|
140
|
+
# (clean this part up)
|
141
|
+
no_stroke
|
142
|
+
push_matrix
|
143
|
+
begin_shape(PConstants::QUADS)
|
144
|
+
translate(x * scl - w * 0.5, y * scl - h * 0.5, 0)
|
145
|
+
fill(z[x][y] + 127, 220)
|
146
|
+
vertex(0, 0, z[x][y])
|
147
|
+
fill(z[x + 1][y] + 127, 220)
|
148
|
+
vertex(scl, 0, z[x + 1][y])
|
149
|
+
fill(z[x + 1][y + 1] + 127, 220)
|
150
|
+
vertex(scl, scl, z[x + 1][y + 1])
|
151
|
+
fill(z[x][y + 1] + 127, 220)
|
152
|
+
vertex(0, scl, z[x][y + 1])
|
153
|
+
end_shape
|
154
|
+
pop_matrix
|
155
|
+
end
|
156
|
+
end
|
157
|
+
end
|
158
|
+
end
|
159
|
+
|
160
|
+
```
|
161
|
+
|
162
|
+
See also the [pbox2d](https://github.com/ruby-processing/jbox2d) gem.
|