glimmer-dsl-swing 0.0.1 → 0.0.2

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: ecbd6a72ae4955c7f90995ef135f1aac59fc4b3294377fa4b7957b1b22069715
4
- data.tar.gz: a58db866e29fd2d2f6620314918b629a94095cbe717ce7ca6c998d30a6d4348d
3
+ metadata.gz: d91f9d5241c9f9414d4f4c343568a71f19657560b72713a4fbfe4711af0e120f
4
+ data.tar.gz: 25079ddbf4e8b83a899b4857e88aa9dacfbde3f67147c7708047113654e42df7
5
5
  SHA512:
6
- metadata.gz: 1c675e8abe364913657308555622a3969d7eed06b0e95894946686fa01e9493bf56e2a016bb5c135edcb1e6ac2a11fea91809c248724257f2d2ab4db59607d0a
7
- data.tar.gz: a7c4ccc5cac6eececddf64760737c9765f9ef7c9b40efa6a6a77eb326b2257a425d222297087cb3a93a9589b215d9edbe8ddff27452ac0fcc14582aab228b6b8
6
+ metadata.gz: 23641076d917e3223517cfabfd82c72973360b4bff14032567e67e6352b4dd40e6e628d920833786401a8b0d65b3959d6303e6721cd2fd95254ff365e8bc64ee
7
+ data.tar.gz: f1b4f292413767713e88bf115e0b16cb4df5644f72cfb79c80f5043dbc4bfe639e6e3fb5ec79ec515b3e526e094c4be9aed3a48ed2a3ba7d402978517643770c
data/CHANGELOG.md CHANGED
@@ -1,5 +1,12 @@
1
1
  # Change Log
2
2
 
3
+ ## 0.0.2
4
+
5
+ - General Java 2D shape support by nesting under any component
6
+ - Support setting `jframe` `minimum_size width, height` without building `Dimension` object manually
7
+ - Hello, Shapes! sample
8
+ - Improve Hello, Button! sample
9
+
3
10
  ## 0.0.1
4
11
 
5
12
  - Initial version of Glimmer DSL for Swing
data/README.md CHANGED
@@ -1,4 +1,4 @@
1
- # [<img src="https://raw.githubusercontent.com/AndyObtiva/glimmer/master/images/glimmer-logo-hi-res.png" height=85 />](https://github.com/AndyObtiva/glimmer) Glimmer DSL for Swing 0.0.1
1
+ # [<img src="https://raw.githubusercontent.com/AndyObtiva/glimmer/master/images/glimmer-logo-hi-res.png" height=85 />](https://github.com/AndyObtiva/glimmer) Glimmer DSL for Swing 0.0.2
2
2
  ## JRuby Swing Desktop Development GUI Library
