glimmer-dsl-swt 4.17.6.0 → 4.17.7.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 50dd550729725e788ad32393c82aa34c1e39cbc536b0bfce60734603c052b1cf
4
- data.tar.gz: 19cf9cb269726720dac30ebf82d458afc1c535861153be8e3fad8ba0864f4a5f
3
+ metadata.gz: 2a6e9aed9497c88e3858e2e4a5c3734d784fce7aed040f4f538433e2318317d1
4
+ data.tar.gz: 10edec048056954ef796359f731f72d85ff586ec011291ece257d2d268fc34f6
5
5
  SHA512:
6
- metadata.gz: f2dffb27676fc7884bd58927e1648677ec972b56b56fdd9a6162c99e252fe6018b3f135766abf739a215d46398136422bdf656a52832821b326b6c02dbed9a8a
7
- data.tar.gz: 93c4fb967105b1271e3425155ccb3e5e71acb796d63eac3990a984fc0094708ec7be11faf0f9f0760c5c16e3168a6e477d6737bca444801c4425556458978a81
6
+ metadata.gz: de93b471548a07642f95d134a838b8e4ecf9045f209fa50d3ec8958b8d5c5bc3f39bc9ed0071a24724c2313913ed807d20b97ecd4b4313f52413e178606bca5c
7
+ data.tar.gz: 206afc10eb6b566e0617da956f92507145e50393c30b8e398580af8565ea8a3cde61c03fbdc675e9b52a616fcfd7c1920764901c1318c94272848fc95572a12c
@@ -1,5 +1,13 @@
1
1
  # Change Log
2
2
 
3
+ ### 4.17.7.0
4
+
5
+ - `checkbox_group` built-in custom widget
6
+ - Hello, Checkbox Group! Sample
7
+ - Refactor `radio_group` to render labels instead of relying on radio button text since they are better stylable
8
+ - Refactor Glimmer Meta-Sample to use `radio_group` instead of `radio`
9
+ - Fix issue with ExpandBar fill_layout with the extra element at the end (remove it)
10
+
3
11
  ### 4.17.6.0
4
12
 
5
13
  - New `radio_group` built-in Glimmer custom widget
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 SWT 4.17.6.0
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 SWT 4.17.7.0
2
2
  ## JRuby Desktop Development GUI Library
