@innovastudio/contentbuilder 1.0.58 → 1.0.62

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.
Files changed (60) hide show
  1. package/package.json +1 -1
  2. package/public/contentbuilder/contentbuilder.css +19 -6
  3. package/public/contentbuilder/contentbuilder.esm.js +514 -56
  4. package/public/contentbuilder/contentbuilder.min.js +8 -8
  5. package/public/contentbuilder/themes/colored-blue.css +1 -1
  6. package/public/contentbuilder/themes/colored-blue2.css +1 -1
  7. package/public/contentbuilder/themes/colored-blue3.css +1 -1
  8. package/public/contentbuilder/themes/colored-blue4.css +1 -1
  9. package/public/contentbuilder/themes/colored-blue5.css +1 -1
  10. package/public/contentbuilder/themes/colored-blue6.css +1 -1
  11. package/public/contentbuilder/themes/colored-blue7.css +1 -1
  12. package/public/contentbuilder/themes/colored-blue8.css +1 -1
  13. package/public/contentbuilder/themes/colored-dark.css +1 -1
  14. package/public/contentbuilder/themes/colored-darkblue.css +1 -1
  15. package/public/contentbuilder/themes/colored-gray.css +1 -1
  16. package/public/contentbuilder/themes/colored-green.css +1 -1
  17. package/public/contentbuilder/themes/colored-green2.css +1 -1
  18. package/public/contentbuilder/themes/colored-green3.css +1 -1
  19. package/public/contentbuilder/themes/colored-green4.css +1 -1
  20. package/public/contentbuilder/themes/colored-green5.css +1 -1
  21. package/public/contentbuilder/themes/colored-magenta.css +1 -1
  22. package/public/contentbuilder/themes/colored-orange.css +1 -1
  23. package/public/contentbuilder/themes/colored-orange2.css +1 -1
  24. package/public/contentbuilder/themes/colored-orange3.css +1 -1
  25. package/public/contentbuilder/themes/colored-pink.css +1 -1
  26. package/public/contentbuilder/themes/colored-pink2.css +1 -1
  27. package/public/contentbuilder/themes/colored-pink3.css +1 -1
  28. package/public/contentbuilder/themes/colored-pink4.css +1 -1
  29. package/public/contentbuilder/themes/colored-purple.css +1 -1
  30. package/public/contentbuilder/themes/colored-purple2.css +1 -1
  31. package/public/contentbuilder/themes/colored-red.css +1 -1
  32. package/public/contentbuilder/themes/colored-red2.css +1 -1
  33. package/public/contentbuilder/themes/colored-red3.css +1 -1
  34. package/public/contentbuilder/themes/colored-red4.css +1 -1
  35. package/public/contentbuilder/themes/colored-red5.css +1 -1
  36. package/public/contentbuilder/themes/colored-yellow.css +1 -1
  37. package/public/contentbuilder/themes/colored-yellow2.css +1 -1
  38. package/public/contentbuilder/themes/dark-blue.css +1 -1
  39. package/public/contentbuilder/themes/dark-blue2.css +1 -1
  40. package/public/contentbuilder/themes/dark-blue3.css +1 -1
  41. package/public/contentbuilder/themes/dark-gray.css +1 -1
  42. package/public/contentbuilder/themes/dark-pink.css +1 -1
  43. package/public/contentbuilder/themes/dark-purple.css +1 -1
  44. package/public/contentbuilder/themes/dark-red.css +1 -1
  45. package/public/contentbuilder/themes/dark.css +1 -1
  46. package/public/contentbuilder/themes/light-blue.css +1 -1
  47. package/public/contentbuilder/themes/light-blue2.css +1 -1
  48. package/public/contentbuilder/themes/light-blue3.css +1 -1
  49. package/public/contentbuilder/themes/light-cyan.css +1 -1
  50. package/public/contentbuilder/themes/light-gray.css +1 -1
  51. package/public/contentbuilder/themes/light-gray2.css +1 -1
  52. package/public/contentbuilder/themes/light-gray3.css +1 -1
  53. package/public/contentbuilder/themes/light-green.css +1 -1
  54. package/public/contentbuilder/themes/light-pink.css +1 -1
  55. package/public/contentbuilder/themes/light-pink2.css +1 -1
  56. package/public/contentbuilder/themes/light-purple.css +1 -1
  57. package/public/contentbuilder/themes/light-purple2.css +1 -1
  58. package/public/contentbuilder/themes/light-red.css +1 -1
  59. package/public/contentbuilder/themes/light-yellow.css +1 -1
  60. package/public/contentbuilder/themes/light-yellow2.css +1 -1
@@ -2396,6 +2396,7 @@ class Util {
2396
2396
  on = true;
2397
2397
  }
2398
2398
  }