3
3
  [![Gem Version](https://badge.fury.io/rb/glimmer-dsl-swing.svg)](http://badge.fury.io/rb/glimmer-dsl-swing)
4
4
  [![Join the chat at https://gitter.im/AndyObtiva/glimmer](https://badges.gitter.im/AndyObtiva/glimmer.svg)](https://gitter.im/AndyObtiva/glimmer?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge)
@@ -64,7 +64,7 @@ gem install glimmer-dsl-swing
64
64
 
65
65
  Add the following to `Gemfile`:
66
66
  ```
67
- gem 'glimmer-dsl-swing', '~> 0.0.1'
67
+ gem 'glimmer-dsl-swing', '~> 0.0.2'
68
68
  ```
69
69
 
70
70
  And, then run:
@@ -86,6 +86,153 @@ jframe('Hello, World!') {
86
86
  }.show
87
87
  ```
88
88
 
89
+ ## Glimmer GUI DSL
90
+
91
+ The Glimmer GUI DSL enables development of desktop graphical user interfaces in a manner similar to HTML, but in one language, Ruby, thus avoiding the multi-language separation dissonance encountered on the web, especially given that Ruby looping/conditional constructs do not need scriptlets to be added around View code. This makes desktop development extremely productive.
92
+
93
+ 1 - Keywords
94
+
95
+ You may declare any swing/awt component with its keyword, which is the underscored version of the class name. For example, `jframe` is the keyword for `javax.swing.JFrame` (`j_frame` is acceptable too)
96
+
97
+ Examples:
98
+
99
+ ```ruby
100
+ jframe
101
+ jbutton
102
+ jlabel
103
+ ```
104
+
105
+ 2 - Arguments
106
+
107
+ You may pass any arguments that a [swing](https://docs.oracle.com/javase/8/docs/api/javax/swing/package-summary.html)/[awt](https://docs.oracle.com/javase/8/docs/api/java/awt/package-summary.html) component constructor accepts to its Glimmer keyword.
108
+
109
+ Example `JFrame`, `JLabel`, and `JButton` have a constructor signature that accepts a string representing title or text:
110
+
111
+ ```ruby
112
+ jframe('Hello, World!')
113
+ jbutton('Push Me')
114
+ jlabel('Name')
115
+ ```
116
+
117
+ The recommended style is to always wrap arguments with parentheses for component keywords.
118
+
119
+ 3 - Content Block
120
+
121
+ You may pass a content block to any [swing](https://docs.oracle.com/javase/8/docs/api/javax/swing/package-summary.html)/[awt](https://docs.oracle.com/javase/8/docs/api/java/awt/package-summary.html) component keyword, which contains properties and/or nested components.
122
+
123
+ Example:
124
+
125
+ ```ruby
126
+ jframe('Hello, World!') {
127
+ minimum_size 320, 240
128
+
129
+ jlabel('Hello, World!')
130
+ }
131
+ ```
132
+
133
+ The recommended style for the content block is to always be curly braces to denote as View nesting code different from the logic in looping/conditional constructs that utilize `do;end` instead.
134
+
135
+ Property arguments never have parentheses.
136
+
137
+ 4 - Listeners
138
+
139
+ You may declare listeners with their event method name on the [swing](https://docs.oracle.com/javase/8/docs/api/javax/swing/package-summary.html)/[awt](https://docs.oracle.com/javase/8/docs/api/java/awt/package-summary.html) listener class (these are the classes in the signatures of `AddXYZListener` methods on [swing](https://docs.oracle.com/javase/8/docs/api/javax/swing/package-summary.html)/[awt](https://docs.oracle.com/javase/8/docs/api/java/awt/package-summary.html) component classes).
140
+
141
+ For example, `JButton` has an `AddXYZListener` method called `AddActionListener`, which accepts an `ActionListener` class. That class has one event method: `actionPerformed`. In Glimmer, you simply underscore that and prefix with `on_`:
142
+
143
+ ```ruby
144
+ jframe('Hello, Button!') {
145
+ jbutton('Click') {
146
+ on_action_performed do
147
+ puts 'Clicked!'
148
+ end
149
+ }
150
+ }
151
+ ```
152
+
153
+ The recommended style for listeners is always a `do; end` block.
154
+
155
+ 5 - Component Proxy & Methods
156
+
157
+ When utilizing the Glimmer GUI DSL, you get back proxy objects that wrap [swing](https://docs.oracle.com/javase/8/docs/api/javax/swing/package-summary.html)/[awt](https://docs.oracle.com/javase/8/docs/api/java/awt/package-summary.html) components. To access the original component wrapped by the proxy object, you may call the `#original` method.
158
+
159
+ Furthermore, you may invoke any method available on the component on the proxy object, like the `#show` method on `JFrame`.
160
+
161
+ ```ruby
162
+ frame1 = jframe('Hello, World!') {
163
+ # ...
164
+ }
165
+ frame1.show
166
+ ```
167
+
168
+ ### Shape DSL
169
+
170
+ [Glimmer DSL for Swing](https://rubygems.org/gems/glimmer-dsl-swing) might be the only Ruby Swing DSL out there that supports an additional Shape DSL.
171
+
172
+ This enables declarative painting of arbitrary shapes using Java 2D, which is similar to how SVG works on the web.
173
+
174
+ Simply utilize underscored shape names from the `java.awt.geom` [package classes](https://docs.oracle.com/javase/8/docs/api/java/awt/geom/package-summary.html) minus the `2D` suffix, following the same general rules of the [Glimmer GUI DSL](#glimmer-gui-dsl).
175
+
176
+ For example, `Arc2D` becomes simply `arc`.
177
+
178
+ Additionally, you can set `draw_color` or `fill_color` property as an rgb/rgba hash (e.g. `r: 255, g: 0, b: 0`)
179
+
180
+ Example:
181
+
182
+ ```ruby
183
+ require 'glimmer-dsl-swing'
184
+
185
+ include Glimmer
186
+
187
+ jframe('Hello, Shapes!') {
188
+ minimum_size 400, 400
189
+
190
+ arc(40, 40, 90, 90, 30, 230, 0) {
191
+ fill_color r: 255, g: 0, b: 0
192
+ draw_color r: 0, g: 255, b: 255
193
+ }
194
+
195
+ arc(40, 140, 90, 90, 30, 230, 1) {
196
+ fill_color r: 255, g: 0, b: 0
197
+ draw_color r: 0, g: 255, b: 255
198
+ }
199
+
200
+ arc(40, 240, 90, 90, 30, 230, 2) {
201
+ fill_color r: 255, g: 0, b: 0
202
+ draw_color r: 0, g: 255, b: 255
203
+ }
204
+
205
+ ellipse(140, 40, 180, 90) {
206
+ fill_color r: 0, g: 255, b: 255
207
+ draw_color r: 255, g: 0, b: 0
208
+ }
209
+
210
+ rectangle(140, 140, 180, 90) {
211
+ fill_color r: 0, g: 255, b: 255
212
+ draw_color r: 255, g: 0, b: 0
213
+ }
214
+
215
+ round_rectangle(140, 240, 180, 90, 60, 40) {
216
+ fill_color r: 0, g: 255, b: 255
217
+ draw_color r: 255, g: 0, b: 0
218
+ }
219
+
220
+ line(180, 60, 280, 110) {
221
+ draw_color r: 0, g: 0, b: 0
222
+ }
223
+
224
+ quad_curve(170, 60, 180, 90, 220, 100) {
225
+ draw_color r: 0, g: 0, b: 0
226
+ }
227
+
228
+ cubic_curve(190, 60, 240, 40, 220, 80, 260, 70) {
229
+ draw_color r: 0, g: 0, b: 0
230
+ }
231
+ }.show
232
+ ```
233
+
234
+ ![screenshots/glimmer-dsl-swing-mac-hello-shapes.png](screenshots/glimmer-dsl-swing-mac-hello-shapes.png)
235
+
89
236
  ## Girb (Glimmer IRB)
90
237
 
91
238
  You can run the `girb` command (`bin/girb` if you cloned the project locally):
@@ -102,6 +249,18 @@ This gives you `irb` with the `glimmer-dsl-gtk` gem loaded and the `Glimmer` mod
102
249
 
103
250
  #### Hello, World!
104
251
 
252
+ Run with gem installed:
253
+
254
+ ```
255
+ jruby -r glimmer-dsl-swing -e "require 'samples/hello/hello_world'"
256
+ ```
257
+
258
+ Or run from locally cloned project directory:
259
+
260
+ ```
261
+ jruby -r ./lib/glimmer-dsl-swing samples/hello/hello_world.rb
262
+ ```
263
+
105
264
  ![screenshots/glimmer-dsl-swing-mac-hello-world.png](screenshots/glimmer-dsl-swing-mac-hello-world.png)
106
265
 
107
266
  ```ruby
@@ -116,6 +275,18 @@ jframe('Hello, World!') {
116
275
 
117
276
  #### Hello, Button!
118
277
 
278
+ Run with gem installed:
279
+
280
+ ```
281
+ jruby -r glimmer-dsl-swing -e "require 'samples/hello/hello_button'"
282
+ ```
283
+
284
+ Or run from locally cloned project directory:
285
+
286
+ ```
287
+ jruby -r ./lib/glimmer-dsl-swing samples/hello/hello_button.rb
288
+ ```
289
+
119
290
  ![screenshots/glimmer-dsl-swing-mac-hello-button.png](screenshots/glimmer-dsl-swing-mac-hello-button.png)
120
291
 
121
292
  ```ruby
@@ -125,11 +296,79 @@ include Glimmer
125
296
 
126
297
  jframe('Hello, Button!') {
127
298
  @button = jbutton('Click To Increment: 0') {
128
- on_action_performed {
299
+ on_action_performed do
129
300
  button_text_match = @button.text.match(/(.*)(\d+)$/)
130
301
  count = button_text_match[2].to_i + 1
131
302
  @button.text = "#{button_text_match[1]}#{count}"
132
- }
303
+ end
304
+ }
305
+ }.show
306
+ ```
307
+
308
+ #### Hello, Shapes!
309
+
310
+ Run with gem installed:
311
+
312
+ ```
313
+ jruby -r glimmer-dsl-swing -e "require 'samples/hello/hello_shapes'"
314
+ ```
315
+
316
+ Or run from locally cloned project directory:
317
+
318
+ ```
319
+ jruby -r ./lib/glimmer-dsl-swing samples/hello/hello_shapes.rb
320
+ ```
321
+
322
+ ![screenshots/glimmer-dsl-swing-mac-hello-shapes.png](screenshots/glimmer-dsl-swing-mac-hello-shapes.png)
323
+
324
+ ```ruby
325
+ require 'glimmer-dsl-swing'
326
+
327
+ include Glimmer
328
+
329
+ jframe('Hello, Shapes!') {
330
+ minimum_size 400, 400
331
+
332
+ arc(40, 40, 90, 90, 30, 230, 0) {
333
+ fill_color r: 255, g: 0, b: 0
334
+ draw_color r: 0, g: 255, b: 255
335
+ }
336
+
337
+ arc(40, 140, 90, 90, 30, 230, 1) {
338
+ fill_color r: 255, g: 0, b: 0
339
+ draw_color r: 0, g: 255, b: 255
340
+ }
341
+
342
+ arc(40, 240, 90, 90, 30, 230, 2) {
343
+ fill_color r: 255, g: 0, b: 0
344
+ draw_color r: 0, g: 255, b: 255
345
+ }
346
+
347
+ ellipse(140, 40, 180, 90) {
348
+ fill_color r: 0, g: 255, b: 255
349
+ draw_color r: 255, g: 0, b: 0
350
+ }
351
+
352
+ rectangle(140, 140, 180, 90) {
353
+ fill_color r: 0, g: 255, b: 255
354
+ draw_color r: 255, g: 0, b: 0
355
+ }
356
+
357
+ round_rectangle(140, 240, 180, 90, 60, 40) {
358
+ fill_color r: 0, g: 255, b: 255
359
+ draw_color r: 255, g: 0, b: 0
360
+ }
361
+
362
+ line(180, 60, 280, 110) {
363
+ draw_color r: 0, g: 0, b: 0
364
+ }
365
+
366
+ quad_curve(170, 60, 180, 90, 220, 100) {
367
+ draw_color r: 0, g: 0, b: 0
368
+ }
369
+
370
+ cubic_curve(190, 60, 240, 40, 220, 80, 260, 70) {
371
+ draw_color r: 0, g: 0, b: 0
133
372
  }
134
373
  }.show
135
374
  ```
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.0.1
1
+ 0.0.2
data/bin/girb CHANGED
File without changes
Binary file
@@ -29,12 +29,12 @@ module Glimmer
29
29
  include ParentExpression
30
30
 
31
31
  def can_interpret?(parent, keyword, *args, &block)
32
- keyword = "j_#{keyword[1..-1]}" if keyword.match(/j[a-z]/)
32
+ keyword = "j_#{keyword[1..-1]}" if keyword.match(/j[a-z]/) # TODO move this logic to ComponentProxy
33
33
  Glimmer::Swing::ComponentProxy.exist?(keyword)
34
34
  end
35
35
 
36
36
  def interpret(parent, keyword, *args, &block)
37
- keyword = "j_#{keyword[1..-1]}" if keyword.match(/j[a-z]/)
37
+ keyword = "j_#{keyword[1..-1]}" if keyword.match(/j[a-z]/) # TODO move this logic to ComponentProxy
38
38
  Glimmer::Swing::ComponentProxy.create(parent, keyword, *args, &block)
39
39
  end
40
40
 
@@ -39,6 +39,7 @@ module Glimmer
39
39
  listener
40
40
  property
41
41
  component
42
+ shape
42
43
  ]
43
44
  )
44
45
  end
@@ -27,13 +27,16 @@ module Glimmer
27
27
  module Swing
28
28
  class PropertyExpression < Expression
29
29
  def can_interpret?(parent, keyword, *args, &block)
30
- parent.is_a?(Glimmer::Swing::ComponentProxy) and
30
+ (
31
+ parent.is_a?(Glimmer::Swing::ComponentProxy) or
32
+ parent.is_a?(Glimmer::Swing::ShapeProxy)
33
+ ) and
31
34
  block.nil? and
32
35
  parent.respond_to?(keyword, *args)
33
36
  end
34
37
 
35
38
  def interpret(parent, keyword, *args, &block)
36
- parent.send(keyword, *args)
39
+ parent.send("#{keyword}=", *args)
37
40
  end
38
41
  end
39
42
  end
@@ -0,0 +1,48 @@
1
+ # Copyright (c) 2021 Andy Maleh
2
+ #
3
+ # Permission is hereby granted, free of charge, to any person obtaining
4
+ # a copy of this software and associated documentation files (the
5
+ # "Software"), to deal in the Software without restriction, including
6
+ # without limitation the rights to use, copy, modify, merge, publish,
7
+ # distribute, sublicense, and/or sell copies of the Software, and to
8
+ # permit persons to whom the Software is furnished to do so, subject to
9
+ # the following conditions:
10
+ #
11
+ # The above copyright notice and this permission notice shall be
12
+ # included in all copies or substantial portions of the Software.
13
+ #
14
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
15
+ # EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16
+ # MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
17
+ # NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
18
+ # LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
19
+ # OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
+ # WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
21
+
22
+ require 'glimmer/dsl/expression'
23
+ require 'glimmer/dsl/parent_expression'
24
+
25
+ module Glimmer
26
+ module DSL
27
+ module Swing
28
+ class ShapeExpression < Expression
29
+ include ParentExpression
30
+
31
+ def can_interpret?(parent, keyword, *args, &block)
32
+ Glimmer::Swing::ShapeProxy.exist?(keyword)
33
+ end
34
+
35
+ def interpret(parent, keyword, *args, &block)
36
+ Glimmer::Swing::ShapeProxy.create(parent, keyword, *args, &block)
37
+ end
38
+
39
+ def add_content(parent, keyword, *args, &block)
40
+ super
41
+ parent.post_add_content
42
+ end
43
+ end
44
+ end
45
+ end
46
+ end
47
+
48
+ require 'glimmer/swing/shape_proxy'
@@ -31,11 +31,21 @@ module Glimmer
31
31
  DEFAULT_WIDTH = 190
32
32
  DEFAULT_HEIGHT = 150
33
33
 
34
+ def set_minimum_size(*args)
35
+ @minimum_size_set = true
36
+ if args.size == 1 && args.first.is_a?(Java::JavaAwt::Dimension)
37
+ super
38
+ else
39
+ super(Java::JavaAwt::Dimension.new(*args))
40
+ end
41
+ end
42
+ alias minimum_size= set_minimum_size
43
+
34
44
  def post_add_content
35
45
  unless @initial_content_added
36
46
  @initial_content_added = true
37
- the_width = width == 0 ? DEFAULT_WIDTH : width
38
- the_height = height == 0 ? DEFAULT_HEIGHT : height
47
+ the_width = @minimum_size_set ? minimum_size.width : DEFAULT_WIDTH
48
+ the_height = @minimum_size_set ? minimum_size.height : DEFAULT_HEIGHT
39
49
  set_minimum_size(Java::JavaAwt::Dimension.new(the_width, the_height))
40
50
  set_default_close_operation(Java::JavaxSwing::JFrame::EXIT_ON_CLOSE)
41
51
  end
@@ -32,7 +32,7 @@ module Glimmer
32
32
 
33
33
  class << self
34
34
  def exist?(keyword)
35
- !!component_proxy_class(keyword)
35
+ !!component_class(keyword)
36
36
  end
37
37
 
38
38
  def create(parent, keyword, *args, &block)
@@ -70,10 +70,10 @@ module Glimmer
70
70
  end
71
71
 
72
72
  def component_class(keyword)
73
- unless flyweight_component_class.keys.include?(keyword)
73
+ unless flyweight_component_class[keyword]
74
74
  begin
75
- pd component_class_name = component_class_symbol(keyword).to_s
76
- pd component_class = eval(component_class_name)
75
+ component_class_name = component_class_symbol(keyword).to_s
76
+ component_class = eval(component_class_name)
77
77
  unless component_class.ancestors.include?(Java::JavaAwt::Component)
78
78
  component_class = component_class_manual_entries[keyword]
79
79
  if component_class.nil?
@@ -81,6 +81,25 @@ module Glimmer
81
81
  return nil
82
82
  end
83
83
  end
84
+ component_class = Class.new(component_class) {
85
+ attr_accessor :shape_proxies
86
+
87
+ def paint(g2)
88
+ super(g2)
89
+ shape_proxies.each do |shape_proxy|
90
+ original_color = g2.get_color
91
+ if shape_proxy.fill_color
92
+ g2.color = Color.new(shape_proxy.fill_color[:r], shape_proxy.fill_color[:g], shape_proxy.fill_color[:b], shape_proxy.fill_color[:a] || 255)
93
+ g2.fill(shape_proxy)
94
+ end
95
+ if shape_proxy.draw_color
96
+ g2.color = Color.new(shape_proxy.draw_color[:r], shape_proxy.draw_color[:g], shape_proxy.draw_color[:b], shape_proxy.draw_color[:a] || 255)
97
+ g2.draw(shape_proxy)
98
+ end
99
+ g2.color = original_color
100
+ end
101
+ end
102
+ }
84
103
  flyweight_component_class[keyword] = component_class
85
104
  rescue SyntaxError, NameError => e
86
105
  Glimmer::Config.logger.debug {e.full_message}
@@ -106,7 +125,7 @@ module Glimmer
106
125
  @keyword = keyword
107
126
  @args = args
108
127
  @block = block
109
- build_widget
128
+ build
110
129
  post_add_content if @block.nil?
111
130
  end
112
131
 
@@ -117,7 +136,15 @@ module Glimmer
117
136
 
118
137
  # Subclasses may override to perform post initialization work on an added child (normally must also call super)
119
138
  def post_initialize_child(child)
120
- add(child)
139
+ if child.is_a?(ComponentProxy)
140
+ add(child)
141
+ elsif child.is_a?(ShapeProxy)
142
+ shape_proxies << child
143
+ end
144
+ end
145
+
146
+ def shape_proxies
147
+ @shape_proxies ||= []
121
148
  end
122
149
 
123
150
  def respond_to?(method_name, *args, &block)
@@ -130,7 +157,9 @@ module Glimmer
130
157
  end
131
158
 
132
159
  def method_missing(method_name, *args, &block)
133
- if @original.respond_to?("set_#{method_name}", true) && !args.empty?
160
+ if respond_to?("#{method_name}=", true) && !args.empty?
161
+ send("#{method_name}=", *args)
162
+ elsif @original.respond_to?("set_#{method_name}", true) && !args.empty?
134
163
  send_to_original("set_#{method_name}", *args, &block)
135
164
  elsif @original.respond_to?(method_name, true)
136
165
  send_to_original(method_name, *args, &block)
@@ -224,10 +253,9 @@ module Glimmer
224
253
 
225
254
  private
226
255
 
227
- def build_widget
228
- pd keyword
229
- pd ComponentProxy.component_class(keyword)
256
+ def build
230
257
  @original = ComponentProxy.component_class(keyword).new(*normalize_args(args))
258
+ @original.shape_proxies = shape_proxies
231
259
  end
232
260
 
233
261
  def normalize_args(args)
@@ -240,3 +268,4 @@ module Glimmer
240
268
  end
241
269
 
242
270
  Dir[File.expand_path("./#{File.basename(__FILE__, '.rb')}/*.rb", __dir__)].each {|f| require f}
271
+ require 'glimmer/swing/shape_proxy'
@@ -0,0 +1,167 @@
1
+ # Copyright (c) 2021 Andy Maleh
2
+ #
3
+ # Permission is hereby granted, free of charge, to any person obtaining
4
+ # a copy of this software and associated documentation files (the
5
+ # "Software"), to deal in the Software without restriction, including
6
+ # without limitation the rights to use, copy, modify, merge, publish,
7
+ # distribute, sublicense, and/or sell copies of the Software, and to
8
+ # permit persons to whom the Software is furnished to do so, subject to
9
+ # the following conditions:
10
+ #
11
+ # The above copyright notice and this permission notice shall be
12
+ # included in all copies or substantial portions of the Software.
13
+ #
14
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
15
+ # EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16
+ # MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
17
+ # NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
18
+ # LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
19
+ # OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
+ # WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
21
+
22
+ require 'glimmer/swing/packages'
23
+
24
+ module Glimmer
25
+ module Swing
26
+ # Proxy for Java2D shape objects
27
+ #
28
+ # Follows the Proxy Design Pattern
29
+ class ShapeProxy
30
+ include Packages
31
+
32
+ class << self
33
+ def exist?(keyword)
34
+ !!shape_class(keyword)
35
+ end
36
+
37
+ def create(parent, keyword, *args, &block)
38
+ shape_proxy_class(keyword).new(parent, keyword, *args, &block)
39
+ end
40
+
41
+ def shape_proxy_class(keyword)
42
+ begin
43
+ class_name = shape_proxy_class_symbol(keyword)
44
+ Glimmer::Swing::ShapeProxy.const_get(class_name)
45
+ rescue => e
46
+ Glimmer::Config.logger.debug e.full_message
47
+ Glimmer::Swing::ShapeProxy
48
+ end
49
+ end
50
+
51
+ def shape_proxy_class_symbol(keyword)
52
+ "#{keyword.camelcase(:upper)}Proxy".to_sym
53
+ end
54
+
55
+ def shape_class_symbol(keyword)
56
+ keyword.camelcase(:upper).to_sym
57
+ end
58
+
59
+ def keyword(shape_proxy_class)
60
+ shape_proxy_class.to_s.underscore.sub(/_proxy$/, '')
61
+ end
62
+
63
+ def shape_class_manual_entries
64
+ # add mappings for any classes (minus the namespace) that conflict with standard Ruby classes
65
+ {
66
+ # example:
67
+ # 'date_time' => Java::OrgEclipseSwtWidgets::DateTime
68
+ }
69
+ end
70
+
71
+ def shape_class(keyword)
72
+ unless flyweight_shape_class.keys.include?(keyword)
73
+ begin
74
+ shape_class_name = shape_class_symbol(keyword).to_s
75
+ shape_class = eval("#{shape_class_name}2D::Double") rescue eval(shape_class_name)
76
+ unless shape_class.ancestors.include?(Java::JavaAwt::Shape)
77
+ shape_class = shape_class_manual_entries[keyword]
78
+ if shape_class.nil?
79
+ Glimmer::Config.logger.debug {"Class #{shape_class} matching #{keyword} is not a subclass of java.awt.Component"}
80
+ return nil
81
+ end
82
+ end
83
+ flyweight_shape_class[keyword] = shape_class
84
+ rescue SyntaxError, NameError => e
85
+ Glimmer::Config.logger.debug {e.full_message}
86
+ nil
87
+ rescue => e
88
+ Glimmer::Config.logger.debug {e.full_message}
89
+ nil
90
+ end
91
+ end
92
+ flyweight_shape_class[keyword]
93
+ end
94
+
95
+ # Flyweight Design Pattern memoization cache. Can be cleared if memory is needed.
96
+ def flyweight_shape_class
97
+ @flyweight_shape_class ||= {}
98
+ end
99
+ end
100
+
101
+ attr_reader :parent_proxy, :original, :args, :keyword, :block
102
+ attr_accessor :draw_color, :fill_color
103
+
104
+ def initialize(parent, keyword, *args, &block)
105
+ @parent_proxy = parent
106
+ @keyword = keyword
107
+ @args = args
108
+ @block = block
109
+ build
110
+ post_add_content if @block.nil?
111
+ end
112
+
113
+ # Subclasses may override to perform post add_content work (normally must call super)
114
+ def post_add_content
115
+ @parent_proxy&.post_initialize_child(self)
116
+ end
117
+
118
+ # Subclasses may override to perform post initialization work on an added child (normally must also call super)
119
+ def post_initialize_child(child)
120
+ if child.is_a?(ShapeProxy)
121
+ add(child)
122
+ end
123
+ end
124
+
125
+ def respond_to?(method_name, *args, &block)
126
+ respond_to_original?(method_name, *args, &block) ||
127
+ super(method_name, true)
128
+ end
129
+
130
+ def respond_to_original?(method_name, *args, &block)
131
+ @original.respond_to?(method_name, true) || @original.respond_to?("set_#{method_name}", true)
132
+ end
133
+
134
+ def method_missing(method_name, *args, &block)
135
+ if @original.respond_to?("set_#{method_name}", true) && !args.empty?
136
+ send_to_original("set_#{method_name}", *args, &block)
137
+ elsif @original.respond_to?(method_name, true)
138
+ send_to_original(method_name, *args, &block)
139
+ else
140
+ super
141
+ end
142
+ end
143
+
144
+ def send_to_original(method_name, *args, &block)
145
+ @original.send(method_name, *normalize_args(args), &block)
146
+ end
147
+
148
+ def content(&block)
149
+ Glimmer::DSL::Engine.add_content(self, Glimmer::DSL::Swing::ShapeExpression.new, @keyword, &block)
150
+ end
151
+
152
+ private
153
+
154
+ def build
155
+ @original = ShapeProxy.shape_class(keyword).new(*normalize_args(args))
156
+ end
157
+
158
+ def normalize_args(args)
159
+ args.map do |arg|
160
+ arg.is_a?(ShapeProxy) ? arg.original : arg
161
+ end
162
+ end
163
+ end
164
+ end
165
+ end
166
+
167
+ Dir[File.expand_path("./#{File.basename(__FILE__, '.rb')}/*.rb", __dir__)].each {|f| require f}
@@ -36,8 +36,6 @@ require 'facets/string/camelcase'
36
36
  require 'facets/hash/stringify_keys'
37
37
 
38
38
  # Internal requires
39
- # require 'ext/glimmer/config'
40
- # require 'ext/glimmer'
41
39
  require 'glimmer/swing'
42
40
  require 'glimmer/swing/ext/glimmer'
43
41
  require 'glimmer/swing/ext/glimmer/config'
@@ -4,10 +4,10 @@ include Glimmer
4
4
 
5
5
  jframe('Hello, Button!') {
6
6
  @button = jbutton('Click To Increment: 0') {
7
- on_action_performed {
8
- button_text_match = @button.text.match(/(.*)(\d+)$/)
7
+ on_action_performed do
8
+ button_text_match = @button.text.match(/([^0-9]+)(\d+)$/)
9
9
  count = button_text_match[2].to_i + 1
10
10
  @button.text = "#{button_text_match[1]}#{count}"
11
- }
11
+ end
12
12
  }
13
13
  }.show
@@ -0,0 +1,49 @@
1
+ require 'glimmer-dsl-swing'
2
+
3
+ include Glimmer
4
+
5
+ jframe('Hello, Shapes!') {
6
+ minimum_size 400, 400
7
+
8
+ arc(40, 40, 90, 90, 30, 230, 0) {
9
+ fill_color r: 255, g: 0, b: 0
10
+ draw_color r: 0, g: 255, b: 255
11
+ }
12
+
13
+ arc(40, 140, 90, 90, 30, 230, 1) {
14
+ fill_color r: 255, g: 0, b: 0
15
+ draw_color r: 0, g: 255, b: 255
16
+ }
17
+
18
+ arc(40, 240, 90, 90, 30, 230, 2) {
19
+ fill_color r: 255, g: 0, b: 0
20
+ draw_color r: 0, g: 255, b: 255
21
+ }
22
+
23
+ ellipse(140, 40, 180, 90) {
24
+ fill_color r: 0, g: 255, b: 255
25
+ draw_color r: 255, g: 0, b: 0
26
+ }
27
+
28
+ rectangle(140, 140, 180, 90) {
29
+ fill_color r: 0, g: 255, b: 255
30
+ draw_color r: 255, g: 0, b: 0
31
+ }
32
+
33
+ round_rectangle(140, 240, 180, 90, 60, 40) {
34
+ fill_color r: 0, g: 255, b: 255
35
+ draw_color r: 255, g: 0, b: 0
36
+ }
37
+
38
+ line(180, 60, 280, 110) {
39
+ draw_color r: 0, g: 0, b: 0
40
+ }
41
+
42
+ quad_curve(170, 60, 180, 90, 220, 100) {
43
+ draw_color r: 0, g: 0, b: 0
44
+ }
45
+
46
+ cubic_curve(190, 60, 240, 40, 220, 80, 260, 70) {
47
+ draw_color r: 0, g: 0, b: 0
48
+ }
49
+ }.show
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: glimmer-dsl-swing
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.1
4
+ version: 0.0.2
5
5
  platform: ruby
6
6
  authors:
7
7
  - Andy Maleh
@@ -202,6 +202,7 @@ executables:
202
202
  - girb
203
203
  extensions: []
204
204
  extra_rdoc_files:
205
+ - CHANGELOG.md
205
206
  - LICENSE.txt
206
207
  - README.md
207
208
  files:
@@ -217,6 +218,7 @@ files:
217
218
  - lib/glimmer/dsl/swing/dsl.rb
218
219
  - lib/glimmer/dsl/swing/listener_expression.rb
219
220
  - lib/glimmer/dsl/swing/property_expression.rb
221
+ - lib/glimmer/dsl/swing/shape_expression.rb
220
222
  - lib/glimmer/swing.rb
221
223
  - lib/glimmer/swing/component_listener_proxy.rb
222
224
  - lib/glimmer/swing/component_proxy.rb
@@ -224,7 +226,9 @@ files:
224
226
  - lib/glimmer/swing/ext/glimmer.rb
225
227
  - lib/glimmer/swing/ext/glimmer/config.rb
226
228
  - lib/glimmer/swing/packages.rb
229
+ - lib/glimmer/swing/shape_proxy.rb
227
230
  - samples/hello/hello_button.rb
231
+ - samples/hello/hello_shapes.rb
228
232
  - samples/hello/hello_world.rb
229
233
  homepage: http://github.com/AndyObtiva/glimmer-dsl-swing
230
234
  licenses:
@@ -246,7 +250,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
246
250
  - !ruby/object:Gem::Version
247
251
  version: '0'
248
252
  requirements: []
249
- rubygems_version: 3.1.6
253
+ rubygems_version: 3.2.29
250
254
  signing_key:
251
255
  specification_version: 4
252
256
  summary: Glimmer DSL for Swing