glimmer-dsl-libui 0.0.28 → 0.1.0

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: 54faaec785d114536e8b747aa55f7d7bd043339e99f041722d60d70623a9b648
4
- data.tar.gz: 9391f99834f34e2b878b2dbf41b7a8ff3f1ab58daf003acdf33a4f93a2e0777c
3
+ metadata.gz: f0e5255370f70684a7f60de75fe52399f604761996059b23370ce53c4e11cdd1
4
+ data.tar.gz: 00fe32154a83c206843d2386406cde3841da5296cb432585d8aedf421578c47c
5
5
  SHA512:
6
- metadata.gz: 8f2d65ebb19e77c5fab1e037c751af43635a03b07671c8e03ac507bf4e01c04e37c083ffe91a4b18796505801e0d77d84770d0aa13951785422db6ae3c11830f
7
- data.tar.gz: 34965b3e01a55733b767dccb4356b4902627a55fd6843295c76fc473a4b049456c7ee59df12bfc9f61541668b763a394d1fb43955f057f6cc8f6a4f72a2ae6b3
6
+ metadata.gz: 92ef8efbe6d9563dcf20affce754ea4f8fd6ee3eceec014f7499a8ea15631e0127877526ca313513129aee506dc9b363651dde235e2e965a456ddcb2df29c7ae
7
+ data.tar.gz: 9ceec5135f065862bfc7590883346dc0930380da5e12f6b575a5c4a6c1c6d45e7d575392daf0b003cf78889a5c90cc4033cd48783e1a6c2cd5f4e53d4814b009
data/CHANGELOG.md CHANGED
@@ -1,5 +1,14 @@
1
1
  # Change Log
2
2
 
3
+ ## 0.1.0
4
+
5
+ - Support examples/basic_area.rb
6
+ - Support `area` control
7
+ - Support `path(fill_mode)` control
8
+ - Support `rectangle(x, y, width, height)` figure
9
+ - Support `path` `fill` property
10
+ - Support `path` `stroke` property
11
+
3
12
  ## 0.0.28
4
13
 
5
14
  - Support automatic table row change when updating a row in `cell_rows` (e.g. `data[3] = ['new', 'row', 'cell', 'values']`)
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 LibUI 0.0.28
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 LibUI 0.1.0
2
2
  ## Prerequisite-Free Ruby Desktop Development GUI Library
