ruby-macrodroid 0.8.12 → 0.9.4

Sign up to get free protection for your applications and to get access to all the features.
@@ -7,7 +7,95 @@
7
7
  # MacroObject
8
8
  #
9
9
 
10
+ module ObjectX
11
+
12
+ def action_to_object(ap, e, item, macro)
13
+
14
+ debug = true
15
+
16
+ puts 'inside action_to_object: item.xml: ' + item.xml if debug
17
+
18
+ if item.element('description') then
19
+
20
+ item.xpath('description').map do |description|
21
+
22
+ inner_lines = description.text.to_s.strip.lines
23
+ puts 'inner_lines: ' + inner_lines.inspect if debug
24
+
25
+ action = if e.text.to_s.strip.empty? then
26
+ inner_lines.shift.strip
27
+ else
28
+ e.text.strip
29
+ end
30
+
31
+ puts 'action: ' + action.inspect if debug
32
+
33
+ r = ap.find_action action
34
+ puts 'r: ' + r.inspect if debug
35
+ puts 'description: ' + description.xml.inspect if debug
36
+ #o = r[0].new([description, self]) if r
37
+ index = macro.actions.length
38
+ macro.add Action.new
39
+ o = object_create(r[0],[description, macro]) if r
40
+ macro.actions[index] = o
41
+ puts 'after o' if debug
42
+ o
43
+
44
+ end
45
+
46
+ else
47
+
48
+ action = e.text.strip
49
+ puts 'action: ' + action.inspect if @debug
50
+ r = ap.find_action action
51
+
52
+ a = e.xpath('item/*')
53
+
54
+ h = if a.any? then
55
+ a.map {|node| [node.name.to_sym, node.text.to_s]}.to_h
56
+ else
57
+ {}
58
+ end
59
+ puts 'h: ' + h.inspect if @debug
60
+
61
+ #r = ap.find_action action
62
+ #r[0].new(h.merge(macro: self)) if r
63
+ o = object_create(r[0], h.merge(macro: macro)) if r
64
+ macro.add o
65
+ o
66
+
67
+ end
68
+
69
+
70
+ end
10
71
 
72
+ def object_create(klass, *args)
73
+
74
+ begin
75
+ klass.new(*args)
76
+ rescue
77
+ raise MacroError, klass.to_s + ': ' + ($!).to_s
78
+ end
79
+ end
80
+
81
+ def varify(label, value='')
82
+
83
+ type = VAR_TYPES[value.class.to_s.to_sym]
84
+
85
+ h = {
86
+ boolean_value: false,
87
+ decimal_value: 0.0,
88
+ int_value: 0,
89
+ name: label,
90
+ string_value: '',
91
+ type: type[0]
92
+ }
93
+ h[type[1]] = value
94
+ h
95
+
96
+ end
97
+
98
+ end
11
99
 
12
100
  class MacroObject
13
101
  using ColouredText
@@ -34,19 +122,7 @@ class MacroObject
34
122
 
35
123
  def to_h()
36
124
 
37
- h = @h
38
-
39
- h2 = h.inject({}) do |r,x|
40
- puts 'x: ' + x.inspect if @debug
41
- key, value = x
42
- puts 'key: ' + key.inspect if @debug
43
- new_key = key.to_s.gsub(/\w_\w/){|x| x[0] + x[-1].upcase}
44
- new_key = new_key.prepend 'm_' unless @list.include? new_key
45
- new_key = 'm_SIGUID' if new_key == 'm_siguid'
46
- r.merge(new_key => value)
47
- end
48
-
49
- h2.merge('m_classType' => self.class.to_s)
125
+ hashify(@h)
50
126
 
51
127
  end
52
128
 
@@ -98,13 +174,31 @@ class MacroObject
98
174
 
99
175
  def object(h={})
100
176
 
101
- puts ('inside object h:' + h.inspect).debug if @debug
177
+ puts ('inside object h:' + h.inspect).debug if $debug
102
178
  klass = Object.const_get h[:class_type]
103
179
  puts klass.inspect.highlight if $debug
104
180
 
105
181
  klass.new h
106
182
 
