glimmer-dsl-web 0.0.5 → 0.0.7
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 +18 -0
- data/LICENSE.txt +1 -1
- data/README.md +416 -61
- data/VERSION +1 -1
- data/glimmer-dsl-web.gemspec +11 -6
- data/lib/glimmer/data_binding/element_binding.rb +4 -4
- data/lib/glimmer/dsl/web/bind_expression.rb +36 -0
- data/lib/glimmer/dsl/web/data_binding_expression.rb +30 -0
- data/lib/glimmer/dsl/web/dsl.rb +6 -0
- data/lib/glimmer/dsl/web/element_expression.rb +2 -20
- data/lib/glimmer/dsl/web/general_element_expression.rb +29 -0
- data/lib/glimmer/dsl/web/p_expression.rb +2 -21
- data/lib/glimmer/dsl/web/select_expression.rb +12 -0
- data/lib/glimmer/dsl/web/shine_data_binding_expression.rb +42 -0
- data/lib/glimmer/util/proc_tracker.rb +1 -1
- data/lib/glimmer/web/element_proxy.rb +134 -589
- data/lib/glimmer/web/event_proxy.rb +1 -1
- data/lib/glimmer/web/listener_proxy.rb +1 -1
- data/lib/glimmer/web.rb +1 -1
- data/lib/glimmer-dsl-web/ext/date.rb +4 -1
- data/lib/glimmer-dsl-web/samples/hello/hello_button.rb +1 -1
- data/lib/glimmer-dsl-web/samples/hello/hello_data_binding.rb +181 -0
- data/lib/glimmer-dsl-web/samples/hello/hello_form.rb +1 -1
- data/lib/glimmer-dsl-web/samples/hello/hello_input_date_time.rb +117 -0
- data/lib/glimmer-dsl-web/samples/hello/hello_world.rb +1 -1
- data/lib/glimmer-dsl-web.rb +1 -2
- metadata +9 -23
- data/lib/glimmer/web/property_owner.rb +0 -24
data/lib/glimmer/web.rb
CHANGED
@@ -1,4 +1,3 @@
|
|
1
|
-
# TODO double check if the latest Opal implemented everything below already
|
2
1
|
require 'date'
|
3
2
|
require 'time'
|
4
3
|
|
@@ -13,6 +12,10 @@ class DateTime < Date
|
|
13
12
|
end
|
14
13
|
end
|
15
14
|
end
|
15
|
+
|
16
|
+
def now
|
17
|
+
Time.now.to_datetime
|
18
|
+
end
|
16
19
|
|
17
20
|
def to_date
|
18
21
|
@time.to_date
|
@@ -0,0 +1,181 @@
|
|
1
|
+
# Copyright (c) 2023-2024 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-web'
|
23
|
+
|
24
|
+
Address = Struct.new(:street, :street2, :city, :state, :zip_code, :billing_and_shipping, keyword_init: true) do
|
25
|
+
STATES = {
|
26
|
+
"AK"=>"Alaska",
|
27
|
+
"AL"=>"Alabama",
|
28
|
+
"AR"=>"Arkansas",
|
29
|
+
"AS"=>"American Samoa",
|
30
|
+
"AZ"=>"Arizona",
|
31
|
+
"CA"=>"California",
|
32
|
+
"CO"=>"Colorado",
|
33
|
+
"CT"=>"Connecticut",
|
34
|
+
"DC"=>"District of Columbia",
|
35
|
+
"DE"=>"Delaware",
|
36
|
+
"FL"=>"Florida",
|
37
|
+
"GA"=>"Georgia",
|
38
|
+
"GU"=>"Guam",
|
39
|
+
"HI"=>"Hawaii",
|
40
|
+
"IA"=>"Iowa",
|
41
|
+
"ID"=>"Idaho",
|
42
|
+
"IL"=>"Illinois",
|
43
|
+
"IN"=>"Indiana",
|
44
|
+
"KS"=>"Kansas",
|
45
|
+
"KY"=>"Kentucky",
|
46
|
+
"LA"=>"Louisiana",
|
47
|
+
"MA"=>"Massachusetts",
|
48
|
+
"MD"=>"Maryland",
|
49
|
+
"ME"=>"Maine",
|
50
|
+
"MI"=>"Michigan",
|
51
|
+
"MN"=>"Minnesota",
|
52
|
+
"MO"=>"Missouri",
|
53
|
+
"MS"=>"Mississippi",
|
54
|
+
"MT"=>"Montana",
|
55
|
+
"NC"=>"North Carolina",
|
56
|
+
"ND"=>"North Dakota",
|
57
|
+
"NE"=>"Nebraska",
|
58
|
+
"NH"=>"New Hampshire",
|
59
|
+
"NJ"=>"New Jersey",
|
60
|
+
"NM"=>"New Mexico",
|
61
|
+
"NV"=>"Nevada",
|
62
|
+
"NY"=>"New York",
|
63
|
+
"OH"=>"Ohio",
|
64
|
+
"OK"=>"Oklahoma",
|
65
|
+
"OR"=>"Oregon",
|
66
|
+
"PA"=>"Pennsylvania",
|
67
|
+
"PR"=>"Puerto Rico",
|
68
|
+
"RI"=>"Rhode Island",
|
69
|
+
"SC"=>"South Carolina",
|
70
|
+
"SD"=>"South Dakota",
|
71
|
+
"TN"=>"Tennessee",
|
72
|
+
"TX"=>"Texas",
|
73
|
+
"UT"=>"Utah",
|
74
|
+
"VA"=>"Virginia",
|
75
|
+
"VI"=>"Virgin Islands",
|
76
|
+
"VT"=>"Vermont",
|
77
|
+
"WA"=>"Washington",
|
78
|
+
"WI"=>"Wisconsin",
|
79
|
+
"WV"=>"West Virginia",
|
80
|
+
"WY"=>"Wyoming"
|
81
|
+
}
|
82
|
+
|
83
|
+
def state_code
|
84
|
+
STATES.invert[state]
|
85
|
+
end
|
86
|
+
|
87
|
+
def state_code=(value)
|
88
|
+
self.state = STATES[value]
|
89
|
+
end
|
90
|
+
|
91
|
+
def summary
|
92
|
+
string_attributes = to_h.except(:billing_and_shipping)
|
93
|
+
summary = string_attributes.values.map(&:to_s).reject(&:empty?).join(', ')
|
94
|
+
summary += " (Billing & Shipping)" if billing_and_shipping
|
95
|
+
summary
|
96
|
+
end
|
97
|
+
end
|
98
|
+
|
99
|
+
@address = Address.new(
|
100
|
+
street: '123 Main St',
|
101
|
+
street2: 'Apartment 3C, 2nd door to the right',
|
102
|
+
city: 'San Diego',
|
103
|
+
state: 'California',
|
104
|
+
zip_code: '91911',
|
105
|
+
billing_and_shipping: true,
|
106
|
+
)
|
107
|
+
|
108
|
+
include Glimmer
|
109
|
+
|
110
|
+
Document.ready? do
|
111
|
+
div {
|
112
|
+
div(style: 'display: grid; grid-auto-columns: 80px 260px;') { |address_div|
|
113
|
+
label('Street: ', for: 'street-field')
|
114
|
+
input(id: 'street-field') {
|
115
|
+
# Bidirectional Data-Binding with <=> ensures input.value and @address.street
|
116
|
+
# automatically stay in sync when either side changes
|
117
|
+
value <=> [@address, :street]
|
118
|
+
}
|
119
|
+
|
120
|
+
label('Street 2: ', for: 'street2-field')
|
121
|
+
textarea(id: 'street2-field') {
|
122
|
+
value <=> [@address, :street2]
|
123
|
+
}
|
124
|
+
|
125
|
+
label('City: ', for: 'city-field')
|
126
|
+
input(id: 'city-field') {
|
127
|
+
value <=> [@address, :city]
|
128
|
+
}
|
129
|
+
|
130
|
+
label('State: ', for: 'state-field')
|
131
|
+
select(id: 'state-field') {
|
132
|
+
Address::STATES.each do |state_code, state|
|
133
|
+
option(value: state_code) { state }
|
134
|
+
end
|
135
|
+
|
136
|
+
value <=> [@address, :state_code]
|
137
|
+
}
|
138
|
+
|
139
|
+
label('Zip Code: ', for: 'zip-code-field')
|
140
|
+
input(id: 'zip-code-field', type: 'number', min: '0', max: '99999') {
|
141
|
+
# Bidirectional Data-Binding with <=> ensures input.value and @address.zip_code
|
142
|
+
# automatically stay in sync when either side changes
|
143
|
+
# on_write option specifies :to_s method to invoke on value before writing to model attribute
|
144
|
+
# to ensure the numeric zip code value is stored as a String
|
145
|
+
value <=> [@address, :zip_code,
|
146
|
+
on_write: :to_s,
|
147
|
+
]
|
148
|
+
}
|
149
|
+
|
150
|
+
div(style: 'grid-column: 1 / span 2') {
|
151
|
+
input(id: 'billing-and-shipping-field', type: 'checkbox') {
|
152
|
+
checked <=> [@address, :billing_and_shipping]
|
153
|
+
}
|
154
|
+
label(for: 'billing-and-shipping-field') {
|
155
|
+
'Use this address for both Billing & Shipping'
|
156
|
+
}
|
157
|
+
}
|
158
|
+
|
159
|
+
style {
|
160
|
+
<<~CSS
|
161
|
+
#{address_div.selector} * {
|
162
|
+
margin: 5px;
|
163
|
+
}
|
164
|
+
#{address_div.selector} input, #{address_div.selector} select {
|
165
|
+
grid-column: 2;
|
166
|
+
}
|
167
|
+
CSS
|
168
|
+
}
|
169
|
+
}
|
170
|
+
|
171
|
+
div(style: 'margin: 5px') {
|
172
|
+
# Unidirectional Data-Binding is done with <= to ensure @address.summary changes
|
173
|
+
# automatically update div.inner_text
|
174
|
+
# (computed by changes to address attributes, meaning if street changes,
|
175
|
+
# @address.summary is automatically recomputed.)
|
176
|
+
inner_text <= [@address, :summary,
|
177
|
+
computed_by: @address.members + ['state_code'],
|
178
|
+
]
|
179
|
+
}
|
180
|
+
}.render
|
181
|
+
end
|
@@ -0,0 +1,117 @@
|
|
1
|
+
# Copyright (c) 2023-2024 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-web'
|
23
|
+
|
24
|
+
class TimePresenter
|
25
|
+
attr_accessor :date_time, :month_string, :week_string
|
26
|
+
|
27
|
+
def initialize
|
28
|
+
@date_time = Time.now
|
29
|
+
end
|
30
|
+
|
31
|
+
def month_string
|
32
|
+
@date_time&.strftime('%Y-%m')
|
33
|
+
end
|
34
|
+
|
35
|
+
def month_string=(value)
|
36
|
+
if value.match(/^\d{4}-\d{2}$/)
|
37
|
+
year, month = value.split('-')
|
38
|
+
self.date_time = Time.new(year, month, date_time.day, date_time.hour, date_time.min)
|
39
|
+
end
|
40
|
+
end
|
41
|
+
|
42
|
+
def week_string
|
43
|
+
return nil if @date_time.nil?
|
44
|
+
year = @date_time.year
|
45
|
+
week = ((@date_time.yday / 7).to_i + 1).to_s.rjust(2, '0')
|
46
|
+
"#{year}-W#{week}"
|
47
|
+
end
|
48
|
+
|
49
|
+
def date_time_string
|
50
|
+
@date_time&.strftime('%Y-%m-%dT%H:%M')
|
51
|
+
end
|
52
|
+
|
53
|
+
def date_time_string=(value)
|
54
|
+
if value.match(/^\d{4}-\d{2}-\d{2}T\d{2}:\d{2}$/)
|
55
|
+
date_time_parts = value.split('T')
|
56
|
+
date_parts = date_time_parts.first.split('-')
|
57
|
+
time_parts = date_time_parts.last.split(':')
|
58
|
+
self.date_time = Time.new(*date_parts, *time_parts)
|
59
|
+
end
|
60
|
+
end
|
61
|
+
end
|
62
|
+
|
63
|
+
@time_presenter = TimePresenter.new
|
64
|
+
|
65
|
+
include Glimmer
|
66
|
+
|
67
|
+
Document.ready? do
|
68
|
+
div {
|
69
|
+
div(style: 'display: grid; grid-auto-columns: 130px 260px;') { |container_div|
|
70
|
+
label('Date Time: ', for: 'date-time-field')
|
71
|
+
input(id: 'date-time-field', type: 'datetime-local') {
|
72
|
+
# Bidirectional Data-Binding with <=> ensures input.value and @time_presenter.date_time
|
73
|
+
# automatically stay in sync when either side changes
|
74
|
+
value <=> [@time_presenter, :date_time]
|
75
|
+
}
|
76
|
+
|
77
|
+
label('Date: ', for: 'date-field')
|
78
|
+
input(id: 'date-field', type: 'date') {
|
79
|
+
value <=> [@time_presenter, :date_time]
|
80
|
+
}
|
81
|
+
|
82
|
+
label('Time: ', for: 'time-field')
|
83
|
+
input(id: 'time-field', type: 'time') {
|
84
|
+
value <=> [@time_presenter, :date_time]
|
85
|
+
}
|
86
|
+
|
87
|
+
label('Month: ', for: 'month-field')
|
88
|
+
input(id: 'month-field', type: 'month') {
|
89
|
+
value <=> [@time_presenter, :month_string, computed_by: :date_time]
|
90
|
+
}
|
91
|
+
|
92
|
+
label('Week: ', for: 'week-field')
|
93
|
+
input(id: 'week-field', type: 'week', disabled: true) {
|
94
|
+
value <=> [@time_presenter, :week_string, computed_by: :date_time]
|
95
|
+
}
|
96
|
+
|
97
|
+
label('Time String: ', for: 'time-string-field')
|
98
|
+
input(id: 'time-string-field', type: 'text') {
|
99
|
+
value <=> [@time_presenter, :date_time_string, computed_by: :date_time]
|
100
|
+
}
|
101
|
+
|
102
|
+
style {
|
103
|
+
<<~CSS
|
104
|
+
#{container_div.selector} * {
|
105
|
+
margin: 5px;
|
106
|
+
}
|
107
|
+
#{container_div.selector} label {
|
108
|
+
grid-column: 1;
|
109
|
+
}
|
110
|
+
#{container_div.selector} input {
|
111
|
+
grid-column: 2;
|
112
|
+
}
|
113
|
+
CSS
|
114
|
+
}
|
115
|
+
}
|
116
|
+
}.render
|
117
|
+
end
|
data/lib/glimmer-dsl-web.rb
CHANGED
@@ -1,4 +1,4 @@
|
|
1
|
-
# Copyright (c) 2023 Andy Maleh
|
1
|
+
# Copyright (c) 2023-2024 Andy Maleh
|
2
2
|
#
|
3
3
|
# Permission is hereby granted, free of charge, to any person obtaining
|
4
4
|
# a copy of this software and associated documentation files (the
|
@@ -48,7 +48,6 @@ if RUBY_ENGINE == 'opal'
|
|
48
48
|
require 'opal-async'
|
49
49
|
require 'async/ext'
|
50
50
|
require 'to_collection'
|
51
|
-
require 'pure-struct' # TODO double check if the latest Opal implemented everything below already
|
52
51
|
require 'glimmer-dsl-web/vendor/jquery'
|
53
52
|
require 'opal-jquery'
|
54
53
|
require 'opal/jquery/local_storage'
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: glimmer-dsl-web
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0.
|
4
|
+
version: 0.0.7
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Andy Maleh
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2024-01-02 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: glimmer
|
@@ -86,26 +86,6 @@ dependencies:
|
|
86
86
|
- - "<"
|
87
87
|
- !ruby/object:Gem::Version
|
88
88
|
version: 3.0.0
|
89
|
-
- !ruby/object:Gem::Dependency
|
90
|
-
name: pure-struct
|
91
|
-
requirement: !ruby/object:Gem::Requirement
|
92
|
-
requirements:
|
93
|
-
- - ">="
|
94
|
-
- !ruby/object:Gem::Version
|
95
|
-
version: 1.0.2
|
96
|
-
- - "<"
|
97
|
-
- !ruby/object:Gem::Version
|
98
|
-
version: 2.0.0
|
99
|
-
type: :runtime
|
100
|
-
prerelease: false
|
101
|
-
version_requirements: !ruby/object:Gem::Requirement
|
102
|
-
requirements:
|
103
|
-
- - ">="
|
104
|
-
- !ruby/object:Gem::Version
|
105
|
-
version: 1.0.2
|
106
|
-
- - "<"
|
107
|
-
- !ruby/object:Gem::Version
|
108
|
-
version: 2.0.0
|
109
89
|
- !ruby/object:Gem::Dependency
|
110
90
|
name: puts_debuggerer
|
111
91
|
requirement: !ruby/object:Gem::Requirement
|
@@ -259,22 +239,28 @@ files:
|
|
259
239
|
- lib/glimmer-dsl-web/ext/date.rb
|
260
240
|
- lib/glimmer-dsl-web/ext/exception.rb
|
261
241
|
- lib/glimmer-dsl-web/samples/hello/hello_button.rb
|
242
|
+
- lib/glimmer-dsl-web/samples/hello/hello_data_binding.rb
|
262
243
|
- lib/glimmer-dsl-web/samples/hello/hello_form.rb
|
244
|
+
- lib/glimmer-dsl-web/samples/hello/hello_input_date_time.rb
|
263
245
|
- lib/glimmer-dsl-web/samples/hello/hello_world.rb
|
264
246
|
- lib/glimmer-dsl-web/vendor/jquery.js
|
265
247
|
- lib/glimmer/config/opal_logger.rb
|
266
248
|
- lib/glimmer/data_binding/element_binding.rb
|
249
|
+
- lib/glimmer/dsl/web/bind_expression.rb
|
250
|
+
- lib/glimmer/dsl/web/data_binding_expression.rb
|
267
251
|
- lib/glimmer/dsl/web/dsl.rb
|
268
252
|
- lib/glimmer/dsl/web/element_expression.rb
|
253
|
+
- lib/glimmer/dsl/web/general_element_expression.rb
|
269
254
|
- lib/glimmer/dsl/web/listener_expression.rb
|
270
255
|
- lib/glimmer/dsl/web/p_expression.rb
|
271
256
|
- lib/glimmer/dsl/web/property_expression.rb
|
257
|
+
- lib/glimmer/dsl/web/select_expression.rb
|
258
|
+
- lib/glimmer/dsl/web/shine_data_binding_expression.rb
|
272
259
|
- lib/glimmer/util/proc_tracker.rb
|
273
260
|
- lib/glimmer/web.rb
|
274
261
|
- lib/glimmer/web/element_proxy.rb
|
275
262
|
- lib/glimmer/web/event_proxy.rb
|
276
263
|
- lib/glimmer/web/listener_proxy.rb
|
277
|
-
- lib/glimmer/web/property_owner.rb
|
278
264
|
homepage: http://github.com/AndyObtiva/glimmer-dsl-web
|
279
265
|
licenses:
|
280
266
|
- MIT
|
@@ -1,24 +0,0 @@
|
|
1
|
-
module Glimmer
|
2
|
-
module Web
|
3
|
-
# Adapts Glimmer UI classes to SWT JavaBean property owner classes (which are now adapted to Opal)
|
4
|
-
module PropertyOwner
|
5
|
-
# TODO consider adding has_attribute?
|
6
|
-
|
7
|
-
def get_attribute(attribute_name)
|
8
|
-
send(attribute_getter(attribute_name))
|
9
|
-
end
|
10
|
-
|
11
|
-
def set_attribute(attribute_name, *args)
|
12
|
-
send(attribute_setter(attribute_name), *args) unless args.size == 1 && send(attribute_getter(attribute_name)) == args.first
|
13
|
-
end
|
14
|
-
|
15
|
-
def attribute_setter(attribute_name)
|
16
|
-
"#{attribute_name.to_s.underscore}="
|
17
|
-
end
|
18
|
-
|
19
|
-
def attribute_getter(attribute_name)
|
20
|
-
attribute_name.to_s.underscore
|
21
|
-
end
|
22
|
-
end
|
23
|
-
end
|
24
|
-
end
|