3
3
  [![Gem Version](https://badge.fury.io/rb/glimmer-dsl-libui.svg)](http://badge.fury.io/rb/glimmer-dsl-libui)
4
4
  [![Maintainability](https://api.codeclimate.com/v1/badges/ce2853efdbecf6ebdc73/maintainability)](https://codeclimate.com/github/AndyObtiva/glimmer-dsl-libui/maintainability)
@@ -43,7 +43,7 @@ Other [Glimmer](https://rubygems.org/gems/glimmer) DSL gems you might be interes
43
43
 
44
44
  ## Table of Contents
45
45
 
46
- - [Glimmer DSL for LibUI 0.0.28](#-glimmer-dsl-for-libui-0028)
46
+ - [Glimmer DSL for LibUI 0.1.0](#-glimmer-dsl-for-libui-010)
47
47
  - [Glimmer GUI DSL Concepts](#glimmer-gui-dsl-concepts)
48
48
  - [Usage](#usage)
49
49
  - [API](#api)
@@ -53,6 +53,7 @@ Other [Glimmer](https://rubygems.org/gems/glimmer) DSL gems you might be interes
53
53
  - [Extra Dialogs](#extra-dialogs)
54
54
  - [Extra Operations](#extra-operations)
55
55
  - [Table API](#table-api)
56
+ - [Area API](#area-api)
56
57
  - [Smart Defaults and Conventions](#smart-defaults-and-conventions)
57
58
  - [API Gotchas](#api-gotchas)
58
59
  - [Original API](#original-api)
@@ -80,6 +81,7 @@ Other [Glimmer](https://rubygems.org/gems/glimmer) DSL gems you might be interes
80
81
  - [Basic Table Checkbox Text](#basic-table-checkbox-text)
81
82
  - [Basic Table Progress Bar](#basic-table-progress-bar)
82
83
  - [Form Table](#form-table)
84
+ - [Basic Area](#basic-area)
83
85
  - [Contributing to glimmer-dsl-libui](#contributing-to-glimmer-dsl-libui)
84
86
  - [Help](#help)
85
87
  - [Issues](#issues)
@@ -167,7 +169,7 @@ gem install glimmer-dsl-libui
167
169
  Or install via Bundler `Gemfile`:
168
170
 
169
171
  ```ruby
170
- gem 'glimmer-dsl-libui', '~> 0.0.28'
172
+ gem 'glimmer-dsl-libui', '~> 0.1.0'
171
173
  ```
172
174
 
173
175
  Add `require 'glimmer-dsl-libui'` at the top, and then `include Glimmer` into the top-level main object for testing or into an actual class for serious usage.
@@ -223,11 +225,12 @@ w.libui # => #<Fiddle::Pointer:0x00007fde53997980 ptr=0x00007fde51352a60 size=0
223
225
  Control(Args) | Properties | Listeners
224
226
  ------------- | ---------- | ---------
225
227
  `about_menu_item` | None | `on_clicked`
228
+ `area` | None | None
226
229
  `button(text as String)` | `text` (`String`) | `on_clicked`
227
230
  `button_column(name as String)` | `enabled` (Boolean) | None
228
231
  `checkbox(text as String)` | `checked` (Boolean), `text` (`String`) | `on_toggled`
229
- `checkbox_column(name as String)` | `editable` (Boolean) [Windows-only due to a current libui limitation] | None
230
- `checkbox_text_column(name as String)` | `editable` (Boolean) [Windows-only due to a current libui limitation], `editable_checkbox` (Boolean) [Windows-only due to a current libui limitation], `editable_text` (Boolean) | None
232
+ `checkbox_column(name as String)` | `editable` (Boolean) | None
233
+ `checkbox_text_column(name as String)` | `editable` (Boolean), `editable_checkbox` (Boolean), `editable_text` (Boolean) | None
231
234
  `combobox` | `items` (`Array` of `String`), `selected` (`Integer`) | `on_selected`
232
235
  `color_button` | `color` (Array of `red` as `Float`, `green` as `Float`, `blue` as `Float`, `alpha` as `Float`), `red` as `Float`, `green` as `Float`, `blue` as `Float`, `alpha` as `Float` | `on_changed`
233
236
  `date_picker` | `time` (`Hash` of keys: `sec` as `Integer`, `min` as `Integer`, `hour` as `Integer`, `mday` as `Integer`, `mon` as `Integer`, `year` as `Integer`, `wday` as `Integer`, `yday` as `Integer`, `dst` as Boolean) | `on_changed`
@@ -251,11 +254,13 @@ Control(Args) | Properties | Listeners
251
254
  `msg_box(window as Glimmer::LibUI::WindowProxy, title as String, description as String)` | None | None
252
255
  `msg_box_error(window as Glimmer::LibUI::WindowProxy, title as String, description as String)` | None | None
253
256
  `non_wrapping_multiline_entry` | `read_only` (Boolean), `text` (`String`) | `on_changed`
257
+ `path` | `fill` (`Hash` of `:r` as `0`-`255`, `:g` as `0`-`255`, `:b` as `0`-`255`, `:a` as `0.0`-`1.0`), `stroke` (`Hash` of `:r` as `0`-`255`, `:g` as `0`-`255`, `:b` as `0`-`255`, `:a` as `0.0`-`1.0`, `:cap` as `Numeric`, `:join` as `Numeric`, `:thickness` as `Numeric`, `:miter_limit` as `Numeric` ) | None
254
258
  `preferences_menu_item` | None | `on_clicked`
255
259
  `progress_bar` | `value` (`Numeric`) | None
256
260
  `progress_bar_column(name as String)` | None | None
257
261
  `quit_menu_item` | None | `on_clicked`
258
262
  `radio_buttons` | `selected` (`Integer`) | `on_selected`
263
+ `rectangle(x as Numeric, y as Numeric, width as Numeric, height as Numeric)` | None | None
259
264
  `slider(min as Numeric, max as Numeric)` | `value` (`Numeric`) | `on_changed`
260
265
  `spinbox(min as Numeric, max as Numeric)` | `value` (`Numeric`) | `on_changed`
261
266
  `tab` | `margined` (Boolean), `num_pages` (`Integer`) | None
@@ -321,6 +326,10 @@ Note that the `cell_rows` property declaration results in "implicit data-binding
321
326
  - Inserting cell rows: Calling `Array#<<`, `Array#push`, `Array#prepend`, or any insertion/addition `Array` method automatically inserts rows in actual `table` control
322
327
  - Changing cell rows: Calling `Array#[]=`, `Array#map!`, or any update `Array` method automatically updates rows in actual `table` control
323
328
 
329
+ ### Area API
330
+
331
+ The `area` control can have a `path` nested underneath declaratively, containing figures like `rectangle`, and all the drawing logic is generated automatically from that.
332
+
324
333
  ### Smart Defaults and Conventions
325
334
 
326
335
  - `horizontal_box`, `vertical_box`, `grid`, and `form` controls have `padded` as `true` upon instantiation to ensure more user-friendly GUI by default
@@ -349,11 +358,12 @@ Note that the `cell_rows` property declaration results in "implicit data-binding
349
358
  - Table `cell_rows` data has implicit data-binding to table cell values for deletion, insertion, and change (done by diffing `cell_rows` value before and after change and auto-informing `table` of deletions [`LibUI.table_model_row_deleted`], insertions [`LibUI.table_model_row_deleted`], and changes [`LibUI.table_model_row_changed`]). When deleting data rows from `cell_rows` array, then actual rows from the `table` are automatically deleted. When inserting data rows into `cell_rows` array, then actual `table` rows are automatically inserted. When updating data rows in `cell_rows` array, then actual `table` rows are automatically updated.
350
359
  - `image` instances are automatically freed from memory after `window` is destroyed.
351
360
  - `image` `width` and `height` can be left off if it has one `image_part` only as they default to the same `width` and `height` of the `image_part`
361
+ - `area` paths are specified declaratively with figures underneath (e.g. `rectangle`) and `area` draw listener is automatically generated
352
362
 
353
363
  ### API Gotchas
354
364
 
355
365
  - There is no proper way to destroy `grid` children due to [libui](https://github.com/andlabs/libui) not offering any API for deleting them from `grid` (no `grid_delete` similar to `box_delete` for `horizontal_box` and `vertical_box`).
356
- - `table` `checkbox_column` and `checkbox_text_column` checkbox editing currently only works in Windows due to a current limitation in [libui](https://github.com/andlabs/libui).
366
+ - `table` `checkbox_column` and `checkbox_text_column` checkbox editing only works on Windows and Linux (not Mac) due to a current limitation in [libui](https://github.com/andlabs/ui/issues/357).
357
367
 
358
368
  ### Original API
359
369
 
@@ -2581,6 +2591,104 @@ window('Contacts', 600, 600) { |w|
2581
2591
  }.show
2582
2592
  ```
2583
2593
 
2594
+ ### Basic Area
2595
+
2596
+ [examples/basic_area.rb](examples/basic_area.rb)
2597
+
2598
+ Run with this command from the root of the project if you cloned the project:
2599
+
2600
+ ```
2601
+ ruby -r './lib/glimmer-dsl-libui' examples/basic_area.rb
2602
+ ```
2603
+
2604
+ Run with this command if you installed the [Ruby gem](https://rubygems.org/gems/glimmer-dsl-libui):
2605
+
2606
+ ```
2607
+ ruby -r glimmer-dsl-libui -e "require 'examples/basic_area'"
2608
+ ```
2609
+
2610
+ Mac
2611
+
2612
+ ![glimmer-dsl-libui-mac-basic-area.png](images/glimmer-dsl-libui-mac-basic-area.png)
2613
+
2614
+ Linux
2615
+
2616
+ ![glimmer-dsl-libui-linux-basic-area.png](images/glimmer-dsl-libui-linux-basic-area.png)
2617
+
2618
+ [LibUI](https://github.com/kojix2/LibUI) Original Version:
2619
+
2620
+ ```ruby
2621
+ require 'libui'
2622
+
2623
+ UI = LibUI
2624
+
2625
+ UI.init
2626
+
2627
+ handler = UI::FFI::AreaHandler.malloc
2628
+ area = UI.new_area(handler)
2629
+ brush = UI::FFI::DrawBrush.malloc
2630
+
2631
+ handler_draw_event = Fiddle::Closure::BlockCaller.new(0, [1, 1, 1]) do |_, _, area_draw_params|
2632
+ path = UI.draw_new_path(0)
2633
+ UI.draw_path_add_rectangle(path, 0, 0, 400, 400)
2634
+ UI.draw_path_end(path)
2635
+ brush.Type = 0
2636
+ brush.R = 0.4
2637
+ brush.G = 0.4
2638
+ brush.B = 0.8
2639
+ brush.A = 1.0
2640
+ area_draw_params = UI::FFI::AreaDrawParams.new(area_draw_params)
2641
+ UI.draw_fill(area_draw_params.Context, path, brush.to_ptr)
2642
+ UI.draw_free_path(path)
2643
+ end
2644
+
2645
+ handler.Draw = handler_draw_event
2646
+ handler.MouseEvent = Fiddle::Closure::BlockCaller.new(0, [0]) {}
2647
+ handler.MouseCrossed = Fiddle::Closure::BlockCaller.new(0, [0]) {}
2648
+ handler.DragBroken = Fiddle::Closure::BlockCaller.new(0, [0]) {}
2649
+ handler.KeyEvent = Fiddle::Closure::BlockCaller.new(0, [0]) {}
2650
+
2651
+ box = UI.new_vertical_box
2652
+ UI.box_set_padded(box, 1)
2653
+ UI.box_append(box, area, 1)
2654
+
2655
+ main_window = UI.new_window('Basic Area', 400, 400, 1)
2656
+ UI.window_set_margined(main_window, 1)
2657
+ UI.window_set_child(main_window, box)
2658
+
2659
+ UI.window_on_closing(main_window) do
2660
+ UI.control_destroy(main_window)
2661
+ UI.quit
2662
+ 0
2663
+ end
2664
+ UI.control_show(main_window)
2665
+
2666
+ UI.main
2667
+ UI.quit
2668
+ ```
2669
+
2670
+ [Glimmer DSL for LibUI](https://rubygems.org/gems/glimmer-dsl-libui) Version:
2671
+
2672
+ ```ruby
2673
+ require 'glimmer-dsl-libui'
2674
+
2675
+ include Glimmer
2676
+
2677
+ window('Basic Area', 400, 400) {
2678
+ margined true
2679
+
2680
+ vertical_box {
2681
+ area {
2682
+ path { # a stable path is added declaratively
2683
+ rectangle(0, 0, 400, 400)
2684
+
2685
+ fill r: 102, g: 102, b: 204, a: 1.0
2686
+ }
2687
+ }
2688
+ }
2689
+ }.show
2690
+ ```
2691
+
2584
2692
  ## Contributing to glimmer-dsl-libui
2585
2693
 
2586
2694
  - Check out the latest master to make sure the feature hasn't been
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.0.28
1
+ 0.1.0
@@ -0,0 +1,17 @@
1
+ require 'glimmer-dsl-libui'
2
+
3
+ include Glimmer
4
+
5
+ window('Basic Area', 400, 400) {
6
+ margined true
7
+
8
+ vertical_box {
9
+ area {
10
+ path { # a stable path is added declaratively
11
+ rectangle(0, 0, 400, 400)
12
+
13
+ fill r: 102, g: 102, b: 204, a: 1.0
14
+ }
15
+ }
16
+ }
17
+ }.show
Binary file
@@ -0,0 +1,33 @@
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
+ module Glimmer
23
+ module FiddleConsumer
24
+ # Protects Fiddle::Closure::BlockCaller objects from garbage collection.
25
+ def fiddle_closure_block_caller(*args, &block)
26
+ @blockcaller ||= []
27
+ args << [0] if args.size == 1 # Argument types are ommited
28
+ blockcaller = ::Fiddle::Closure::BlockCaller.new(*args, &block)
29
+ @blockcaller << blockcaller
30
+ blockcaller
31
+ end
32
+ end
33
+ end
@@ -0,0 +1,68 @@
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/libui/control_proxy'
23
+ require 'glimmer/fiddle_consumer'
24
+
25
+ module Glimmer
26
+ module LibUI
27
+ # Proxy for LibUI area objects
28
+ #
29
+ # Follows the Proxy Design Pattern
30
+ class AreaProxy < ControlProxy
31
+ include Glimmer::FiddleConsumer
32
+
33
+ attr_reader :area_handler
34
+
35
+ def post_initialize_child(child)
36
+ super
37
+ children << child
38
+ end
39
+
40
+ def post_add_content
41
+ super
42
+ install_listeners
43
+ end
44
+
45
+ def children
46
+ @children ||= []
47
+ end
48
+
49
+ private
50
+
51
+ def build_control
52
+ @area_handler = ::LibUI::FFI::AreaHandler.malloc
53
+ @libui = ::LibUI.new_area(@area_handler)
54
+ end
55
+
56
+ def install_listeners
57
+ @area_handler.Draw = fiddle_closure_block_caller(0, [1, 1, 1]) do |_, _, area_draw_params|
58
+ area_draw_params = ::LibUI::FFI::AreaDrawParams.new(area_draw_params)
59
+ children.each {|child| child.draw(area_draw_params)}
60
+ end
61
+ @area_handler.MouseEvent = fiddle_closure_block_caller(0, [0]) {}
62
+ @area_handler.MouseCrossed = fiddle_closure_block_caller(0, [0]) {}
63
+ @area_handler.DragBroken = fiddle_closure_block_caller(0, [0]) {}
64
+ @area_handler.KeyEvent = fiddle_closure_block_caller(0, [0]) {}
65
+ end
66
+ end
67
+ end
68
+ end
@@ -0,0 +1,141 @@
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/libui/control_proxy'
23
+
24
+ module Glimmer
25
+ module LibUI
26
+ # Proxy for LibUI path objects
27
+ #
28
+ # Follows the Proxy Design Pattern
29
+ class PathProxy < ControlProxy
30
+ # TODO support mode without parent proxy
31
+ def initialize(keyword, parent, args, &block)
32
+ @keyword = keyword
33
+ @parent_proxy = parent
34
+ @args = args
35
+ @block = block
36
+ @enabled = true
37
+ post_add_content if @block.nil?
38
+ end
39
+
40
+ def post_initialize_child(child)
41
+ super
42
+ children << child
43
+ end
44
+
45
+ def children
46
+ @children ||= []
47
+ end
48
+
49
+ def draw(area_draw_params)
50
+ build_control
51
+ children.each {|child| child.draw(area_draw_params)}
52
+ ::LibUI.draw_path_end(@libui)
53
+ ::LibUI.draw_fill(area_draw_params.Context, @libui, fill_draw_brush.to_ptr) unless fill.empty?
54
+ ::LibUI.draw_stroke(area_draw_params.Context, @libui, stroke_draw_brush, draw_stroke_params) unless stroke.empty?
55
+ ::LibUI.draw_free_path(@libui)
56
+ end
57
+
58
+ def draw_fill_mode
59
+ @args[0].is_a?(Integer) ? @args[0] : @args[0].to_s == 'alternate' ? 1 : 0
60
+ end
61
+
62
+ def fill(args = nil)
63
+ if args.nil?
64
+ @fill ||= {}
65
+ else
66
+ @fill = args
67
+ end
68
+ end
69
+ alias fill= fill
70
+ alias set_fill fill
71
+
72
+ def fill_draw_brush
73
+ @fill_draw_brush ||= ::LibUI::FFI::DrawBrush.malloc
74
+ init_draw_brush(@fill_draw_brush, @fill)
75
+ @fill_draw_brush
76
+ end
77
+
78
+ def stroke(args = nil)
79
+ if args.nil?
80
+ @stroke ||= {}
81
+ else
82
+ @stroke = args
83
+ end
84
+ end
85
+ alias stroke= stroke
86
+ alias set_stroke stroke
87
+
88
+ def stroke_draw_brush
89
+ @stroke_draw_brush ||= ::LibUI::FFI::DrawBrush.malloc
90
+ init_draw_brush(@stroke_draw_brush, @stroke)
91
+ @stroke_draw_brush
92
+ end
93
+
94
+ def draw_stroke_params
95
+ @draw_stroke_params ||= ::LibUI::FFI::DrawStrokeParams.malloc
96
+ @draw_stroke_params.Cap = @stroke[:cap] || 0 # flat
97
+ @draw_stroke_params.Join = @stroke[:join] || 0 # miter
98
+ @draw_stroke_params.Thickness = @stroke[:thickness] || 1
99
+ @draw_stroke_params.MiterLimit = @stroke[:miter_limit] || 10 # DEFAULT_MITER_LIMIT
100
+ @draw_stroke_params_dashes ||= Fiddle::Pointer.malloc(8)
101
+ @draw_stroke_params.Dashes = @draw_stroke_params_dashes
102
+ @draw_stroke_params.NumDashes = @stroke[:num_dashes] || 0 # TODO reimplement this line correctly (perhaps no need to pass num dashes, yet dashes themselves and use their count here)
103
+ @draw_stroke_params.DashPhase = @stroke[:dash_phase] || 0
104
+ @draw_stroke_params
105
+ end
106
+
107
+ def destroy
108
+ if @parent_proxy
109
+ @parent_proxy.children.delete(self)
110
+ end
111
+ end
112
+
113
+ private
114
+
115
+ def build_control
116
+ @libui = ::LibUI.draw_new_path(draw_fill_mode)
117
+ end
118
+
119
+ def init_draw_brush(draw_brush, draw_brush_args)
120
+ case draw_brush_args[:type]
121
+ when Integer
122
+ draw_brush.Type = draw_brush_args[:type]
123
+ when :solid, 'solid'
124
+ draw_brush.Type = 0
125
+ when :linear_gradient, 'linear_gradient'
126
+ draw_brush.Type = 1
127
+ when :radial_gradient, 'radial_gradient'
128
+ draw_brush.Type = 2
129
+ when :image, 'image'
130
+ draw_brush.Type = 3
131
+ else
132
+ draw_brush.Type = 0
133
+ end
134
+ draw_brush.R = (draw_brush_args[:r] || draw_brush_args[:red]).to_f / 255.0
135
+ draw_brush.G = (draw_brush_args[:g] || draw_brush_args[:green]).to_f / 255.0
136
+ draw_brush.B = (draw_brush_args[:b] || draw_brush_args[:blue]).to_f / 255.0
137
+ draw_brush.A = (draw_brush_args[:a] || draw_brush_args[:alpha])
138
+ end
139
+ end
140
+ end
141
+ end
@@ -0,0 +1,56 @@
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/libui/control_proxy'
23
+
24
+ module Glimmer
25
+ module LibUI
26
+ # Proxy for LibUI rectangle objects
27
+ #
28
+ # Follows the Proxy Design Pattern
29
+ class RectangleProxy < ControlProxy
30
+ def initialize(keyword, parent, args, &block)
31
+ @keyword = keyword
32
+ @parent_proxy = parent
33
+ @args = args
34
+ @block = block
35
+ @enabled = true
36
+ post_add_content if @block.nil?
37
+ end
38
+
39
+ def draw(area_draw_params)
40
+ ::LibUI.draw_path_add_rectangle(@parent_proxy.libui, *@args)
41
+ end
42
+
43
+ def destroy
44
+ if @parent_proxy
45
+ @parent_proxy.children.delete(self)
46
+ end
47
+ end
48
+
49
+ private
50
+
51
+ def build_control
52
+ # No Op
53
+ end
54
+ end
55
+ end
56
+ end
@@ -21,6 +21,7 @@
21
21
 
22
22
  require 'glimmer/libui/control_proxy'
23
23
  require 'glimmer/data_binding/observer'
24
+ require 'glimmer/fiddle_consumer'
24
25
 
25
26
  using ArrayIncludeMethods
26
27
 
@@ -30,6 +31,8 @@ module Glimmer
30
31
  #
31
32
  # Follows the Proxy Design Pattern
32
33
  class TableProxy < ControlProxy
34
+ include Glimmer::FiddleConsumer
35
+
33
36
  attr_reader :model_handler, :model, :table_params, :columns
34
37
 
35
38
  def initialize(keyword, parent, args, &block)
@@ -112,8 +115,8 @@ module Glimmer
112
115
 
113
116
  def build_control
114
117
  @model_handler = ::LibUI::FFI::TableModelHandler.malloc
115
- @model_handler.NumColumns = rbcallback(4) { @columns.map {|c| c.is_a?(DualColumn) ? 2 : 1}.sum }
116
- @model_handler.ColumnType = rbcallback(4, [1, 1, 4]) do |_, _, column|
118
+ @model_handler.NumColumns = fiddle_closure_block_caller(4) { @columns.map {|c| c.is_a?(DualColumn) ? 2 : 1}.sum }
119
+ @model_handler.ColumnType = fiddle_closure_block_caller(4, [1, 1, 4]) do |_, _, column|
117
120
  case @columns[column]
118
121
  when TextColumnProxy, ButtonColumnProxy, NilClass
119
122
  0
@@ -123,8 +126,8 @@ module Glimmer
123
126
  2
124
127
  end
125
128
  end
126
- @model_handler.NumRows = rbcallback(4) { cell_rows.count }
127
- @model_handler.CellValue = rbcallback(1, [1, 1, 4, 4]) do |_, _, row, column|
129
+ @model_handler.NumRows = fiddle_closure_block_caller(4) { cell_rows.count }
130
+ @model_handler.CellValue = fiddle_closure_block_caller(1, [1, 1, 4, 4]) do |_, _, row, column|
128
131
  the_cell_rows = expanded_cell_rows
129
132
  case @columns[column]
130
133
  when TextColumnProxy, ButtonColumnProxy, NilClass
@@ -137,7 +140,7 @@ module Glimmer
137
140
  ::LibUI.new_table_value_int((expanded_cell_rows[row] && (expanded_cell_rows[row][column].to_i)))
138
141
  end
139
142
  end
140
- @model_handler.SetCellValue = rbcallback(0, [1, 1, 4, 4, 1]) do |_, _, row, column, val|
143
+ @model_handler.SetCellValue = fiddle_closure_block_caller(0, [1, 1, 4, 4, 1]) do |_, _, row, column, val|
141
144
  case @columns[column]
142
145
  when TextColumnProxy
143
146
  column = @columns[column].index
@@ -167,16 +170,6 @@ module Glimmer
167
170
  end
168
171
  end
169
172
 
170
- def rbcallback(*args, &block)
171
- # TODO consider moving to a more general reusable location in the future (e.g. when used with `AreaProxy`)
172
- # Protects BlockCaller objects from garbage collection.
173
- @blockcaller ||= []
174
- args << [0] if args.size == 1 # Argument types are ommited
175
- blockcaller = Fiddle::Closure::BlockCaller.new(*args, &block)
176
- @blockcaller << blockcaller
177
- blockcaller
178
- end
179
-
180
173
  def next_column_index
181
174
  @next_column_index ||= -1
182
175
  @next_column_index += 1
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: glimmer-dsl-libui
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.28
4
+ version: 0.1.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Andy Maleh
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2021-09-27 00:00:00.000000000 Z
11
+ date: 2021-09-28 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: glimmer
@@ -194,6 +194,7 @@ files:
194
194
  - VERSION
195
195
  - bin/girb
196
196
  - bin/girb_runner.rb
197
+ - examples/basic_area.rb
197
198
  - examples/basic_button.rb
198
199
  - examples/basic_entry.rb
199
200
  - examples/basic_table.rb
@@ -227,7 +228,9 @@ files:
227
228
  - lib/glimmer/dsl/libui/property_expression.rb
228
229
  - lib/glimmer/dsl/libui/save_file_expression.rb
229
230
  - lib/glimmer/dsl/libui/tab_item_expression.rb
231
+ - lib/glimmer/fiddle_consumer.rb
230
232
  - lib/glimmer/libui/about_menu_item_proxy.rb
233
+ - lib/glimmer/libui/area_proxy.rb
231
234
  - lib/glimmer/libui/box.rb
232
235
  - lib/glimmer/libui/button_column_proxy.rb
233
236
  - lib/glimmer/libui/button_proxy.rb
@@ -259,10 +262,12 @@ files:
259
262
  - lib/glimmer/libui/menu_proxy.rb
260
263
  - lib/glimmer/libui/multiline_entry_proxy.rb
261
264
  - lib/glimmer/libui/non_wrapping_multiline_entry_proxy.rb
265
+ - lib/glimmer/libui/path_proxy.rb
262
266
  - lib/glimmer/libui/preferences_menu_item_proxy.rb
263
267
  - lib/glimmer/libui/progress_bar_column_proxy.rb
264
268
  - lib/glimmer/libui/quit_menu_item_proxy.rb
265
269
  - lib/glimmer/libui/radio_buttons_proxy.rb
270
+ - lib/glimmer/libui/rectangle_proxy.rb
266
271
  - lib/glimmer/libui/separator_menu_item_proxy.rb
267
272
  - lib/glimmer/libui/tab_item_proxy.rb
268
273
  - lib/glimmer/libui/table_proxy.rb