@skylord123/node-red-pebble-timeline 1.0.0
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.
- package/LICENSE +21 -0
- package/README.md +73 -0
- package/examples/README.md +7 -0
- package/examples/example.json +598 -0
- package/examples/example.png +0 -0
- package/package.json +25 -0
- package/pebble-timeline-add.html +926 -0
- package/pebble-timeline-add.js +744 -0
- package/pebble-timeline-config.html +63 -0
- package/pebble-timeline-config.js +13 -0
- package/pebble-timeline-delete.html +122 -0
- package/pebble-timeline-delete.js +190 -0
- package/pebble-timeline-list.html +151 -0
- package/pebble-timeline-list.js +195 -0
|
@@ -0,0 +1,926 @@
|
|
|
1
|
+
<style>
|
|
2
|
+
/* Additional styles for the Pebble Timeline Add node */
|
|
3
|
+
.form-section-title.calendar-active {
|
|
4
|
+
color: #4285f4;
|
|
5
|
+
}
|
|
6
|
+
|
|
7
|
+
.form-section-title.sports-active {
|
|
8
|
+
color: #ea4335;
|
|
9
|
+
}
|
|
10
|
+
|
|
11
|
+
.form-section-title.weather-active {
|
|
12
|
+
color: #34a853;
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
.form-subsection {
|
|
16
|
+
margin-left: 10px;
|
|
17
|
+
padding-left: 10px;
|
|
18
|
+
border-left: 2px solid #eee;
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
.create-notification, .update-notification, .reminders-section, .actions-section {
|
|
22
|
+
display: none;
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
/* Improve visual hierarchy */
|
|
26
|
+
.form-section {
|
|
27
|
+
margin-top: 15px;
|
|
28
|
+
border-top: 1px solid #f0f0f0;
|
|
29
|
+
padding-top: 10px;
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
.form-section-title {
|
|
33
|
+
font-weight: bold;
|
|
34
|
+
margin-bottom: 10px;
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
.form-tips {
|
|
38
|
+
font-size: 0.9em;
|
|
39
|
+
}
|
|
40
|
+
</style>
|
|
41
|
+
|
|
42
|
+
<script type="text/javascript">
|
|
43
|
+
RED.nodes.registerType('pebble-timeline-add', {
|
|
44
|
+
category: 'Pebble',
|
|
45
|
+
color: '#1da1f2',
|
|
46
|
+
defaults: {
|
|
47
|
+
name: { value: "" },
|
|
48
|
+
config: { type: "pebble-timeline-config", required: true },
|
|
49
|
+
|
|
50
|
+
// Server override options
|
|
51
|
+
apiUrl: { value: "null" },
|
|
52
|
+
apiUrlType: { value: "jsonata" },
|
|
53
|
+
|
|
54
|
+
token: { value: "null" },
|
|
55
|
+
tokenType: { value: "jsonata" },
|
|
56
|
+
|
|
57
|
+
// Pin basic properties
|
|
58
|
+
pinId: { value: "payload.id" },
|
|
59
|
+
pinIdType: { value: "msg" },
|
|
60
|
+
|
|
61
|
+
time: { value: "payload.time" },
|
|
62
|
+
timeType: { value: "msg" },
|
|
63
|
+
|
|
64
|
+
duration: { value: "payload.duration" },
|
|
65
|
+
durationType: { value: "msg" },
|
|
66
|
+
|
|
67
|
+
// Pin layout properties
|
|
68
|
+
layoutType: { value: "genericPin" },
|
|
69
|
+
|
|
70
|
+
title: { value: "topic" },
|
|
71
|
+
titleType: { value: "msg" },
|
|
72
|
+
|
|
73
|
+
subtitle: { value: "payload.subtitle" },
|
|
74
|
+
subtitleType: { value: "msg" },
|
|
75
|
+
|
|
76
|
+
body: { value: "payload.body" },
|
|
77
|
+
bodyType: { value: "msg" },
|
|
78
|
+
|
|
79
|
+
tinyIcon: { value: "payload.tinyIcon" },
|
|
80
|
+
tinyIconType: { value: "msg" },
|
|
81
|
+
|
|
82
|
+
smallIcon: { value: "payload.smallIcon" },
|
|
83
|
+
smallIconType: { value: "msg" },
|
|
84
|
+
|
|
85
|
+
largeIcon: { value: "payload.largeIcon" },
|
|
86
|
+
largeIconType: { value: "msg" },
|
|
87
|
+
|
|
88
|
+
// Color properties
|
|
89
|
+
primaryColor: { value: "payload.primaryColor" },
|
|
90
|
+
primaryColorType: { value: "msg" },
|
|
91
|
+
|
|
92
|
+
secondaryColor: { value: "payload.secondaryColor" },
|
|
93
|
+
secondaryColorType: { value: "msg" },
|
|
94
|
+
|
|
95
|
+
backgroundColor: { value: "payload.backgroundColor" },
|
|
96
|
+
backgroundColorType: { value: "msg" },
|
|
97
|
+
|
|
98
|
+
// Notifications
|
|
99
|
+
createNotification: { value: false },
|
|
100
|
+
updateNotification: { value: false },
|
|
101
|
+
|
|
102
|
+
// Advanced pin properties not commonly used
|
|
103
|
+
headings: { value: "null" },
|
|
104
|
+
headingsType: { value: "jsonata" },
|
|
105
|
+
|
|
106
|
+
paragraphs: { value: "null" },
|
|
107
|
+
paragraphsType: { value: "jsonata" },
|
|
108
|
+
|
|
109
|
+
lastUpdated: { value: "null" },
|
|
110
|
+
lastUpdatedType: { value: "jsonata" },
|
|
111
|
+
|
|
112
|
+
// Notification properties - Create
|
|
113
|
+
createNotificationTitle: { value: "payload.createNotification.title" },
|
|
114
|
+
createNotificationTitleType: { value: "msg" },
|
|
115
|
+
|
|
116
|
+
createNotificationBody: { value: "payload.createNotification.body" },
|
|
117
|
+
createNotificationBodyType: { value: "msg" },
|
|
118
|
+
|
|
119
|
+
createNotificationTinyIcon: { value: "payload.createNotification.tinyIcon" },
|
|
120
|
+
createNotificationTinyIconType: { value: "msg" },
|
|
121
|
+
|
|
122
|
+
// Notification properties - Update
|
|
123
|
+
updateNotificationTime: { value: "payload.updateNotification.time" },
|
|
124
|
+
updateNotificationTimeType: { value: "msg" },
|
|
125
|
+
|
|
126
|
+
updateNotificationTitle: { value: "payload.updateNotification.title" },
|
|
127
|
+
updateNotificationTitleType: { value: "msg" },
|
|
128
|
+
|
|
129
|
+
updateNotificationBody: { value: "payload.updateNotification.body" },
|
|
130
|
+
updateNotificationBodyType: { value: "msg" },
|
|
131
|
+
|
|
132
|
+
updateNotificationTinyIcon: { value: "payload.updateNotification.tinyIcon" },
|
|
133
|
+
updateNotificationTinyIconType: { value: "msg" },
|
|
134
|
+
|
|
135
|
+
// Additional fields for specific layouts
|
|
136
|
+
locationName: { value: "payload.locationName" },
|
|
137
|
+
locationNameType: { value: "msg" },
|
|
138
|
+
|
|
139
|
+
// Weather layout specific
|
|
140
|
+
shortTitle: { value: "payload.shortTitle" },
|
|
141
|
+
shortTitleType: { value: "msg" },
|
|
142
|
+
|
|
143
|
+
shortSubtitle: { value: "payload.shortSubtitle" },
|
|
144
|
+
shortSubtitleType: { value: "msg" },
|
|
145
|
+
|
|
146
|
+
displayTime: { value: "pin" },
|
|
147
|
+
|
|
148
|
+
// Sports layout specific
|
|
149
|
+
rankAway: { value: "payload.rankAway" },
|
|
150
|
+
rankAwayType: { value: "msg" },
|
|
151
|
+
|
|
152
|
+
rankHome: { value: "payload.rankHome" },
|
|
153
|
+
rankHomeType: { value: "msg" },
|
|
154
|
+
|
|
155
|
+
nameAway: { value: "payload.nameAway" },
|
|
156
|
+
nameAwayType: { value: "msg" },
|
|
157
|
+
|
|
158
|
+
nameHome: { value: "payload.nameHome" },
|
|
159
|
+
nameHomeType: { value: "msg" },
|
|
160
|
+
|
|
161
|
+
recordAway: { value: "payload.recordAway" },
|
|
162
|
+
recordAwayType: { value: "msg" },
|
|
163
|
+
|
|
164
|
+
recordHome: { value: "payload.recordHome" },
|
|
165
|
+
recordHomeType: { value: "msg" },
|
|
166
|
+
|
|
167
|
+
scoreAway: { value: "payload.scoreAway" },
|
|
168
|
+
scoreAwayType: { value: "msg" },
|
|
169
|
+
|
|
170
|
+
scoreHome: { value: "payload.scoreHome" },
|
|
171
|
+
scoreHomeType: { value: "msg" },
|
|
172
|
+
|
|
173
|
+
sportsGameState: { value: "pre-game" },
|
|
174
|
+
|
|
175
|
+
// Advanced options
|
|
176
|
+
reminders: { value: false },
|
|
177
|
+
reminderData: { value: "payload.reminders" },
|
|
178
|
+
reminderDataType: { value: "msg" },
|
|
179
|
+
|
|
180
|
+
actions: { value: false },
|
|
181
|
+
actionData: { value: "payload.actions" },
|
|
182
|
+
actionDataType: { value: "msg" }
|
|
183
|
+
},
|
|
184
|
+
inputs: 1,
|
|
185
|
+
outputs: 1,
|
|
186
|
+
icon: "font-awesome/fa-clock-o",
|
|
187
|
+
label: function() {
|
|
188
|
+
return this.name || "Add Timeline Pin";
|
|
189
|
+
},
|
|
190
|
+
oneditprepare: function() {
|
|
191
|
+
// Setup TypedInput for server override options
|
|
192
|
+
$("#node-input-apiUrl").typedInput({
|
|
193
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
194
|
+
typeField: "#node-input-apiUrlType"
|
|
195
|
+
});
|
|
196
|
+
|
|
197
|
+
$("#node-input-token").typedInput({
|
|
198
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
199
|
+
typeField: "#node-input-tokenType"
|
|
200
|
+
});
|
|
201
|
+
|
|
202
|
+
// Setup TypedInput for all configurable fields
|
|
203
|
+
$("#node-input-pinId").typedInput({
|
|
204
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
205
|
+
typeField: "#node-input-pinIdType"
|
|
206
|
+
});
|
|
207
|
+
|
|
208
|
+
$("#node-input-time").typedInput({
|
|
209
|
+
types: ["msg", "flow", "global", "str", "date", "jsonata"],
|
|
210
|
+
typeField: "#node-input-timeType"
|
|
211
|
+
});
|
|
212
|
+
|
|
213
|
+
$("#node-input-duration").typedInput({
|
|
214
|
+
types: ["msg", "flow", "global", "num", "jsonata"],
|
|
215
|
+
typeField: "#node-input-durationType"
|
|
216
|
+
});
|
|
217
|
+
|
|
218
|
+
// Layout properties
|
|
219
|
+
$("#node-input-title").typedInput({
|
|
220
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
221
|
+
typeField: "#node-input-titleType"
|
|
222
|
+
});
|
|
223
|
+
|
|
224
|
+
$("#node-input-subtitle").typedInput({
|
|
225
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
226
|
+
typeField: "#node-input-subtitleType"
|
|
227
|
+
});
|
|
228
|
+
|
|
229
|
+
$("#node-input-body").typedInput({
|
|
230
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
231
|
+
typeField: "#node-input-bodyType"
|
|
232
|
+
});
|
|
233
|
+
|
|
234
|
+
$("#node-input-tinyIcon").typedInput({
|
|
235
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
236
|
+
typeField: "#node-input-tinyIconType"
|
|
237
|
+
});
|
|
238
|
+
|
|
239
|
+
$("#node-input-smallIcon").typedInput({
|
|
240
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
241
|
+
typeField: "#node-input-smallIconType"
|
|
242
|
+
});
|
|
243
|
+
|
|
244
|
+
$("#node-input-largeIcon").typedInput({
|
|
245
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
246
|
+
typeField: "#node-input-largeIconType"
|
|
247
|
+
});
|
|
248
|
+
|
|
249
|
+
// Color properties
|
|
250
|
+
$("#node-input-primaryColor").typedInput({
|
|
251
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
252
|
+
typeField: "#node-input-primaryColorType"
|
|
253
|
+
});
|
|
254
|
+
|
|
255
|
+
$("#node-input-secondaryColor").typedInput({
|
|
256
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
257
|
+
typeField: "#node-input-secondaryColorType"
|
|
258
|
+
});
|
|
259
|
+
|
|
260
|
+
$("#node-input-backgroundColor").typedInput({
|
|
261
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
262
|
+
typeField: "#node-input-backgroundColorType"
|
|
263
|
+
});
|
|
264
|
+
|
|
265
|
+
// Create Notification properties
|
|
266
|
+
$("#node-input-createNotificationTitle").typedInput({
|
|
267
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
268
|
+
typeField: "#node-input-createNotificationTitleType"
|
|
269
|
+
});
|
|
270
|
+
|
|
271
|
+
$("#node-input-createNotificationBody").typedInput({
|
|
272
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
273
|
+
typeField: "#node-input-createNotificationBodyType"
|
|
274
|
+
});
|
|
275
|
+
|
|
276
|
+
$("#node-input-createNotificationTinyIcon").typedInput({
|
|
277
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
278
|
+
typeField: "#node-input-createNotificationTinyIconType"
|
|
279
|
+
});
|
|
280
|
+
|
|
281
|
+
// Update Notification properties
|
|
282
|
+
$("#node-input-updateNotificationTime").typedInput({
|
|
283
|
+
types: ["msg", "flow", "global", "str", "date", "jsonata"],
|
|
284
|
+
typeField: "#node-input-updateNotificationTimeType"
|
|
285
|
+
});
|
|
286
|
+
|
|
287
|
+
$("#node-input-updateNotificationTitle").typedInput({
|
|
288
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
289
|
+
typeField: "#node-input-updateNotificationTitleType"
|
|
290
|
+
});
|
|
291
|
+
|
|
292
|
+
$("#node-input-updateNotificationBody").typedInput({
|
|
293
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
294
|
+
typeField: "#node-input-updateNotificationBodyType"
|
|
295
|
+
});
|
|
296
|
+
|
|
297
|
+
$("#node-input-updateNotificationTinyIcon").typedInput({
|
|
298
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
299
|
+
typeField: "#node-input-updateNotificationTinyIconType"
|
|
300
|
+
});
|
|
301
|
+
|
|
302
|
+
// Additional fields
|
|
303
|
+
$("#node-input-locationName").typedInput({
|
|
304
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
305
|
+
typeField: "#node-input-locationNameType"
|
|
306
|
+
});
|
|
307
|
+
|
|
308
|
+
// Weather layout specific
|
|
309
|
+
$("#node-input-shortTitle").typedInput({
|
|
310
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
311
|
+
typeField: "#node-input-shortTitleType"
|
|
312
|
+
});
|
|
313
|
+
|
|
314
|
+
$("#node-input-shortSubtitle").typedInput({
|
|
315
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
316
|
+
typeField: "#node-input-shortSubtitleType"
|
|
317
|
+
});
|
|
318
|
+
|
|
319
|
+
// Sports layout specific
|
|
320
|
+
$("#node-input-rankAway").typedInput({
|
|
321
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
322
|
+
typeField: "#node-input-rankAwayType"
|
|
323
|
+
});
|
|
324
|
+
|
|
325
|
+
$("#node-input-rankHome").typedInput({
|
|
326
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
327
|
+
typeField: "#node-input-rankHomeType"
|
|
328
|
+
});
|
|
329
|
+
|
|
330
|
+
$("#node-input-nameAway").typedInput({
|
|
331
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
332
|
+
typeField: "#node-input-nameAwayType"
|
|
333
|
+
});
|
|
334
|
+
|
|
335
|
+
$("#node-input-nameHome").typedInput({
|
|
336
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
337
|
+
typeField: "#node-input-nameHomeType"
|
|
338
|
+
});
|
|
339
|
+
|
|
340
|
+
$("#node-input-recordAway").typedInput({
|
|
341
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
342
|
+
typeField: "#node-input-recordAwayType"
|
|
343
|
+
});
|
|
344
|
+
|
|
345
|
+
$("#node-input-recordHome").typedInput({
|
|
346
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
347
|
+
typeField: "#node-input-recordHomeType"
|
|
348
|
+
});
|
|
349
|
+
|
|
350
|
+
$("#node-input-scoreAway").typedInput({
|
|
351
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
352
|
+
typeField: "#node-input-scoreAwayType"
|
|
353
|
+
});
|
|
354
|
+
|
|
355
|
+
$("#node-input-scoreHome").typedInput({
|
|
356
|
+
types: ["msg", "flow", "global", "str", "jsonata"],
|
|
357
|
+
typeField: "#node-input-scoreHomeType"
|
|
358
|
+
});
|
|
359
|
+
|
|
360
|
+
// Advanced options
|
|
361
|
+
$("#node-input-reminderData").typedInput({
|
|
362
|
+
types: ["msg", "flow", "global", "json", "jsonata"],
|
|
363
|
+
typeField: "#node-input-reminderDataType"
|
|
364
|
+
});
|
|
365
|
+
|
|
366
|
+
$("#node-input-actionData").typedInput({
|
|
367
|
+
types: ["msg", "flow", "global", "json", "jsonata"],
|
|
368
|
+
typeField: "#node-input-actionDataType"
|
|
369
|
+
});
|
|
370
|
+
|
|
371
|
+
$("#node-input-headings").typedInput({
|
|
372
|
+
types: ["msg", "flow", "global", "json", "jsonata"],
|
|
373
|
+
typeField: "#node-input-headingsType"
|
|
374
|
+
});
|
|
375
|
+
|
|
376
|
+
$("#node-input-paragraphs").typedInput({
|
|
377
|
+
types: ["msg", "flow", "global", "json", "jsonata"],
|
|
378
|
+
typeField: "#node-input-paragraphsType"
|
|
379
|
+
});
|
|
380
|
+
|
|
381
|
+
$("#node-input-lastUpdated").typedInput({
|
|
382
|
+
types: ["msg", "flow", "global", "str", "date", "jsonata"],
|
|
383
|
+
typeField: "#node-input-lastUpdatedType"
|
|
384
|
+
});
|
|
385
|
+
|
|
386
|
+
// Show/hide sections based on layout type
|
|
387
|
+
$("#node-input-layoutType").on("change", function() {
|
|
388
|
+
const layoutType = $(this).val();
|
|
389
|
+
|
|
390
|
+
// Hide all layout specific sections
|
|
391
|
+
$(".layout-specific").hide();
|
|
392
|
+
|
|
393
|
+
// Show common layout fields
|
|
394
|
+
$(".layout-common").show();
|
|
395
|
+
|
|
396
|
+
// Show layout specific fields with visual indication
|
|
397
|
+
if (layoutType === "calendarPin") {
|
|
398
|
+
$(".layout-calendar").fadeIn(300);
|
|
399
|
+
$("#node-dialog").find(".form-section-title").filter(function() {
|
|
400
|
+
return $(this).text() === "Pin Layout";
|
|
401
|
+
}).addClass("calendar-active");
|
|
402
|
+
} else if (layoutType === "sportsPin") {
|
|
403
|
+
$(".layout-sports").fadeIn(300);
|
|
404
|
+
$("#node-dialog").find(".form-section-title").filter(function() {
|
|
405
|
+
return $(this).text() === "Pin Layout";
|
|
406
|
+
}).addClass("sports-active");
|
|
407
|
+
} else if (layoutType === "weatherPin") {
|
|
408
|
+
$(".layout-weather").fadeIn(300);
|
|
409
|
+
$("#node-dialog").find(".form-section-title").filter(function() {
|
|
410
|
+
return $(this).text() === "Pin Layout";
|
|
411
|
+
}).addClass("weather-active");
|
|
412
|
+
} else {
|
|
413
|
+
$("#node-dialog").find(".form-section-title").filter(function() {
|
|
414
|
+
return $(this).text() === "Pin Layout";
|
|
415
|
+
}).removeClass("calendar-active sports-active weather-active");
|
|
416
|
+
}
|
|
417
|
+
});
|
|
418
|
+
|
|
419
|
+
// Show/hide notifications based on checkboxes with animation
|
|
420
|
+
$("#node-input-createNotification").on("change", function() {
|
|
421
|
+
if ($(this).is(":checked")) {
|
|
422
|
+
$(".create-notification").slideDown(300);
|
|
423
|
+
$(this).closest(".form-row").css("margin-bottom", "0");
|
|
424
|
+
} else {
|
|
425
|
+
$(".create-notification").slideUp(300);
|
|
426
|
+
}
|
|
427
|
+
});
|
|
428
|
+
|
|
429
|
+
$("#node-input-updateNotification").on("change", function() {
|
|
430
|
+
if ($(this).is(":checked")) {
|
|
431
|
+
$(".update-notification").slideDown(300);
|
|
432
|
+
$(this).closest(".form-row").css("margin-bottom", "0");
|
|
433
|
+
} else {
|
|
434
|
+
$(".update-notification").slideUp(300);
|
|
435
|
+
}
|
|
436
|
+
});
|
|
437
|
+
|
|
438
|
+
// Show/hide advanced options with animation
|
|
439
|
+
$("#node-input-reminders").on("change", function() {
|
|
440
|
+
if ($(this).is(":checked")) {
|
|
441
|
+
$(".reminders-section").slideDown(300);
|
|
442
|
+
$(this).closest(".form-row").css("margin-bottom", "0");
|
|
443
|
+
} else {
|
|
444
|
+
$(".reminders-section").slideUp(300);
|
|
445
|
+
}
|
|
446
|
+
});
|
|
447
|
+
|
|
448
|
+
$("#node-input-actions").on("change", function() {
|
|
449
|
+
if ($(this).is(":checked")) {
|
|
450
|
+
$(".actions-section").slideDown(300);
|
|
451
|
+
$(this).closest(".form-row").css("margin-bottom", "0");
|
|
452
|
+
} else {
|
|
453
|
+
$(".actions-section").slideUp(300);
|
|
454
|
+
}
|
|
455
|
+
});
|
|
456
|
+
|
|
457
|
+
// Initialize with current values
|
|
458
|
+
$("#node-input-layoutType").trigger("change");
|
|
459
|
+
$("#node-input-createNotification").trigger("change");
|
|
460
|
+
$("#node-input-updateNotification").trigger("change");
|
|
461
|
+
$("#node-input-reminders").trigger("change");
|
|
462
|
+
$("#node-input-actions").trigger("change");
|
|
463
|
+
}
|
|
464
|
+
});
|
|
465
|
+
</script>
|
|
466
|
+
|
|
467
|
+
<script type="text/html" data-template-name="pebble-timeline-add">
|
|
468
|
+
<div class="form-row">
|
|
469
|
+
<label for="node-input-name"><i class="fa fa-tag"></i> Name</label>
|
|
470
|
+
<input type="text" id="node-input-name" placeholder="Name">
|
|
471
|
+
</div>
|
|
472
|
+
|
|
473
|
+
<div class="form-row">
|
|
474
|
+
<label for="node-input-config"><i class="fa fa-cog"></i> Config</label>
|
|
475
|
+
<input type="text" id="node-input-config">
|
|
476
|
+
</div>
|
|
477
|
+
|
|
478
|
+
<div class="form-section">
|
|
479
|
+
<div class="form-section-title">Server Overrides (Optional)</div>
|
|
480
|
+
|
|
481
|
+
<div class="form-row">
|
|
482
|
+
<label for="node-input-apiUrl"><i class="fa fa-globe"></i> API URL</label>
|
|
483
|
+
<input type="text" id="node-input-apiUrl" style="width: 70%">
|
|
484
|
+
<input type="hidden" id="node-input-apiUrlType">
|
|
485
|
+
<div class="form-tips">Override the API URL configured in the config node. Defaults to https://timeline-api.rebble.io</div>
|
|
486
|
+
</div>
|
|
487
|
+
|
|
488
|
+
<div class="form-row">
|
|
489
|
+
<label for="node-input-token"><i class="fa fa-key"></i> Token</label>
|
|
490
|
+
<input type="text" id="node-input-token" style="width: 70%">
|
|
491
|
+
<input type="hidden" id="node-input-tokenType">
|
|
492
|
+
<div class="form-tips">Override the timeline token configured in the config node</div>
|
|
493
|
+
</div>
|
|
494
|
+
</div>
|
|
495
|
+
|
|
496
|
+
<div class="form-section">
|
|
497
|
+
<div class="form-section-title">Pin Basic Properties</div>
|
|
498
|
+
|
|
499
|
+
<div class="form-row">
|
|
500
|
+
<label for="node-input-pinId"><i class="fa fa-id-card"></i> ID</label>
|
|
501
|
+
<input type="text" id="node-input-pinId" style="width: 70%">
|
|
502
|
+
<input type="hidden" id="node-input-pinIdType">
|
|
503
|
+
<div class="form-tips">Developer-implemented identifier for this pin event, which cannot be re-used. Maximum 64 characters. This id must be unique and cannot be reused even after deletion.</div>
|
|
504
|
+
</div>
|
|
505
|
+
|
|
506
|
+
<div class="form-row">
|
|
507
|
+
<label for="node-input-time"><i class="fa fa-clock-o"></i> Time</label>
|
|
508
|
+
<input type="text" id="node-input-time" style="width: 70%">
|
|
509
|
+
<input type="hidden" id="node-input-timeType">
|
|
510
|
+
<div class="form-tips">The start time of the event in ISO date-time format (e.g., 2023-01-01T12:00:00Z). This is the time the pin will appear on the timeline.</div>
|
|
511
|
+
</div>
|
|
512
|
+
|
|
513
|
+
<div class="form-row">
|
|
514
|
+
<label for="node-input-duration"><i class="fa fa-hourglass-half"></i> Duration</label>
|
|
515
|
+
<input type="text" id="node-input-duration" style="width: 70%">
|
|
516
|
+
<input type="hidden" id="node-input-durationType">
|
|
517
|
+
<div class="form-tips">The duration of the event in minutes. Optional but recommended for events with a specific length.</div>
|
|
518
|
+
</div>
|
|
519
|
+
</div>
|
|
520
|
+
|
|
521
|
+
<div class="form-section">
|
|
522
|
+
<div class="form-section-title">Pin Layout</div>
|
|
523
|
+
|
|
524
|
+
<div class="form-row">
|
|
525
|
+
<label for="node-input-layoutType"><i class="fa fa-th-large"></i> Layout Type</label>
|
|
526
|
+
<select id="node-input-layoutType">
|
|
527
|
+
<option value="genericPin">Generic Pin</option>
|
|
528
|
+
<option value="calendarPin">Calendar Pin</option>
|
|
529
|
+
<option value="sportsPin">Sports Pin</option>
|
|
530
|
+
<option value="weatherPin">Weather Pin</option>
|
|
531
|
+
</select>
|
|
532
|
+
<div class="form-tips">The type of layout the pin will use. Different layouts have different required fields and visual appearances.</div>
|
|
533
|
+
</div>
|
|
534
|
+
|
|
535
|
+
<div class="form-row layout-common">
|
|
536
|
+
<label for="node-input-title"><i class="fa fa-font"></i> Title</label>
|
|
537
|
+
<input type="text" id="node-input-title" style="width: 70%">
|
|
538
|
+
<input type="hidden" id="node-input-titleType">
|
|
539
|
+
<div class="form-tips">The title of the pin when viewed on the watch. This is a required field for all pin types.</div>
|
|
540
|
+
</div>
|
|
541
|
+
|
|
542
|
+
<div class="form-row layout-common">
|
|
543
|
+
<label for="node-input-subtitle"><i class="fa fa-text-height"></i> Subtitle</label>
|
|
544
|
+
<input type="text" id="node-input-subtitle" style="width: 70%">
|
|
545
|
+
<input type="hidden" id="node-input-subtitleType">
|
|
546
|
+
<div class="form-tips">Shorter subtitle text for additional details. For weather pins, this can show high/low temperatures.</div>
|
|
547
|
+
</div>
|
|
548
|
+
|
|
549
|
+
<div class="form-row layout-common">
|
|
550
|
+
<label for="node-input-body"><i class="fa fa-align-left"></i> Body</label>
|
|
551
|
+
<input type="text" id="node-input-body" style="width: 70%">
|
|
552
|
+
<input type="hidden" id="node-input-bodyType">
|
|
553
|
+
<div class="form-tips">The body text of the pin. Maximum of 512 characters. For weather pins, this is typically the forecast description.</div>
|
|
554
|
+
</div>
|
|
555
|
+
|
|
556
|
+
<div class="form-row layout-common">
|
|
557
|
+
<label for="node-input-tinyIcon"><i class="fa fa-picture-o"></i> Tiny Icon</label>
|
|
558
|
+
<input type="text" id="node-input-tinyIcon" style="width: 70%">
|
|
559
|
+
<input type="hidden" id="node-input-tinyIconType">
|
|
560
|
+
<div class="form-tips">URI of the pin's tiny icon. Use 'system://images/ICON_NAME' format with one of the system icons (e.g., system://images/NOTIFICATION_FLAG, system://images/TIMELINE_CALENDAR).</div>
|
|
561
|
+
</div>
|
|
562
|
+
|
|
563
|
+
<div class="form-row layout-common">
|
|
564
|
+
<label for="node-input-smallIcon"><i class="fa fa-picture-o"></i> Small Icon</label>
|
|
565
|
+
<input type="text" id="node-input-smallIcon" style="width: 70%">
|
|
566
|
+
<input type="hidden" id="node-input-smallIconType">
|
|
567
|
+
<div class="form-tips">URI of the pin's small icon. Use 'system://images/ICON_NAME' format with one of the system icons.</div>
|
|
568
|
+
</div>
|
|
569
|
+
|
|
570
|
+
<div class="form-row layout-common">
|
|
571
|
+
<label for="node-input-largeIcon"><i class="fa fa-picture-o"></i> Large Icon</label>
|
|
572
|
+
<input type="text" id="node-input-largeIcon" style="width: 70%">
|
|
573
|
+
<input type="hidden" id="node-input-largeIconType">
|
|
574
|
+
<div class="form-tips">URI of the pin's large icon. Use 'system://images/ICON_NAME' format with one of the system icons.</div>
|
|
575
|
+
</div>
|
|
576
|
+
|
|
577
|
+
<!-- Colors -->
|
|
578
|
+
<div class="form-row layout-common">
|
|
579
|
+
<label for="node-input-primaryColor"><i class="fa fa-paint-brush"></i> Primary Color</label>
|
|
580
|
+
<input type="text" id="node-input-primaryColor" style="width: 70%">
|
|
581
|
+
<input type="hidden" id="node-input-primaryColorType">
|
|
582
|
+
<div class="form-tips">Six-digit color hexadecimal string or case-insensitive SDK constant (e.g.: '#665566' or 'mintgreen'), for primary text color.</div>
|
|
583
|
+
</div>
|
|
584
|
+
|
|
585
|
+
<div class="form-row layout-common">
|
|
586
|
+
<label for="node-input-secondaryColor"><i class="fa fa-paint-brush"></i> Secondary Color</label>
|
|
587
|
+
<input type="text" id="node-input-secondaryColor" style="width: 70%">
|
|
588
|
+
<input type="hidden" id="node-input-secondaryColorType">
|
|
589
|
+
<div class="form-tips">Six-digit color hexadecimal string or case-insensitive SDK constant for the layout's secondary-colored elements.</div>
|
|
590
|
+
</div>
|
|
591
|
+
|
|
592
|
+
<div class="form-row layout-common">
|
|
593
|
+
<label for="node-input-backgroundColor"><i class="fa fa-paint-brush"></i> Background Color</label>
|
|
594
|
+
<input type="text" id="node-input-backgroundColor" style="width: 70%">
|
|
595
|
+
<input type="hidden" id="node-input-backgroundColorType">
|
|
596
|
+
<div class="form-tips">Six-digit color hexadecimal string or case-insensitive SDK constant for the layout's background color.</div>
|
|
597
|
+
</div>
|
|
598
|
+
|
|
599
|
+
<!-- Layout specific sections -->
|
|
600
|
+
|
|
601
|
+
<!-- Calendar and Weather Layout Common Fields -->
|
|
602
|
+
<div class="layout-specific layout-calendar layout-weather" style="margin-top: 15px; padding: 10px; background-color: #f9f9f9; border-radius: 5px; display: none;">
|
|
603
|
+
<div class="form-subsection-title" style="font-weight: bold; margin-bottom: 10px; color: #555;">Calendar/Weather Specific Fields</div>
|
|
604
|
+
|
|
605
|
+
<div class="form-row">
|
|
606
|
+
<label for="node-input-locationName"><i class="fa fa-map-marker"></i> Location</label>
|
|
607
|
+
<input type="text" id="node-input-locationName" style="width: 70%">
|
|
608
|
+
<input type="hidden" id="node-input-locationNameType">
|
|
609
|
+
<div class="form-tips">Name of the location of this pin event. Used for Calendar and Weather pins both in the timeline view and detail view.</div>
|
|
610
|
+
</div>
|
|
611
|
+
</div>
|
|
612
|
+
|
|
613
|
+
<!-- Weather Layout Specific Fields -->
|
|
614
|
+
<div class="layout-specific layout-weather" style="margin-top: 15px; padding: 10px; background-color: #f0f7ff; border-radius: 5px; display: none;">
|
|
615
|
+
<div class="form-subsection-title" style="font-weight: bold; margin-bottom: 10px; color: #555;">Weather Specific Fields</div>
|
|
616
|
+
|
|
617
|
+
<div class="form-row">
|
|
618
|
+
<label for="node-input-shortTitle"><i class="fa fa-font"></i> Short Title</label>
|
|
619
|
+
<input type="text" id="node-input-shortTitle" style="width: 70%">
|
|
620
|
+
<input type="hidden" id="node-input-shortTitleType">
|
|
621
|
+
<div class="form-tips">Used instead of title in the main timeline view (for Weather pins). This helps provide a more concise title in the timeline view.</div>
|
|
622
|
+
</div>
|
|
623
|
+
|
|
624
|
+
<div class="form-row">
|
|
625
|
+
<label for="node-input-shortSubtitle"><i class="fa fa-text-height"></i> Short Subtitle</label>
|
|
626
|
+
<input type="text" id="node-input-shortSubtitle" style="width: 70%">
|
|
627
|
+
<input type="hidden" id="node-input-shortSubtitleType">
|
|
628
|
+
<div class="form-tips">Used instead of subtitle in the main timeline view (for Weather pins). For weather, this commonly shows temperatures (e.g., '40°/65°').</div>
|
|
629
|
+
</div>
|
|
630
|
+
|
|
631
|
+
<div class="form-row">
|
|
632
|
+
<label for="node-input-displayTime"><i class="fa fa-clock-o"></i> Display Time</label>
|
|
633
|
+
<select id="node-input-displayTime">
|
|
634
|
+
<option value="pin">Show Pin Time</option>
|
|
635
|
+
<option value="none">Don't Show Time</option>
|
|
636
|
+
</select>
|
|
637
|
+
<div class="form-tips">Controls whether to display the pin's time in the title of the detail view and description. For weather forecasts, this can be useful to distinguish between different forecast periods.</div>
|
|
638
|
+
</div>
|
|
639
|
+
</div>
|
|
640
|
+
|
|
641
|
+
<!-- Sports Layout Specific Fields -->
|
|
642
|
+
<div class="layout-specific layout-sports" style="margin-top: 15px; padding: 10px; background-color: #fff0f0; border-radius: 5px; display: none;">
|
|
643
|
+
<div class="form-subsection-title" style="font-weight: bold; margin-bottom: 10px; color: #555;">Sports Specific Fields</div>
|
|
644
|
+
|
|
645
|
+
<!-- Teams Section -->
|
|
646
|
+
<div style="border-bottom: 1px solid #eee; margin-bottom: 10px; padding-bottom: 5px;">
|
|
647
|
+
<div class="form-section-subtitle" style="font-size: 0.9em; margin-bottom: 5px;">Team Information</div>
|
|
648
|
+
|
|
649
|
+
<div class="form-row">
|
|
650
|
+
<label for="node-input-nameAway"><i class="fa fa-users"></i> Away Team</label>
|
|
651
|
+
<input type="text" id="node-input-nameAway" style="width: 70%">
|
|
652
|
+
<input type="hidden" id="node-input-nameAwayType">
|
|
653
|
+
<div class="form-tips">Short name of the away team. Maximum 4 characters (e.g., 'POR', 'LAC', 'NYK').</div>
|
|
654
|
+
</div>
|
|
655
|
+
|
|
656
|
+
<div class="form-row">
|
|
657
|
+
<label for="node-input-nameHome"><i class="fa fa-users"></i> Home Team</label>
|
|
658
|
+
<input type="text" id="node-input-nameHome" style="width: 70%">
|
|
659
|
+
<input type="hidden" id="node-input-nameHomeType">
|
|
660
|
+
<div class="form-tips">Short name of the home team. Maximum 4 characters (e.g., 'LAL', 'BOS', 'CHI').</div>
|
|
661
|
+
</div>
|
|
662
|
+
</div>
|
|
663
|
+
|
|
664
|
+
<!-- Rankings Section -->
|
|
665
|
+
<div style="border-bottom: 1px solid #eee; margin-bottom: 10px; padding-bottom: 5px;">
|
|
666
|
+
<div class="form-section-subtitle" style="font-size: 0.9em; margin-bottom: 5px;">Team Rankings (Pre-Game)</div>
|
|
667
|
+
|
|
668
|
+
<div class="form-row">
|
|
669
|
+
<label for="node-input-rankAway"><i class="fa fa-sort-numeric-asc"></i> Away Rank</label>
|
|
670
|
+
<input type="text" id="node-input-rankAway" style="width: 70%">
|
|
671
|
+
<input type="hidden" id="node-input-rankAwayType">
|
|
672
|
+
<div class="form-tips">The rank of the away team. Should be about 2 characters (e.g., '03'). Shown before the event begins instead of score.</div>
|
|
673
|
+
</div>
|
|
674
|
+
|
|
675
|
+
<div class="form-row">
|
|
676
|
+
<label for="node-input-rankHome"><i class="fa fa-sort-numeric-asc"></i> Home Rank</label>
|
|
677
|
+
<input type="text" id="node-input-rankHome" style="width: 70%">
|
|
678
|
+
<input type="hidden" id="node-input-rankHomeType">
|
|
679
|
+
<div class="form-tips">The rank of the home team. Should be about 2 characters (e.g., '08'). Shown before the event begins instead of score.</div>
|
|
680
|
+
</div>
|
|
681
|
+
|
|
682
|
+
<div class="form-row">
|
|
683
|
+
<label for="node-input-recordAway"><i class="fa fa-list-ol"></i> Away Record</label>
|
|
684
|
+
<input type="text" id="node-input-recordAway" style="width: 70%">
|
|
685
|
+
<input type="hidden" id="node-input-recordAwayType">
|
|
686
|
+
<div class="form-tips">Record of the away team in wins-losses format. About 5 characters (e.g., '39-19').</div>
|
|
687
|
+
</div>
|
|
688
|
+
|
|
689
|
+
<div class="form-row">
|
|
690
|
+
<label for="node-input-recordHome"><i class="fa fa-list-ol"></i> Home Record</label>
|
|
691
|
+
<input type="text" id="node-input-recordHome" style="width: 70%">
|
|
692
|
+
<input type="hidden" id="node-input-recordHomeType">
|
|
693
|
+
<div class="form-tips">Record of the home team in wins-losses format. About 5 characters (e.g., '39-21').</div>
|
|
694
|
+
</div>
|
|
695
|
+
</div>
|
|
696
|
+
|
|
697
|
+
<!-- Scores Section -->
|
|
698
|
+
<div style="border-bottom: 1px solid #eee; margin-bottom: 10px; padding-bottom: 5px;">
|
|
699
|
+
<div class="form-section-subtitle" style="font-size: 0.9em; margin-bottom: 5px;">Game Scores (In-Game)</div>
|
|
700
|
+
|
|
701
|
+
<div class="form-row">
|
|
702
|
+
<label for="node-input-scoreAway"><i class="fa fa-trophy"></i> Away Score</label>
|
|
703
|
+
<input type="text" id="node-input-scoreAway" style="width: 70%">
|
|
704
|
+
<input type="hidden" id="node-input-scoreAwayType">
|
|
705
|
+
<div class="form-tips">Score of the away team. About 2 characters (e.g., '54'). Shown after the event begins instead of rank.</div>
|
|
706
|
+
</div>
|
|
707
|
+
|
|
708
|
+
<div class="form-row">
|
|
709
|
+
<label for="node-input-scoreHome"><i class="fa fa-trophy"></i> Home Score</label>
|
|
710
|
+
<input type="text" id="node-input-scoreHome" style="width: 70%">
|
|
711
|
+
<input type="hidden" id="node-input-scoreHomeType">
|
|
712
|
+
<div class="form-tips">Score of the home team. About 2 characters (e.g., '49'). Shown after the event begins instead of rank.</div>
|
|
713
|
+
</div>
|
|
714
|
+
</div>
|
|
715
|
+
|
|
716
|
+
<!-- Game State Section -->
|
|
717
|
+
<div>
|
|
718
|
+
<div class="form-section-subtitle" style="font-size: 0.9em; margin-bottom: 5px;">Game State</div>
|
|
719
|
+
|
|
720
|
+
<div class="form-row">
|
|
721
|
+
<label for="node-input-sportsGameState"><i class="fa fa-dot-circle-o"></i> Game State</label>
|
|
722
|
+
<select id="node-input-sportsGameState">
|
|
723
|
+
<option value="pre-game">Pre-Game</option>
|
|
724
|
+
<option value="in-game">In-Game</option>
|
|
725
|
+
</select>
|
|
726
|
+
<div class="form-tips">'in-game' for in-game or post-game displays (shows scores), 'pre-game' for pre-game displays (shows ranks).</div>
|
|
727
|
+
</div>
|
|
728
|
+
</div>
|
|
729
|
+
</div>
|
|
730
|
+
</div>
|
|
731
|
+
|
|
732
|
+
<div class="form-section">
|
|
733
|
+
<div class="form-section-title">Notifications</div>
|
|
734
|
+
|
|
735
|
+
<!-- Create Notification Section -->
|
|
736
|
+
<div class="form-row" style="margin-bottom:0;">
|
|
737
|
+
<input type="checkbox" id="node-input-createNotification" style="width: auto; margin-left: 125px; vertical-align: top">
|
|
738
|
+
<label for="node-input-createNotification" style="width: auto">
|
|
739
|
+
Create Notification
|
|
740
|
+
</label>
|
|
741
|
+
<div class="form-tips">The notification shown when the event is first created on the watch. Use this to alert users about new timeline events.</div>
|
|
742
|
+
</div>
|
|
743
|
+
|
|
744
|
+
<!-- Create Notification Fields - Conditionally displayed -->
|
|
745
|
+
<div class="create-notification" style="padding-left: 20px; border-left: 2px solid #ddd; margin-left: 10px;">
|
|
746
|
+
<div class="form-row" style="margin-top: 10px;">
|
|
747
|
+
<label for="node-input-createNotificationTitle"><i class="fa fa-font"></i> Title</label>
|
|
748
|
+
<input type="text" id="node-input-createNotificationTitle" style="width: 70%">
|
|
749
|
+
<input type="hidden" id="node-input-createNotificationTitleType">
|
|
750
|
+
<div class="form-tips">The title of the create notification. Keep it short and informative (e.g., 'New Event').</div>
|
|
751
|
+
</div>
|
|
752
|
+
|
|
753
|
+
<div class="form-row">
|
|
754
|
+
<label for="node-input-createNotificationBody"><i class="fa fa-align-left"></i> Body</label>
|
|
755
|
+
<input type="text" id="node-input-createNotificationBody" style="width: 70%">
|
|
756
|
+
<input type="hidden" id="node-input-createNotificationBodyType">
|
|
757
|
+
<div class="form-tips">The body text of the create notification. For example, 'A new appointment has been added to your calendar at 4pm.'</div>
|
|
758
|
+
</div>
|
|
759
|
+
|
|
760
|
+
<div class="form-row">
|
|
761
|
+
<label for="node-input-createNotificationTinyIcon"><i class="fa fa-picture-o"></i> Icon</label>
|
|
762
|
+
<input type="text" id="node-input-createNotificationTinyIcon" style="width: 70%">
|
|
763
|
+
<input type="hidden" id="node-input-createNotificationTinyIconType">
|
|
764
|
+
<div class="form-tips">URI of the notification's tiny icon (e.g., 'system://images/NOTIFICATION_FLAG').</div>
|
|
765
|
+
</div>
|
|
766
|
+
</div>
|
|
767
|
+
|
|
768
|
+
<!-- Update Notification Section -->
|
|
769
|
+
<div class="form-row" style="margin-bottom:0; margin-top: 15px;">
|
|
770
|
+
<input type="checkbox" id="node-input-updateNotification" style="width: auto; margin-left: 125px; vertical-align: top">
|
|
771
|
+
<label for="node-input-updateNotification" style="width: auto">
|
|
772
|
+
Update Notification
|
|
773
|
+
</label>
|
|
774
|
+
<div class="form-tips">The notification shown when the event is updated but already exists on the watch. Only shown if the update time is newer than the last update time.</div>
|
|
775
|
+
</div>
|
|
776
|
+
|
|
777
|
+
<!-- Update Notification Fields - Conditionally displayed -->
|
|
778
|
+
<div class="update-notification" style="padding-left: 20px; border-left: 2px solid #ddd; margin-left: 10px;">
|
|
779
|
+
<div class="form-row" style="margin-top: 10px;">
|
|
780
|
+
<label for="node-input-updateNotificationTime"><i class="fa fa-clock-o"></i> Time</label>
|
|
781
|
+
<input type="text" id="node-input-updateNotificationTime" style="width: 70%">
|
|
782
|
+
<input type="hidden" id="node-input-updateNotificationTimeType">
|
|
783
|
+
<div class="form-tips">The new time of the pin update. Only shown if newer than the last update time. Use ISO date-time format.</div>
|
|
784
|
+
</div>
|
|
785
|
+
|
|
786
|
+
<div class="form-row">
|
|
787
|
+
<label for="node-input-updateNotificationTitle"><i class="fa fa-font"></i> Title</label>
|
|
788
|
+
<input type="text" id="node-input-updateNotificationTitle" style="width: 70%">
|
|
789
|
+
<input type="hidden" id="node-input-updateNotificationTitleType">
|
|
790
|
+
<div class="form-tips">The title of the update notification. For example, 'Reminder' or 'Event Updated'.</div>
|
|
791
|
+
</div>
|
|
792
|
+
|
|
793
|
+
<div class="form-row">
|
|
794
|
+
<label for="node-input-updateNotificationBody"><i class="fa fa-align-left"></i> Body</label>
|
|
795
|
+
<input type="text" id="node-input-updateNotificationBody" style="width: 70%">
|
|
796
|
+
<input type="hidden" id="node-input-updateNotificationBodyType">
|
|
797
|
+
<div class="form-tips">The body text of the update notification. For example, 'The meeting has been rescheduled to 4pm.'</div>
|
|
798
|
+
</div>
|
|
799
|
+
|
|
800
|
+
<div class="form-row">
|
|
801
|
+
<label for="node-input-updateNotificationTinyIcon"><i class="fa fa-picture-o"></i> Icon</label>
|
|
802
|
+
<input type="text" id="node-input-updateNotificationTinyIcon" style="width: 70%">
|
|
803
|
+
<input type="hidden" id="node-input-updateNotificationTinyIconType">
|
|
804
|
+
<div class="form-tips">URI of the notification's tiny icon (e.g., 'system://images/NOTIFICATION_FLAG').</div>
|
|
805
|
+
</div>
|
|
806
|
+
</div>
|
|
807
|
+
</div>
|
|
808
|
+
|
|
809
|
+
<div class="form-section">
|
|
810
|
+
<div class="form-section-title">Advanced Options</div>
|
|
811
|
+
|
|
812
|
+
<!-- Reminders Section -->
|
|
813
|
+
<div class="form-row" style="margin-bottom:0;">
|
|
814
|
+
<input type="checkbox" id="node-input-reminders" style="width: auto; margin-left: 125px; vertical-align: top">
|
|
815
|
+
<label for="node-input-reminders" style="width: auto">
|
|
816
|
+
Add Reminders
|
|
817
|
+
</label>
|
|
818
|
+
<div class="form-tips">Add reminders that are shown before the pin's time. Reminders work even when the Pebble is disconnected from the phone.</div>
|
|
819
|
+
</div>
|
|
820
|
+
|
|
821
|
+
<!-- Reminders Fields - Conditionally displayed -->
|
|
822
|
+
<div class="reminders-section" style="padding-left: 20px; border-left: 2px solid #ddd; margin-left: 10px; margin-bottom: 15px;">
|
|
823
|
+
<div class="form-row" style="margin-top: 10px;">
|
|
824
|
+
<label for="node-input-reminderData"><i class="fa fa-list"></i> Reminder Data</label>
|
|
825
|
+
<input type="text" id="node-input-reminderData" style="width: 70%">
|
|
826
|
+
<input type="hidden" id="node-input-reminderDataType">
|
|
827
|
+
<div class="form-tips">Array of reminder objects, each with time and layout properties. Maximum 3 reminders per pin. Example: [{"time":"2023-01-01T11:45:00Z","layout":{"type":"genericReminder","title":"15 min reminder","tinyIcon":"system://images/TIMELINE_CALENDAR"}}]</div>
|
|
828
|
+
</div>
|
|
829
|
+
</div>
|
|
830
|
+
|
|
831
|
+
<!-- Actions Section -->
|
|
832
|
+
<div class="form-row" style="margin-bottom:0;">
|
|
833
|
+
<input type="checkbox" id="node-input-actions" style="width: auto; margin-left: 125px; vertical-align: top">
|
|
834
|
+
<label for="node-input-actions" style="width: auto">
|
|
835
|
+
Add Actions
|
|
836
|
+
</label>
|
|
837
|
+
<div class="form-tips">Add interactive actions to the pin that can be executed by the user. These allow users to respond to or interact with pins.</div>
|
|
838
|
+
</div>
|
|
839
|
+
|
|
840
|
+
<!-- Actions Fields - Conditionally displayed -->
|
|
841
|
+
<div class="actions-section" style="padding-left: 20px; border-left: 2px solid #ddd; margin-left: 10px; margin-bottom: 15px;">
|
|
842
|
+
<div class="form-row" style="margin-top: 10px;">
|
|
843
|
+
<label for="node-input-actionData"><i class="fa fa-list"></i> Action Data</label>
|
|
844
|
+
<input type="text" id="node-input-actionData" style="width: 70%">
|
|
845
|
+
<input type="hidden" id="node-input-actionDataType">
|
|
846
|
+
<div class="form-tips">Array of action objects. Example for openWatchApp: [{"title":"View Schedule","type":"openWatchApp","launchCode":15}]. Example for http: [{"title":"Confirm","type":"http","url":"https://example.com/api/confirm","method":"POST","bodyJSON":{"status":"confirmed"}}]</div>
|
|
847
|
+
</div>
|
|
848
|
+
</div>
|
|
849
|
+
|
|
850
|
+
<!-- Additional Layout Options Section -->
|
|
851
|
+
<div class="form-subsection" style="margin-top: 15px;">
|
|
852
|
+
<div class="form-subsection-title" style="margin-bottom: 10px; font-weight: bold;">Additional Layout Options</div>
|
|
853
|
+
|
|
854
|
+
<div class="form-row layout-common">
|
|
855
|
+
<label for="node-input-headings"><i class="fa fa-header"></i> Headings</label>
|
|
856
|
+
<input type="text" id="node-input-headings" style="width: 70%">
|
|
857
|
+
<input type="hidden" id="node-input-headingsType">
|
|
858
|
+
<div class="form-tips">List of section headings in this layout. Example: ["Details", "Location", "Notes"]. The list must be less than 128 characters in total length.</div>
|
|
859
|
+
</div>
|
|
860
|
+
|
|
861
|
+
<div class="form-row layout-common">
|
|
862
|
+
<label for="node-input-paragraphs"><i class="fa fa-paragraph"></i> Paragraphs</label>
|
|
863
|
+
<input type="text" id="node-input-paragraphs" style="width: 70%">
|
|
864
|
+
<input type="hidden" id="node-input-paragraphsType">
|
|
865
|
+
<div class="form-tips">List of paragraphs in this layout. Must equal the number of headings. Example: ["Meeting with team", "Conference Room A", "Bring presentation materials"]. The list must be less than 1024 characters in total length.</div>
|
|
866
|
+
</div>
|
|
867
|
+
|
|
868
|
+
<div class="form-row layout-common">
|
|
869
|
+
<label for="node-input-lastUpdated"><i class="fa fa-refresh"></i> Last Updated</label>
|
|
870
|
+
<input type="text" id="node-input-lastUpdated" style="width: 70%">
|
|
871
|
+
<input type="hidden" id="node-input-lastUpdatedType">
|
|
872
|
+
<div class="form-tips">Timestamp of when the pin's data (e.g., weather forecast or sports score) was last updated. Use ISO date-time format.</div>
|
|
873
|
+
</div>
|
|
874
|
+
</div>
|
|
875
|
+
</div>
|
|
876
|
+
</script>
|
|
877
|
+
|
|
878
|
+
<script type="text/html" data-help-name="pebble-timeline-add">
|
|
879
|
+
<p>Adds a pin to the Pebble Timeline.</p>
|
|
880
|
+
|
|
881
|
+
<h3>Inputs</h3>
|
|
882
|
+
<dl class="message-properties">
|
|
883
|
+
<dt>payload <span class="property-type">object</span></dt>
|
|
884
|
+
<dd>The pin data to add to the timeline. This can be overridden by the node's configuration.</dd>
|
|
885
|
+
<dt>topic <span class="property-type">string</span></dt>
|
|
886
|
+
<dd>Used as the pin title by default if not otherwise configured.</dd>
|
|
887
|
+
<dt>payload.id <span class="property-type">string</span></dt>
|
|
888
|
+
<dd>The unique identifier for the pin (if not specified in the node configuration).</dd>
|
|
889
|
+
<dt>payload.time <span class="property-type">string</span></dt>
|
|
890
|
+
<dd>The time for the pin in ISO date-time format.</dd>
|
|
891
|
+
</dl>
|
|
892
|
+
|
|
893
|
+
<h3>Outputs</h3>
|
|
894
|
+
<dl class="message-properties">
|
|
895
|
+
<dt>payload <span class="property-type">object</span></dt>
|
|
896
|
+
<dd>The result of the API call, including the pin data that was added to the timeline.</dd>
|
|
897
|
+
</dl>
|
|
898
|
+
|
|
899
|
+
<h3>Details</h3>
|
|
900
|
+
<p>This node adds a pin to the Pebble Timeline. It supports all pin types and layouts as documented in the Pebble API.</p>
|
|
901
|
+
<p>You can configure the pin directly in the node or provide the pin data in the input message. If both are provided, the node's configuration takes precedence.</p>
|
|
902
|
+
<p>Pins are stored locally organized by timeline token, with each token having its own separate list of pins. When adding pins, the system automatically cleans up any pins older than one month from all tokens to prevent the storage file from growing too large.</p>
|
|
903
|
+
|
|
904
|
+
<h4>Pin Layouts</h4>
|
|
905
|
+
<ul>
|
|
906
|
+
<li><strong>genericPin</strong>: Generic layout for pins of no particular type</li>
|
|
907
|
+
<li><strong>calendarPin</strong>: Standard layout for calendar events</li>
|
|
908
|
+
<li><strong>sportsPin</strong>: Layout for displaying sports game information</li>
|
|
909
|
+
<li><strong>weatherPin</strong>: Layout for displaying weather forecasts</li>
|
|
910
|
+
</ul>
|
|
911
|
+
|
|
912
|
+
<h4>Pin Icons</h4>
|
|
913
|
+
<p>Use system://images/ICON_NAME for icons, where ICON_NAME is one of:</p>
|
|
914
|
+
<ul>
|
|
915
|
+
<li>NOTIFICATION_FLAG, NOTIFICATION_GENERIC, NOTIFICATION_REMINDER</li>
|
|
916
|
+
<li>TIMELINE_CALENDAR, TIMELINE_WEATHER, TIMELINE_SPORTS</li>
|
|
917
|
+
<li>SUNRISE, SUNSET, PARTLY_CLOUDY, CLOUDY_DAY</li>
|
|
918
|
+
<li>AMERICAN_FOOTBALL, BASKETBALL, SOCCER_GAME, BASEBALL</li>
|
|
919
|
+
<li>And many more - see Pebble developer docs for the complete list</li>
|
|
920
|
+
</ul>
|
|
921
|
+
|
|
922
|
+
<h3>References</h3>
|
|
923
|
+
<ul>
|
|
924
|
+
<li><a href="https://developer.pebble.com/guides/pebble-timeline/pin-structure/">Pebble Timeline Pin Structure</a></li>
|
|
925
|
+
</ul>
|
|
926
|
+
</script>
|