2399
+ /*
2399
2400
  if(on) {
2400
2401
  parent._cb.clearFont();
2401
2402
  } else {
@@ -2406,6 +2407,13 @@ class Util {
2406
2407
  //parent._cb.applyFont(fontfamily, fontstyle, provider);
2407
2408
  parent._cb.setFont(fontfamily, fontstyle, fontdisplay, provider);
2408
2409
  }
2410
+ */
2411
+ var provider = elm.getAttribute('data-provider');
2412
+ var fontfamily = elm.getAttribute('data-font-family');
2413
+ var fontstyle = elm.getAttribute('data-font-style');
2414
+ var fontdisplay = elm.getAttribute('data-font-display');
2415
+ //parent._cb.applyFont(fontfamily, fontstyle, provider);
2416
+ parent._cb.setFont(fontfamily, fontstyle, fontdisplay, provider);
2409
2417
 
2410
2418
  });
2411
2419
  }
@@ -2597,6 +2605,7 @@ class Util {
2597
2605
  on = true;
2598
2606
  }
2599
2607
  }
2608
+ /*
2600
2609
  if(on) {
2601
2610
  parent._cb.clearFont();
2602
2611
  } else {
@@ -2607,6 +2616,13 @@ class Util {
2607
2616
  //parent._cb.applyFont(fontfamily, fontstyle, provider);
2608
2617
  parent._cb.setFont(fontfamily, fontstyle, fontdisplay, provider);
2609
2618
  }
2619
+ */
2620
+ var provider = elm.getAttribute('data-provider');
2621
+ var fontfamily = elm.getAttribute('data-font-family');
2622
+ var fontstyle = elm.getAttribute('data-font-style');
2623
+ var fontdisplay = elm.getAttribute('data-font-display');
2624
+ //parent._cb.applyFont(fontfamily, fontstyle, provider);
2625
+ parent._cb.setFont(fontfamily, fontstyle, fontdisplay, provider);
2610
2626
 
2611
2627
  });
2612
2628
  }
@@ -2716,6 +2732,16 @@ class Dom {
2716
2732
  return children;
2717
2733
  }
2718
2734
 
