pict-section-formeditor 1.0.8 → 1.0.10
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/package.json +12 -12
- package/source/Pict-Section-FormEditor-DefaultConfiguration.js +5 -0
- package/source/providers/Pict-Provider-FormEditorDragDrop.js +138 -65
- package/source/providers/Pict-Provider-FormEditorManifestOps.js +457 -233
- package/source/providers/Pict-Provider-FormEditorRendering.js +8 -7
- package/source/providers/Pict-Provider-FormEditorUtilities.js +10 -11
- package/source/views/PictView-FormEditor-InlineEditing.js +4 -6
- package/source/views/PictView-FormEditor-InputTypePicker.js +4 -6
- package/source/views/PictView-FormEditor-PropertiesPanel.js +81 -27
- package/source/views/PictView-FormEditor.js +43 -8
- package/test/Pict-Section-FormEditor_tests.js +125 -141
- package/user-documentation/solverfunctions/intercept.md +91 -0
- package/user-documentation/solverfunctions/slope.md +86 -0
- /package/docs/{cover.md → _cover.md} +0 -0
package/package.json
CHANGED
|
@@ -1,13 +1,13 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "pict-section-formeditor",
|
|
3
|
-
"version": "1.0.
|
|
3
|
+
"version": "1.0.10",
|
|
4
4
|
"description": "Pict visual editor for pict-section-form configurations",
|
|
5
5
|
"main": "source/Pict-Section-FormEditor.js",
|
|
6
6
|
"scripts": {
|
|
7
7
|
"start": "node source/Pict-Section-FormEditor.js",
|
|
8
|
-
"test": "npx
|
|
9
|
-
"tests": "npx
|
|
10
|
-
"coverage": "npx
|
|
8
|
+
"test": "npx quack test",
|
|
9
|
+
"tests": "npx quack test -g",
|
|
10
|
+
"coverage": "npx quack coverage",
|
|
11
11
|
"build": "npx quack build",
|
|
12
12
|
"example": "npx quack examples",
|
|
13
13
|
"docs": "npx quack prepare-docs ./docs -d ./modules",
|
|
@@ -24,16 +24,16 @@
|
|
|
24
24
|
},
|
|
25
25
|
"homepage": "https://github.com/stevenvelozo/pict-section-formeditor#readme",
|
|
26
26
|
"dependencies": {
|
|
27
|
-
"pict-section-code": "^1.0.
|
|
28
|
-
"pict-section-content": "^0.0.
|
|
29
|
-
"pict-section-form": "^1.0.
|
|
30
|
-
"pict-section-markdowneditor": "^1.0.
|
|
31
|
-
"pict-section-objecteditor": "^1.0.
|
|
32
|
-
"pict-view": "^1.0.
|
|
27
|
+
"pict-section-code": "^1.0.3",
|
|
28
|
+
"pict-section-content": "^0.0.7",
|
|
29
|
+
"pict-section-form": "^1.0.193",
|
|
30
|
+
"pict-section-markdowneditor": "^1.0.1",
|
|
31
|
+
"pict-section-objecteditor": "^1.0.1",
|
|
32
|
+
"pict-view": "^1.0.67"
|
|
33
33
|
},
|
|
34
34
|
"devDependencies": {
|
|
35
|
-
"pict": "^1.0.
|
|
36
|
-
"quackage": "^1.0.
|
|
35
|
+
"pict": "^1.0.355",
|
|
36
|
+
"quackage": "^1.0.59"
|
|
37
37
|
},
|
|
38
38
|
"mocha": {
|
|
39
39
|
"diff": true,
|
|
@@ -3291,6 +3291,7 @@ module.exports = (
|
|
|
3291
3291
|
.pict-fe-add-solver-helper select
|
|
3292
3292
|
{
|
|
3293
3293
|
flex: 1;
|
|
3294
|
+
min-width: 0;
|
|
3294
3295
|
padding: 5px 8px;
|
|
3295
3296
|
border: 1px solid #D4CFC6;
|
|
3296
3297
|
border-radius: 4px;
|
|
@@ -3299,6 +3300,10 @@ module.exports = (
|
|
|
3299
3300
|
font-size: 12px;
|
|
3300
3301
|
font-family: inherit;
|
|
3301
3302
|
}
|
|
3303
|
+
.pict-fe-add-solver-helper .pict-fe-solver-add-btn
|
|
3304
|
+
{
|
|
3305
|
+
flex-shrink: 0;
|
|
3306
|
+
}
|
|
3302
3307
|
.pict-fe-add-solver-helper select:focus
|
|
3303
3308
|
{
|
|
3304
3309
|
outline: none;
|
|
@@ -193,69 +193,104 @@ class FormEditorDragDrop extends libPictProvider
|
|
|
193
193
|
}
|
|
194
194
|
case 'row':
|
|
195
195
|
{
|
|
196
|
-
let
|
|
196
|
+
let tmpMOps = this._ParentFormEditor._ManifestOpsProvider;
|
|
197
197
|
let tmpTargetSection = tmpManifest.Sections[tmpTargetIndices[0]];
|
|
198
|
-
|
|
198
|
+
let tmpTargetGroup = tmpTargetSection && tmpTargetSection.Groups ? tmpTargetSection.Groups[tmpTargetIndices[1]] : null;
|
|
199
|
+
if (!tmpTargetSection || !tmpTargetGroup)
|
|
199
200
|
{
|
|
200
201
|
return;
|
|
201
202
|
}
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
|
|
203
|
+
|
|
204
|
+
// Get source row's addresses before any changes
|
|
205
|
+
let tmpSourceRows = tmpMOps.getRowsForGroupByIndex(tmpSourceIndices[0], tmpSourceIndices[1]);
|
|
206
|
+
let tmpSourceRow = tmpSourceRows[tmpSourceIndices[2]];
|
|
207
|
+
if (!tmpSourceRow || !Array.isArray(tmpSourceRow.Inputs))
|
|
205
208
|
{
|
|
206
209
|
return;
|
|
207
210
|
}
|
|
208
|
-
|
|
211
|
+
let tmpMovedAddresses = tmpSourceRow.Inputs.slice();
|
|
212
|
+
|
|
213
|
+
let tmpSameContainer = (tmpSourceIndices[0] === tmpTargetIndices[0]) && (tmpSourceIndices[1] === tmpTargetIndices[1]);
|
|
214
|
+
let tmpInsertIdx = this._computeInsertIndex(tmpSourceIndices[2], tmpTargetIndices[2], tmpSameContainer, tmpInsertPosition);
|
|
215
|
+
|
|
216
|
+
// Update PictForm.Section/Group on moved descriptors
|
|
217
|
+
for (let i = 0; i < tmpMovedAddresses.length; i++)
|
|
209
218
|
{
|
|
210
|
-
|
|
219
|
+
let tmpDescriptor = tmpManifest.Descriptors[tmpMovedAddresses[i]];
|
|
220
|
+
if (tmpDescriptor && tmpDescriptor.PictForm)
|
|
221
|
+
{
|
|
222
|
+
tmpDescriptor.PictForm.Section = tmpTargetSection.Hash || '';
|
|
223
|
+
tmpDescriptor.PictForm.Group = tmpTargetGroup.Hash || '';
|
|
224
|
+
}
|
|
211
225
|
}
|
|
212
226
|
|
|
213
|
-
|
|
227
|
+
// Build desired row order for the target group
|
|
228
|
+
let tmpTargetRows = tmpMOps.getRowsForGroupByIndex(tmpTargetIndices[0], tmpTargetIndices[1]);
|
|
214
229
|
|
|
215
|
-
|
|
216
|
-
let
|
|
217
|
-
|
|
230
|
+
// Find and remove the moved row from the list
|
|
231
|
+
for (let i = tmpTargetRows.length - 1; i >= 0; i--)
|
|
232
|
+
{
|
|
233
|
+
if (tmpTargetRows[i].Inputs.length > 0 && tmpMovedAddresses.indexOf(tmpTargetRows[i].Inputs[0]) >= 0)
|
|
234
|
+
{
|
|
235
|
+
tmpTargetRows.splice(i, 1);
|
|
236
|
+
break;
|
|
237
|
+
}
|
|
238
|
+
}
|
|
218
239
|
|
|
219
|
-
//
|
|
220
|
-
|
|
240
|
+
// Insert at the computed position
|
|
241
|
+
tmpTargetRows.splice(tmpInsertIdx, 0, { Inputs: tmpMovedAddresses });
|
|
242
|
+
|
|
243
|
+
// Reassign Row numbers based on desired order
|
|
244
|
+
for (let i = 0; i < tmpTargetRows.length; i++)
|
|
245
|
+
{
|
|
246
|
+
tmpMOps._setRowNumberForInputs(tmpManifest, tmpTargetRows[i].Inputs, i + 1);
|
|
247
|
+
}
|
|
248
|
+
|
|
249
|
+
// Reindex source group for cross-container moves
|
|
221
250
|
if (!tmpSameContainer)
|
|
222
251
|
{
|
|
223
|
-
|
|
252
|
+
tmpMOps._reindexGroupRows(tmpSourceIndices[0], tmpSourceIndices[1]);
|
|
224
253
|
}
|
|
225
254
|
break;
|
|
226
255
|
}
|
|
227
256
|
case 'input':
|
|
228
257
|
{
|
|
229
|
-
let
|
|
258
|
+
let tmpMOps = this._ParentFormEditor._ManifestOpsProvider;
|
|
230
259
|
let tmpTargetSection = tmpManifest.Sections[tmpTargetIndices[0]];
|
|
231
|
-
|
|
260
|
+
let tmpTargetGroup = tmpTargetSection && tmpTargetSection.Groups ? tmpTargetSection.Groups[tmpTargetIndices[1]] : null;
|
|
261
|
+
if (!tmpTargetSection || !tmpTargetGroup)
|
|
232
262
|
{
|
|
233
263
|
return;
|
|
234
264
|
}
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
}
|
|
241
|
-
let tmpSourceRow = tmpSourceGroup.Rows[tmpSourceIndices[2]];
|
|
242
|
-
let tmpTargetRow = tmpTargetGroup.Rows[tmpTargetIndices[2]];
|
|
243
|
-
if (!tmpSourceRow || !Array.isArray(tmpSourceRow.Inputs) || !tmpTargetRow)
|
|
265
|
+
|
|
266
|
+
// Get source address before any changes
|
|
267
|
+
let tmpSourceRows = tmpMOps.getRowsForGroupByIndex(tmpSourceIndices[0], tmpSourceIndices[1]);
|
|
268
|
+
let tmpSourceRow = (tmpSourceIndices[2] >= 0 && tmpSourceIndices[2] < tmpSourceRows.length) ? tmpSourceRows[tmpSourceIndices[2]] : null;
|
|
269
|
+
if (!tmpSourceRow || !Array.isArray(tmpSourceRow.Inputs) || tmpSourceIndices[3] < 0 || tmpSourceIndices[3] >= tmpSourceRow.Inputs.length)
|
|
244
270
|
{
|
|
245
271
|
return;
|
|
246
272
|
}
|
|
247
|
-
|
|
248
|
-
{
|
|
249
|
-
tmpTargetRow.Inputs = [];
|
|
250
|
-
}
|
|
273
|
+
let tmpAddress = tmpSourceRow.Inputs[tmpSourceIndices[3]];
|
|
251
274
|
|
|
252
|
-
|
|
275
|
+
// Get target row's current inputs before any changes
|
|
276
|
+
let tmpTargetRows = tmpMOps.getRowsForGroupByIndex(tmpTargetIndices[0], tmpTargetIndices[1]);
|
|
277
|
+
let tmpTargetRow = (tmpTargetIndices[2] >= 0 && tmpTargetIndices[2] < tmpTargetRows.length) ? tmpTargetRows[tmpTargetIndices[2]] : null;
|
|
278
|
+
let tmpTargetInputs = (tmpTargetRow && Array.isArray(tmpTargetRow.Inputs)) ? tmpTargetRow.Inputs.slice() : [];
|
|
253
279
|
|
|
254
|
-
|
|
255
|
-
let
|
|
256
|
-
|
|
280
|
+
// Compute insert position
|
|
281
|
+
let tmpSameRow = (tmpSourceIndices[0] === tmpTargetIndices[0]) && (tmpSourceIndices[1] === tmpTargetIndices[1]) && (tmpSourceIndices[2] === tmpTargetIndices[2]);
|
|
282
|
+
let tmpInsertIdx = this._computeInsertIndex(tmpSameRow ? tmpSourceIndices[3] : -1, tmpTargetIndices[3], tmpSameRow, tmpInsertPosition);
|
|
257
283
|
|
|
258
|
-
//
|
|
284
|
+
// Build desired input order for the target row
|
|
285
|
+
// Remove moved address if it's already in the target list (same-row case)
|
|
286
|
+
let tmpAddrIdx = tmpTargetInputs.indexOf(tmpAddress);
|
|
287
|
+
if (tmpAddrIdx >= 0)
|
|
288
|
+
{
|
|
289
|
+
tmpTargetInputs.splice(tmpAddrIdx, 1);
|
|
290
|
+
}
|
|
291
|
+
tmpTargetInputs.splice(tmpInsertIdx, 0, tmpAddress);
|
|
292
|
+
|
|
293
|
+
// Update Descriptor's PictForm metadata
|
|
259
294
|
if (typeof tmpAddress === 'string' && tmpManifest.Descriptors && tmpManifest.Descriptors[tmpAddress])
|
|
260
295
|
{
|
|
261
296
|
let tmpDescriptor = tmpManifest.Descriptors[tmpAddress];
|
|
@@ -267,6 +302,16 @@ class FormEditorDragDrop extends libPictProvider
|
|
|
267
302
|
tmpDescriptor.PictForm.Group = tmpTargetGroup.Hash || '';
|
|
268
303
|
tmpDescriptor.PictForm.Row = tmpTargetIndices[2] + 1;
|
|
269
304
|
}
|
|
305
|
+
|
|
306
|
+
// Reorder Descriptor keys to achieve desired input order
|
|
307
|
+
tmpMOps._reorderDescriptorsForRow(tmpTargetInputs);
|
|
308
|
+
|
|
309
|
+
// Reindex source group if cross-group move
|
|
310
|
+
let tmpSameGroup = (tmpSourceIndices[0] === tmpTargetIndices[0]) && (tmpSourceIndices[1] === tmpTargetIndices[1]);
|
|
311
|
+
if (!tmpSameGroup)
|
|
312
|
+
{
|
|
313
|
+
tmpMOps._reindexGroupRows(tmpSourceIndices[0], tmpSourceIndices[1]);
|
|
314
|
+
}
|
|
270
315
|
break;
|
|
271
316
|
}
|
|
272
317
|
case 'subcolumn':
|
|
@@ -540,63 +585,68 @@ class FormEditorDragDrop extends libPictProvider
|
|
|
540
585
|
case 'row':
|
|
541
586
|
{
|
|
542
587
|
// Container is a group; indices = [sectionIndex, groupIndex]
|
|
543
|
-
let
|
|
588
|
+
let tmpMOps = this._ParentFormEditor._ManifestOpsProvider;
|
|
544
589
|
let tmpTargetSection = tmpManifest.Sections[tmpContainerIndices[0]];
|
|
545
|
-
|
|
590
|
+
let tmpTargetGroup = tmpTargetSection && tmpTargetSection.Groups ? tmpTargetSection.Groups[tmpContainerIndices[1]] : null;
|
|
591
|
+
if (!tmpTargetSection || !tmpTargetGroup)
|
|
546
592
|
{
|
|
547
593
|
return;
|
|
548
594
|
}
|
|
549
|
-
|
|
550
|
-
|
|
551
|
-
|
|
595
|
+
|
|
596
|
+
// Get source row's addresses
|
|
597
|
+
let tmpSourceRows = tmpMOps.getRowsForGroupByIndex(tmpSourceIndices[0], tmpSourceIndices[1]);
|
|
598
|
+
let tmpSourceRow = tmpSourceRows[tmpSourceIndices[2]];
|
|
599
|
+
if (!tmpSourceRow || !Array.isArray(tmpSourceRow.Inputs))
|
|
552
600
|
{
|
|
553
601
|
return;
|
|
554
602
|
}
|
|
555
|
-
|
|
603
|
+
let tmpMovedAddresses = tmpSourceRow.Inputs.slice();
|
|
604
|
+
|
|
605
|
+
// Update PictForm.Section/Group on moved descriptors
|
|
606
|
+
for (let i = 0; i < tmpMovedAddresses.length; i++)
|
|
556
607
|
{
|
|
557
|
-
|
|
608
|
+
let tmpDescriptor = tmpManifest.Descriptors[tmpMovedAddresses[i]];
|
|
609
|
+
if (tmpDescriptor && tmpDescriptor.PictForm)
|
|
610
|
+
{
|
|
611
|
+
tmpDescriptor.PictForm.Section = tmpTargetSection.Hash || '';
|
|
612
|
+
tmpDescriptor.PictForm.Group = tmpTargetGroup.Hash || '';
|
|
613
|
+
}
|
|
558
614
|
}
|
|
559
615
|
|
|
560
|
-
|
|
561
|
-
|
|
616
|
+
// Assign row number to place at end of target group
|
|
617
|
+
let tmpTargetRows = tmpMOps.getRowsForGroupByIndex(tmpContainerIndices[0], tmpContainerIndices[1]);
|
|
618
|
+
let tmpNextRowNum = tmpTargetRows.length + 1;
|
|
619
|
+
tmpMOps._setRowNumberForInputs(tmpManifest, tmpMovedAddresses, tmpNextRowNum);
|
|
562
620
|
|
|
563
|
-
|
|
564
|
-
|
|
621
|
+
// Reindex source group to close the gap
|
|
622
|
+
let tmpSameGroup = (tmpSourceIndices[0] === tmpContainerIndices[0]) && (tmpSourceIndices[1] === tmpContainerIndices[1]);
|
|
623
|
+
if (!tmpSameGroup)
|
|
565
624
|
{
|
|
566
|
-
|
|
625
|
+
tmpMOps._reindexGroupRows(tmpSourceIndices[0], tmpSourceIndices[1]);
|
|
567
626
|
}
|
|
568
627
|
break;
|
|
569
628
|
}
|
|
570
629
|
case 'input':
|
|
571
630
|
{
|
|
572
631
|
// Container is a row; indices = [sectionIndex, groupIndex, rowIndex]
|
|
573
|
-
let
|
|
632
|
+
let tmpMOps = this._ParentFormEditor._ManifestOpsProvider;
|
|
574
633
|
let tmpTargetSection = tmpManifest.Sections[tmpContainerIndices[0]];
|
|
575
|
-
|
|
576
|
-
|
|
577
|
-
return;
|
|
578
|
-
}
|
|
579
|
-
let tmpSourceGroup = tmpSourceSection.Groups[tmpSourceIndices[1]];
|
|
580
|
-
let tmpTargetGroup = tmpTargetSection.Groups[tmpContainerIndices[1]];
|
|
581
|
-
if (!tmpSourceGroup || !Array.isArray(tmpSourceGroup.Rows) || !tmpTargetGroup || !Array.isArray(tmpTargetGroup.Rows))
|
|
634
|
+
let tmpTargetGroup = tmpTargetSection && tmpTargetSection.Groups ? tmpTargetSection.Groups[tmpContainerIndices[1]] : null;
|
|
635
|
+
if (!tmpTargetSection || !tmpTargetGroup)
|
|
582
636
|
{
|
|
583
637
|
return;
|
|
584
638
|
}
|
|
585
|
-
|
|
586
|
-
|
|
587
|
-
|
|
639
|
+
|
|
640
|
+
// Get source address
|
|
641
|
+
let tmpSourceRows = tmpMOps.getRowsForGroupByIndex(tmpSourceIndices[0], tmpSourceIndices[1]);
|
|
642
|
+
let tmpSourceRow = (tmpSourceIndices[2] >= 0 && tmpSourceIndices[2] < tmpSourceRows.length) ? tmpSourceRows[tmpSourceIndices[2]] : null;
|
|
643
|
+
if (!tmpSourceRow || !Array.isArray(tmpSourceRow.Inputs) || tmpSourceIndices[3] < 0 || tmpSourceIndices[3] >= tmpSourceRow.Inputs.length)
|
|
588
644
|
{
|
|
589
645
|
return;
|
|
590
646
|
}
|
|
591
|
-
|
|
592
|
-
{
|
|
593
|
-
tmpTargetRow.Inputs = [];
|
|
594
|
-
}
|
|
647
|
+
let tmpAddress = tmpSourceRow.Inputs[tmpSourceIndices[3]];
|
|
595
648
|
|
|
596
|
-
|
|
597
|
-
tmpTargetRow.Inputs.push(tmpAddress);
|
|
598
|
-
|
|
599
|
-
// Update Descriptor metadata
|
|
649
|
+
// Update Descriptor PictForm metadata
|
|
600
650
|
if (typeof tmpAddress === 'string' && tmpManifest.Descriptors && tmpManifest.Descriptors[tmpAddress])
|
|
601
651
|
{
|
|
602
652
|
let tmpDescriptor = tmpManifest.Descriptors[tmpAddress];
|
|
@@ -608,6 +658,29 @@ class FormEditorDragDrop extends libPictProvider
|
|
|
608
658
|
tmpDescriptor.PictForm.Group = tmpTargetGroup.Hash || '';
|
|
609
659
|
tmpDescriptor.PictForm.Row = tmpContainerIndices[2] + 1;
|
|
610
660
|
}
|
|
661
|
+
|
|
662
|
+
// Place at end of target row's input order
|
|
663
|
+
let tmpTargetRows = tmpMOps.getRowsForGroupByIndex(tmpContainerIndices[0], tmpContainerIndices[1]);
|
|
664
|
+
let tmpTargetRow = (tmpContainerIndices[2] >= 0 && tmpContainerIndices[2] < tmpTargetRows.length) ? tmpTargetRows[tmpContainerIndices[2]] : null;
|
|
665
|
+
let tmpTargetInputs = (tmpTargetRow && Array.isArray(tmpTargetRow.Inputs)) ? tmpTargetRow.Inputs.slice() : [];
|
|
666
|
+
|
|
667
|
+
// Remove from current position if it's there (same-row case)
|
|
668
|
+
let tmpAddrIdx = tmpTargetInputs.indexOf(tmpAddress);
|
|
669
|
+
if (tmpAddrIdx >= 0)
|
|
670
|
+
{
|
|
671
|
+
tmpTargetInputs.splice(tmpAddrIdx, 1);
|
|
672
|
+
}
|
|
673
|
+
tmpTargetInputs.push(tmpAddress);
|
|
674
|
+
|
|
675
|
+
// Reorder Descriptor keys
|
|
676
|
+
tmpMOps._reorderDescriptorsForRow(tmpTargetInputs);
|
|
677
|
+
|
|
678
|
+
// Reindex source group if cross-group
|
|
679
|
+
let tmpSameGroup = (tmpSourceIndices[0] === tmpContainerIndices[0]) && (tmpSourceIndices[1] === tmpContainerIndices[1]);
|
|
680
|
+
if (!tmpSameGroup)
|
|
681
|
+
{
|
|
682
|
+
tmpMOps._reindexGroupRows(tmpSourceIndices[0], tmpSourceIndices[1]);
|
|
683
|
+
}
|
|
611
684
|
break;
|
|
612
685
|
}
|
|
613
686
|
case 'subcolumn':
|