3
3
  [![Gem Version](https://badge.fury.io/rb/glimmer-dsl-swt.svg)](http://badge.fury.io/rb/glimmer-dsl-swt)
4
4
  [![Travis CI](https://travis-ci.com/AndyObtiva/glimmer-dsl-swt.svg?branch=master)](https://travis-ci.com/github/AndyObtiva/glimmer-dsl-swt)
@@ -350,6 +350,7 @@ Glimmer App:
350
350
  - [Hello, Radio!](#hello-radio)
351
351
  - [Hello, Radio Group!](#hello-radio-group)
352
352
  - [Hello, Checkbox!](#hello-checkbox)
353
+ - [Hello, Checkbox Group!](#hello-checkbox-group)
353
354
  - [Elaborate Samples](#elaborate-samples)
354
355
  - [User Profile](#user-profile)
355
356
  - [Login](#login)
@@ -443,7 +444,7 @@ jgem install glimmer-dsl-swt
443
444
 
444
445
  Or this command if you want a specific version:
445
446
  ```
446
- jgem install glimmer-dsl-swt -v 4.17.6.0
447
+ jgem install glimmer-dsl-swt -v 4.17.7.0
447
448
  ```
448
449
 
449
450
  `jgem` is JRuby's version of `gem` command.
@@ -519,7 +520,7 @@ bin/glimmer samples
519
520
  Below are the full usage instructions that come up when running `glimmer` without args.
520
521
 
521
522
  ```
522
- Glimmer (Ruby Desktop Development GUI Library) - JRuby Gem: glimmer-dsl-swt v4.17.6.0
523
+ Glimmer (Ruby Desktop Development GUI Library) - JRuby Gem: glimmer-dsl-swt v4.17.7.0
523
524
 
524
525
  Usage: glimmer [--bundler] [--pd] [--quiet] [--debug] [--log-level=VALUE] [[ENV_VAR=VALUE]...] [[-jruby-option]...] (application.rb or task[task_args]) [[application2.rb]...]
525
526
 
@@ -996,7 +997,7 @@ Output:
996
997
 
997
998
  Css glimmer-dsl-css 1.1.0 AndyMaleh Glimmer DSL for CSS
998
999
  Opal glimmer-dsl-opal 0.4.0 AndyMaleh Glimmer DSL for Opal
999
- Swt glimmer-dsl-swt 4.17.6.0 AndyMaleh Glimmer DSL for SWT
1000
+ Swt glimmer-dsl-swt 4.17.7.0 AndyMaleh Glimmer DSL for SWT
1000
1001
  Tk glimmer-dsl-tk 0.0.6 AndyMaleh Glimmer DSL for Tk
1001
1002
  Xml glimmer-dsl-xml 1.1.0 AndyMaleh Glimmer DSL for XML
1002
1003
  ```
@@ -3078,6 +3079,55 @@ shell(:no_resize) {
3078
3079
 
3079
3080
  Also, you may invoke `Display.setAppVersion('1.0.0')` if needed for OS app version identification reasons during development, replacing `'1.0.0'` with your application version.
3080
3081
 
3082
+ #### Checkbox Group Widget
3083
+
3084
+ `checkbox_group` (or alias `check_group`) is a Glimmer built-in custom widget that displays a list of `checkbox` buttons (`button(:check)`) based on its `items` property.
3085
+
3086
+ `checkbox_group` consists of a root `composite` (with `grid_layout 1, false` by default) that holds nested `checkbox` (`button(:check)`) widgets.
3087
+
3088
+ The `selection` property determines which `checkbox` buttons are checked. It expects an `Array` of `String` objects
3089
+ The `selection_indices` property determines which `checkbox` button indices are checked. It expects an `Array` of index `Integer` objects that are zero-based.
3090
+ The `checkboxes` property returns the list of nested `checkbox` widgets.
3091
+
3092
+ When data-binding `selection`, the model property should have a matching property with `_options` suffix (e.g. `activities_options` for `activities`) to provide an `Array` of `String` objects for `checkbox` buttons.
3093
+
3094
+ You may see an example at the [Hello, Checkbox Group!](#hello-checkbox-group) sample.
3095
+
3096
+ ![Hello Checkbox Group](images/glimmer-hello-checkbox-group.png)
3097
+
3098
+ #### Radio Group Widget
3099
+
3100
+ `radio_group` is a Glimmer built-in custom widget that displays a list of `radio` buttons (`button(:radio)`) based on its `items` property, which expects an `Array` of `String` objects.
3101
+
3102
+ `radio_group` consists of a root `composite` (with `grid_layout 1, false` by default) that holds nested `radio` widgets.
3103
+
3104
+ The `selection` property determines which `radio` button is selected. It expects a `String`
3105
+ The `selection_index` property determines which `radio` button index is selected. It expects an index integer that is zero-based.
3106
+ The `radios` property returns the list of nested `radio` widgets.
3107
+
3108
+ When data-binding `selection`, the model property should have a matching property with `_options` suffix (e.g. `country_options` for `country`) to provide text for `radio` buttons.
3109
+
3110
+ This custom widget is used in the [Glimmer Meta-Sample (The Sample of Samples)](#samples):
3111
+
3112
+ ![Glimmer Meta-Sample](images/glimmer-meta-sample.png)
3113
+
3114
+ Glimmer Meta-Sample Code Example:
3115
+
3116
+ ```ruby
3117
+ # ...
3118
+ radio_group { |radio_group_proxy|
3119
+ row_layout(:vertical) {
3120
+ fill true
3121
+ }
3122
+ selection bind(sample_directory, :selected_sample_name)
3123
+ font height: 24
3124
+ }
3125
+
3126
+ # ...
3127
+ ```
3128
+
3129
+ You may see another example at the [Hello, Radio Group!](#hello-radio-group) sample.
3130
+
3081
3131
  #### Code Text Widget
3082
3132
 
3083
3133
  `code_text` is a Glimmer built-in custom widget that displays syntax highlighted Ruby code in a customized SWT [StyledText](https://help.eclipse.org/2020-09/topic/org.eclipse.platform.doc.isv/reference/api/org/eclipse/swt/custom/StyledText.html) widget.
@@ -3662,7 +3712,7 @@ Hello, Radio!
3662
3712
 
3663
3713
  #### Hello, Radio Group!
3664
3714
 
3665
- This sample demonstrates the use of a `radio_group` in Glimmer, which is a terser way of representing multiple radio buttons by relying on data-binding to automatically spawn the `radio` widgets based on available options on the model.
3715
+ This sample demonstrates the use of a `radio_group` in Glimmer, which provides terser syntax for representing multiple radio buttons by relying on data-binding to automatically spawn the `radio` widgets based on available options on the model.
3666
3716
 
3667
3717
  Code:
3668
3718
 
@@ -3684,6 +3734,18 @@ Hello, Checkbox!
3684
3734
 
3685
3735
  ![Hello Checkbox](images/glimmer-hello-checkbox.png)
3686
3736
 
3737
+ #### Hello, Checkbox Group!
3738
+
3739
+ This sample demonstrates the use of a `checkbox_group` (aka `check_group`) in Glimmer, which provides terser syntax for representing multiple checkbox buttons (`button(:check)`) by relying on data-binding to automatically spawn the `checkbox` widgets (`button(:check)`) based on available options on the model.
3740
+
3741
+ Code:
3742
+
3743
+ [samples/hello/hello_checkbox_group.rb](https://github.com/AndyObtiva/glimmer-dsl-swt/blob/master/samples/hello/hello_checkbox_group.rb)
3744
+
3745
+ Hello, Checkbox Group!
3746
+
3747
+ ![Hello Checkbox Group](images/glimmer-hello-checkbox-group.png)
3748
+
3687
3749
  ### Elaborate Samples
3688
3750
 
3689
3751
  For more elaborate samples, check the following:
data/VERSION CHANGED
@@ -1 +1 @@
1
- 4.17.6.0
1
+ 4.17.7.0
@@ -2,16 +2,16 @@
2
2
  # DO NOT EDIT THIS FILE DIRECTLY
3
3
  # Instead, edit Juwelier::Tasks in Rakefile, and run 'rake gemspec'
4
4
  # -*- encoding: utf-8 -*-
5
- # stub: glimmer-dsl-swt 4.17.6.0 ruby lib
5
+ # stub: glimmer-dsl-swt 4.17.7.0 ruby lib
6
6
 
7
7
  Gem::Specification.new do |s|
8
8
  s.name = "glimmer-dsl-swt".freeze
9
- s.version = "4.17.6.0"
9
+ s.version = "4.17.7.0"
10
10
 
11
11
  s.required_rubygems_version = Gem::Requirement.new(">= 0".freeze) if s.respond_to? :required_rubygems_version=
12
12
  s.require_paths = ["lib".freeze]
13
13
  s.authors = ["AndyMaleh".freeze]
14
- s.date = "2020-10-28"
14
+ s.date = "2020-10-29"
15
15
  s.description = "Glimmer DSL for SWT (JRuby Desktop Development GUI Library)".freeze
16
16
  s.email = "andy.am@gmail.com".freeze
17
17
  s.executables = ["glimmer".freeze, "girb".freeze]
@@ -45,6 +45,7 @@ Gem::Specification.new do |s|
45
45
  "lib/glimmer/dsl/swt/async_exec_expression.rb",
46
46
  "lib/glimmer/dsl/swt/bind_expression.rb",
47
47
  "lib/glimmer/dsl/swt/block_property_expression.rb",
48
+ "lib/glimmer/dsl/swt/checkbox_group_selection_data_binding_expression.rb",
48
49
  "lib/glimmer/dsl/swt/color_expression.rb",
49
50
  "lib/glimmer/dsl/swt/column_properties_expression.rb",
50
51
  "lib/glimmer/dsl/swt/combo_selection_data_binding_expression.rb",
@@ -86,6 +87,7 @@ Gem::Specification.new do |s|
86
87
  "lib/glimmer/rake_task/scaffold.rb",
87
88
  "lib/glimmer/swt/color_proxy.rb",
88
89
  "lib/glimmer/swt/cursor_proxy.rb",
90
+ "lib/glimmer/swt/custom/checkbox_group.rb",
89
91
  "lib/glimmer/swt/custom/code_text.rb",
90
92
  "lib/glimmer/swt/custom/radio_group.rb",
91
93
  "lib/glimmer/swt/display_proxy.rb",
@@ -125,6 +127,7 @@ Gem::Specification.new do |s|
125
127
  "samples/elaborate/user_profile.rb",
126
128
  "samples/hello/hello_browser.rb",
127
129
  "samples/hello/hello_checkbox.rb",
130
+ "samples/hello/hello_checkbox_group.rb",
128
131
  "samples/hello/hello_combo.rb",
129
132
  "samples/hello/hello_computed.rb",
130
133
  "samples/hello/hello_computed/contact.rb",
@@ -0,0 +1,61 @@
1
+ # Copyright (c) 2007-2020 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/data_binding/model_binding'
24
+ require 'glimmer/data_binding/widget_binding'
25
+
26
+ module Glimmer
27
+ module DSL
28
+ module SWT
29
+ class CheckboxGroupSelectionDataBindingExpression < Expression
30
+
31
+ def can_interpret?(parent, keyword, *args, &block)
32
+ keyword == 'selection' and
33
+ block.nil? and
34
+ (parent.is_a?(Glimmer::SWT::Custom::CheckboxGroup) or (parent.is_a?(Glimmer::UI::CustomWidget) and parent.body_root.is_a?(Glimmer::SWT::Custom::CheckboxGroup)) ) and
35
+ args.size == 1 and
36
+ args[0].is_a?(DataBinding::ModelBinding) and
37
+ args[0].evaluate_options_property.is_a?(Array)
38
+ end
39
+
40
+ def interpret(parent, keyword, *args, &block)
41
+ model_binding = args[0]
42
+
43
+ #TODO make this options observer dependent and all similar observers in widget specific data binding handlers
44
+ # TODO consider delegating some of this work
45
+ widget_binding = DataBinding::WidgetBinding.new(parent, 'items')
46
+ widget_binding.call(model_binding.evaluate_options_property)
47
+ model = model_binding.base_model
48
+ widget_binding.observe(model, model_binding.options_property_name)
49
+
50
+ widget_binding = DataBinding::WidgetBinding.new(parent, 'selection')
51
+ widget_binding.call(model_binding.evaluate_property)
52
+ widget_binding.observe(model, model_binding.property_name_expression)
53
+
54
+ parent.on_widget_selected do
55
+ model_binding.call(widget_binding.evaluate_property)
56
+ end
57
+ end
58
+ end
59
+ end
60
+ end
61
+ end
@@ -27,6 +27,7 @@ require 'glimmer/ui/custom_widget'
27
27
  require 'glimmer/ui/custom_shell'
28
28
  require 'glimmer/swt/custom/code_text'
29
29
  require 'glimmer/swt/custom/radio_group'
30
+ require 'glimmer/swt/custom/checkbox_group'
30
31
 
31
32
  module Glimmer
32
33
  module DSL
@@ -41,6 +41,7 @@ module Glimmer
41
41
  layout
42
42
  widget_listener
43
43
  combo_selection_data_binding
44
+ checkbox_group_selection_data_binding
44
45
  radio_group_selection_data_binding
45
46
  list_selection_data_binding
46
47
  tree_items_data_binding
@@ -0,0 +1,160 @@
1
+ require 'glimmer/ui/custom_widget'
2
+
3
+ module Glimmer
4
+ module SWT
5
+ module Custom
6
+ # CodeText is a customization of StyledText with support for Ruby Syntax Highlighting
7
+ class CheckboxGroup
8
+ include Glimmer::UI::CustomWidget
9
+
10
+ body {
11
+ composite # just an empty composite to hold checkboxs upon data-binding `selection`
12
+ }
13
+
14
+ def items=(text_array)
15
+ selection_value = selection
16
+ @items = Array[*text_array]
17
+ build_checkboxes
18
+ end
19
+
20
+ def items
21
+ @items || []
22
+ end
23
+
24
+ def selection=(selection_texts)
25
+ items.count.times do |index|
26
+ checkbox = checkboxes[index]
27
+ item = items[index]
28
+ label_text = labels[index]&.text
29
+ checkbox.selection = selection_texts.to_a.include?(label_text)
30
+ end
31
+ selection_texts
32
+ end
33
+
34
+ def selection
35
+ selection_indices.map do |selection_index|
36
+ labels[selection_index]&.text
37
+ end
38
+ end
39
+
40
+ def selection_indices=(indices)
41
+ self.selection=(indices.to_a.map {|index| items[index]})
42
+ end
43
+ alias select selection_indices=
44
+
45
+ def selection_indices
46
+ checkboxes.each_with_index.map do |checkbox, index|
47
+ index if checkbox.selection
48
+ end.to_a.compact
49
+ end
50
+
51
+ def checkboxes
52
+ @checkboxes ||= []
53
+ end
54
+ alias checks checkboxes
55
+
56
+ def labels
57
+ @labels ||= []
58
+ end
59
+
60
+ def can_handle_observation_request?(observation_request)
61
+ checkboxes.first&.can_handle_observation_request?(observation_request) || super(observation_request)
62
+ end
63
+
64
+ def handle_observation_request(observation_request, &block)
65
+ observation_requests << [observation_request, block]
66
+ delegate_observation_request_to_checkboxes(observation_request, &block)
67
+ super
68
+ end
69
+
70
+ def delegate_observation_request_to_checkboxes(observation_request, &block)
71
+ if observation_request != 'on_widget_disposed'
72
+ checkboxes.count.times do |index|
73
+ checkbox = checkboxes[index]
74
+ label = labels[index]
75
+ listener_block = lambda do |event|
76
+ event.widget = self.swt_widget
77
+ block.call(event)
78
+ end
79
+ if observation_request == 'on_widget_selected'
80
+ checkbox.handle_observation_request(observation_request, &listener_block) if checkbox.can_handle_observation_request?(observation_request)
81
+ label.handle_observation_request('on_mouse_up', &listener_block)
82
+ else
83
+ checkbox.handle_observation_request(observation_request, &listener_block) if checkbox.can_handle_observation_request?(observation_request)
84
+ label.handle_observation_request(observation_request, &listener_block) if label.can_handle_observation_request?(observation_request)
85
+ end
86
+ end
87
+ end
88
+ end
89
+
90
+ def observation_requests
91
+ @observation_requests ||= Set.new
92
+ end
93
+
94
+ def has_attribute?(attribute_name, *args)
95
+ (@composites.to_a + @checkboxes.to_a + @labels.to_a).map do |widget_proxy|
96
+ return true if widget_proxy.has_attribute?(attribute_name, *args)
97
+ end
98
+ super
99
+ end
100
+
101
+ def set_attribute(attribute_name, *args)
102
+ excluded_attributes = ['selection']
103
+ unless excluded_attributes.include?(attribute_name.to_s)
104
+ (@composites.to_a + @checkboxes.to_a + @labels.to_a).each do |widget_proxy|
105
+ widget_proxy.set_attribute(attribute_name, *args) if widget_proxy.has_attribute?(attribute_name, *args)
106
+ end
107
+ end
108
+ super
109
+ end
110
+
111
+ private
112
+
113
+ def build_checkboxes
114
+ current_selection = selection
115
+ @composites.to_a.each(&:dispose)
116
+ @checkboxes = []
117
+ @labels = []
118
+ @composites = []
119
+ items.each do |item|
120
+ body_root.content {
121
+ @composites << composite {
122
+ grid_layout(2, false) {
123
+ margin_width 0
124
+ margin_height 0
125
+ horizontal_spacing 0
126
+ vertical_spacing 0
127
+ }
128
+ checkboxes << checkbox { |checkbox_proxy|
129
+ on_widget_selected {
130
+ self.selection_indices = checkboxes.each_with_index.map {|cb, i| i if cb.selection}.to_a.compact
131
+ }
132
+ }
133
+ labels << label { |label_proxy|
134
+ layout_data :fill, :center, true, false
135
+ text item
136
+ on_mouse_up { |event|
137
+ found_text = labels.each_with_index.detect {|l, i| event.widget == l.swt_widget}[0]&.text
138
+ selection_values = self.selection
139
+ if selection_values.include?(found_text)
140
+ selection_values.delete(found_text)
141
+ else
142
+ selection_values << found_text
143
+ end
144
+ self.selection = selection_values
145
+ }
146
+ }
147
+ }
148
+ }
149
+ end
150
+ observation_requests.to_a.each do |observation_request, block|
151
+ delegate_observation_request_to_checkboxes(observation_request, &block)
152
+ end
153
+ self.selection = current_selection
154
+ end
155
+ end
156
+
157
+ CheckGroup = CheckboxGroup
158
+ end
159
+ end
160
+ end
@@ -7,8 +7,6 @@ module Glimmer
7
7
  class RadioGroup
8
8
  include Glimmer::UI::CustomWidget
9
9
 
10
- # TODO support setting font, background, foreground, cursor
11
-
12
10
  body {
13
11
  composite # just an empty composite to hold radios upon data-binding `selection`
14
12
  }
@@ -20,18 +18,20 @@ module Glimmer
20
18
  end
21
19
 
22
20
  def items
23
- @items
21
+ @items || []
24
22
  end
25
23
 
26
24
  def selection=(text)
27
- radios.each do |radio|
28
- radio.selection = radio.text == text
25
+ radios.count.times do |index|
26
+ radio = radios[index]
27
+ item = items[index]
28
+ radio.selection = item == text
29
29
  end
30
30
  end
31
31
 
32
32
  def selection
33
- # TODO use labels to retrieve text since they are better customizable with fonts while maintaining alignment with radio buttons
34
- radios.detect(&:selection)&.text.to_s
33
+ selection_value = labels[selection_index]&.text unless selection_index == -1
34
+ selection_value.to_s
35
35
  end
36
36
 
37
37
  def selection_index=(index)
@@ -47,6 +47,10 @@ module Glimmer
47
47
  @radios ||= []
48
48
  end
49
49
 
50
+ def labels
51
+ @labels ||= []
52
+ end
53
+
50
54
  def can_handle_observation_request?(observation_request)
51
55
  radios.first&.can_handle_observation_request?(observation_request) || super(observation_request)
52
56
  end
@@ -58,15 +62,31 @@ module Glimmer
58
62
  end
59
63
 
60
64
  def delegate_observation_request_to_radios(observation_request, &block)
61
- if observation_request != 'on_widget_disposed' && radios.first&.can_handle_observation_request?(observation_request)
62
- radios.each do |radio|
63
- radio_block = lambda do |event|
64
- if event.widget.selection || selection_index == -1
65
+ if observation_request != 'on_widget_disposed'
66
+ radios.count.times do |index|
67
+ radio = radios[index]
68
+ label = labels[index]
69
+ if observation_request == 'on_widget_selected'
70
+ radio_block = lambda do |event|
71
+ if event.widget.selection || selection_index == -1
72
+ event.widget = self.swt_widget
73
+ block.call(event)
74
+ end
75
+ end
76
+ label_block = lambda do |event|
77
+ self.selection_index = index
78
+ block.call(event)
79
+ end
80
+ radio.handle_observation_request(observation_request, &radio_block) if radio.can_handle_observation_request?(observation_request)
81
+ label.handle_observation_request('on_mouse_up', &label_block)
82
+ else
83
+ listener_block = lambda do |event|
65
84
  event.widget = self.swt_widget
66
85
  block.call(event)
67
86
  end
87
+ radio.handle_observation_request(observation_request, &listener_block) if radio.can_handle_observation_request?(observation_request)
88
+ label.handle_observation_request(observation_request, &listener_block) if label.can_handle_observation_request?(observation_request)
68
89
  end
69
- radio.handle_observation_request(observation_request, &block)
70
90
  end
71
91
  end
72
92
  end
@@ -75,18 +95,52 @@ module Glimmer
75
95
  @observation_requests ||= Set.new
76
96
  end
77
97
 
98
+ def has_attribute?(attribute_name, *args)
99
+ (@composites.to_a + @radios.to_a + @labels.to_a).map do |widget_proxy|
100
+ return true if widget_proxy.has_attribute?(attribute_name, *args)
101
+ end
102
+ super
103
+ end
104
+
105
+ def set_attribute(attribute_name, *args)
106
+ excluded_attributes = ['selection']
107
+ unless excluded_attributes.include?(attribute_name.to_s)
108
+ (@composites.to_a + @radios.to_a + @labels.to_a).each do |widget_proxy|
109
+ widget_proxy.set_attribute(attribute_name, *args) if widget_proxy.has_attribute?(attribute_name, *args)
110
+ end
111
+ end
112
+ super
113
+ end
114
+
78
115
  private
79
116
 
80
117
  def build_radios
81
- # TODO consider doing a diff instead of disposing and rebuilding everything in the future
82
- # TODO add labels since they are better customizable with fonts while maintaining alignment with radio buttons
83
118
  current_selection = selection
84
- radios.each(&:dispose) # TODO take care of the fact that dispose removes the observers attached
119
+ @composites.to_a.each(&:dispose)
85
120
  @radios = []
121
+ @labels = []
122
+ @composites = []
86
123
  items.each do |item|
87
124
  body_root.content {
88
- radios << radio {
89
- text item
125
+ @composites << composite {
126
+ grid_layout(2, false) {
127
+ margin_width 0
128
+ margin_height 0
129
+ horizontal_spacing 0
130
+ vertical_spacing 0
131
+ }
132
+ radios << radio { |radio_proxy|
133
+ on_widget_selected {
134
+ self.selection = items[radios.index(radio_proxy)]
135
+ }
136
+ }
137
+ labels << label { |label_proxy|
138
+ layout_data :fill, :center, true, false
139
+ text item
140
+ on_mouse_up {
141
+ self.selection = label_proxy.text
142
+ }
143
+ }
90
144
  }
91
145
  }
92
146
  end
@@ -61,7 +61,6 @@ module Glimmer
61
61
 
62
62
  def post_add_content
63
63
  @swt_expand_item.setHeight(swt_widget.computeSize(SWTProxy[:default], SWTProxy[:default]).y) unless @swt_expand_item.getHeight > 0
64
- WidgetProxy.new('composite', self, []) # adding filler since it seems like the last child gets a bad style, so this gets it instead
65
64
  end
66
65
 
67
66
  def has_attribute?(attribute_name, *args)
@@ -50,6 +50,7 @@ module Glimmer
50
50
  'check' => [:check],
51
51
  'drag_source' => [:drop_copy],
52
52
  'drop_target' => [:drop_copy],
53
+ 'expand_bar' => [:v_scroll],
53
54
  'list' => [:border, :v_scroll],
54
55
  'menu_item' => [:push],
55
56
  'radio' => [:radio],
@@ -61,7 +62,6 @@ module Glimmer
61
62
  'toggle' => [:toggle],
62
63
  'tool_bar' => [:push],
63
64
  'tool_item' => [:push],
64
- 'expand_bar' => [:v_scroll],
65
65
  'tree' => [:virtual, :border, :h_scroll, :v_scroll],
66
66
  }
67
67
 
@@ -91,11 +91,11 @@ module Glimmer
91
91
  }
92
92
 
93
93
  KEYWORD_ALIASES = {
94
- 'radio' => 'button',
94
+ 'arrow' => 'button',
95
95
  'checkbox' => 'button',
96
96
  'check' => 'button',
97
+ 'radio' => 'button',
97
98
  'toggle' => 'button',
98
- 'arrow' => 'button',
99
99
  }
100
100
 
101
101
  class << self
@@ -20,7 +20,7 @@ class Sample
20
20
  end
21
21
 
22
22
  def content
23
- @content ||= File.read(file)
23
+ @content = File.read(file)
24
24
  end
25
25
 
26
26
  def launch
@@ -58,12 +58,12 @@ class SampleDirectory
58
58
 
59
59
  def all_samples
60
60
  @all_samples ||= sample_directories.map(&:samples).reduce(:+)
61
- end
61
+ end
62
62
  end
63
63
 
64
64
  include Glimmer # used for observe syntax
65
65
 
66
- attr_accessor :file
66
+ attr_accessor :file, :selected_sample_name
67
67
 
68
68
  def initialize(file)
69
69
  self.file = file
@@ -92,7 +92,20 @@ class SampleDirectory
92
92
  end
93
93
  end
94
94
  @samples
95
- end
95
+ end
96
+
97
+ def selected_sample_name_options
98
+ samples.map(&:name)
99
+ end
100
+
101
+ def selected_sample_name=(selected_name)
102
+ @selected_sample_name = selected_name
103
+ unless selected_name.nil?
104
+ (self.class.sample_directories - [self]).each { |sample_dir| sample_dir.selected_sample_name = nil }
105
+ self.class.selected_sample = samples.detect { |sample| sample.name == @selected_sample_name }
106
+ end
107
+ end
108
+
96
109
  end
97
110
 
98
111
  class MetaSampleApplication
@@ -114,26 +127,18 @@ class MetaSampleApplication
114
127
  expand_bar {
115
128
  layout_data(:fill, :fill, true, true)
116
129
  font height: 30
117
-
130
+
118
131
  SampleDirectory.sample_directories.each { |sample_directory|
119
132
  expand_item {
120
133
  layout_data(:fill, :fill, true, true)
121
- grid_layout 2, false
122
134
  text "#{sample_directory.name} Samples"
123
135
 
124
- sample_directory.samples.each { |sample|
125
- label_radio = radio {
126
- selection bind(sample, :selected)
127
- }
128
- label {
129
- layout_data :fill, :center, true, false
130
- text sample.name
131
- font height: 24
132
-
133
- on_mouse_up {
134
- sample.selected = true
135
- }
136
+ radio_group { |radio_group_proxy|
137
+ row_layout(:vertical) {
138
+ fill true
136
139
  }
140
+ selection bind(sample_directory, :selected_sample_name)
141
+ font height: 24
137
142
  }
138
143
  }
139
144
  }
@@ -157,7 +162,7 @@ class MetaSampleApplication
157
162
  caret nil
158
163
  }
159
164
 
160
- weights 1, 2
165
+ weights 4, 9
161
166
  }
162
167
  }.open
163
168
  end
@@ -19,22 +19,22 @@
19
19
  # OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
20
  # WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
21
21
 
22
- class Person
23
- attr_accessor :skiing, :snowboarding, :snowmobiling, :snowshoeing
24
-
25
- def initialize
26
- reset_activities
22
+ class HelloCheckbox
23
+ class Person
24
+ attr_accessor :skiing, :snowboarding, :snowmobiling, :snowshoeing
25
+
26
+ def initialize
27
+ reset_activities
28
+ end
29
+
30
+ def reset_activities
31
+ self.skiing = false
32
+ self.snowboarding = true
33
+ self.snowmobiling = false
34
+ self.snowshoeing = false
35
+ end
27
36
  end
28
37
 
29
- def reset_activities
30
- self.skiing = false
31
- self.snowboarding = true
32
- self.snowmobiling = false
33
- self.snowshoeing = false
34
- end
35
- end
36
-
37
- class HelloCheckbox
38
38
  include Glimmer
39
39
 
40
40
  def launch
@@ -0,0 +1,68 @@
1
+ # Copyright (c) 2007-2020 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
+ class HelloCheckboxGroup
23
+ class Person
24
+ attr_accessor :activities
25
+
26
+ def initialize
27
+ reset_activities
28
+ end
29
+
30
+ def activities_options
31
+ ['Skiing', 'Snowboarding', 'Snowmobiling', 'Snowshoeing']
32
+ end
33
+
34
+ def reset_activities
35
+ self.activities = ['Snowboarding']
36
+ end
37
+ end
38
+
39
+ include Glimmer
40
+
41
+ def launch
42
+ person = Person.new
43
+
44
+ shell {
45
+ text 'Hello, Checkbox Group!'
46
+ row_layout :vertical
47
+
48
+ label {
49
+ text 'Check all snow activities you are interested in:'
50
+ font style: :bold
51
+ }
52
+
53
+ checkbox_group {
54
+ selection bind(person, :activities)
55
+ }
56
+
57
+ button {
58
+ text 'Reset Activities'
59
+
60
+ on_widget_selected do
61
+ person.reset_activities
62
+ end
63
+ }
64
+ }.open
65
+ end
66
+ end
67
+
68
+ HelloCheckboxGroup.new.launch
@@ -19,20 +19,20 @@
19
19
  # OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
20
  # WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
21
21
 
22
- class Person
23
- attr_accessor :country, :country_options
24
-
25
- def initialize
26
- self.country_options = ['', 'Canada', 'US', 'Mexico']
27
- reset_country
28
- end
29
-
30
- def reset_country
31
- self.country = 'Canada'
22
+ class HelloCombo
23
+ class Person
24
+ attr_accessor :country, :country_options
25
+
26
+ def initialize
27
+ self.country_options = ['', 'Canada', 'US', 'Mexico']
28
+ reset_country
29
+ end
30
+
31
+ def reset_country
32
+ self.country = 'Canada'
33
+ end
32
34
  end
33
- end
34
35
 
35
- class HelloCombo
36
36
  include Glimmer
37
37
 
38
38
  def launch
@@ -55,6 +55,7 @@ class HelloExpandBar
55
55
  button {
56
56
  text 'Database'
57
57
  }
58
+ composite # just filler
58
59
  }
59
60
 
60
61
  expand_item {
@@ -72,6 +73,7 @@ class HelloExpandBar
72
73
  button {
73
74
  text 'Scientific Calculator'
74
75
  }
76
+ composite # just filler
75
77
  }
76
78
 
77
79
  expand_item {
@@ -89,6 +91,7 @@ class HelloExpandBar
89
91
  button {
90
92
  text 'Papers'
91
93
  }
94
+ composite # just filler
92
95
  }
93
96
 
94
97
  on_item_expanded { |expand_event|
@@ -99,7 +102,6 @@ class HelloExpandBar
99
102
  @status_label.text = "#{expand_event.item.text} Collapsed!"
100
103
  }
101
104
 
102
-
103
105
  }
104
106
  }.open
105
107
  end
@@ -19,30 +19,30 @@
19
19
  # OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
20
  # WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
21
21
 
22
- class Person
23
- attr_accessor :provinces, :provinces_options
24
-
25
- def initialize
26
- self.provinces_options=[
27
- "",
28
- "Quebec",
29
- "Ontario",
30
- "Manitoba",
31
- "Saskatchewan",
32
- "Alberta",
33
- "British Columbia",
34
- "Nova Skotia",
35
- "Newfoundland"
36
- ]
37
- self.provinces = ["Quebec", "Manitoba", "Alberta"]
38
- end
39
-
40
- def reset_provinces
41
- self.provinces = ["Quebec", "Manitoba", "Alberta"]
42
- end
43
- end
44
-
45
22
  class HelloListMultiSelection
23
+ class Person
24
+ attr_accessor :provinces, :provinces_options
25
+
26
+ def initialize
27
+ self.provinces_options=[
28
+ "",
29
+ "Quebec",
30
+ "Ontario",
31
+ "Manitoba",
32
+ "Saskatchewan",
33
+ "Alberta",
34
+ "British Columbia",
35
+ "Nova Skotia",
36
+ "Newfoundland"
37
+ ]
38
+ self.provinces = ["Quebec", "Manitoba", "Alberta"]
39
+ end
40
+
41
+ def reset_provinces
42
+ self.provinces = ["Quebec", "Manitoba", "Alberta"]
43
+ end
44
+ end
45
+
46
46
  include Glimmer
47
47
 
48
48
  def launch
@@ -19,21 +19,22 @@
19
19
  # OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
20
  # WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
21
21
 
22
- class Person
23
- attr_accessor :country, :country_options
24
-
25
- def initialize
26
- self.country_options=["", "Canada", "US", "Mexico"]
27
- self.country = "Canada"
28
- end
29
-
30
- def reset_country
31
- self.country = "Canada"
32
- end
33
- end
34
-
35
22
  class HelloListSingleSelection
23
+ class Person
24
+ attr_accessor :country, :country_options
25
+
26
+ def initialize
27
+ self.country_options=["", "Canada", "US", "Mexico"]
28
+ self.country = "Canada"
29
+ end
30
+
31
+ def reset_country
32
+ self.country = "Canada"
33
+ end
34
+ end
35
+
36
36
  include Glimmer
37
+
37
38
  def launch
38
39
  person = Person.new
39
40
 
@@ -19,25 +19,25 @@
19
19
  # OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
20
  # WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
21
21
 
22
- class Person
23
- attr_accessor :male, :female, :child, :teen, :adult, :senior
24
-
25
- def initialize
26
- reset
22
+ class HelloRadio
23
+ class Person
24
+ attr_accessor :male, :female, :child, :teen, :adult, :senior
25
+
26
+ def initialize
27
+ reset
28
+ end
29
+
30
+ def reset
31
+ self.male = nil
32
+ self.female = nil
33
+ self.child = nil
34
+ self.teen = nil
35
+ self.adult = true
36
+ self.senior = nil
37
+ end
27
38
  end
28
39
 
29
- def reset
30
- self.male = nil
31
- self.female = nil
32
- self.child = nil
33
- self.teen = nil
34
- self.adult = true
35
- self.senior = nil
36
- end
37
- end
38
-
39
- class HelloRadio
40
- include Glimmer
40
+ include Glimmer
41
41
 
42
42
  def launch
43
43
  person = Person.new
@@ -19,28 +19,28 @@
19
19
  # OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
20
  # WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
21
21
 
22
- class Person
23
- attr_accessor :gender, :age_group
24
-
25
- def initialize
26
- reset
27
- end
28
-
29
- def gender_options
30
- ['Male', 'Female']
31
- end
32
-
33
- def age_group_options
34
- ['Child', 'Teen', 'Adult', 'Senior']
35
- end
36
-
37
- def reset
38
- self.gender = nil
39
- self.age_group = 'Adult'
22
+ class HelloRadioGroup
23
+ class Person
24
+ attr_accessor :gender, :age_group
25
+
26
+ def initialize
27
+ reset
28
+ end
29
+
30
+ def gender_options
31
+ ['Male', 'Female']
32
+ end
33
+
34
+ def age_group_options
35
+ ['Child', 'Teen', 'Adult', 'Senior']
36
+ end
37
+
38
+ def reset
39
+ self.gender = nil
40
+ self.age_group = 'Adult'
41
+ end
40
42
  end
41
- end
42
43
 
43
- class HelloRadioGroup
44
44
  include Glimmer
45
45
 
46
46
  def launch
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: glimmer-dsl-swt
3
3
  version: !ruby/object:Gem::Version
4
- version: 4.17.6.0
4
+ version: 4.17.7.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - AndyMaleh
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2020-10-28 00:00:00.000000000 Z
11
+ date: 2020-10-29 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  requirement: !ruby/object:Gem::Requirement
@@ -345,6 +345,7 @@ files:
345
345
  - lib/glimmer/dsl/swt/async_exec_expression.rb
346
346
  - lib/glimmer/dsl/swt/bind_expression.rb
347
347
  - lib/glimmer/dsl/swt/block_property_expression.rb
348
+ - lib/glimmer/dsl/swt/checkbox_group_selection_data_binding_expression.rb
348
349
  - lib/glimmer/dsl/swt/color_expression.rb
349
350
  - lib/glimmer/dsl/swt/column_properties_expression.rb
350
351
  - lib/glimmer/dsl/swt/combo_selection_data_binding_expression.rb
@@ -386,6 +387,7 @@ files:
386
387
  - lib/glimmer/rake_task/scaffold.rb
387
388
  - lib/glimmer/swt/color_proxy.rb
388
389
  - lib/glimmer/swt/cursor_proxy.rb
390
+ - lib/glimmer/swt/custom/checkbox_group.rb
389
391
  - lib/glimmer/swt/custom/code_text.rb
390
392
  - lib/glimmer/swt/custom/radio_group.rb
391
393
  - lib/glimmer/swt/display_proxy.rb
@@ -425,6 +427,7 @@ files:
425
427
  - samples/elaborate/user_profile.rb
426
428
  - samples/hello/hello_browser.rb
427
429
  - samples/hello/hello_checkbox.rb
430
+ - samples/hello/hello_checkbox_group.rb
428
431
  - samples/hello/hello_combo.rb
429
432
  - samples/hello/hello_computed.rb
430
433
  - samples/hello/hello_computed/contact.rb