2735
+ getElementOffset(el) {
2736
+ const rect = el.getBoundingClientRect();
2737
+ return {
2738
+ top: rect.top + window.pageYOffset,
2739
+ left: rect.left + window.pageXOffset,
2740
+ width: rect.width,
2741
+ height: rect.height
2742
+ };
2743
+ }
2744
+
2719
2745
  parentsHasClass(element, classname) {
2720
2746
  while (element) {
2721
2747
  // if(classname==='is-side') console.log(element.nodeName); // NOTE: click on svg can still returns undefined in IE11
@@ -2925,40 +2951,45 @@ class Dom {
2925
2951
  }
2926
2952
 
2927
2953
  textSelection() {
2954
+ /*
2928
2955
  try {
2929
- var elm;
2930
- var curr = window.getSelection().getRangeAt(0).commonAncestorContainer;
2931
-
2932
- if (curr.nodeType === 3) {
2933
- // text node
2934
- elm = curr.parentNode;
2935
-
2936
- if (this.parentsHasClass(elm, 'is-builder')) {
2937
- return elm;
2956
+ var elm;
2957
+ var curr = window.getSelection().getRangeAt(0).commonAncestorContainer;
2958
+ if (curr.nodeType === 3) { // text node
2959
+ elm = curr.parentNode;
2960
+ if(this.parentsHasClass(elm, 'is-builder')) {
2961
+ return elm;
2962
+ }
2963
+ else {
2964
+ return false;
2965
+ }
2938
2966
  } else {
2939
- return false;
2940
- }
2941
- } else {
2942
- elm = curr;
2943
- var nodeName = elm.nodeName.toLowerCase();
2944
-
2945
- if (nodeName === 'i' && elm.innerHTML === '') {
2946
- //icon
2947
- if (this.parentsHasClass(elm, 'is-builder')) {
2948
- return elm;
2949
- }
2950
- } // Check if a block (because when placing cursor using arrow keys on empty block, nodeType=1 not 3)
2951
-
2952
-
2953
- if (nodeName === 'p' || nodeName === 'h1' || nodeName === 'h2' || nodeName === 'h3' || nodeName === 'h4' || nodeName === 'h5' || nodeName === 'h6' || nodeName === 'li' || nodeName === 'pre' || nodeName === 'blockquote') {
2954
- return elm;
2967
+ elm = curr;
2968
+ var nodeName = elm.nodeName.toLowerCase();
2969
+ if(nodeName === 'i' && elm.innerHTML === '') { //icon
2970
+ if(this.parentsHasClass(elm, 'is-builder')) {
2971
+ return elm;
2972
+ }
2973
+ }
2974
+
2975
+ // Check if a block (because when placing cursor using arrow keys on empty block, nodeType=1 not 3)
2976
+ if(nodeName === 'p' || nodeName === 'h1' || nodeName === 'h2'
2977
+ || nodeName === 'h3' || nodeName === 'h4' || nodeName === 'h5'
2978
+ || nodeName === 'h6' || nodeName === 'li' || nodeName === 'pre'
2979
+ || nodeName === 'blockquote') {
2980
+ return elm;
2981
+ }
2982
+ return false;
2955
2983
  }
2956
-
2957
- return false;
2958
- }
2959
2984
  } catch (e) {
2960
- return false;
2985
+ return false;
2961
2986
  }
2987
+ */
2988
+ const selection = this.getSelection();
2989
+ const anchorNode = selection.anchorNode;
2990
+ if (!anchorNode) return false;
2991
+ const container = anchorNode.nodeType !== Node.TEXT_NODE && anchorNode.nodeType !== Node.COMMENT_NODE ? anchorNode : anchorNode.parentElement;
2992
+ return container;
2962
2993
  }
2963
2994
 
2964
2995
  getStyle(element, property) {
@@ -3010,7 +3041,347 @@ class Dom {
3010
3041
  }
3011
3042
  }
3012
3043
  } // ---
3044
+ // execCommand replacement
3045
+
3046
+
3047
+ execCommand(action, value, callback) {
3048
+ const selection = this.getSelection();
3049
+ if (!selection) return;
3050
+ const anchorNode = selection.anchorNode;
3051
+
3052
+ if (anchorNode) {
3053
+ const container = anchorNode.nodeType !== Node.TEXT_NODE && anchorNode.nodeType !== Node.COMMENT_NODE ? anchorNode : anchorNode.parentElement;
3054
+ const sameSelection = container && container.innerText === selection.toString();
3055
+ let newElement;
3056
+
3057
+ if (sameSelection || selection.toString().trim() === '') {
3058
+ newElement = this.updateSelection(action, value, container);
3059
+ } else {
3060
+ newElement = this.replaceSelection(action, value, selection, container);
3061
+ }
3062
+
3063
+ if (callback) callback(true, newElement);
3064
+ } else {
3065
+ if (callback) callback(false);
3066
+ }
3067
+ }
3068
+
3069
+ updateSelection(action, value, container) {
3070
+ // container.style[action] = value; //APPLY => Use getStyleValue to check if toggle is needed.
3071
+ container.style[action] = this.getStyleValue(container, action, value); // Optional, better if used: check if the style is the same as its parent. If so, clear it.
3072
+
3073
+ this.checkStyleIfSameAsParent(container, action);
3074
+ this.cleanChildren(action, container); // this.cleanUnusedSpan(container);
3075
+
3076
+ return container;
3077
+ }
3078
+
3079
+ replaceSelection(action, value, selection, container) {
3080
+ const range = selection.getRangeAt(0);
3081
+ const fragment = range.extractContents();
3082
+ const span = this.createSpan(container, action, value);
3083
+ span.appendChild(fragment);
3084
+ this.cleanChildren(action, span); // this.cleanUnusedSpan(span);
3085
+
3086
+ range.insertNode(span);
3087
+ selection.selectAllChildren(span); // Optional, better if used: check if the style is the same as its parent. If so, clear it.
3088
+
3089
+ this.checkStyleIfSameAsParent(span, action);
3090
+ return span;
3091
+ }
3092
+
3093
+ checkStyleIfSameAsParent(element, action) {
3094
+ if (element.parentNode) {
3095
+ if (element.parentNode.style[action] === element.style[action] || window.getComputedStyle(element.parentNode, null).getPropertyValue(action) === element.style[action]) {
3096
+ element.style[action] = '';
3097
+
3098
+ if (element.getAttribute('style') === '' || element.style === null) {
3099
+ element.removeAttribute('style');
3100
+ } // let unused = ( element.attributes.length === 0 || (element.attributes.length === 1 && element.hasAttribute('data-keep')));
3101
+ // if (element.nodeName.toLowerCase() === 'span' && unused) {
3102
+ // const text = document.createTextNode(element.textContent);
3103
+ // element.parentElement.replaceChild(text, element);
3104
+ // }
3105
+
3106
+ }
3107
+ }
3108
+ }
3109
+
3110
+ createSpan(container, action, value) {
3111
+ const span = document.createElement('span'); // span.style[action] = value; //APPLY => Use getStyleValue to check if toggle is needed.
3112
+
3113
+ span.style[action] = this.getStyleValue(container, action, value);
3114
+ return span;
3115
+ }
3116
+
3117
+ findParentStyle(node, action) {
3118
+ if (node.nodeName.toUpperCase() === 'HTML' || node.nodeName.toUpperCase() === 'BODY') {
3119
+ return null;
3120
+ }
3121
+
3122
+ if (!node.parentNode) {
3123
+ return null;
3124
+ }
3125
+
3126
+ const hasStyle = node.style[action] !== null && node.style[action] !== undefined && node.style[action] !== '';
3127
+
3128
+ if (hasStyle) {
3129
+ return node;
3130
+ }
3131
+
3132
+ this.findParentStyle(node.parentNode, action);
3133
+ }
3134
+
3135
+ getStyleValue(container, action, value) {
3136
+ if (action === 'font-weight' || action === 'font-style' || action === 'text-decoration' || action === 'text-transform') {
3137
+ // Toggle
3138
+ // let currentValue = window.getComputedStyle(container, null).getPropertyValue(action);
3139
+ let parent = this.findParentStyle(container, action);
3140
+ let currentValue;
3141
+
3142
+ if (parent) {
3143
+ currentValue = parent.style[action];
3144
+ }
3145
+
3146
+ if (value === currentValue) {
3147
+ //toggle here
3148
+ // value = 'initial'; // the problem with initial is that it is always refer to font-weight: 400 (won;t work for custom 300 for normal paragraph)
3149
+ // so we'll do the test first, to find the actuat initial value
3150
+ container.style[action] = ''; // test
3013
3151
 
3152
+ let initialValue = window.getComputedStyle(container, null).getPropertyValue(action); // get the actual initial value
3153
+ // console.log('initial:' +initialValue);
3154
+
3155
+ container.style[action] = currentValue; //return back from test
3156
+
3157
+ value = initialValue;
3158
+ }
3159
+ }
3160
+
3161
+ return value;
3162
+ }
3163
+
3164
+ getSelection() {
3165
+ if (window && window.getSelection) {
3166
+ return window.getSelection();
3167
+ } else if (document && document.getSelection) {
3168
+ return document.getSelection();
3169
+ } else if (document && document.selection) {
3170
+ return document.selection.createRange().text;
3171
+ }
3172
+
3173
+ return null;
3174
+ }
3175
+
3176
+ cleanChildren(action, span) {
3177
+ if (!span.hasChildNodes()) {
3178
+ return;
3179
+ } // Direct children with same style rule
3180
+
3181
+
3182
+ const children = Array.from(span.children).filter(element => {
3183
+ return element.style[action] !== undefined && element.style[action.style] !== '';
3184
+ });
3185
+
3186
+ if (children && children.length > 0) {
3187
+ children.forEach(element => {
3188
+ element.style[action] = '';
3189
+
3190
+ if (element.getAttribute('style') === '' || element.style === null) {
3191
+ element.removeAttribute('style');
3192
+ }
3193
+ });
3194
+ } // Deeper childrens
3195
+
3196
+
3197
+ const cleanChildrenChildren = Array.from(span.children).map(element => {
3198
+ return this.cleanChildren(action, element);
3199
+ });
3200
+
3201
+ if (!cleanChildrenChildren || cleanChildrenChildren.length <= 0) {
3202
+ return;
3203
+ }
3204
+ } // Clean HTML stuff
3205
+
3206
+
3207
+ removeEmptyStyle(area) {
3208
+ if (!area.hasChildNodes()) {
3209
+ return;
3210
+ }
3211
+
3212
+ const children = Array.from(area.children).filter(element => {
3213
+ return element.getAttribute('style');
3214
+ });
3215
+
3216
+ if (children && children.length > 0) {
3217
+ children.forEach(element => {
3218
+ if (element.getAttribute('style').trim() === '' || element.style === null) {
3219
+ element.removeAttribute('style');
3220
+ }
3221
+ });
3222
+ } // Deeper childrens
3223
+
3224
+
3225
+ const removeEmptyStyleChildren = Array.from(area.children).map(element => {
3226
+ return this.removeEmptyStyle(element);
3227
+ });
3228
+
3229
+ if (!removeEmptyStyleChildren || removeEmptyStyleChildren.length <= 0) {
3230
+ return;
3231
+ }
3232
+ }
3233
+
3234
+ cleanEmptySpans(area) {
3235
+ let spans = area.querySelectorAll('span');
3236
+ const filter = Array.prototype.filter;
3237
+ let children = filter.call(spans, element => {
3238
+ return element.attributes.length === 0;
3239
+ }); // Remove empty spans
3240
+
3241
+ if (children && children.length > 0) {
3242
+ children.forEach(element => {
3243
+ element.outerHTML = element.innerHTML;
3244
+ });
3245
+ } // Remove spans which have empty content
3246
+
3247
+
3248
+ spans = area.querySelectorAll('span');
3249
+ filter.call(spans, element => {
3250
+ if (element.innerHTML === '') {
3251
+ element.parentNode.removeChild(element);
3252
+ }
3253
+ }); // Recheck
3254
+
3255
+ spans = area.querySelectorAll('span');
3256
+ children = filter.call(spans, element => {
3257
+ return element.attributes.length === 0;
3258
+ });
3259
+
3260
+ if (children && children.length > 0) {
3261
+ this.cleanEmptySpans(area);
3262
+ } else {
3263
+ return;
3264
+ }
3265
+ } // Font Size stuff
3266
+
3267
+
3268
+ cleanClassSize(span, className) {
3269
+ if (!span.hasChildNodes()) {
3270
+ return;
3271
+ } // Direct children with same style rule
3272
+
3273
+
3274
+ const children = Array.from(span.children).filter(element => {
3275
+ return this.hasClass(element, className);
3276
+ });
3277
+
3278
+ if (children && children.length > 0) {
3279
+ children.forEach(element => {
3280
+ this.removeClass(element, className);
3281
+ });
3282
+ } // Deeper childrens
3283
+
3284
+
3285
+ const cleanClassSizeChildren = Array.from(span.children).map(element => {
3286
+ return this.cleanClassSize(element, className);
3287
+ });
3288
+
3289
+ if (!cleanClassSizeChildren || cleanClassSizeChildren.length <= 0) {
3290
+ return;
3291
+ }
3292
+ } // Remove Format stuff
3293
+
3294
+
3295
+ removeFormat() {
3296
+ const selection = this.getSelection();
3297
+ if (!selection) return;
3298
+ const anchorNode = selection.anchorNode;
3299
+ if (!anchorNode) return;
3300
+ const container = anchorNode.nodeType !== Node.TEXT_NODE && anchorNode.nodeType !== Node.COMMENT_NODE ? anchorNode : anchorNode.parentElement;
3301
+ const sameSelection = container && container.innerText === selection.toString();
3302
+
3303
+ if (sameSelection || selection.toString().trim() === '') {
3304
+ this.cleanElement(container);
3305
+ } else {
3306
+ this.cleanSelection(selection);
3307
+ }
3308
+ }
3309
+
3310
+ cleanElement(elm) {
3311
+ elm.style.fontWeight = '';
3312
+ elm.style.fontStyle = '';
3313
+ elm.style.textDecoration = '';
3314
+ elm.style.textTransform = '';
3315
+ elm.style.fontFamily = '';
3316
+ elm.style.fontSize = '';
3317
+ elm.style.color = '';
3318
+ elm.style.backgroundColor = '';
3319
+ elm.classList.forEach(item => {
3320
+ if (item.indexOf('size-') !== -1) {
3321
+ this.removeClass(elm, item);
3322
+ }
3323
+ });
3324
+ let elms = elm.querySelectorAll('*');
3325
+ elms.forEach(elm => {
3326
+ elm.style.fontWeight = '';
3327
+ elm.style.fontStyle = '';
3328
+ elm.style.textDecoration = '';
3329
+ elm.style.textTransform = '';
3330
+ elm.style.fontFamily = '';
3331
+ elm.style.fontSize = '';
3332
+ elm.style.color = '';
3333
+ elm.style.backgroundColor = '';
3334
+ elm.classList.forEach(item => {
3335
+ if (item.indexOf('size-') !== -1) {
3336
+ this.removeClass(elm, item);
3337
+ }
3338
+ });
3339
+ });
3340
+ this.cleanUnusedSpan(elm); // causes lost selection
3341
+ }
3342
+
3343
+ cleanSelection(selection) {
3344
+ const range = selection.getRangeAt(0);
3345
+ const fragment = range.extractContents();
3346
+ const span = document.createElement('span');
3347
+ span.appendChild(fragment);
3348
+ range.insertNode(span);
3349
+ selection.selectAllChildren(span);
3350
+ this.cleanElement(span);
3351
+ }
3352
+
3353
+ cleanUnusedSpan(span) {
3354
+ if (!span.hasChildNodes()) {
3355
+ return;
3356
+ } // Direct children with no style
3357
+
3358
+
3359
+ const children = Array.from(span.children).filter(element => {
3360
+ if (element.getAttribute('style') === '' || element.style === null) {
3361
+ element.removeAttribute('style');
3362
+ }
3363
+
3364
+ let unused = element.attributes.length === 0 || element.attributes.length === 1 && element.hasAttribute('data-keep');
3365
+ return element.nodeName.toLowerCase() === 'span' && unused;
3366
+ });
3367
+
3368
+ if (children && children.length > 0) {
3369
+ children.forEach(element => {
3370
+ const text = document.createTextNode(element.textContent);
3371
+ element.parentElement.replaceChild(text, element);
3372
+ });
3373
+ return;
3374
+ } // Deeper childrens
3375
+
3376
+
3377
+ const cleanUnusedSpanChildren = Array.from(span.children).map(element => {
3378
+ return this.cleanUnusedSpan(element);
3379
+ });
3380
+
3381
+ if (!cleanUnusedSpanChildren || cleanUnusedSpanChildren.length <= 0) {
3382
+ return;
3383
+ }
3384
+ }
3014
3385
 
3015
3386
  }