107
- end
183
+ end
184
+
185
+ private
186
+
187
+ def hashify(h)
188
+
189
+ h2 = h.inject({}) do |r,x|
190
+ puts 'x: ' + x.inspect if $debug
191
+ key, value = x
192
+ puts 'key: ' + key.inspect if $debug
193
+ new_key = key.to_s.gsub(/\w_\w/){|x| x[0] + x[-1].upcase}
194
+ new_key = new_key.prepend 'm_' unless @list.include? new_key
195
+ new_key = 'm_SIGUID' if new_key == 'm_siguid'
196
+ new_val = value.is_a?(Hash) ? hashify(value) : value
197
+ r.merge(new_key => new_val)
198
+ end
199
+
200
+ h2.merge('m_classType' => self.class.to_s)
201
+ end
108
202
 
109
203
  end
110
204
 
@@ -794,6 +794,13 @@ class MacroDroidVariableConstraint < Constraint
794
794
 
795
795
  def initialize(h={})
796
796
 
797
+ if h[:loperand] then
798
+ h[:variable] = {}
799
+ h[:variable][:name] = h[:loperand]
800
+ h[:variable][:type] = 2
801
+ h[:string_value] = h[:roperand]
802
+ end
803
+
797
804
  options = {
798
805
 
799
806
  :enable_regex=>false,
@@ -825,11 +832,24 @@ class MacroDroidVariableConstraint < Constraint
825
832
 
826
833
  def to_s(colour: false, indent: 0)
827
834
 
828
- a = [:int_greater_than, :int_less_than, :int_not_equal,
829
- :string_equal].zip(['>','<','!=', '='])
830
- operator = a.find {|label,_| @h[label]}.last
835
+ a = [:int_greater_than, :int_less_than, :int_not_equal,
836
+ :string_equal].zip(['>','<','!=', '='])
837
+ operator = a.find {|label,_| @h[label]}.last
838
+
839
+ var = @h[:variable]
840
+
841
+ type = case var[:type]
842
+ when 0 # boolean
843
+ :boolean_value
844
+ when 1 # integer
845
+ :int_value
846
+ when 2 # string
847
+ :string_value
848
+ when 3 # decimal
849
+ :decimal_Value
850
+ end
831
851
 
832
- @s = "%s %s %s" % [@h[:variable][:name], operator, @h[:int_value]]
852
+ @s = "%s %s %s" % [@h[:variable][:name], operator, @h[type]]
833
853
  super()
834
854
  end
835
855
 
@@ -3,6 +3,10 @@
3
3
 
4
4
  # This file contains the following classes:
5
5
  #
6
+ # ## Nlp classes
7
+ #
8
+ # TriggersNlp ActionsNlp ConstraintsNlp
9
+ #
6
10
  # ## Macro class
7
11
  #
8
12
  # Macro
@@ -12,32 +16,414 @@
12
16
  VAR_TYPES = {
13
17
  String: [2, :string_value],
14
18
  TrueClass: [0, :boolean_value],
15
- TrueClass: [0, :boolean_value],
19
+ FalseClass: [0, :boolean_value],
16
20
  Integer: [1, :int_value],
17
21
  Float: [3, :decimal_value]
18
22
  }
19
23
 
20
24
 
25
+
26
+ class TriggersNlp
27
+ include AppRoutes
28
+
29
+ def initialize(macro=nil)
30
+
31
+ super()
32
+ params = {macro: macro}
33
+ triggers(params)
34
+
35
+ end
36
+
37
+ def triggers(params)
38
+
39
+ # e.g. at 7:30pm daily
40
+ get /^(?:at )?(\d+:\d+(?:[ap]m)?) daily/i do |time, days|
41
+ [TimerTrigger, {time: time,
42
+ days: %w(Mon Tue Wed Thu Fri Sat Sun).join(', ')}]
43
+ end
44
+
45
+ get /^(?:at )?(\d+:\d+(?:[ap]m)?) (?:on )?(.*)/i do |time, days|
46
+ [TimerTrigger, {time: time, days: days}]
47
+ end
48
+
49
+ # time.is? 'at 18:30pm on Mon or Tue'
50
+ get /^time.is\? ['"](?:at )?(\d+:\d+(?:[ap]m)?) (?:on )?(.*)['"]/i do |time, days|
51
+ [TimerTrigger, {time: time, days: days.gsub(' or ',', ')}]
52
+ end
53
+
54
+ get /^shake[ _]device\??$/i do
55
+ [ShakeDeviceTrigger, {}]
56
+ end
57
+
58
+ get /^Flip Device (.*)$/i do |motion|
59
+ facedown = motion =~ /Face Up (?:->|to) Face Down/i
60
+ [FlipDeviceTrigger, {face_down: facedown }]
61
+ end
62
+
63
+ get /^flip_device_down\?$/i do
64
+ [FlipDeviceTrigger, {face_down: true }]
65
+ end
66
+
67
+ get /^flip_device_up\?$/i do
68
+ [FlipDeviceTrigger, {face_down: false }]
69
+ end
70
+
71
+ get /^Failed Login Attempt$/i do
72
+ [FailedLoginTrigger, {}]
73
+ end
74
+
75
+ get /^failed_login?$/i do
76
+ [FailedLoginTrigger, {}]
77
+ end
78
+
79
+ get /^Geofence (Entry|Exit) \(([^\)]+)/i do |direction, name|
80
+ enter_area = direction.downcase.to_sym == :entry
81
+ [GeofenceTrigger, {name: name, enter_area: enter_area}]
82
+ end
83
+
84
+ get /^location (entered|exited) \(([^\)]+)/i do |direction, name|
85
+ enter_area = direction.downcase.to_sym == :entered
86
+ [GeofenceTrigger, {name: name, enter_area: enter_area}]
87
+ end
88
+
89
+ # eg. Proximity Sensor (Near)
90
+ #
91
+ get /^Proximity Sensor \(([^\)]+)\)/i do |distance|
92
+
93
+ [ProximityTrigger, {distance: distance}]
94
+ end
95
+
96
+ # eg. Proximity near
97
+ #
98
+ get /^Proximity (near|far|slow wave|fast wave)/i do |distance|
99
+
100
+ [ProximityTrigger, {distance: distance}]
101
+ end
102
+
103
+ get /^WebHook \(Url\)/i do
104
+ [WebHookTrigger, params]
105
+ end
106
+
107
+ get /^WebHook/i do
108
+ [WebHookTrigger, params]
109
+ end
110
+
111
+ get /^wh/i do
112
+ [WebHookTrigger, params]
113
+ end
114
+
115
+ # MacroDroid specific ---------------------------------------------------------------
116
+
117
+ get /^EmptyTrigger$/i do
118
+ [EmptyTrigger, params]
119
+ end
120
+
121
+ end
122
+
123
+ alias find_trigger run_route
124
+
125
+ def to_s(colour: false)
126
+ 'TriggersNlp ' + @h.inspect
127
+ end
128
+
129
+ alias to_summary to_s
130
+ end
131
+
132
+ class ActionsNlp
133
+ include AppRoutes
134
+
135
+ def initialize(macro=nil)
136
+
137
+ super()
138
+ params = {macro: macro}
139
+ actions(params)
140
+
141
+ end
142
+
143
+ def actions(params)
144
+
145
+ # e.g. message popup: hello world!
146
+ get /^message popup: (.*)/i do |msg|
147
+ [ToastAction, {msg: msg}]
148
+ end
149
+
150
+ # e.g. Popup Message 'hello world!'
151
+ get /^Popup[ _]Message ['"]([^'"]+)/i do |msg|
152
+ [ToastAction, {msg: msg}]
153
+ end
154
+
155
+ # e.g. Popup Message\n hello world!
156
+ get /^Popup Message\n\s+(.*)/im do |msg|
157
+ [ToastAction, {msg: msg}]
158
+ end
159
+
160
+ # e.g. Popup Message
161
+ get /^Popup Message$/i do
162
+ [ToastAction, {}]
163
+ end
164
+
165
+ # e.g. say current time
166
+ get /^say current[ _]time/i do
167
+ [SayTimeAction, {}]
168
+ end
169
+
170
+ get /^Torch :?(.*)/i do |onoffstate|
171
+ state = %w(on off toggle).index onoffstate.downcase
172
+ [CameraFlashLightAction, {state: state}]
173
+ end
174
+
175
+ get /^Take Picture/i do
176
+ [TakePictureAction, {}]
177
+ end
178
+
179
+ get /^take_picture/i do
180
+ [TakePictureAction, {}]
181
+ end
182
+
183
+ # -- DEVICE ACTIONS ------------------------------------------------------
184
+
185
+ get /^Speak text \(([^\)]+)\)/i do |text|
186
+ [SpeakTextAction, {text: text}]
187
+ end
188
+
189
+ get /^Speak text ['"]([^'"]+)/i do |text|
190
+ [SpeakTextAction, {text: text}]
191
+ end
192
+
193
+ get /^Speak text$/i do |text|
194
+ [SpeakTextAction, {}]
195
+ end
196
+
197
+ get /^Vibrate \(([^\)]+)/i do |pattern|
198
+ [VibrateAction, {pattern: pattern}]
199
+ end
200
+
201
+ # e.g. Display Notification: Hi there: This is the body of the message
202
+ get /^Display Notification: ([^:]+): [^$]+$/i do |subject, text|
203
+ [NotificationAction, {subject: subject, text: text}]
204
+ end
205
+
206
+
207
+ # e.g. Enable Wifi
208
+ get /^(Enable|Disable) Wifi$/i do |raw_state|
209
+
210
+ state = raw_state.downcase.to_sym == :enable ? 0 : 1
211
+ [SetWifiAction, {state: state}]
212
+
213
+ end
214
+
215
+ # e.g. Play: Altair
216
+ get /^Play: (.*)$/i do |name|
217
+
218
+ [PlaySoundAction, {file_path: name}]
219
+
220
+ end
221
+
222
+ # e.g. Launch Settings
223
+ get /^Launch (.*)$/i do |application|
224
+
225
+ h = {
226
+ application_name: application,
227
+ package_to_launch: 'com.android.' + application.downcase
228
+ }
229
+ [LaunchActivityAction, h]
230
+
231
+ end
232
+
233
+ # e.g. HTTP GET http://someurl.com/something
234
+ get /^HTTP GET ([^$]+)$/i do |url|
235
+
236
+ [OpenWebPageAction, url_to_open: url]
237
+
238
+ end
239
+
240
+ get /^HTTP GET$/i do
241
+
242
+ [OpenWebPageAction, {}]
243
+
244
+ end
245
+
246
+ # e.g. webhook entered_kitchen
247
+ #
248
+ get /(?:webhook|HTTP GET) ([^$]+)$/i do |s|
249
+ key = s =~ /^http/ ? :url_to_open : :identifier
250
+ [OpenWebPageAction, {key => s}]
251
+ end
252
+
253
+ #
254
+ get /^WebHook \(Url\)/i do
255
+ [OpenWebPageAction, params]
256
+ end
257
+
258
+ # e.g. webhook entered_kitchen
259
+ #
260
+ get /^webhook$/i do
261
+ [OpenWebPageAction, params]
262
+ end
263
+
264
+ # -- Location ---------------------------------------------------------
265
+
266
+ get /^Force Location Update$/i do
267
+ [ForceLocationUpdateAction, params]
268
+ end
269
+
270
+ get /^Share Location$/i do
271
+ [ShareLocationAction, params]
272
+ end
273
+
274
+ #a: Keep Device Awake Screen On Until Disabled
275
+ #
276
+ get /Keep Device Awake Screen On Until Disabled/i do
277
+ [KeepAwakeAction, {enabled: true, permanent: true, screen_option: 0}]
278
+ end
279
+
280
+
281
+ #a: Keep Device Awake Screen On 1h 1m 1s
282
+ #
283
+ get /Keep Device Awake Screen On ([^$]+)/i do |duration|
284
+
285
+ a = duration.split.map(&:to_i)
286
+ secs = Subunit.new(units={minutes:60, hours:60, seconds: 60}, a).to_i
287
+
288
+ h = {
289
+ permanent: true, screen_option: 0, seconds_to_stay_awake_for: secs
290
+ }
291
+ [KeepAwakeAction, h]
292
+ end
293
+
294
+ get /Keep Device Awake$/i do
295
+ [KeepAwakeAction, params]
296
+ end
297
+
298
+ #a: Disable Keep Awake
299
+ #
300
+ get /Disable Keep Awake/i do
301
+ [KeepAwakeAction, {enabled: false, screen_option: 0}]
302
+ end
303
+
304
+ #e.g a: if Airplane mode enabled
305
+ #
306
+ get /if (.*)/i do
307
+ [IfConditionAction, {}]
308
+ end
309
+
310
+ get /End If/i do
311
+ [EndIfAction, {}]
312
+ end
313
+
314
+ # -- MacroDroid Specific ------------------------------------------------
315
+ #
316
+ get /^Set Variable$/i do
317
+ [SetVariableAction, {}]
318
+ end
319
+
320
+ end
321
+
322
+ alias find_action run_route
323
+
324
+
325
+ end
326
+
327
+ class ConstraintsNlp
328
+ include AppRoutes
329
+
330
+ def initialize()
331
+
332
+ super()
333
+ params = {}
334
+ constraints(params)
335
+
336
+ end
337
+
338
+ def constraints(params)
339
+
340
+ # Device State
341
+
342
+ get /^Device (locked|unlocked)/i do |state|
343
+ [DeviceLockedConstraint, {locked: state.downcase == 'locked'}]
344
+ end
345
+
346
+ get /^airplane mode (.*)/i do |state|
347
+ [AirplaneModeConstraint, {enabled: (state =~ /^enabled|on$/i) == 0}]
348
+ end
349
+
350
+ #
351
+
352
+ # -- MacroDroid specific -----------------------------------------------------------------------
353
+
354
+ get /^(\w+) (=) (\[?\w+\]?)/i do |loperand, operator, roperand|
355
+
356
+ h = {
357
+ loperand: loperand,
358
+ operator: operator,
359
+ roperand: roperand
360
+ }
361
+
362
+ [MacroDroidVariableConstraint, h]
363
+
364
+ end
365
+
366
+ # -- Sensors -----------------------------------
367
+ #
368
+ get /^Light Sensor (Less|Greater) than (50.0)lx/i do |operator, val|
369
+
370
+ level, option = operator.downcase == 'less' ? [-1,0] : [1,1]
371
+
372
+ h = {
373
+ light_level: level,
374
+ light_level_float: val,
375
+ option: option
376
+ }
377
+
378
+ [LightLevelConstraint, h]
379
+ end
380
+
381
+ get /^Proximity Sensor: (Near|Far)/i do |distance|
382
+ [ProximitySensorConstraint, {near: distance.downcase == 'near'}]
383
+ end
384
+
385
+
386
+ # -- Screen and Speaker ---------------------------
387
+ #
388
+ get /^Screen (On|Off)/i do |state|
389
+ [ScreenOnOffConstraint, {screen_on: state.downcase == 'on'}]
390
+ end
391
+
392
+ end
393
+
394
+ alias find_constraint run_route
395
+
396
+ end
397
+
398
+
399
+ class MacroError < Exception
400
+ end
401
+
21
402
  class Macro
22
403
  using ColouredText
23
404
  using Params
405
+ include ObjectX
24
406
 
25
407
  attr_reader :local_variables, :triggers, :actions, :constraints,
26
408
  :guid, :deviceid
27
- attr_accessor :title, :description
409
+ attr_accessor :title, :description, :remote_url
28
410
 
29
- def initialize(name=nil, geofences: nil, deviceid: nil, debug: false)
411
+ def initialize(name=nil, geofences: nil, deviceid: nil, remote_url: nil,
412
+ debug: false)
30
413
 
31
414
  @title, @geofences, @deviceid, @debug = name, geofences, deviceid, debug
415
+ @remote_url = remote_url
32
416
 
33
417
  puts 'inside Macro#initialize' if @debug
34
418
 
35
- @local_variables, @triggers, @actions, @constraints = [], [], [], []
419
+ @local_variables, @triggers, @actions, @constraints = {}, [], [], []
36
420
  @h = {}
37
421
 
38
422
  end
39
423
 
40
424
  def add(obj)
425
+ puts 'inside add; ' + obj.inspect
426
+ puts '@actions: ' + @actions.inspect
41
427
 
42
428
  if obj.kind_of? Trigger then
43
429
 
@@ -59,9 +445,13 @@ class Macro
59
445
  end
60
446
 
61
447
  def to_h()
448
+
449
+ a = @local_variables.map do |k,v|
450
+ varify(k,v).to_camelcase.map{|key,value| ['m_' + key, value]}.to_h
451
+ end
62
452
 
63
453
  h = {
64
- local_variables: varify(@local_variables),
454
+ local_variables: a,
65
455
  m_trigger_list: @triggers.map(&:to_h),
66
456
  m_action_list: @actions.map(&:to_h),
67
457
  m_category: @category,
@@ -71,7 +461,7 @@ class Macro
71
461
  m_excludeLog: false,
72
462
  m_GUID: guid(),
73
463
  m_isOrCondition: false,
74
- m_enabled: false,
464
+ m_enabled: true,
75
465
  m_descriptionOpen: false,
76
466
  m_headingColor: 0
77
467
  }
@@ -96,7 +486,7 @@ class Macro
96
486
  if h[:local_variables].any? and h[:local_variables].first.any? then
97
487
 
98
488
  @local_variables = h[:local_variables].map do |var|
99
-
489
+
100
490
  val = case var[:type]
101
491
  when 0 # boolean
102
492
  var[:boolean_value]
@@ -115,7 +505,7 @@ class Macro
115
505
 
116
506
  # fetch the triggers
117
507
  @triggers = h[:trigger_list].map do |trigger|
118
- puts 'trigger: ' + trigger.inspect
508
+ puts 'trigger: ' + trigger.inspect if @debug
119
509
  #exit
120
510
  object(trigger.to_snake_case)
121
511
 
@@ -194,37 +584,33 @@ class Macro
194
584
 
195
585
  @title = node.text('macro') || node.attributes[:name]
196
586
 
197
- @local_variables = node.xpath('variable').map do |e|
198
- e.text.split(/: +/,2)
587
+ d = node.element('description')
588
+
589
+ if d then
590
+
591
+ desc = []
592
+ desc << d.text.strip
593
+
594
+ if d.element('item/description') then
595
+ desc << d.text('item/description').strip
596
+ end
597
+
598
+ @description = desc.join("\n")
599
+
199
600
  end
200
601
 
602
+ node.xpath('variable').each {|e| set_var(*e.text.to_s.split(/: */,2)) }
603
+
201
604
  #@description = node.attributes[:description]
202
605
 
203
606
  tp = TriggersNlp.new(self)
204
607
 
205
- @triggers = node.xpath('trigger').map do |e|
608
+ @triggers = node.xpath('trigger').flat_map do |e|
206
609
 
207
610
  r = tp.find_trigger e.text
208
611
 
209
612
  puts 'found trigger ' + r.inspect if @debug
210
613
 
211
- if r then
212
- if r[0] == GeofenceTrigger then
213
- GeofenceTrigger.new(r[1], geofences: @geofences)
214
- else
215
- r[0].new(r[1])
216
- end
217
- end
218
-
219
- end
220
-
221
- ap = ActionsNlp.new
222
-
223
- @actions = node.xpath('action').flat_map do |e|
224
-
225
- puts 'action e: ' + e.xml.inspect if @debug
226
- puts 'e.text ' + e.text if @debug
227
-
228
614
  item = e.element('item')
229
615
  if item then
230
616
 
@@ -235,26 +621,27 @@ class Macro
235
621
  inner_lines = description.text.to_s.strip.lines
236
622
  puts 'inner_lines: ' + inner_lines.inspect if @debug
237
623
 
238
- action = if e.text.to_s.strip.empty? then
624
+ trigger = if e.text.to_s.strip.empty? then
239
625
  inner_lines.shift.strip
240
626
  else
241
627
  e.text.strip
242
628
  end
243
629
 
244
- puts 'action: ' + action.inspect if @debug
630
+ puts 'trigger: ' + trigger.inspect if @debug
245
631
 
246
- r = ap.find_action action
632
+ r = tp.find_trigger trigger
247
633
  puts 'r: ' + r.inspect if @debug
248
- o = r[0].new(description) if r
249
- puts 'after o'
634
+ #o = r[0].new([description, self]) if r
635
+ o = object_create(r[0], [description, self]) if r
636
+ puts 'after o' if @debug
250
637
  o
251
638
 
252
639
  end
253
640
 
254
641
  else
255
642
 
256
- action = e.text.strip
257
- r = ap.find_action action
643
+ trigger = e.text.strip
644
+ r = tp.find_trigger trigger
258
645
 
259
646
  a = e.xpath('item/*')
260
647
 
@@ -264,18 +651,56 @@ class Macro
264
651
  {}
265
652
  end
266
653
 
267
- r = ap.find_action action
268
- r[0].new(h) if r
654
+ r = tp.find_trigger trigger
655
+ #r[0].new(h) if r
656
+ if r then
657
+ object_create(r[0], h)
658
+ else
659
+ raise MacroError, 'App-routes: Trigger "' + trigger + '" not found'
660
+ end
269
661
 
270
662
  end
271
663
 
664
+ else
665
+
666
+ trigger = e.text.strip
667
+ r = tp.find_trigger trigger
668
+ #r[0].new(r[1]) if r
669
+
670
+ if r then
671
+ object_create(r[0],r[1])
672
+ else
673
+ raise MacroError, 'App-routes: Trigger "' + trigger + '" not found'
674
+ end
675
+
676
+ end
677
+
678
+
679
+ end
680
+
681
+
682
+
683
+ ap = ActionsNlp.new self
684
+
685
+ node.xpath('action').each do |e|
686
+
687
+ puts 'action e: ' + e.xml.inspect if @debug
688
+ puts 'e.text ' + e.text if @debug
689
+
690
+ item = e.element('item')
691
+
692
+ if item then
693
+
694
+ action_to_object(ap, e, item, self)
695
+
272
696
  else
273
697
 
274
698
  action = e.text.strip
275
699
  r = ap.find_action action
276
- r[0].new(r[1]) if r
700
+ #r[0].new(r[1]) if r
701
+ self.add object_create(r[0],r[1]) if r
277
702
 
278
- end
703
+ end
279
704
 
280
705
  end
281
706
 
@@ -286,9 +711,7 @@ class Macro
286
711
  r = cp.find_constraint e.text
287
712
  puts 'found constraint ' + r.inspect if @debug
288
713
 
289
- if r then
290
- r[0].new(r[1])
291
- end
714
+ object_create(r[0], r[1]) if r
292
715
 
293
716
  end
294
717
 
@@ -333,6 +756,27 @@ class Macro
333
756
  def set_env()
334
757
  @triggers.each(&:set_env)
335
758
  end
759
+
760
+ def set_var(label, v='')
761
+
762
+ value = if v.to_f.to_s == v
763
+ v.to_f
764
+ elsif v.downcase == 'true'
765
+ true
766
+ elsif v.downcase == 'false'
767
+ false
768
+ elsif v.to_i.to_s == v
769
+ v.to_i
770
+ else
771
+ v
772
+ end
773
+
774
+ if not @local_variables.has_key? label.to_sym then
775
+ @local_variables.merge!({label.to_sym => value})
776
+ end
777
+
778
+ varify(label, value)
779
+ end
336
780
 
337
781
  def to_pc()
338
782
 
@@ -378,13 +822,21 @@ EOF
378
822
  puts 'before triggers' if @debug
379
823
 
380
824
  a << @triggers.map do |x|
825
+
826
+ puts 'x: ' + x.inspect if @debug
827
+ raise 'Macro#to_s trigger cannot be nil' if x.nil?
828
+
381
829
  s =-x.to_s(colour: colour)
830
+ puts 's: ' + s.inspect if @debug
382
831
 
383
832
  s2 = if s.lines.length > 1 then
384
833
  "\n" + s.lines.map {|x| x.prepend (' ' * (indent+1)) }.join
385
834
  else
386
835
  ' ' + s
387
836
  end
837
+
838
+ puts 's2: ' + s2.inspect if @debug
839
+
388
840
  #s.lines > 1 ? "\n" + x : x
389
841
  (colour ? "t".bg_red.gray.bold : 't') + ":" + s2
390
842
  end.join("\n")
@@ -519,43 +971,24 @@ EOF
519
971
 
520
972
  puts ('inside object h:' + h.inspect).debug if @debug
521
973
  klass = Object.const_get h[:class_type]
522
- puts klass.inspect.highlight if $debug
974
+ puts klass.inspect.highlight if @debug
523
975
 
524
976
  if klass == GeofenceTrigger then
525
- puts 'GeofenceTrigger found'.highlight if $debug
977
+ puts 'GeofenceTrigger found'.highlight if @debug
526
978
  GeofenceTrigger.new(h, geofences: @geofences)
527
979
  else
528
- puts 'before klass'
980
+ puts 'before klass' if @debug
529
981
  h2 = h.merge( macro: self)
530
- puts 'h2: ' + h2.inspect
982
+ puts 'h2: ' + h2.inspect if @debug
531
983
  r = klass.new h2
532
- puts 'r:' + r.inspect
984
+ puts 'r:' + r.inspect if @debug
533
985
  r
534
986
 
535
987
  end
536
988
 
537
989
  end
538
990
 
539
- def varify(local_variables)
540
-
541
-
542
- local_variables.map do |key, value|
543
-
544
-
545
- type = VAR_TYPES[value.class.to_s.to_sym]
546
-
547
- h = {
548
- boolean_value: false,
549
- decimal_value: 0.0,
550
- int_value: 0,
551
- name: key,
552
- string_value: '',
553
- type: type[0]
554
- }
555
- h[type[1]] = value
556
- h
557
- end
558
-
559
- end
991
+
992
+
560
993
 
561
994
  end