19
19
class ExternalModule extends AbstractExternalModule {
20
20
private $ survey_APF_fields = [];
21
21
22
+ function isFirstRepeatEventOrForm () {
23
+ $ val = ($ this ->isFirstRepeatEvent () || $ this ->isFirstRepeatForm ());
24
+ return $ val ;
25
+ }
26
+
27
+ function isNthRepeatEventOrForm () {
28
+ $ val = ($ this ->isNthRepeatEvent () || $ this ->isNthRepeatForm ());
29
+ return $ val ;
30
+ }
31
+
22
32
/**
23
- * Returns true if the event is either a "Repeat Entire Event" or "Repeat Instrument" repeating event .
33
+ * Returns true if the event is a "Repeat Entire Event (repeat all instruments together)" and is the first instance .
24
34
*/
25
- function isRepeatEvent () {
26
- $ val = ($ this ->isRepeatEntireEvent () || $ this ->isRepeatInstrument ());
27
- return $ val ;
35
+ function isFirstRepeatEvent () {
36
+ if ($ _GET ['instance ' ] == 1 && $ GLOBALS ['isRepeatingEvent ' ]) {
37
+ return true ;
38
+ }
39
+ return false ;
28
40
}
29
41
30
42
/**
31
- * Returns true if the event is a "Repeat Entire Event (repeat all instruments together)" and is not first instance.
43
+ * Returns true if the event is a "Repeat Entire Event (repeat all instruments together)" and is NOT first instance.
32
44
*/
33
- function isRepeatEntireEvent () {
34
- // The first instance of Repeating events are treated differently from events where $_GET['instance'] > 1.
35
- // For the first instance, we look at previous event. For $_GET['instance'] > 1, we look at the current event.
36
- // Because $GLOBALS['isRepeatingEvent'] is true regardless of the instance of the event, we also check for the current instance.
45
+ function isNthRepeatEvent () {
37
46
if ($ _GET ['instance ' ] > 1 && $ GLOBALS ['isRepeatingEvent ' ]) {
38
47
return true ;
39
48
}
40
49
return false ;
41
50
}
42
51
43
52
/**
44
- * Returns true if the event is a "Repeat Instrument (repeat independently of each other)".
53
+ * Returns true if the event is a "Repeat Instrument (repeat independently of each other)" and is the first instance.
45
54
*/
46
- function isRepeatInstrument () {
47
- return $ GLOBALS ['isRepeatingForm ' ];
55
+ function isFirstRepeatForm () {
56
+ return ($ _GET ['instance ' ] == 1 && $ GLOBALS ['isRepeatingForm ' ]);
57
+ }
58
+
59
+ /**
60
+ * Returns true if the event is a "Repeat Instrument (repeat independently of each other)" and is NOT the first instance.
61
+ */
62
+ function isNthRepeatForm () {
63
+ return ($ _GET ['instance ' ] > 1 && $ GLOBALS ['isRepeatingForm ' ]);
48
64
}
49
65
50
66
/**
@@ -192,29 +208,27 @@ function setDefaultValues() {
192
208
$ source_form = $ Proj ->metadata [$ source_field ]['form_name ' ];
193
209
194
210
// Getting previous event ID.
195
- // For non repeating events the previous event is the closest event prior to the current event
196
- // For repeating events, (Repeat Entire Event & Repeat Instrument) the previous event is the current event
211
+ // For the first instance of a repeating event/form, the previous event is the closest saved event/form prior to the current event/form.
212
+ // For the nth instance of a repeating event/form, the previous event is the current event.
197
213
foreach ($ events as $ event ) {
198
- // Only break for non repeating events.
199
- // Non repeating events should not get data from current event, whereas, repeating events with instances depend on data from the current event i.e., $_GET['event_id']
200
- if ($ event == $ _GET ['event_id ' ] && !$ this ->isRepeatEvent ()) {
214
+ if (!in_array ($ source_form , $ Proj ->eventsForms [$ event ])) {
201
215
break ;
202
216
}
203
217
204
- if (in_array ($ source_form , $ Proj ->eventsForms [$ event ]) && !$ this ->isRepeatEvent ()) {
205
- $ prev_event = $ event ;
206
- $ form_name = "" ;
207
- } elseif (in_array ($ source_form , $ Proj ->eventsForms [$ event ]) && $ this ->isRepeatEntireEvent ()) {
208
- $ prev_event = $ _GET ['event_id ' ];
209
- $ form_name = "" ;
218
+ // Only break for the first instance of an event/form.
219
+ // First instance events or forms need data from previous events/forms, whereas, nth repeating events/forms depend on data from the current event i.e., $_GET['event_id']
220
+ if ($ event == $ _GET ['event_id ' ] && $ this ->isFirstRepeatEventOrForm ()) {
210
221
break ;
211
- } elseif (in_array ($ source_form , $ Proj ->eventsForms [$ event ]) && $ this ->isRepeatInstrument ()) {
212
- // Repeat instruments behave differently from 'Repeat Entire Event' and non repeating events.
213
- // Repeat instruments require the $Proj->metadata[$field_name]['form_name'] when looking up the data from the event
222
+ }
223
+
224
+ // Set the previous event for first instance of a repeat event/form to the previous event.
225
+ // Set the previous event for the nth instance of a repeat event/form to the current event.
226
+ if ($ this ->isFirstRepeatEventOrForm ()) {
227
+ $ prev_event = $ event ;
228
+ } elseif ($ this ->isNthRepeatEventOrForm ()) {
214
229
$ prev_event = $ _GET ['event_id ' ];
215
- $ form_name = $ source_form ;
216
230
break ;
217
- }
231
+ }
218
232
}
219
233
220
234
if (!$ prev_event ) {
@@ -225,12 +239,20 @@ function setDefaultValues() {
225
239
// isset returns true for event instances when $prev_event_field_value is equal to an empty string ("").
226
240
// An additional check to verify the value is not empty is required.
227
241
$ prev_event_field_value = $ data [$ prev_event ][$ source_field ];
242
+
243
+ // The object returned by $instances = $data['repeat_instances'][$event] changes dependening on if the data is from an event or a form.
244
+ // For repeating events, the key for $instances is an empty string ("") i.e., ["": ...]
245
+ // For repeating forms, the key for $instances is the form name i.e., ["baseline_data": ...]
246
+ $ instances = ($ data ['repeat_instances ' ][$ prev_event ][$ source_form ]) ?? ($ data ['repeat_instances ' ][$ prev_event ]["" ]);
247
+
228
248
if (isset ($ prev_event_field_value ) && !empty ($ prev_event_field_value )) {
229
249
$ default_value = $ prev_event_field_value ;
230
- } elseif (isset ($ data [ ' repeat_instances ' ][ $ prev_event ][ $ form_name ] )) {
250
+ } elseif (isset ($ instances )) {
231
251
// Handling repeat events by using the most recent instance of the previous event to source values
232
- $ most_recent_instance = array_slice ($ data ['repeat_instances ' ][$ prev_event ][$ form_name ], -1 )[0 ];
233
- $ default_value = $ most_recent_instance [$ source_field ];
252
+ // $instances are out of order when form data is deleted.
253
+ // In that case, using array_slice($instances, -1)[0] is unreliable and can return the instance
254
+ $ max = max (array_keys ($ instances ));
255
+ $ default_value = $ instances [$ max ][$ source_field ];
234
256
}
235
257
236
258
// Handling checkboxes case.
0 commit comments