3016
3387
 
@@ -8702,6 +9073,8 @@ class HtmlUtil {
8702
9073
  dom$E.removeAttributes(elms, 'draggable');
8703
9074
  elms = tmp.querySelectorAll('[data-animated]');
8704
9075
  dom$E.removeAttributes(elms, 'data-animated');
9076
+ elms = tmp.querySelectorAll('[data-saveforundo]');
9077
+ dom$E.removeAttributes(elms, 'data-saveforundo');
8705
9078
  elms = tmp.querySelectorAll('[hidesnippetaddtool]');
8706
9079
  dom$E.removeAttributes(elms, 'hidesnippetaddtool');
8707
9080
  elms = tmp.querySelectorAll('[gray]');
@@ -8747,6 +9120,8 @@ class HtmlUtil {
8747
9120
  Array.prototype.forEach.call(emptystyles, emptystyle => {
8748
9121
  emptystyle.removeAttribute('style');
8749
9122
  });
9123
+ dom$E.removeEmptyStyle(tmp);
9124
+ dom$E.cleanEmptySpans(tmp);
8750
9125
  elms = tmp.querySelectorAll('[data-keep]');
8751
9126
  dom$E.removeAttributes(elms, 'data-keep'); //Cleanup button <span contenteditable="false"><a contenteditable="true">button</a></span>
8752
9127
 
@@ -44940,6 +45315,10 @@ class ColumnTool {
44940
45315
  <button title="${util.out('Clear')}" class="input-cell-textcolor" data-command=""><svg class="is-icon-flex" style="flex:none;width:18px;height:18px;margin-top: 2px;"><use xlink:href="#ion-ios-close-empty"></use></svg></button>
44941
45316
  </div>
44942
45317
 
45318
+ <div style="padding-top:20px;">
45319
+ <label class="label-cell-grayscale label-checkbox" for="chkCellGrayscale"><input id="chkCellGrayscale" class="chk-cell-grayscale" type="checkbox" /> ${util.out('Grayscale')}</label>
45320
+ </div>
45321
+
44943
45322
  <div style="display:none;padding-top:20px;padding-bottom:3px;">${util.out('Enlarge Row')}:</div>
44944
45323
  <div style="display: none;">
44945
45324
  <button title="${util.out('Normal')}" class="input-row-enlarge" data-command="0" style="margin-right:1px;">${util.out('Normal')}</button>
@@ -45261,6 +45640,7 @@ class ColumnTool {
45261
45640
 
45262
45641
  this.showHideLockIndicator(cell);
45263
45642
  this.builder.element.applyBehavior(cell);
45643
+ this.columnMore.style.display = '';
45264
45644
  e.preventDefault();
45265
45645
  }); // Open Column Settings
45266
45646
 
@@ -45603,6 +45983,22 @@ class ColumnTool {
45603
45983
  this.builder.opts.onChange();
45604
45984
  });
45605
45985
  });
