glimmer-dsl-tk 0.0.41 → 0.0.45
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 +4 -4
- data/CHANGELOG.md +28 -0
- data/README.md +126 -63
- data/VERSION +1 -1
- data/glimmer-dsl-tk.gemspec +0 -0
- data/lib/glimmer/dsl/tk/list_selection_data_binding_expression.rb +1 -1
- data/lib/glimmer/tk/drag_and_drop_extension.rb +39 -9
- data/lib/glimmer/tk/lbl_proxy.rb +33 -0
- data/lib/glimmer/tk/menu_proxy.rb +7 -6
- data/lib/glimmer/tk/root_proxy.rb +1 -1
- data/lib/glimmer/tk/scrollbar_frame_proxy.rb +1 -1
- data/lib/glimmer/tk/widget.rb +28 -0
- data/lib/glimmer/tk/widget_proxy.rb +25 -5
- data/lib/glimmer-dsl-tk.rb +4 -3
- data/lib/os.rb +36 -0
- data/samples/elaborate/meta_sample.rb +10 -0
- data/samples/hello/hello_drag_and_drop.rb +112 -61
- data/samples/hello/hello_menu_bar.rb +3 -8
- data/samples/hello/hello_text.rb +2 -7
- metadata +6 -23
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 0a9655c46ab2b4638e96077e0795a6b7201456baf020ade27838d139797d3a44
|
4
|
+
data.tar.gz: dc2b2924a180df216a16161aa938b4429f814a59f18e0fba945b73eb40513bd6
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: cab872767a730b059ebdaee18a124f0ded5e9fa0d5f980592b2c9fc9a20d756894846a4662b1f20043108987424daf6b79f895df639d1e273b66cad90f8437ae
|
7
|
+
data.tar.gz: 5a92bbe321b0ca538fbebc84d5e076047b2a761294f47be236f041853873c60787ce593dd142e7a5ba9671b9cdc7faaf1ca6d9f41c9a45fed1dde8cc55b5f184
|
data/CHANGELOG.md
CHANGED
@@ -1,5 +1,33 @@
|
|
1
1
|
# Change Log
|
2
2
|
|
3
|
+
## 0.0.45
|
4
|
+
|
5
|
+
- Support `lbl` widget as the non-tile-themed version of `label` (i.e. `::TkLabel` not `::Tk::Tile::TLabel`)
|
6
|
+
- Add `#proxy` method to all Tk widgets to return Glimmer widget proxy objects (e.g. `Tk::Tile::TButton#proxy` returns `Glimmer::Tk::WidgetProxy` object)
|
7
|
+
- Provide question mark alias of `event.drop_accepted` (i.e. `drop_accepted?`)
|
8
|
+
- Have `DragAndDropEvent` `source`/`target` be the enhanced Glimmer widget proxy instead of the unenhanced Tk widget
|
9
|
+
- Look into improving code that uses `TkLabel` explicitly in Hello, Drag and Drop! (do `event.tooltip.content {label {...} }` with Glimmer DSL instead)
|
10
|
+
- Add Glimmer Style Guide
|
11
|
+
- Fix issue with dropping button and list unto checkbox in Hello, Drag and Drop!
|
12
|
+
|
13
|
+
## 0.0.44
|
14
|
+
|
15
|
+
- Fix issue with not being able to drop list into checkbox in Hello, Drag and Drop! by disabling functionality for list just like button
|
16
|
+
|
17
|
+
## 0.0.43
|
18
|
+
|
19
|
+
- Modified Hello, Drag and Drop! to include a list
|
20
|
+
- Removed the need to require `'glimmer/tk/drag_and_drop_extension'` to do drag and drop; it is automatically included in `require 'glimmer-dsl-tk'` now.
|
21
|
+
- Remove 'os' gem due to Tk having the capability to detect the OS it is on using `Tk.windowingsystem` (include Glimmer implementation of `OS` class having `OS.mac?`, `OS.windows?` and `OS.linux?`)
|
22
|
+
- Default to 'clam' Tk theme on Linux ('alt' looks a bit too classic with certain widgets)
|
23
|
+
|
24
|
+
## 0.0.42
|
25
|
+
|
26
|
+
- Add vertical/horizontal scrollbars to Meta-Sample
|
27
|
+
- Keep only vertical scrollbar in Hello, Text!
|
28
|
+
- Fix issue with including bwidgets and iwidgets in Windows (by removing from default requires, leaving to users to require manually when needed only and only systems that support them)
|
29
|
+
- Fix Hello, Menu Bar! sample in Windows (by disabling Windows-special System menu, which does not seem to be working in Tk)
|
30
|
+
|
3
31
|
## 0.0.41
|
4
32
|
|
5
33
|
- Support `scrollbar_frame` Glimmer custom widget as a frame that automatically provides scrollbars when its content's size exceeds its size
|
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 Tk 0.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 Tk 0.0.45
|
2
2
|
## MRI Ruby Desktop Development GUI Library
|
3
3
|
[](http://badge.fury.io/rb/glimmer-dsl-tk)
|
4
4
|
[](https://github.com/AndyObtiva/glimmer-dsl-tk/actions/workflows/ruby.yml)
|
@@ -100,6 +100,7 @@ Other [Glimmer](https://github.com/AndyObtiva/glimmer) DSL gems:
|
|
100
100
|
- [Radiobutton Data-Binding](#radiobutton-data-binding)
|
101
101
|
- [Command Callback](#command-callback)
|
102
102
|
- [Gotchas](#gotchas)
|
103
|
+
- [Glimmer Style Guide](#glimmer-style-guide)
|
103
104
|
- [Samples](#samples)
|
104
105
|
- [Hello, World!](#hello-world)
|
105
106
|
- [Hello, Button!](#hello-button)
|
@@ -181,7 +182,7 @@ gem install glimmer-dsl-tk
|
|
181
182
|
|
182
183
|
Add the following to `Gemfile`:
|
183
184
|
```
|
184
|
-
gem 'glimmer-dsl-tk', '
|
185
|
+
gem 'glimmer-dsl-tk', '0.0.45'
|
185
186
|
```
|
186
187
|
|
187
188
|
And, then run:
|
@@ -225,6 +226,8 @@ The Glimmer GUI DSL follows these simple concepts in mapping from Tk syntax:
|
|
225
226
|
- **Content/Options Block**: Any keyword may optionally be followed by a Ruby curly-brace block containing nested widgets (content) and attributes (options). Attributes are simply Tk option keywords followed by arguments and no block (e.g. `title 'Hello, World!'` under a `root`)
|
226
227
|
- **Event Binding Block**: `on(event) {}` keyword receiving a Tk binding event name (e.g. `KeyPress` or `ComboboxSelected`). Surrounding event by `<>` is optional as [Glimmer DSL for Tk](https://rubygems.org/gems/glimmer-dsl-tk) can take care of that automatically.
|
227
228
|
|
229
|
+
Note that Glimmer widgets are proxy objects (wrappers) for Tk widgets. To get wrapped Tk widget from a Glimmer widget, you simply invoke `#tk` method. To get the proxy of a wrapped Tk widget, you may invoke `#proxy` method.
|
230
|
+
|
228
231
|
Example of an app written in [Tk](https://www.tcl.tk/) imperative syntax:
|
229
232
|
|
230
233
|
```ruby
|
@@ -303,6 +306,7 @@ keyword(args) | attributes | event bindings & callbacks
|
|
303
306
|
`spinbox` | `text`, `from`, `to`, `increment`, `format`, [more attributes](https://tcl.tk/man/tcl8.6/TkCmd/text.htm#M116) | `command {}`, `'increment'`, `'decrement'`
|
304
307
|
`frame(text: nil)` | `width`, `height`, `borderwidth`, `relief` (`'flat' (default), 'raised', 'sunken', 'solid', 'ridge', 'groove'`) | None
|
305
308
|
`label` | `text`, `image` (optional keyword args: `subsample`, `zoom`, `from`, `to`, `shrink`, `compositingrule`), `compound` (`'center', 'top', 'bottom', 'left', 'right'`), `font` (`'default', 'text', 'fixed', 'menu', 'heading', 'caption', 'small_caption', 'icon', 'tooltip'`), `relief` (`'flat' (default), 'raised', 'sunken', 'solid', 'ridge', 'groove'`), `justify` (`'left', 'center', 'right'`), `foreground`, `background` | None
|
309
|
+
`lbl` (non-theme version of `label`) | `text`, `image` (optional keyword args: `subsample`, `zoom`, `from`, `to`, `shrink`, `compositingrule`), `compound` (`'center', 'top', 'bottom', 'left', 'right'`), `font` (`'default', 'text', 'fixed', 'menu', 'heading', 'caption', 'small_caption', 'icon', 'tooltip'`), `relief` (`'flat' (default), 'raised', 'sunken', 'solid', 'ridge', 'groove'`), `justify` (`'left', 'center', 'right'`), `foreground`, `background`, `bg`, `bitmap`, [more here](https://tcl.tk/man/tcl8.6/TkCmd/label.htm) | None
|
306
310
|
`list` | `selectmode`, `selection` | None
|
307
311
|
`message_box(type: , message: , detail: , title: , icon: , default: , parent: )` | None | None
|
308
312
|
`menu(label: nil) (label is nil if nested under root/toplevel for menu bar)` | None | None
|
@@ -824,6 +828,14 @@ More details can be found in the [Hello, Button!](#hello-button) sample below.
|
|
824
828
|
|
825
829
|
- Setting `background` attribute on `frame` or `label` does not work in `'aqua'` theme on the Mac (only in `'classic'` theme)
|
826
830
|
|
831
|
+
## Glimmer Style Guide
|
832
|
+
|
833
|
+
- Widget arguments are always wrapped by parentheses.
|
834
|
+
- Widget blocks are always declared with curly braces `{}` to clearly visualize hierarchical view code and separate from logic code.
|
835
|
+
- Widget attribute declarations always have arguments that are never wrapped inside parentheses and never take a block.
|
836
|
+
- Widget listeners are always declared with `on` keyword receiving listener event name as an argument. Their multi-line blocks have a `do; end` style to distinguish as logic from widget keywords and attributes.
|
837
|
+
- Pure logic multi-line blocks that do not constitute GUI DSL view elements in general always have `do; end` style to clearly separate logic code from view code.
|
838
|
+
|
827
839
|
## Samples
|
828
840
|
|
829
841
|
The easiest way to run samples is by launching the Glimmer Meta-Sample (the Sample of Samples).
|
@@ -2683,140 +2695,191 @@ Glimmer app:
|
|
2683
2695
|
Glimmer code (from [samples/hello/hello_drag_and_drop.rb](samples/hello/hello_drag_and_drop.rb)):
|
2684
2696
|
|
2685
2697
|
```ruby
|
2686
|
-
require
|
2687
|
-
require "glimmer/tk/drag_and_drop_extension"
|
2698
|
+
require 'glimmer-dsl-tk'
|
2688
2699
|
|
2689
2700
|
include Glimmer
|
2690
2701
|
|
2691
2702
|
root {
|
2692
2703
|
title "Hello, Drag and Drop!"
|
2704
|
+
|
2693
2705
|
frame {
|
2694
2706
|
padding 5
|
2707
|
+
|
2695
2708
|
labelframe {
|
2696
2709
|
text "Drag sources"
|
2697
2710
|
padding 5
|
2711
|
+
|
2698
2712
|
label {
|
2699
|
-
text "Entry"
|
2700
2713
|
grid :row => 0, :column => 0
|
2714
|
+
text "Label"
|
2715
|
+
}
|
2716
|
+
label {
|
2717
|
+
grid :row => 0, :column => 1, :pady => 10, :sticky => "e"
|
2718
|
+
text "Drag label text"
|
2719
|
+
width 30
|
2720
|
+
drag_source true
|
2721
|
+
}
|
2722
|
+
|
2723
|
+
label {
|
2724
|
+
grid :row => 1, :column => 0
|
2725
|
+
text "Entry"
|
2701
2726
|
}
|
2702
2727
|
entry {
|
2728
|
+
grid :row => 1, :column => 1, :pady => 5, :sticky => "e"
|
2703
2729
|
text "Drag entry text"
|
2704
2730
|
width 30
|
2705
|
-
|
2706
|
-
|
2707
|
-
|
2731
|
+
|
2732
|
+
# This is how to do `drag_source true` the manual way for use in exceptional cases
|
2733
|
+
on_drag_start do |event|
|
2734
|
+
event.data = event.source.text
|
2708
2735
|
event.source.configure(:cursor => "hand2")
|
2709
|
-
|
2710
|
-
|
2711
|
-
|
2712
|
-
|
2713
|
-
|
2714
|
-
|
2715
|
-
|
2716
|
-
|
2717
|
-
|
2736
|
+
event.tooltip.content {
|
2737
|
+
lbl { # non-tile-theme version of label
|
2738
|
+
text event.data + " "
|
2739
|
+
bg "yellow"
|
2740
|
+
bitmap "warning"
|
2741
|
+
compound "right"
|
2742
|
+
}
|
2743
|
+
}
|
2744
|
+
end
|
2745
|
+
on_drag_motion do |event|
|
2746
|
+
if event.drop_accepted?
|
2718
2747
|
event.source.configure(:cursor => "hand1")
|
2719
2748
|
else
|
2720
2749
|
event.source.configure(:cursor => "hand2")
|
2721
2750
|
end
|
2722
2751
|
event.tooltip.geometry("+#{event.x_root + 10}+#{event.y_root - 4}")
|
2723
|
-
|
2724
|
-
}
|
2725
|
-
label {
|
2726
|
-
text "Label"
|
2727
|
-
grid :row => 1, :column => 0
|
2728
|
-
}
|
2729
|
-
label {
|
2730
|
-
text "Drag label text"
|
2731
|
-
width 30
|
2732
|
-
grid :row => 1, :column => 1, :pady => 10, :sticky => "e"
|
2733
|
-
drag_source true
|
2752
|
+
end
|
2734
2753
|
}
|
2754
|
+
|
2735
2755
|
label {
|
2736
|
-
text "Combobox"
|
2737
2756
|
grid :row => 2, :column => 0
|
2757
|
+
text "Combobox"
|
2738
2758
|
}
|
2739
2759
|
combobox {
|
2760
|
+
grid :row => 2, :column => 1, :pady => 5, :sticky => "e"
|
2740
2761
|
text "Spain"
|
2741
2762
|
values %w[USA Canada Mexico Columbia UK Australia Germany Italy Spain]
|
2742
2763
|
width 27
|
2743
|
-
|
2744
|
-
on_drag_start
|
2745
|
-
event.data = event.source.
|
2746
|
-
|
2764
|
+
|
2765
|
+
on_drag_start do |event|
|
2766
|
+
event.data = event.source.text
|
2767
|
+
end
|
2747
2768
|
}
|
2769
|
+
|
2748
2770
|
label {
|
2749
|
-
text "Button"
|
2750
2771
|
grid :row => 3, :column => 0
|
2772
|
+
text 'List'
|
2773
|
+
}
|
2774
|
+
list {
|
2775
|
+
grid :row => 3, :column => 1, :pady => 5, :sticky => "e"
|
2776
|
+
selectmode 'browse'
|
2777
|
+
items %w[USA Canada Mexico]
|
2778
|
+
selection 'Canada'
|
2779
|
+
height 3
|
2780
|
+
|
2781
|
+
on_drag_start do |event|
|
2782
|
+
event.data = event.source.selection.first
|
2783
|
+
end
|
2784
|
+
}
|
2785
|
+
|
2786
|
+
label {
|
2787
|
+
grid :row => 4, :column => 0
|
2788
|
+
text "Button"
|
2751
2789
|
}
|
2752
2790
|
button {
|
2791
|
+
grid :row => 4, :column => 1, :pady => 5, :sticky => "w"
|
2753
2792
|
text "Drag it"
|
2754
|
-
grid :row => 3, :column => 1, :pady => 5, :sticky => "w"
|
2755
2793
|
drag_source true
|
2756
2794
|
}
|
2757
2795
|
}
|
2758
2796
|
|
2759
2797
|
labelframe {
|
2760
|
-
text "Drop targets"
|
2761
2798
|
grid :sticky => "nsew", :pady => 15
|
2799
|
+
text "Drop targets"
|
2762
2800
|
padding 5
|
2801
|
+
|
2763
2802
|
label {
|
2764
|
-
text "Entry"
|
2765
2803
|
grid :row => 0, :column => 0
|
2804
|
+
text "Label"
|
2766
2805
|
}
|
2767
|
-
|
2806
|
+
label {
|
2807
|
+
grid :row => 0, :column => 1, :pady => 10, :sticky => "e"
|
2768
2808
|
width 30
|
2769
|
-
|
2770
|
-
|
2771
|
-
|
2772
|
-
|
2809
|
+
borderwidth 2
|
2810
|
+
relief "solid"
|
2811
|
+
|
2812
|
+
on_drop do |event|
|
2813
|
+
event.target.text = event.data
|
2814
|
+
end
|
2773
2815
|
}
|
2816
|
+
|
2774
2817
|
label {
|
2775
|
-
text "Label"
|
2776
2818
|
grid :row => 1, :column => 0
|
2819
|
+
text "Entry"
|
2777
2820
|
}
|
2778
|
-
|
2821
|
+
entry {
|
2822
|
+
grid :row => 1, :column => 1, :pady => 5, :sticky => "e"
|
2779
2823
|
width 30
|
2780
|
-
|
2781
|
-
borderwidth 2
|
2782
|
-
relief "solid"
|
2824
|
+
|
2783
2825
|
on_drop { |event|
|
2784
|
-
event.target.
|
2826
|
+
event.target.text = event.data
|
2785
2827
|
}
|
2786
2828
|
}
|
2829
|
+
|
2787
2830
|
label {
|
2788
|
-
text "Combobox"
|
2789
2831
|
grid :row => 2, :column => 0
|
2832
|
+
text "Combobox"
|
2790
2833
|
}
|
2791
2834
|
combobox {
|
2792
|
-
width 27
|
2793
2835
|
grid :row => 2, :column => 1, :pady => 5, :sticky => "e"
|
2794
|
-
|
2795
|
-
|
2796
|
-
|
2836
|
+
width 27
|
2837
|
+
|
2838
|
+
on_drop do |event|
|
2839
|
+
event.target.text = event.data
|
2840
|
+
end
|
2797
2841
|
}
|
2842
|
+
|
2798
2843
|
label {
|
2799
|
-
text "Button"
|
2800
2844
|
grid :row => 3, :column => 0
|
2845
|
+
text 'List'
|
2846
|
+
}
|
2847
|
+
list {
|
2848
|
+
grid :row => 3, :column => 1, :pady => 5, :sticky => "e"
|
2849
|
+
selectmode 'browse'
|
2850
|
+
height 3
|
2851
|
+
|
2852
|
+
on_drop do |event|
|
2853
|
+
event.target.items += [event.data]
|
2854
|
+
end
|
2855
|
+
}
|
2856
|
+
|
2857
|
+
label {
|
2858
|
+
grid :row => 4, :column => 0
|
2859
|
+
text "Button"
|
2801
2860
|
}
|
2802
2861
|
button {
|
2862
|
+
grid :row => 4, :column => 1, :pady => 5, :sticky => "w"
|
2803
2863
|
text "Drop here"
|
2804
|
-
|
2805
|
-
on_drop
|
2864
|
+
|
2865
|
+
on_drop do |event|
|
2806
2866
|
event.target.text = event.data
|
2807
|
-
|
2867
|
+
end
|
2808
2868
|
}
|
2869
|
+
|
2809
2870
|
label {
|
2871
|
+
grid :row => 5, :column => 0
|
2810
2872
|
text "Checkbutton"
|
2811
|
-
grid :row => 4, :column => 0
|
2812
2873
|
}
|
2813
2874
|
checkbutton {
|
2814
|
-
|
2815
|
-
|
2816
|
-
|
2875
|
+
grid :row => 5, :column => 1, :pady => 5, :sticky => "w"
|
2876
|
+
text "Drop here to destroy a widget"
|
2877
|
+
|
2878
|
+
on_drop do |event|
|
2817
2879
|
event.target.text = event.data
|
2818
|
-
|
2819
|
-
|
2880
|
+
# execute asynchronously after 100ms to ensure all events have been processed before destruction
|
2881
|
+
::Tk.after(100) {event.source.destroy}
|
2882
|
+
end
|
2820
2883
|
}
|
2821
2884
|
}
|
2822
2885
|
}
|
data/VERSION
CHANGED
@@ -1 +1 @@
|
|
1
|
-
0.0.
|
1
|
+
0.0.45
|
data/glimmer-dsl-tk.gemspec
CHANGED
Binary file
|
@@ -50,7 +50,7 @@ module Glimmer
|
|
50
50
|
#TODO check if nested data binding works for list widget and other widgets that need custom data binding
|
51
51
|
list_selection_binding.observe(model, model_binding.property_name_expression)
|
52
52
|
|
53
|
-
parent.
|
53
|
+
parent.on('<TreeviewSelect>') do
|
54
54
|
model_binding.call(list_selection_binding.evaluate_property)
|
55
55
|
end
|
56
56
|
end
|
@@ -1,3 +1,24 @@
|
|
1
|
+
# Copyright (c) 2020-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
|
+
|
1
22
|
require "json"
|
2
23
|
|
3
24
|
module Glimmer
|
@@ -23,7 +44,7 @@ module Glimmer
|
|
23
44
|
@on_drop_block = value
|
24
45
|
self.tk.bind("<DropEvent>", proc { |tk_event|
|
25
46
|
drop_event = DragAndDropEvent.json_create(JSON.parse("{" + tk_event.detail + "}"))
|
26
|
-
@on_drop_block.call(drop_event) if self
|
47
|
+
@on_drop_block.call(drop_event) if self == drop_event.target
|
27
48
|
})
|
28
49
|
self.tk.bind("<DropCheckEvent>", proc { |tk_event|
|
29
50
|
drop_check_event = DragAndDropEvent.json_create(JSON.parse("{" + tk_event.detail + "}"))
|
@@ -40,23 +61,30 @@ module Glimmer
|
|
40
61
|
bind("<DropAcceptedEvent>", proc { |event| drag_event.drop_accepted = true })
|
41
62
|
bind("B1-Motion", proc { |tk_event|
|
42
63
|
if drag_event.nil?
|
43
|
-
tooltip =
|
64
|
+
tooltip = WidgetProxy.new('toplevel', root_parent_proxy, [])
|
65
|
+
tooltip.overrideredirect(1) #create tooltip window to display dragged data
|
44
66
|
tooltip.geometry("+#{tk_event.x_root + 10}+#{tk_event.y_root - 2}")
|
45
|
-
drag_event = DragAndDropEvent.new(self
|
67
|
+
drag_event = DragAndDropEvent.new(self, nil, tooltip, tk_event.x_root, tk_event.y_root, nil, false)
|
46
68
|
if @drag_source
|
47
69
|
tk_event.widget.configure(:cursor => "hand2")
|
48
70
|
# Default data to drag is text
|
49
71
|
drag_event.data = if textvariable_defined? then tk.textvariable.value elsif has_attribute?(:text) then tk.text end
|
50
|
-
|
72
|
+
tooltip_label = WidgetProxy.new('label', tooltip, [])
|
73
|
+
tooltip_label.text = drag_event.data
|
74
|
+
tooltip_label.pack # TODO look into using grid instead to be consistent with the modern Tk way
|
51
75
|
elsif !@on_drag_start_block.nil?
|
52
76
|
@on_drag_start_block.call(drag_event)
|
53
|
-
|
77
|
+
if tooltip.winfo_children().length == 0
|
78
|
+
tooltip_label = WidgetProxy.new('label', tooltip, [])
|
79
|
+
tooltip_label.text = drag_event.data
|
80
|
+
tooltip_label.pack # TODO look into using grid instead to be consistent with the modern Tk way
|
81
|
+
end
|
54
82
|
end
|
55
83
|
else
|
56
84
|
drag_event.x_root, drag_event.y_root = tk_event.x_root, tk_event.y_root
|
57
85
|
drag_event.drop_accepted = false
|
58
86
|
move_over_widget = tk_event.widget.winfo_containing(tk_event.x_root, tk_event.y_root)
|
59
|
-
drag_event.target = move_over_widget
|
87
|
+
drag_event.target = move_over_widget.proxy
|
60
88
|
move_over_widget.event_generate("<DropCheckEvent>", :data => drag_event.to_json)
|
61
89
|
if @on_drag_motion_block.nil?
|
62
90
|
# Default motion behavior:
|
@@ -75,7 +103,7 @@ module Glimmer
|
|
75
103
|
})
|
76
104
|
bind("ButtonRelease-1", proc { |tk_event|
|
77
105
|
if drag_event
|
78
|
-
drag_event.target = tk_event.widget.winfo_containing(tk_event.x_root, tk_event.y_root)
|
106
|
+
drag_event.target = tk_event.widget.winfo_containing(tk_event.x_root, tk_event.y_root).proxy
|
79
107
|
drag_event.source.configure(:cursor => "")
|
80
108
|
drag_event.target.event_generate("<DropEvent>", :data => drag_event.to_json)
|
81
109
|
drag_event.tooltip.destroy
|
@@ -91,6 +119,8 @@ module Glimmer
|
|
91
119
|
end
|
92
120
|
|
93
121
|
DragAndDropEvent = Struct.new(:source, :target, :tooltip, :x_root, :y_root, :data, :drop_accepted) do
|
122
|
+
alias drop_accepted? drop_accepted
|
123
|
+
|
94
124
|
def as_json(*)
|
95
125
|
klass = self.class.name
|
96
126
|
{
|
@@ -104,9 +134,9 @@ module Glimmer
|
|
104
134
|
end
|
105
135
|
|
106
136
|
def self.json_create(object)
|
107
|
-
new(*[ObjectSpace._id2ref(object["v"][0]), ObjectSpace._id2ref(object["v"][1]), ObjectSpace._id2ref(object["v"][2])].concat(object["v"].drop 3))
|
137
|
+
new(*[ObjectSpace._id2ref(object["v"][0]), ObjectSpace._id2ref(object["v"][1]).proxy, ObjectSpace._id2ref(object["v"][2])].concat(object["v"].drop 3))
|
108
138
|
end
|
109
139
|
end
|
110
140
|
end
|
111
141
|
end
|
112
|
-
end
|
142
|
+
end
|
@@ -0,0 +1,33 @@
|
|
1
|
+
# Copyright (c) 2020-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/tk/widget_proxy'
|
23
|
+
|
24
|
+
module Glimmer
|
25
|
+
module Tk
|
26
|
+
# Non-Themable (non-Tile) Tk Label
|
27
|
+
class LblProxy < WidgetProxy
|
28
|
+
def build_widget
|
29
|
+
@tk = ::TkLabel.new(@parent_proxy.tk, *args).tap {|tk| tk.singleton_class.include(Glimmer::Tk::Widget); tk.proxy = self}
|
30
|
+
end
|
31
|
+
end
|
32
|
+
end
|
33
|
+
end
|
@@ -63,19 +63,20 @@ module Glimmer
|
|
63
63
|
def build_widget
|
64
64
|
if application?
|
65
65
|
if OS.mac?
|
66
|
-
@tk = ::TkSysMenu_Apple.new(@parent_proxy.tk)
|
66
|
+
@tk = ::TkSysMenu_Apple.new(@parent_proxy.tk).tap {|tk| tk.singleton_class.include(Glimmer::Tk::Widget); tk.proxy = self}
|
67
67
|
@parent_proxy.tk.add :cascade, :menu => @tk
|
68
68
|
end
|
69
69
|
else
|
70
70
|
if @parent_proxy.parent_proxy.is_a?(ToplevelProxy) && (OS.mac? || OS.linux?) && help?
|
71
|
-
@tk = ::TkSysMenu_Help.new(@parent_proxy.tk)
|
71
|
+
@tk = ::TkSysMenu_Help.new(@parent_proxy.tk).tap {|tk| tk.singleton_class.include(Glimmer::Tk::Widget); tk.proxy = self}
|
72
72
|
elsif @parent_proxy.parent_proxy.is_a?(ToplevelProxy) && OS.mac? && window?
|
73
|
-
@tk = ::Tk::TkSysMenu_Window.new(@parent_proxy.tk)
|
74
|
-
|
75
|
-
|
73
|
+
@tk = ::Tk::TkSysMenu_Window.new(@parent_proxy.tk).tap {|tk| tk.singleton_class.include(Glimmer::Tk::Widget); tk.proxy = self}
|
74
|
+
# Windows system menu does not seem to work
|
75
|
+
# elsif @parent_proxy.parent_proxy.is_a?(ToplevelProxy) && OS.windows? && system?
|
76
|
+
# @tk = ::TkSysMenu_System.new(@parent_proxy.tk).tap {|tk| tk.singleton_class.include(Glimmer::Tk::Widget); tk.proxy = self}
|
76
77
|
else
|
77
78
|
tk_widget_class = self.class.tk_widget_class_for(@keyword)
|
78
|
-
@tk = tk_widget_class.new(@parent_proxy.tk)
|
79
|
+
@tk = tk_widget_class.new(@parent_proxy.tk).tap {|tk| tk.singleton_class.include(Glimmer::Tk::Widget); tk.proxy = self}
|
79
80
|
end
|
80
81
|
case @parent_proxy
|
81
82
|
when MenuProxy
|
@@ -28,7 +28,7 @@ module Glimmer
|
|
28
28
|
# Follows the Proxy Design Pattern
|
29
29
|
class RootProxy < ToplevelProxy
|
30
30
|
def initialize(*args, &block)
|
31
|
-
@tk = ::TkRoot.new
|
31
|
+
@tk = ::TkRoot.new.tap {|tk| tk.singleton_class.include(Glimmer::Tk::Widget); tk.proxy = self}
|
32
32
|
@tk.minsize = DEFAULT_WIDTH, DEFAULT_HEIGHT
|
33
33
|
initialize_defaults
|
34
34
|
post_add_content if block.nil?
|
@@ -103,7 +103,7 @@ module Glimmer
|
|
103
103
|
build_yscrollbar
|
104
104
|
build_xscrollbar
|
105
105
|
tk_widget_class = self.class.tk_widget_class_for('frame')
|
106
|
-
@tk = tk_widget_class.new(@canvas_proxy.tk, *args)
|
106
|
+
@tk = tk_widget_class.new(@canvas_proxy.tk, *args).tap {|tk| tk.singleton_class.include(Glimmer::Tk::Widget); tk.proxy = self}
|
107
107
|
TkcWindow.new(@canvas_proxy.tk, 0, 0, :anchor => "nw", :window => @tk)
|
108
108
|
end
|
109
109
|
|
@@ -0,0 +1,28 @@
|
|
1
|
+
# Copyright (c) 2020-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 Tk
|
24
|
+
module Widget
|
25
|
+
attr_accessor :proxy
|
26
|
+
end
|
27
|
+
end
|
28
|
+
end
|
@@ -20,6 +20,7 @@
|
|
20
20
|
# WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
21
21
|
|
22
22
|
require 'glimmer/data_binding/tk/one_time_observer'
|
23
|
+
require 'glimmer/tk/widget'
|
23
24
|
|
24
25
|
module Glimmer
|
25
26
|
module Tk
|
@@ -49,10 +50,10 @@ module Glimmer
|
|
49
50
|
# TODO consider exposing this via Glimmer::Config
|
50
51
|
potential_tk_widget_class_names = [
|
51
52
|
"::Tk::Tile::#{tk_widget_class_basename}",
|
52
|
-
"::Tk::BWidget::#{tk_widget_class_basename}",
|
53
|
-
"::Tk::Iwidgets::#{tk_widget_class_basename}",
|
54
53
|
"::Tk#{tk_widget_class_basename}",
|
55
54
|
"::Tk::#{tk_widget_class_basename}",
|
55
|
+
"::Tk::BWidget::#{tk_widget_class_basename}",
|
56
|
+
"::Tk::Iwidgets::#{tk_widget_class_basename}",
|
56
57
|
"::Glimmer::Tk::#{tk_widget_class_basename}Proxy",
|
57
58
|
]
|
58
59
|
tk_widget_class = nil
|
@@ -70,7 +71,8 @@ module Glimmer
|
|
70
71
|
|
71
72
|
FONTS_PREDEFINED = %w[default text fixed menu heading caption small_caption icon tooltip]
|
72
73
|
|
73
|
-
attr_reader :parent_proxy, :tk, :args, :keyword, :children
|
74
|
+
attr_reader :parent_proxy, :tk, :args, :keyword, :children, :bind_ids, :destroyed
|
75
|
+
alias destroyed? destroyed
|
74
76
|
|
75
77
|
# Initializes a new Tk Widget
|
76
78
|
#
|
@@ -127,7 +129,7 @@ module Glimmer
|
|
127
129
|
end
|
128
130
|
|
129
131
|
def tk_widget_has_attribute_setter?(attribute)
|
130
|
-
return true if @tk.respond_to?(attribute)
|
132
|
+
return true if @tk.respond_to?(attribute) && attribute != 'focus' # TODO configure exceptions via constant if needed
|
131
133
|
result = nil
|
132
134
|
begin
|
133
135
|
# TK Widget currently doesn't support respond_to? properly, so I have to resort to this trick for now
|
@@ -288,8 +290,10 @@ module Glimmer
|
|
288
290
|
end
|
289
291
|
|
290
292
|
def destroy
|
293
|
+
unbind_all
|
291
294
|
@tk.destroy
|
292
295
|
@on_destroy_procs&.each {|p| p.call(@tk)}
|
296
|
+
@destroyed = true
|
293
297
|
end
|
294
298
|
|
295
299
|
def apply_style(options)
|
@@ -384,6 +388,7 @@ module Glimmer
|
|
384
388
|
if observer.is_a?(Glimmer::DataBinding::ModelBinding)
|
385
389
|
model = observer.model
|
386
390
|
options_model_property = observer.property_name + '_options'
|
391
|
+
# TODO perform data-binding to values too
|
387
392
|
@tk.values = model.send(options_model_property) if model.respond_to?(options_model_property)
|
388
393
|
end
|
389
394
|
@tk.bind('<ComboboxSelected>') {
|
@@ -490,6 +495,16 @@ module Glimmer
|
|
490
495
|
handle_listener(listener_name, &listener)
|
491
496
|
end
|
492
497
|
|
498
|
+
def unbind_all
|
499
|
+
@listeners&.keys&.each do |key|
|
500
|
+
if key.to_s.downcase.include?('command')
|
501
|
+
@tk.send(key, '')
|
502
|
+
else
|
503
|
+
@tk.bind(key, '')
|
504
|
+
end
|
505
|
+
end
|
506
|
+
end
|
507
|
+
|
493
508
|
def content(&block)
|
494
509
|
Glimmer::DSL::Engine.add_content(self, Glimmer::DSL::Tk::WidgetExpression.new, keyword, *args, &block)
|
495
510
|
end
|
@@ -513,6 +528,11 @@ module Glimmer
|
|
513
528
|
!super_only && tk.respond_to?(method, *args, &block)
|
514
529
|
end
|
515
530
|
|
531
|
+
# inspect is overridden to prevent printing very long stack traces
|
532
|
+
def inspect
|
533
|
+
"#{super[0, 150]}... >"
|
534
|
+
end
|
535
|
+
|
516
536
|
private
|
517
537
|
|
518
538
|
# The griddable parent widget proxy to apply grid to (is different from @tk in composite widgets like notebook or scrolledframe)
|
@@ -527,7 +547,7 @@ module Glimmer
|
|
527
547
|
|
528
548
|
def build_widget
|
529
549
|
tk_widget_class = self.class.tk_widget_class_for(@keyword)
|
530
|
-
@tk = tk_widget_class.new(@parent_proxy.tk, *args)
|
550
|
+
@tk = tk_widget_class.new(@parent_proxy.tk, *args).tap {|tk| tk.singleton_class.include(Glimmer::Tk::Widget); tk.proxy = self}
|
531
551
|
end
|
532
552
|
|
533
553
|
def initialize_defaults
|
data/lib/glimmer-dsl-tk.rb
CHANGED
@@ -27,8 +27,8 @@ require 'glimmer'
|
|
27
27
|
require 'puts_debuggerer' if ENV['pd'].to_s.downcase == 'true'
|
28
28
|
# require 'super_module'
|
29
29
|
require 'tk'
|
30
|
-
require 'tkextlib/bwidget'
|
31
|
-
require 'tkextlib/iwidgets'
|
30
|
+
#require 'tkextlib/bwidget' # does not work on Windows
|
31
|
+
#require 'tkextlib/iwidgets' # does not work on Windows
|
32
32
|
require 'os'
|
33
33
|
require 'facets/hash/symbolize_keys'
|
34
34
|
require 'facets/string/underscore'
|
@@ -39,6 +39,7 @@ require 'delegate'
|
|
39
39
|
# require 'ext/glimmer/config'
|
40
40
|
# require 'ext/glimmer'
|
41
41
|
require 'glimmer/dsl/tk/dsl'
|
42
|
+
require 'glimmer/tk/drag_and_drop_extension'
|
42
43
|
|
43
44
|
Glimmer::Config.loop_max_count = -1
|
44
45
|
|
@@ -48,7 +49,7 @@ Glimmer::Config.excluded_keyword_checkers << lambda do |method_symbol, *args|
|
|
48
49
|
result ||= method == 'load_iseq'
|
49
50
|
end
|
50
51
|
|
51
|
-
Tk::Tile::Style.theme_use '
|
52
|
+
Tk::Tile::Style.theme_use 'clam' if OS.linux?
|
52
53
|
|
53
54
|
::TkOption.add '*tearOff', 0
|
54
55
|
|
data/lib/os.rb
ADDED
@@ -0,0 +1,36 @@
|
|
1
|
+
# Copyright (c) 2020-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
|
+
class OS
|
23
|
+
class << self
|
24
|
+
def mac?
|
25
|
+
Tk.windowingsystem == 'aqua'
|
26
|
+
end
|
27
|
+
|
28
|
+
def windows?
|
29
|
+
Tk.windowingsystem == 'win32'
|
30
|
+
end
|
31
|
+
|
32
|
+
def linux?
|
33
|
+
Tk.windowingsystem == 'x11'
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
@@ -130,6 +130,16 @@ class MetaSample
|
|
130
130
|
grid row: 0, column: 1, column_weight: 1
|
131
131
|
value File.read(file_path_for(selected_sample))
|
132
132
|
}
|
133
|
+
|
134
|
+
@yscrollbar = scrollbar {
|
135
|
+
grid row: 0, column: 2
|
136
|
+
}
|
137
|
+
@code_text.yscrollbar @yscrollbar
|
138
|
+
|
139
|
+
@xscrollbar = scrollbar {
|
140
|
+
grid row: 1, column: 1, column_span: 2
|
141
|
+
}
|
142
|
+
@code_text.xscrollbar @xscrollbar
|
133
143
|
}
|
134
144
|
@root.open
|
135
145
|
end
|
@@ -19,140 +19,191 @@
|
|
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
|
-
require
|
23
|
-
require "glimmer/tk/drag_and_drop_extension"
|
22
|
+
require 'glimmer-dsl-tk'
|
24
23
|
|
25
24
|
include Glimmer
|
26
25
|
|
27
26
|
root {
|
28
27
|
title "Hello, Drag and Drop!"
|
28
|
+
|
29
29
|
frame {
|
30
30
|
padding 5
|
31
|
+
|
31
32
|
labelframe {
|
32
33
|
text "Drag sources"
|
33
34
|
padding 5
|
35
|
+
|
34
36
|
label {
|
35
|
-
text "Entry"
|
36
37
|
grid :row => 0, :column => 0
|
38
|
+
text "Label"
|
39
|
+
}
|
40
|
+
label {
|
41
|
+
grid :row => 0, :column => 1, :pady => 10, :sticky => "e"
|
42
|
+
text "Drag label text"
|
43
|
+
width 30
|
44
|
+
drag_source true
|
45
|
+
}
|
46
|
+
|
47
|
+
label {
|
48
|
+
grid :row => 1, :column => 0
|
49
|
+
text "Entry"
|
37
50
|
}
|
38
51
|
entry {
|
52
|
+
grid :row => 1, :column => 1, :pady => 5, :sticky => "e"
|
39
53
|
text "Drag entry text"
|
40
54
|
width 30
|
41
|
-
|
42
|
-
|
43
|
-
|
55
|
+
|
56
|
+
# This is how to do `drag_source true` the manual way for use in exceptional cases
|
57
|
+
on_drag_start do |event|
|
58
|
+
event.data = event.source.text
|
44
59
|
event.source.configure(:cursor => "hand2")
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
51
|
-
|
52
|
-
|
53
|
-
|
60
|
+
event.tooltip.content {
|
61
|
+
lbl { # non-tile-theme version of label
|
62
|
+
text event.data + " "
|
63
|
+
bg "yellow"
|
64
|
+
bitmap "warning"
|
65
|
+
compound "right"
|
66
|
+
}
|
67
|
+
}
|
68
|
+
end
|
69
|
+
on_drag_motion do |event|
|
70
|
+
if event.drop_accepted?
|
54
71
|
event.source.configure(:cursor => "hand1")
|
55
72
|
else
|
56
73
|
event.source.configure(:cursor => "hand2")
|
57
74
|
end
|
58
75
|
event.tooltip.geometry("+#{event.x_root + 10}+#{event.y_root - 4}")
|
59
|
-
|
60
|
-
}
|
61
|
-
label {
|
62
|
-
text "Label"
|
63
|
-
grid :row => 1, :column => 0
|
76
|
+
end
|
64
77
|
}
|
78
|
+
|
65
79
|
label {
|
66
|
-
text "Drag label text"
|
67
|
-
width 30
|
68
|
-
grid :row => 1, :column => 1, :pady => 10, :sticky => "e"
|
69
|
-
drag_source true
|
70
|
-
}
|
71
|
-
label {
|
72
|
-
text "Combobox"
|
73
80
|
grid :row => 2, :column => 0
|
81
|
+
text "Combobox"
|
74
82
|
}
|
75
83
|
combobox {
|
84
|
+
grid :row => 2, :column => 1, :pady => 5, :sticky => "e"
|
76
85
|
text "Spain"
|
77
86
|
values %w[USA Canada Mexico Columbia UK Australia Germany Italy Spain]
|
78
87
|
width 27
|
79
|
-
|
80
|
-
on_drag_start
|
81
|
-
event.data = event.source.
|
82
|
-
|
88
|
+
|
89
|
+
on_drag_start do |event|
|
90
|
+
event.data = event.source.text
|
91
|
+
end
|
83
92
|
}
|
93
|
+
|
84
94
|
label {
|
85
|
-
text "Button"
|
86
95
|
grid :row => 3, :column => 0
|
96
|
+
text 'List'
|
97
|
+
}
|
98
|
+
list {
|
99
|
+
grid :row => 3, :column => 1, :pady => 5, :sticky => "e"
|
100
|
+
selectmode 'browse'
|
101
|
+
items %w[USA Canada Mexico]
|
102
|
+
selection 'Canada'
|
103
|
+
height 3
|
104
|
+
|
105
|
+
on_drag_start do |event|
|
106
|
+
event.data = event.source.selection.first
|
107
|
+
end
|
108
|
+
}
|
109
|
+
|
110
|
+
label {
|
111
|
+
grid :row => 4, :column => 0
|
112
|
+
text "Button"
|
87
113
|
}
|
88
114
|
button {
|
115
|
+
grid :row => 4, :column => 1, :pady => 5, :sticky => "w"
|
89
116
|
text "Drag it"
|
90
|
-
grid :row => 3, :column => 1, :pady => 5, :sticky => "w"
|
91
117
|
drag_source true
|
92
118
|
}
|
93
119
|
}
|
94
120
|
|
95
121
|
labelframe {
|
96
|
-
text "Drop targets"
|
97
122
|
grid :sticky => "nsew", :pady => 15
|
123
|
+
text "Drop targets"
|
98
124
|
padding 5
|
125
|
+
|
99
126
|
label {
|
100
|
-
text "Entry"
|
101
127
|
grid :row => 0, :column => 0
|
128
|
+
text "Label"
|
102
129
|
}
|
103
|
-
|
130
|
+
label {
|
131
|
+
grid :row => 0, :column => 1, :pady => 10, :sticky => "e"
|
104
132
|
width 30
|
105
|
-
|
106
|
-
|
107
|
-
|
108
|
-
|
133
|
+
borderwidth 2
|
134
|
+
relief "solid"
|
135
|
+
|
136
|
+
on_drop do |event|
|
137
|
+
event.target.text = event.data
|
138
|
+
end
|
109
139
|
}
|
140
|
+
|
110
141
|
label {
|
111
|
-
text "Label"
|
112
142
|
grid :row => 1, :column => 0
|
143
|
+
text "Entry"
|
113
144
|
}
|
114
|
-
|
145
|
+
entry {
|
146
|
+
grid :row => 1, :column => 1, :pady => 5, :sticky => "e"
|
115
147
|
width 30
|
116
|
-
|
117
|
-
borderwidth 2
|
118
|
-
relief "solid"
|
148
|
+
|
119
149
|
on_drop { |event|
|
120
|
-
event.target.
|
150
|
+
event.target.text = event.data
|
121
151
|
}
|
122
152
|
}
|
153
|
+
|
123
154
|
label {
|
124
|
-
text "Combobox"
|
125
155
|
grid :row => 2, :column => 0
|
156
|
+
text "Combobox"
|
126
157
|
}
|
127
158
|
combobox {
|
128
|
-
width 27
|
129
159
|
grid :row => 2, :column => 1, :pady => 5, :sticky => "e"
|
130
|
-
|
131
|
-
|
132
|
-
|
160
|
+
width 27
|
161
|
+
|
162
|
+
on_drop do |event|
|
163
|
+
event.target.text = event.data
|
164
|
+
end
|
133
165
|
}
|
166
|
+
|
134
167
|
label {
|
135
|
-
text "Button"
|
136
168
|
grid :row => 3, :column => 0
|
169
|
+
text 'List'
|
170
|
+
}
|
171
|
+
list {
|
172
|
+
grid :row => 3, :column => 1, :pady => 5, :sticky => "e"
|
173
|
+
selectmode 'browse'
|
174
|
+
height 3
|
175
|
+
|
176
|
+
on_drop do |event|
|
177
|
+
event.target.items += [event.data]
|
178
|
+
end
|
179
|
+
}
|
180
|
+
|
181
|
+
label {
|
182
|
+
grid :row => 4, :column => 0
|
183
|
+
text "Button"
|
137
184
|
}
|
138
185
|
button {
|
186
|
+
grid :row => 4, :column => 1, :pady => 5, :sticky => "w"
|
139
187
|
text "Drop here"
|
140
|
-
|
141
|
-
on_drop
|
188
|
+
|
189
|
+
on_drop do |event|
|
142
190
|
event.target.text = event.data
|
143
|
-
|
191
|
+
end
|
144
192
|
}
|
193
|
+
|
145
194
|
label {
|
195
|
+
grid :row => 5, :column => 0
|
146
196
|
text "Checkbutton"
|
147
|
-
grid :row => 4, :column => 0
|
148
197
|
}
|
149
198
|
checkbutton {
|
150
|
-
|
151
|
-
|
152
|
-
|
199
|
+
grid :row => 5, :column => 1, :pady => 5, :sticky => "w"
|
200
|
+
text "Drop here to destroy a widget"
|
201
|
+
|
202
|
+
on_drop do |event|
|
153
203
|
event.target.text = event.data
|
154
|
-
|
155
|
-
|
204
|
+
# execute asynchronously after 100ms to ensure all events have been processed before destruction
|
205
|
+
::Tk.after(100) {event.source.destroy}
|
206
|
+
end
|
156
207
|
}
|
157
208
|
}
|
158
209
|
}
|
@@ -25,7 +25,7 @@ include Glimmer
|
|
25
25
|
|
26
26
|
COLORS = [:white, :red, :yellow, :green, :blue, :magenta, :gray, :black]
|
27
27
|
|
28
|
-
Tk::Tile::Style.theme_use
|
28
|
+
Tk::Tile::Style.theme_use 'classic' if OS.mac? # this enables setting background on label just for demo purposes
|
29
29
|
|
30
30
|
root { |r|
|
31
31
|
title 'Hello, Menu Bar!'
|
@@ -65,11 +65,6 @@ root { |r|
|
|
65
65
|
}
|
66
66
|
end
|
67
67
|
|
68
|
-
# Windows-specific system menu (to the top-left of the window frame)
|
69
|
-
if OS.windows?
|
70
|
-
menu(label: 'System')
|
71
|
-
end
|
72
|
-
|
73
68
|
menu(label: 'File', underline: 0) {
|
74
69
|
menu_item(label: 'New', underline: 0) {
|
75
70
|
accelerator OS.mac? ? 'Command+N' : 'Control+N'
|
@@ -166,7 +161,7 @@ root { |r|
|
|
166
161
|
end
|
167
162
|
}
|
168
163
|
|
169
|
-
menu(label: 'Country', underline:
|
164
|
+
menu(label: 'Country', underline: 0) {
|
170
165
|
['denmark', 'finland', 'france', 'germany', 'italy', 'mexico', 'netherlands', 'norway', 'usa'].each do |image_name|
|
171
166
|
menu_item(:radiobutton, label: image_name.capitalize) {
|
172
167
|
selection image_name == 'usa'
|
@@ -176,7 +171,7 @@ root { |r|
|
|
176
171
|
end
|
177
172
|
}
|
178
173
|
|
179
|
-
menu(label: 'Format', underline:
|
174
|
+
menu(label: 'Format', underline: 3) {
|
180
175
|
menu(label: 'Background Color', underline: 0) {
|
181
176
|
COLORS.each { |color_style|
|
182
177
|
menu_item(:radiobutton, label: color_style.to_s.split('_').map(&:capitalize).join(' ')) {
|
data/samples/hello/hello_text.rb
CHANGED
@@ -282,7 +282,7 @@ class HelloText
|
|
282
282
|
|
283
283
|
@text = text {
|
284
284
|
grid row: 1, column: 0, row_weight: 1
|
285
|
-
|
285
|
+
wrap 'word'
|
286
286
|
undo true
|
287
287
|
value <=> [self, :document]
|
288
288
|
|
@@ -304,15 +304,10 @@ class HelloText
|
|
304
304
|
end
|
305
305
|
}
|
306
306
|
|
307
|
-
@yscrollbar =
|
307
|
+
@yscrollbar = scrollbar {
|
308
308
|
grid row: 1, column: 1
|
309
309
|
}
|
310
310
|
@text.yscrollbar @yscrollbar
|
311
|
-
|
312
|
-
@xscrollbar = x_scrollbar {
|
313
|
-
grid row: 2, column: 0, column_span: 2, row_weight: 0
|
314
|
-
}
|
315
|
-
@text.xscrollbar @xscrollbar
|
316
311
|
}
|
317
312
|
@root.open
|
318
313
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: glimmer-dsl-tk
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0.
|
4
|
+
version: 0.0.45
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- AndyMaleh
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2021-11-
|
11
|
+
date: 2021-11-17 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: glimmer
|
@@ -38,26 +38,6 @@ dependencies:
|
|
38
38
|
- - "~>"
|
39
39
|
- !ruby/object:Gem::Version
|
40
40
|
version: 0.13.1
|
41
|
-
- !ruby/object:Gem::Dependency
|
42
|
-
name: os
|
43
|
-
requirement: !ruby/object:Gem::Requirement
|
44
|
-
requirements:
|
45
|
-
- - ">="
|
46
|
-
- !ruby/object:Gem::Version
|
47
|
-
version: 1.0.0
|
48
|
-
- - "<"
|
49
|
-
- !ruby/object:Gem::Version
|
50
|
-
version: 2.0.0
|
51
|
-
type: :runtime
|
52
|
-
prerelease: false
|
53
|
-
version_requirements: !ruby/object:Gem::Requirement
|
54
|
-
requirements:
|
55
|
-
- - ">="
|
56
|
-
- !ruby/object:Gem::Version
|
57
|
-
version: 1.0.0
|
58
|
-
- - "<"
|
59
|
-
- !ruby/object:Gem::Version
|
60
|
-
version: 2.0.0
|
61
41
|
- !ruby/object:Gem::Dependency
|
62
42
|
name: tk
|
63
43
|
requirement: !ruby/object:Gem::Requirement
|
@@ -232,6 +212,7 @@ files:
|
|
232
212
|
- lib/glimmer/tk/entry_proxy.rb
|
233
213
|
- lib/glimmer/tk/frame_proxy.rb
|
234
214
|
- lib/glimmer/tk/label_proxy.rb
|
215
|
+
- lib/glimmer/tk/lbl_proxy.rb
|
235
216
|
- lib/glimmer/tk/list_proxy.rb
|
236
217
|
- lib/glimmer/tk/menu_item_proxy.rb
|
237
218
|
- lib/glimmer/tk/menu_proxy.rb
|
@@ -245,7 +226,9 @@ files:
|
|
245
226
|
- lib/glimmer/tk/toplevel_proxy.rb
|
246
227
|
- lib/glimmer/tk/treeview_proxy.rb
|
247
228
|
- lib/glimmer/tk/variable_owner.rb
|
229
|
+
- lib/glimmer/tk/widget.rb
|
248
230
|
- lib/glimmer/tk/widget_proxy.rb
|
231
|
+
- lib/os.rb
|
249
232
|
- samples/elaborate/meta_sample.rb
|
250
233
|
- samples/hello/hello_built_in_dialog.rb
|
251
234
|
- samples/hello/hello_button.rb
|
@@ -310,7 +293,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
310
293
|
- !ruby/object:Gem::Version
|
311
294
|
version: '0'
|
312
295
|
requirements: []
|
313
|
-
rubygems_version: 3.2.
|
296
|
+
rubygems_version: 3.2.31
|
314
297
|
signing_key:
|
315
298
|
specification_version: 4
|
316
299
|
summary: Glimmer DSL for Tk
|