45986
+ const chkCellGrayscale = cellSettings.querySelector('.chk-cell-grayscale');
45987
+ dom$l.addEventListener(chkCellGrayscale, 'click', () => {
45988
+ this.builder.uo.saveForUndo();
45989
+ let cell = util.cellSelected();
45990
+
45991
+ if (chkCellGrayscale.checked) {
45992
+ cell.style.filter = 'grayscale(1)';
45993
+ } else {
45994
+ if (cell.style.filter) {
45995
+ cell.style.filter = cell.style.filter.replace('grayscale(1)', '');
45996
+ }
45997
+ } //Trigger Change event
45998
+
45999
+
46000
+ this.builder.opts.onChange();
46001
+ });
45606
46002
  elms = cellSettings.querySelectorAll('.input-cell-height');
45607
46003
  Array.prototype.forEach.call(elms, elm => {
45608
46004
  dom$l.addEventListener(elm, 'click', () => {
@@ -45954,6 +46350,15 @@ class ColumnTool {
45954
46350
  dom$l.addClass(btn, 'on');
45955
46351
  }
45956
46352
 
46353
+ const chkCellGrayscale = this.cellSettings.querySelector('.chk-cell-grayscale');
46354
+ chkCellGrayscale.checked = false;
46355
+
46356
+ if (cell.style.filter) {
46357
+ if (cell.style.filter.indexOf('grayscale') !== -1) {
46358
+ chkCellGrayscale.checked = true;
46359
+ }
46360
+ }
46361
+
45957
46362
  elms = this.cellSettings.querySelectorAll('.input-cell-height');
45958
46363
  Array.prototype.forEach.call(elms, elm => {
45959
46364
  dom$l.removeClass(elm, 'on');
@@ -52507,18 +52912,18 @@ class Rte {
52507
52912
  <button title="18px" data-value="18">18</button>
52508
52913
  <button title="21px" data-value="21">21</button>
52509
52914
  <button title="24px" data-value="24">24</button>
52510
- <button title="28px" data-value="28">28</button>
52915
+ <!--<button title="28px" data-value="28">28</button>-->
52511
52916
  <button title="32px" data-value="32">32</button>
52512
- <!--<button title="35px" data-value="35">35</button>-->
52513
- <button title="38px" data-value="38">38</button>
52514
- <!--<button title="42px" data-value="42">42</button>-->
52917
+ <!--<button title="38px" data-value="38">38</button>-->
52515
52918
  <button title="48px" data-value="48">48</button>
52516
- <!--<button title="54px" data-value="54">54</button>-->
52517
- <button title="60px" data-value="60">60</button>
52518
- <!--<button title="68px" data-value="68">68</button>-->
52919
+ <!--<button title="60px" data-value="60">60</button>-->
52519
52920
  <button title="76px" data-value="76">76</button>
52520
- <!--<button title="84px" data-value="84">84</button>-->
52521
52921
  <button title="96px" data-value="96">96</button>
52922
+
52923
+ <button title="120px" data-value="120">120</button>
52924
+ <button title="160px" data-value="160">160</button>
52925
+ <button title="200px" data-value="200">200</button>
52926
+
52522
52927
  <button title="${util.out('Decrease')}" data-value="-" style="font-size:13px">-</button>
52523
52928
  <button title="${util.out('Increase')}" data-value="+" style="font-size:13px">+</button>
52524
52929
  <button title="${util.out('Clear')}" data-value=""><svg class="is-icon-flex" style="width:18px;height:18px;margin-top: 2px;"><use xlink:href="#ion-ios-close-empty"></use></svg></button>
@@ -54156,6 +54561,20 @@ class Rte {
54156
54561
 
54157
54562
  if (this.builder.activeIcon) {
54158
54563
  elm = this.builder.activeIcon;
54564
+ } // Find block element (line-height only works on block element)
54565
+
54566
+
54567
+ let element = elm;
54568
+
54569
+ while (element) {
54570
+ if (element.tagName === 'BODY' || element.tagName === 'HTML') return false;
54571
+
54572
+ if (window.getComputedStyle(element).getPropertyValue('display') !== 'inline') {
54573
+ elm = element;
54574
+ break;
54575
+ }
54576
+
54577
+ element = element.parentNode;
54159
54578
  } // var text = dom.getSelected();
54160
54579
 
54161
54580
 
@@ -54190,22 +54609,24 @@ class Rte {
54190
54609
  let lineheight;
54191
54610
 
54192
54611
  if (num === '+') {
54193
- lineheight = currentLineHeight + 0.2;
54612
+ lineheight = currentLineHeight + 0.1;
54194
54613
  } else if (num === '-') {
54195
- lineheight = currentLineHeight - 0.2;
54614
+ lineheight = currentLineHeight - 0.1;
54615
+ if (lineheight < 0.2) lineheight = 0.2; // prevent very small number
54196
54616
  } else if (num === '') {
54197
54617
  lineheight = '';
54198
54618
  } else {
54199
54619
  lineheight = num;
54200
54620
  }
54201
-
54202
- if (lineheight < 0.2) lineheight = 0.2; // prevent very small number
54203
-
54204
54621
  /** mod by Jack */
54205
54622
  //elm.style.lineHeight = lineheight;
54206
54623
 
54624
+
54207
54625
  dom$5.doFunction(elm, function (theEl) {
54208
- theEl.style.lineHeight = lineheight;
54626
+ // apply to block element only
54627
+ if (window.getComputedStyle(theEl).getPropertyValue('display') !== 'inline') {
54628
+ theEl.style.lineHeight = lineheight;
54629
+ }
54209
54630
  }, true); //save selection
54210
54631
 
54211
54632
  util.saveSelection();
@@ -57316,7 +57737,8 @@ class ContentBuilder {
57316
57737
  ['#ed2828','dark','contentbuilder/themes/dark-red.css'],
57317
57738
  ],
57318
57739
  */
57319
- colHeight: [300, 350, 400, 450, 500, 550, 600, 650, 700]
57740
+ colHeight: [300, 350, 400, 450, 500, 550, 600, 650, 700] // maxColumns: 6,
57741
+
57320
57742
  }; // obj.preserveSelection = true; (can be set programmatically) to prevent click that clears selection on external custom modal.
57321
57743
 
57322
57744
  this.opts = Object.assign(this, defaults, opts);
@@ -57411,7 +57833,7 @@ class ContentBuilder {
57411
57833
  // DEFAULT: Built-in simple css grid
57412
57834
  this.opts.row = 'row clearfix';
57413
57835
  this.opts.cols = ['column sixth', 'column fifth', 'column fourth', 'column third', 'column half', 'column two-third', 'column two-fourth', 'column two-fifth', 'column two-sixth', 'column full'];
57414
- this.opts.colequal = [['column fifth', 'column fifth', 'column fifth', 'column fifth', 'column fifth'], ['column fourth', 'column fourth', 'column fourth', 'column fourth'], ['column third', 'column third', 'column third'], ['column half', 'column half']];
57836
+ this.opts.colequal = [['column sixth', 'column sixth', 'column sixth', 'column sixth', 'column sixth', 'column sixth'], ['column fifth', 'column fifth', 'column fifth', 'column fifth', 'column fifth'], ['column fourth', 'column fourth', 'column fourth', 'column fourth'], ['column third', 'column third', 'column third'], ['column half', 'column half']];
57415
57837
  this.opts.colsizes = [//needed for columns in which the size increment is not constant.
57416
57838
  [//increment for 3 columns
57417
57839
  ['column third', 'column third', 'column third'], ['column half', 'column fourth', 'column fourth']], [//increment for 2 columns
@@ -59128,11 +59550,13 @@ class ContentBuilder {
59128
59550
  } else if (url.toLowerCase().indexOf('youtube.com') !== -1 || url.toLowerCase().indexOf('vimeo.com') !== -1) {
59129
59551
  this.lightbox.openExternalVideo(url, 'dark', color);
59130
59552
  } else {
59131
- // Will go to the link
59132
- const answer = window.confirm(this.util.out('Do you really want to leave?')); // cancel the navigation and stay on the same page
59553
+ if (url.indexOf('#') === 0) ; else {
59554
+ // Will go to the link
59555
+ const answer = window.confirm(this.util.out('Do you really want to leave?')); // cancel the navigation and stay on the same page
59133
59556
 
59134
- if (!answer) {
59135
- return false;
59557
+ if (!answer) {
59558
+ return false;
59559
+ }
59136
59560
  }
59137
59561
 
59138
59562
  window.location.href = url;
@@ -59251,20 +59675,31 @@ class ContentBuilder {
59251
59675
  return false;
59252
59676
  } else {
59253
59677
  // Will go to the link
59254
- const answer = window.confirm(this.util.out('Do you really want to leave?')); // cancel the navigation and stay on the same page
59678
+ if (url.indexOf('#') === 0) ; else {
59679
+ const answer = window.confirm(this.util.out('Do you really want to leave?')); // cancel the navigation and stay on the same page
59255
59680
 
59256
- if (!answer) {
59257
- e.preventDefault();
59258
- return false;
59681
+ if (!answer) {
59682
+ e.preventDefault();
59683
+ return false;
59684
+ }
59259
59685
  }
59260
59686
  }
59261
59687
  } else {
59262
- const answer = window.confirm(this.util.out('Do you really want to leave?')); // cancel the navigation and stay on the same page
59688
+ let url = link.getAttribute('href');
59263
59689
 
59264
- if (!answer) {
59690
+ if (!url) {
59265
59691
  e.preventDefault();
59266
59692
  return false;
59267
59693
  }
59694
+
59695
+ if (url.indexOf('#') === 0) ; else {
59696
+ const answer = window.confirm(this.util.out('Do you really want to leave?')); // cancel the navigation and stay on the same page
59697
+
59698
+ if (!answer) {
59699
+ e.preventDefault();
59700
+ return false;
59701
+ }
59702
+ }
59268
59703
  }
59269
59704
  }
59270
59705
  } // e.preventDefault();
@@ -59288,7 +59723,30 @@ class ContentBuilder {
59288
59723
  } // Show Lock Indicator
59289
59724
 
59290
59725
 
59291
- this.colTool.showHideLockIndicator(col);
59726
+ this.colTool.showHideLockIndicator(col); // Check if last row, make sure the Row Add Tool visible
59727
+
59728
+ const tool = row.querySelector('.is-rowadd-tool');
59729
+ const tollAddButton = tool.querySelector('button');
59730
+ tollAddButton.style.marginTop = '';
59731
+ const children = Array.from(row.parentNode.children).filter(element => {
59732
+ return element.nodeName.toLowerCase() === 'div';
59733
+ });
59734
+
59735
+ if (children && children.length > 0) {
59736
+ let lastChild = children[children.length - 1];
59737
+
59738
+ if (row === lastChild) {
59739
+ const section = row.parentNode.parentNode;
59740
+ const sectionOffset = dom.getElementOffset(section);
59741
+ let h1 = sectionOffset.top + sectionOffset.height;
59742
+ const rowOffset = dom.getElementOffset(row);
59743
+ let h2 = rowOffset.top + rowOffset.height;
59744
+
59745
+ if (h1 - h2 < 19) {
59746
+ tollAddButton.style.marginTop = '-14px';
59747
+ }
59748
+ }
59749
+ }
59292
59750
  }
59293
59751
 
59294
59752
  handleCellKeypress(e) {