Version Description
- New feature: "To email address" control under "Email me a copy of each submission" allows for more granular control of email settings.
- New feature: "Reply email address" control under "Email me a copy of each submission" for easier exchanges with submitting users.
- Improvement: "Added to" column in Forms screen now lists templates and reusable blocks for better integration with WordPress.
- Improvement: Interface of choices in all choice-based fields has been redesigned for better usability and clarity.
- Bugfix: Display of fields with limited choices wasn't updating correctly in builder's preview screen.
Download this release
Release Info
Developer | happyforms |
Plugin | Form builder to get in touch with visitors, grow your email list and collect payments — Happyforms |
Version | 1.15.4 |
Comparing to | |
See all releases |
Code changes from version 1.15.3 to 1.15.4
- core/assets/css/color.css +1 -1
- core/assets/css/customize.css +100 -26
- core/assets/css/layout.css +1 -1
- core/assets/js/parts/part-checkbox.js +24 -523
- core/assets/js/parts/part-field-choice.js +572 -0
- core/assets/js/parts/part-radio.js +19 -543
- core/assets/js/parts/part-select.js +67 -468
- core/classes/class-form-admin.php +28 -0
- core/classes/class-form-controller.php +16 -12
- core/classes/class-form-email.php +33 -5
- core/classes/class-form-messages.php +4 -4
- core/classes/class-form-option-limiter.php +18 -6
- core/classes/class-form-part-library.php +7 -1
- core/classes/class-validation-messages.php +5 -5
- core/templates/customize-controls/email/email-parts-list.php +17 -0
- core/templates/parts/customize-checkbox.php +44 -28
- core/templates/parts/customize-radio.php +45 -32
- core/templates/parts/customize-select.php +44 -32
- core/templates/parts/frontend-select.php +5 -9
- happyforms.php +2 -2
- inc/assets/js/customize.js +40 -11
- inc/classes/class-happyforms.php +1 -1
- inc/classes/class-message-controller.php +30 -4
- inc/templates/customize-controls/email-parts-list-dummy.php +1 -1
- languages/happyforms.pot +130 -136
- readme.txt +25 -22
core/assets/css/color.css
CHANGED
@@ -126,7 +126,7 @@
|
|
126 |
.happyforms-styles .happyforms-part input[type=tel],
|
127 |
.happyforms-styles .happyforms-part input[type=number],
|
128 |
.happyforms-styles .happyforms-part input[type=range],
|
129 |
-
.happyforms-
|
130 |
height: auto !important;
|
131 |
}
|
132 |
|
126 |
.happyforms-styles .happyforms-part input[type=tel],
|
127 |
.happyforms-styles .happyforms-part input[type=number],
|
128 |
.happyforms-styles .happyforms-part input[type=range],
|
129 |
+
.happyforms-styles .happyforms-part select.happyforms-select {
|
130 |
height: auto !important;
|
131 |
}
|
132 |
|
core/assets/css/customize.css
CHANGED
@@ -268,11 +268,13 @@ span.members-only {
|
|
268 |
|
269 |
#customize-control-abandoned_resume_send_alert_email,
|
270 |
#customize-control-owner_attach_pdf,
|
271 |
-
#customize-control-attach_pdf
|
|
|
272 |
display: none;
|
273 |
}
|
274 |
|
275 |
.happyforms-email-view.has-email.allow-abandoned-resume #customize-control-abandoned_resume_send_alert_email,
|
|
|
276 |
#customize-control-receive_email_alerts.checked ~ #customize-control-owner_attach_pdf,
|
277 |
.has-email #customize-control-send_confirmation_email.checked ~ #customize-control-attach_pdf {
|
278 |
display: block;
|
@@ -372,7 +374,8 @@ p.happyforms-step-progress-counter {
|
|
372 |
z-index: 1;
|
373 |
}
|
374 |
|
375 |
-
.happyforms-widget-title h3
|
|
|
376 |
margin: 0;
|
377 |
padding: 15px;
|
378 |
font-size: 1em !important;
|
@@ -479,7 +482,6 @@ a.happyforms-form-part-logic {
|
|
479 |
|
480 |
a.happyforms-form-part-advanced-settings:before,
|
481 |
a.happyforms-form-part-logic:before,
|
482 |
-
a.advanced-option:before,
|
483 |
a.advanced-column:before {
|
484 |
position: relative;
|
485 |
top: 2px;
|
@@ -490,13 +492,13 @@ a.advanced-column:before {
|
|
490 |
|
491 |
a.happyforms-form-part-advanced-settings.opened:before,
|
492 |
a.happyforms-form-part-logic.opened:before,
|
493 |
-
a.advanced-option.opened:before,
|
494 |
a.advanced-column.opened:before {
|
495 |
content: "\f342";
|
496 |
}
|
497 |
|
498 |
a.happyforms-form-remove,
|
499 |
-
a.happyforms-form-part-remove
|
|
|
500 |
color: #d63638;
|
501 |
}
|
502 |
|
@@ -754,12 +756,18 @@ body.adding-happyforms-parts #customize-preview iframe {
|
|
754 |
box-shadow: 0 1px 2px rgba(0, 0, 0, 0.1);
|
755 |
}
|
756 |
|
757 |
-
.happyforms-part-widget-title-action
|
|
|
758 |
float: right;
|
759 |
cursor: pointer;
|
760 |
}
|
761 |
|
762 |
-
.happyforms-
|
|
|
|
|
|
|
|
|
|
|
763 |
display: inline-block;
|
764 |
padding: 10px;
|
765 |
margin: 0;
|
@@ -777,7 +785,8 @@ body.adding-happyforms-parts #customize-preview iframe {
|
|
777 |
line-height: 1;
|
778 |
}
|
779 |
|
780 |
-
.happyforms-widget-action .toggle-indicator:before
|
|
|
781 |
display: block;
|
782 |
content: '\f140';
|
783 |
font: normal 20px/1 dashicons;
|
@@ -792,7 +801,8 @@ body.adding-happyforms-parts #customize-preview iframe {
|
|
792 |
content: '\f142';
|
793 |
}
|
794 |
|
795 |
-
.happyforms-widget-action:focus .toggle-indicator:before
|
|
|
796 |
box-shadow: 0 0 0 1px #5b9dd9, 0 0 2px 1px rgba(30, 140, 190, .8);
|
797 |
}
|
798 |
|
@@ -850,8 +860,6 @@ body.adding-happyforms-parts #customize-preview iframe {
|
|
850 |
|
851 |
.happyforms-part-widget .options,
|
852 |
.happyforms-part-widget .options-import {
|
853 |
-
border: 1px solid #ddd;
|
854 |
-
padding: 10px;
|
855 |
background-color: #fdfdfd;
|
856 |
}
|
857 |
|
@@ -861,7 +869,6 @@ body.adding-happyforms-parts #customize-preview iframe {
|
|
861 |
margin: 0;
|
862 |
}
|
863 |
|
864 |
-
.happyforms-part-widget .option-list li,
|
865 |
.happyforms-part-widget .column-list li,
|
866 |
.happyforms-part-widget .row-list li {
|
867 |
margin: 0;
|
@@ -869,7 +876,6 @@ body.adding-happyforms-parts #customize-preview iframe {
|
|
869 |
border-bottom: 1px solid #ddd;
|
870 |
}
|
871 |
|
872 |
-
.happyforms-part-widget .option-list li:last-child,
|
873 |
.happyforms-part-widget .column-list li:last-child,
|
874 |
.happyforms-part-widget .row-list li:last-child {
|
875 |
border-bottom: none;
|
@@ -897,18 +903,6 @@ body.adding-happyforms-parts #customize-preview iframe {
|
|
897 |
padding: 0px 5px 0 20px;
|
898 |
}
|
899 |
|
900 |
-
.happyforms-part-widget .happyforms-part-item-handle {
|
901 |
-
position: absolute;
|
902 |
-
left: 0;
|
903 |
-
width: 12px;
|
904 |
-
height: 100%;
|
905 |
-
opacity: 0.2;
|
906 |
-
cursor: move;
|
907 |
-
background-image: url(../svg/draggable-handle.svg);
|
908 |
-
background-size: 6px auto;
|
909 |
-
background-repeat: round;
|
910 |
-
}
|
911 |
-
|
912 |
.happyforms-part-widget .happyforms-part-item-advanced {
|
913 |
display: none;
|
914 |
}
|
@@ -946,8 +940,9 @@ textarea.option-import-area {
|
|
946 |
}
|
947 |
|
948 |
.happyforms-part-widget .option-actions {
|
949 |
-
margin-top: 5px;
|
950 |
text-align: right;
|
|
|
|
|
951 |
}
|
952 |
|
953 |
.happyforms-part-widget .options .delete-option,
|
@@ -1812,3 +1807,82 @@ ul.happyforms-parts-list li[data-part-type="rank_order"] {
|
|
1812 |
.happyforms-widget-content textarea[data-option-attribute=description] {
|
1813 |
margin-bottom: 5px;
|
1814 |
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
268 |
|
269 |
#customize-control-abandoned_resume_send_alert_email,
|
270 |
#customize-control-owner_attach_pdf,
|
271 |
+
#customize-control-attach_pdf,
|
272 |
+
#customize-control-alert_email_reply_to {
|
273 |
display: none;
|
274 |
}
|
275 |
|
276 |
.happyforms-email-view.has-email.allow-abandoned-resume #customize-control-abandoned_resume_send_alert_email,
|
277 |
+
.has-email #customize-control-alert_email_reply_to,
|
278 |
#customize-control-receive_email_alerts.checked ~ #customize-control-owner_attach_pdf,
|
279 |
.has-email #customize-control-send_confirmation_email.checked ~ #customize-control-attach_pdf {
|
280 |
display: block;
|
374 |
z-index: 1;
|
375 |
}
|
376 |
|
377 |
+
.happyforms-widget-title h3,
|
378 |
+
.happyforms-part-widget .options .happyforms-choice-item-widget h3 {
|
379 |
margin: 0;
|
380 |
padding: 15px;
|
381 |
font-size: 1em !important;
|
482 |
|
483 |
a.happyforms-form-part-advanced-settings:before,
|
484 |
a.happyforms-form-part-logic:before,
|
|
|
485 |
a.advanced-column:before {
|
486 |
position: relative;
|
487 |
top: 2px;
|
492 |
|
493 |
a.happyforms-form-part-advanced-settings.opened:before,
|
494 |
a.happyforms-form-part-logic.opened:before,
|
|
|
495 |
a.advanced-column.opened:before {
|
496 |
content: "\f342";
|
497 |
}
|
498 |
|
499 |
a.happyforms-form-remove,
|
500 |
+
a.happyforms-form-part-remove,
|
501 |
+
a.happyforms-delete-item {
|
502 |
color: #d63638;
|
503 |
}
|
504 |
|
756 |
box-shadow: 0 1px 2px rgba(0, 0, 0, 0.1);
|
757 |
}
|
758 |
|
759 |
+
.happyforms-part-widget-title-action,
|
760 |
+
.happyforms-part-item-advanced-option {
|
761 |
float: right;
|
762 |
cursor: pointer;
|
763 |
}
|
764 |
|
765 |
+
.customize-control .option-list .happyforms-part-item-advanced input[type=checkbox] {
|
766 |
+
margin-right: 5px;
|
767 |
+
}
|
768 |
+
|
769 |
+
.happyforms-widget-action,
|
770 |
+
.happyforms-advanced-option-action {
|
771 |
display: inline-block;
|
772 |
padding: 10px;
|
773 |
margin: 0;
|
785 |
line-height: 1;
|
786 |
}
|
787 |
|
788 |
+
.happyforms-widget-action .toggle-indicator:before,
|
789 |
+
.happyforms-part-item-advanced-option .toggle-indicator:before {
|
790 |
display: block;
|
791 |
content: '\f140';
|
792 |
font: normal 20px/1 dashicons;
|
801 |
content: '\f142';
|
802 |
}
|
803 |
|
804 |
+
.happyforms-widget-action:focus .toggle-indicator:before,
|
805 |
+
.happyforms-part-item-advanced-option:focus .toggle-indicator:before {
|
806 |
box-shadow: 0 0 0 1px #5b9dd9, 0 0 2px 1px rgba(30, 140, 190, .8);
|
807 |
}
|
808 |
|
860 |
|
861 |
.happyforms-part-widget .options,
|
862 |
.happyforms-part-widget .options-import {
|
|
|
|
|
863 |
background-color: #fdfdfd;
|
864 |
}
|
865 |
|
869 |
margin: 0;
|
870 |
}
|
871 |
|
|
|
872 |
.happyforms-part-widget .column-list li,
|
873 |
.happyforms-part-widget .row-list li {
|
874 |
margin: 0;
|
876 |
border-bottom: 1px solid #ddd;
|
877 |
}
|
878 |
|
|
|
879 |
.happyforms-part-widget .column-list li:last-child,
|
880 |
.happyforms-part-widget .row-list li:last-child {
|
881 |
border-bottom: none;
|
903 |
padding: 0px 5px 0 20px;
|
904 |
}
|
905 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
906 |
.happyforms-part-widget .happyforms-part-item-advanced {
|
907 |
display: none;
|
908 |
}
|
940 |
}
|
941 |
|
942 |
.happyforms-part-widget .option-actions {
|
|
|
943 |
text-align: right;
|
944 |
+
margin-top: 5px;
|
945 |
+
margin-bottom: 14px;
|
946 |
}
|
947 |
|
948 |
.happyforms-part-widget .options .delete-option,
|
1807 |
.happyforms-widget-content textarea[data-option-attribute=description] {
|
1808 |
margin-bottom: 5px;
|
1809 |
}
|
1810 |
+
|
1811 |
+
|
1812 |
+
/* New Choice Interface */
|
1813 |
+
|
1814 |
+
.happyforms-choice-item-widget {
|
1815 |
+
cursor: move;
|
1816 |
+
}
|
1817 |
+
|
1818 |
+
.happyforms-part-widget .options .happyforms-choice-item-widget h3 {
|
1819 |
+
display: block;
|
1820 |
+
}
|
1821 |
+
|
1822 |
+
.happyforms-choice-item-widget .happyforms-part-item-body {
|
1823 |
+
padding: 0 10px;
|
1824 |
+
margin-top: -13px;
|
1825 |
+
padding-top: 12px;
|
1826 |
+
z-index: 9;
|
1827 |
+
position: relative;
|
1828 |
+
}
|
1829 |
+
|
1830 |
+
.happyforms-choice-item-widget.happyforms-widget-choice-expanded .happyforms-part-item-body {
|
1831 |
+
border: 1px solid #ccd0d4;
|
1832 |
+
border-top: 0;
|
1833 |
+
}
|
1834 |
+
|
1835 |
+
.happyforms-widget-expanded .happyforms-choice-item-widget .happyforms-advanced-option-action .toggle-indicator:before {
|
1836 |
+
content: '\f140';
|
1837 |
+
}
|
1838 |
+
|
1839 |
+
.happyforms-widget-expanded .happyforms-choice-item-widget .happyforms-advanced-option-action .toggle-indicator.opened:before {
|
1840 |
+
content: '\f142';
|
1841 |
+
}
|
1842 |
+
|
1843 |
+
.happyforms-choice-item-widget {
|
1844 |
+
background: #fff;
|
1845 |
+
color: #23282d;
|
1846 |
+
line-height: 1.4em;
|
1847 |
+
-webkit-transition: opacity 0.5s;
|
1848 |
+
transition: opacity 0.5s;
|
1849 |
+
z-index: 1;
|
1850 |
+
}
|
1851 |
+
|
1852 |
+
.happyforms-choice-item-widget .happyforms-part-item-handle {
|
1853 |
+
border: 1px solid #ccd0d4;
|
1854 |
+
overflow: hidden;
|
1855 |
+
position: relative;
|
1856 |
+
z-index: 99;
|
1857 |
+
}
|
1858 |
+
|
1859 |
+
.happyforms-choice-item-widget .happyforms-part-item-handle:hover {
|
1860 |
+
border-color: #999;
|
1861 |
+
-webkit-box-shadow: 0 1px 2px rgb(0 0 0 / 10%);
|
1862 |
+
box-shadow: 0 1px 2px rgb(0 0 0 / 10%);
|
1863 |
+
}
|
1864 |
+
|
1865 |
+
.happyforms-part-widget .happyforms-choice-item-widget .option-actions {
|
1866 |
+
text-align: left;
|
1867 |
+
}
|
1868 |
+
|
1869 |
+
.happyforms-part-widget .links .button {
|
1870 |
+
float: right;
|
1871 |
+
margin: 0;
|
1872 |
+
}
|
1873 |
+
|
1874 |
+
.happyforms-part-widget .links .button {
|
1875 |
+
float: right;
|
1876 |
+
margin-right: 5px;
|
1877 |
+
}
|
1878 |
+
|
1879 |
+
.happyforms-part-widget .links {
|
1880 |
+
text-align: right;
|
1881 |
+
display: block;
|
1882 |
+
clear: both;
|
1883 |
+
padding: 0px 0 30px 0px;
|
1884 |
+
}
|
1885 |
+
|
1886 |
+
.happyforms-item-choice-widget-title .choice-in-widget-title {
|
1887 |
+
color: #646970;
|
1888 |
+
}
|
core/assets/css/layout.css
CHANGED
@@ -444,7 +444,7 @@ h3.happyforms-form__title {
|
|
444 |
|
445 |
.happyforms-part-option__description {
|
446 |
display: block;
|
447 |
-
width:
|
448 |
max-width: 400px;
|
449 |
margin-top: 0px;
|
450 |
margin-left: 31px;
|
444 |
|
445 |
.happyforms-part-option__description {
|
446 |
display: block;
|
447 |
+
width: auto;
|
448 |
max-width: 400px;
|
449 |
margin-top: 0px;
|
450 |
margin-left: 31px;
|
core/assets/js/parts/part-checkbox.js
CHANGED
@@ -36,174 +36,9 @@
|
|
36 |
model: OptionModel,
|
37 |
} );
|
38 |
|
39 |
-
happyForms.classes.views.
|
40 |
-
template: '#customize-happyforms-checkbox-item-heading-template',
|
41 |
-
|
42 |
-
events: {
|
43 |
-
'click .delete-heading': 'onDeleteHeadingClick',
|
44 |
-
'keyup [name=label]': 'onHeadingLabelChange',
|
45 |
-
'change [name=label]': 'onHeadingLabelChange',
|
46 |
-
},
|
47 |
-
|
48 |
-
initialize: function( options ) {
|
49 |
-
this.template = _.template( $( this.template ).text() );
|
50 |
-
this.part = options.part;
|
51 |
-
|
52 |
-
this.listenTo( this, 'ready', this.onReady );
|
53 |
-
},
|
54 |
-
|
55 |
-
render: function() {
|
56 |
-
this.setElement( this.template( this.model.toJSON() ) );
|
57 |
-
|
58 |
-
return this;
|
59 |
-
},
|
60 |
-
|
61 |
-
onReady: function() {
|
62 |
-
$( '[name=label]', this.$el ).trigger( 'focus' );
|
63 |
-
},
|
64 |
-
|
65 |
-
onDeleteHeadingClick: function( e ) {
|
66 |
-
e.preventDefault();
|
67 |
-
|
68 |
-
this.model.collection.remove( this.model );
|
69 |
-
},
|
70 |
-
|
71 |
-
onHeadingLabelChange: function( e ) {
|
72 |
-
this.model.set( 'label', $( e.target ).val() );
|
73 |
-
this.part.trigger( 'change' );
|
74 |
-
|
75 |
-
var data = {
|
76 |
-
id: this.part.get( 'id' ),
|
77 |
-
callback: 'onCheckboxHeadingLabelChangeCallback',
|
78 |
-
options: {
|
79 |
-
itemID: this.model.get( 'id' ),
|
80 |
-
}
|
81 |
-
};
|
82 |
-
|
83 |
-
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
84 |
-
},
|
85 |
-
} );
|
86 |
-
|
87 |
-
happyForms.classes.views.parts.checkboxOption = Backbone.View.extend( {
|
88 |
template: '#customize-happyforms-checkbox-item-template',
|
89 |
|
90 |
-
events: {
|
91 |
-
'click .advanced-option': 'onAdvancedOptionClick',
|
92 |
-
'click .delete-option': 'onDeleteOptionClick',
|
93 |
-
'keyup [name=label]': 'onItemLabelChange',
|
94 |
-
'change [name=label]': 'onItemLabelChange',
|
95 |
-
'keyup [name=description]': 'onItemDescriptionChange',
|
96 |
-
'change [name=is_default]': 'onItemDefaultChange',
|
97 |
-
|
98 |
-
'keyup [name=limit_submissions_amount]': 'onItemLimitSubmissionsAmountChange',
|
99 |
-
'change [name=limit_submissions_amount]': 'onItemLimitSubmissionsAmountChange',
|
100 |
-
},
|
101 |
-
|
102 |
-
initialize: function( options ) {
|
103 |
-
this.template = _.template( $( this.template ).text() );
|
104 |
-
this.part = options.part;
|
105 |
-
|
106 |
-
this.listenTo( this.model, 'change:limit_submissions_amount', this.onChangeMaxSubmissionsAmount );
|
107 |
-
this.listenTo( this, 'ready', this.onReady );
|
108 |
-
},
|
109 |
-
|
110 |
-
onChangeMaxSubmissionsAmount: function( e ) {
|
111 |
-
var model = this.part;
|
112 |
-
|
113 |
-
if ( '' == this.model.get('limit_submissions_amount') ) {
|
114 |
-
return;
|
115 |
-
}
|
116 |
-
|
117 |
-
this.part.fetchHtml( function( response ) {
|
118 |
-
var data = {
|
119 |
-
id: model.get( 'id' ),
|
120 |
-
html: response,
|
121 |
-
};
|
122 |
-
|
123 |
-
happyForms.previewSend( 'happyforms-form-part-refresh', data );
|
124 |
-
|
125 |
-
} );
|
126 |
-
},
|
127 |
-
|
128 |
-
onItemLimitSubmissionsAmountChange: function( e ) {
|
129 |
-
var value = $( '[name="limit_submissions_amount"]', this.$el ).val();
|
130 |
-
|
131 |
-
if ( 0 > value ) {
|
132 |
-
$( '[name="limit_submissions_amount"]', this.$el ).val( '' );
|
133 |
-
return;
|
134 |
-
}
|
135 |
-
|
136 |
-
this.model.set( 'limit_submissions_amount', $( e.target ).val() );
|
137 |
-
this.part.trigger( 'change' );
|
138 |
-
},
|
139 |
-
|
140 |
-
render: function() {
|
141 |
-
this.setElement( this.template( this.model.toJSON() ) );
|
142 |
-
|
143 |
-
return this;
|
144 |
-
},
|
145 |
-
|
146 |
-
onReady: function() {
|
147 |
-
$( '[name=label]', this.$el ).trigger( 'focus' );
|
148 |
-
},
|
149 |
-
|
150 |
-
onAdvancedOptionClick: function( e ) {
|
151 |
-
e.preventDefault();
|
152 |
-
|
153 |
-
$( '.happyforms-part-item-advanced', this.$el ).slideToggle( 300, function() {
|
154 |
-
$( e.target ).toggleClass( 'opened' );
|
155 |
-
} );
|
156 |
-
},
|
157 |
-
|
158 |
-
onDeleteOptionClick: function( e ) {
|
159 |
-
e.preventDefault();
|
160 |
-
|
161 |
-
this.model.collection.remove( this.model );
|
162 |
-
},
|
163 |
-
|
164 |
-
onItemLabelChange: function( e ) {
|
165 |
-
this.model.set( 'label', $( e.target ).val() );
|
166 |
-
this.part.trigger( 'change' );
|
167 |
-
|
168 |
-
var data = {
|
169 |
-
id: this.part.get( 'id' ),
|
170 |
-
callback: 'onCheckboxItemLabelChangeCallback',
|
171 |
-
options: {
|
172 |
-
itemID: this.model.get( 'id' ),
|
173 |
-
}
|
174 |
-
};
|
175 |
-
|
176 |
-
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
177 |
-
},
|
178 |
-
|
179 |
-
onItemDescriptionChange: function( e ) {
|
180 |
-
this.model.set( 'description', $( e.target ).val() );
|
181 |
-
this.part.trigger( 'change' );
|
182 |
-
|
183 |
-
if ( '' == this.model.previousAttributes().description || '' == this.model.get( 'description' ) ) {
|
184 |
-
var self = this;
|
185 |
-
this.part.fetchHtml( function( response ) {
|
186 |
-
var data = {
|
187 |
-
id: self.part.get( 'id' ),
|
188 |
-
html: response,
|
189 |
-
};
|
190 |
-
|
191 |
-
happyForms.previewSend( 'happyforms-form-part-refresh', data );
|
192 |
-
} );
|
193 |
-
} else {
|
194 |
-
|
195 |
-
var data = {
|
196 |
-
id: this.part.get( 'id' ),
|
197 |
-
callback: 'onCheckboxItemDescriptionChangeCallback',
|
198 |
-
options: {
|
199 |
-
itemID: this.model.get( 'id' ),
|
200 |
-
}
|
201 |
-
};
|
202 |
-
|
203 |
-
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
204 |
-
}
|
205 |
-
},
|
206 |
-
|
207 |
onItemDefaultChange: function( e ) {
|
208 |
var $target = $( e.target );
|
209 |
|
@@ -217,7 +52,7 @@
|
|
217 |
|
218 |
var data = {
|
219 |
id: this.part.get( 'id' ),
|
220 |
-
callback: '
|
221 |
options: {
|
222 |
itemID: this.model.get( 'id' ),
|
223 |
}
|
@@ -227,303 +62,41 @@
|
|
227 |
},
|
228 |
} );
|
229 |
|
230 |
-
|
231 |
-
template: '#customize-happyforms-checkbox-template',
|
|
|
232 |
|
233 |
-
|
234 |
-
|
235 |
-
'click .add-heading': 'onAddHeadingClick',
|
236 |
-
'click .import-option': 'onImportOptionClick',
|
237 |
-
'click .import-options': 'onImportOptionsClick',
|
238 |
-
'click .add-options': 'onAddOptionsClick',
|
239 |
-
'change [data-bind=display_type]': 'onDisplayTypeChange',
|
240 |
|
|
|
241 |
'change [data-bind=limit_choices_min]': 'refreshMinMaxChoices',
|
242 |
'change [data-bind=limit_choices_max]': 'refreshMinMaxChoices',
|
243 |
} ),
|
244 |
|
245 |
initialize: function() {
|
246 |
-
happyForms.classes.views.
|
247 |
-
|
248 |
-
this.optionViews = new Backbone.Collection();
|
249 |
|
250 |
-
this.listenTo( this.model.get( 'options' ), 'add', this.onOptionModelAdd );
|
251 |
-
this.listenTo( this.model.get( 'options' ), 'change', this.onOptionModelChange );
|
252 |
-
this.listenTo( this.model.get( 'options' ), 'remove', this.onOptionModelRemove );
|
253 |
-
this.listenTo( this.model.get( 'options' ), 'reset', this.onOptionModelsSorted );
|
254 |
-
this.listenTo( this.optionViews, 'add', this.onOptionViewAdd );
|
255 |
-
this.listenTo( this.optionViews, 'remove', this.onOptionViewRemove );
|
256 |
-
this.listenTo( this.optionViews, 'reset', this.onOptionViewsSorted );
|
257 |
-
this.listenTo( this, 'sort-stop', this.onOptionSortStop );
|
258 |
-
this.listenTo( this, 'ready', this.onReady );
|
259 |
-
|
260 |
-
this.listenTo( this.model, 'change:other_option', this.onAddOtherOption );
|
261 |
-
this.listenTo( this.model, 'change:other_option_label', this.onOtherOptionLabelChange );
|
262 |
-
this.listenTo( this.model, 'change:other_option_placeholder', this.onOtherOptionPlaceholderChange );
|
263 |
this.listenTo( this.model, 'change:limit_choices', this.onLimitChoices );
|
264 |
this.listenTo( this.model.get( 'options' ), 'add remove', this.refreshMinMaxChoices );
|
265 |
},
|
266 |
|
267 |
-
|
268 |
-
|
269 |
-
|
270 |
-
|
271 |
-
|
272 |
-
$( '.option-list', this.$el ).sortable( {
|
273 |
-
handle: '.happyforms-part-item-handle',
|
274 |
-
helper: 'clone',
|
275 |
|
276 |
-
|
277 |
-
this.trigger( 'sort-stop', e, ui );
|
278 |
-
}.bind( this ),
|
279 |
-
} );
|
280 |
},
|
281 |
|
282 |
-
|
283 |
-
|
284 |
-
|
285 |
-
|
286 |
-
|
287 |
|
288 |
-
|
289 |
-
this.model.fetchHtml( function( response ) {
|
290 |
-
var data = {
|
291 |
-
id: model.get( 'id' ),
|
292 |
-
html: response,
|
293 |
-
};
|
294 |
-
|
295 |
-
happyForms.previewSend( 'happyforms-form-part-refresh', data );
|
296 |
-
} );
|
297 |
-
}
|
298 |
-
},
|
299 |
-
|
300 |
-
onOptionModelChange: function( optionModel ) {
|
301 |
-
this.model.trigger( 'change' );
|
302 |
-
},
|
303 |
-
|
304 |
-
onOptionModelRemove: function( optionModel ) {
|
305 |
-
this.model.trigger( 'change' );
|
306 |
-
|
307 |
-
var optionViewModel = this.optionViews.find( function( viewModel ) {
|
308 |
-
return viewModel.get( 'view' ).model.id === optionModel.id;
|
309 |
-
}, this );
|
310 |
-
|
311 |
-
this.optionViews.remove( optionViewModel );
|
312 |
-
|
313 |
-
if ( this.model.get( 'options' ).length == 0 ) {
|
314 |
-
$( '.options ul', this.$el ).html( '' );
|
315 |
-
}
|
316 |
-
|
317 |
-
var data = {
|
318 |
-
id: this.model.get( 'id' ),
|
319 |
-
callback: 'onCheckboxItemDeleteCallback',
|
320 |
-
options: {
|
321 |
-
itemID: optionModel.id,
|
322 |
-
}
|
323 |
-
};
|
324 |
-
|
325 |
-
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
326 |
-
},
|
327 |
-
|
328 |
-
onOptionModelsSorted: function() {
|
329 |
-
this.optionViews.reset( _.map( this.model.get( 'options' ).pluck( 'id' ), function( id ) {
|
330 |
-
return this.optionViews.get( id );
|
331 |
-
}, this ) );
|
332 |
-
|
333 |
-
this.model.trigger( 'change' );
|
334 |
-
|
335 |
-
var model = this.model;
|
336 |
-
|
337 |
-
this.model.fetchHtml( function( response ) {
|
338 |
-
var data = {
|
339 |
-
id: model.get( 'id' ),
|
340 |
-
html: response,
|
341 |
-
};
|
342 |
-
|
343 |
-
happyForms.previewSend( 'happyforms-form-part-refresh', data );
|
344 |
-
} );
|
345 |
-
},
|
346 |
-
|
347 |
-
onOptionsChange: function() {
|
348 |
-
this.model.trigger( 'change' );
|
349 |
-
},
|
350 |
-
|
351 |
-
addOptionView: function( optionModel, options ) {
|
352 |
-
var optionView = null;
|
353 |
-
var optionAttributes = optionModel.attributes;
|
354 |
-
var isHeading = 'undefined' !== typeof optionAttributes.is_heading && 1 == optionAttributes.is_heading;
|
355 |
-
|
356 |
-
if ( isHeading ) {
|
357 |
-
optionView = new happyForms.classes.views.parts.checkboxOptionHeading( _.extend( {
|
358 |
-
model: optionModel,
|
359 |
-
part: this.model,
|
360 |
-
}, options ) );
|
361 |
-
} else {
|
362 |
-
optionView = new happyForms.classes.views.parts.checkboxOption( _.extend( {
|
363 |
-
model: optionModel,
|
364 |
-
part: this.model,
|
365 |
-
}, options ) );
|
366 |
-
}
|
367 |
-
|
368 |
-
var optionViewModel = new Backbone.Model( {
|
369 |
-
id: optionModel.id,
|
370 |
-
view: optionView,
|
371 |
-
} );
|
372 |
-
|
373 |
-
this.optionViews.add( optionViewModel, options );
|
374 |
-
},
|
375 |
-
|
376 |
-
onOptionViewAdd: function( viewModel, collection, options ) {
|
377 |
-
var optionView = viewModel.get( 'view' );
|
378 |
-
$( '.options ul', this.$el ).append( optionView.render().$el );
|
379 |
-
optionView.trigger( 'ready' );
|
380 |
-
},
|
381 |
-
|
382 |
-
onOptionViewRemove: function( viewModel ) {
|
383 |
-
var optionView = viewModel.get( 'view' );
|
384 |
-
optionView.remove();
|
385 |
-
},
|
386 |
-
|
387 |
-
onOptionSortStop: function( e, ui ) {
|
388 |
-
var $sortable = $( '.option-list', this.$el );
|
389 |
-
var ids = $sortable.sortable( 'toArray', { attribute: 'data-option-id' } );
|
390 |
-
|
391 |
-
this.model.get( 'options' ).reset( _.map( ids, function( id ) {
|
392 |
-
return this.model.get( 'options' ).get( id );
|
393 |
-
}, this ) );
|
394 |
-
},
|
395 |
-
|
396 |
-
onOptionViewsSorted: function( optionViews ) {
|
397 |
-
var $stage = $( '.option-list', this.$el );
|
398 |
-
|
399 |
-
optionViews.forEach( function( optionViewModel ) {
|
400 |
-
var optionView = optionViewModel.get( 'view' );
|
401 |
-
var $optionViewEl = optionView.$el;
|
402 |
-
$optionViewEl.detach();
|
403 |
-
$stage.append( $optionViewEl );
|
404 |
-
optionView.trigger( 'refresh' );
|
405 |
-
}, this );
|
406 |
-
},
|
407 |
-
|
408 |
-
getOptionModelID: function() {
|
409 |
-
var prefix = this.model.get( 'id' ) + '_option_';
|
410 |
-
var collection = this.model.get( 'options' );
|
411 |
-
var timestamp = new Date().getTime();
|
412 |
-
var id = prefix + timestamp;
|
413 |
-
|
414 |
-
return id;
|
415 |
-
},
|
416 |
-
|
417 |
-
onAddOptionClick: function( e ) {
|
418 |
-
e.preventDefault();
|
419 |
-
|
420 |
-
var itemID = this.getOptionModelID();
|
421 |
-
var itemModel = new OptionModel( { id: itemID } );
|
422 |
-
this.model.get( 'options' ).add( itemModel );
|
423 |
-
},
|
424 |
-
|
425 |
-
onAddHeadingClick: function( e ) {
|
426 |
-
e.preventDefault();
|
427 |
-
|
428 |
-
var itemID = this.getOptionModelID();
|
429 |
-
var itemModel = new OptionModel( { id: itemID, is_heading: 1 } );
|
430 |
-
this.model.get( 'options' ).add( itemModel );
|
431 |
-
},
|
432 |
-
|
433 |
-
onDisplayTypeChange: function(e) {
|
434 |
-
var $input = $( e.target );
|
435 |
-
var attribute = $input.data( 'bind' );
|
436 |
-
var value = $input.val();
|
437 |
-
|
438 |
-
this.model.set( attribute, $input.val() );
|
439 |
-
|
440 |
-
var data = {
|
441 |
-
id: this.model.get( 'id' ),
|
442 |
-
callback: 'onCheckboxDisplayTypeChangeCallback',
|
443 |
-
};
|
444 |
-
|
445 |
-
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
446 |
-
},
|
447 |
-
|
448 |
-
onImportOptionsClick: function( e ) {
|
449 |
-
e.preventDefault();
|
450 |
-
|
451 |
-
$( '.options', this.$el ).hide();
|
452 |
-
$( '.options-import', this.$el ).show();
|
453 |
-
$( '.links.mode-manual', this.$el ).hide();
|
454 |
-
$( '.links.mode-import', this.$el ).show();
|
455 |
-
$( '.option-import-area', this.$el ).trigger( 'focus' );
|
456 |
-
},
|
457 |
-
|
458 |
-
onAddOptionsClick: function( e ) {
|
459 |
-
e.preventDefault();
|
460 |
-
|
461 |
-
$( '.options', this.$el ).show();
|
462 |
-
$( '.options-import', this.$el ).hide();
|
463 |
-
$( '.links.mode-import', this.$el ).hide();
|
464 |
-
$( '.links.mode-manual', this.$el ).show();
|
465 |
-
$( '.option-import-area', this.$el ).val( '' );
|
466 |
-
},
|
467 |
-
|
468 |
-
onImportOptionClick: function( e ) {
|
469 |
-
e.preventDefault();
|
470 |
-
|
471 |
-
var $textarea = $( '.option-import-area', this.$el );
|
472 |
-
var list = $textarea.val();
|
473 |
-
var self = this;
|
474 |
-
|
475 |
-
var models = list
|
476 |
-
.split( /[\r\n]+/g )
|
477 |
-
.map( function( s ) {
|
478 |
-
return s.trim();
|
479 |
-
} )
|
480 |
-
.filter( function( s ) {
|
481 |
-
return s;
|
482 |
-
} )
|
483 |
-
.forEach( function( label, i, list ) {
|
484 |
-
_.delay( function() {
|
485 |
-
var itemID = self.getOptionModelID();
|
486 |
-
var item = new OptionModel( {
|
487 |
-
id: itemID,
|
488 |
-
label: label
|
489 |
-
} );
|
490 |
-
|
491 |
-
self.model.get( 'options' ).add( item, { refresh: ( list.length - 1 === i ) } );
|
492 |
-
}, i );
|
493 |
-
} );
|
494 |
-
|
495 |
-
$textarea.val( '' );
|
496 |
-
$( '.add-options', this.$el ).trigger( 'click' );
|
497 |
-
},
|
498 |
-
|
499 |
-
onAddOtherOption: function( model, value ) {
|
500 |
-
var $otherOptionOptions = $( '.happyforms-nested-settings[data-trigger="other_option"]', this.$el );
|
501 |
-
|
502 |
-
if ( 1 == value ) {
|
503 |
-
$otherOptionOptions.show();
|
504 |
-
} else {
|
505 |
-
$otherOptionOptions.hide();
|
506 |
-
}
|
507 |
-
|
508 |
-
this.refreshPart();
|
509 |
-
},
|
510 |
-
|
511 |
-
onOtherOptionLabelChange: function( model, value ) {
|
512 |
-
var data = {
|
513 |
-
id: this.model.get( 'id' ),
|
514 |
-
callback: 'onCheckboxOtherOptionLabelChangeCallback'
|
515 |
-
};
|
516 |
-
|
517 |
-
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
518 |
-
},
|
519 |
-
|
520 |
-
onOtherOptionPlaceholderChange: function( model, value ) {
|
521 |
-
var data = {
|
522 |
-
id: this.model.get( 'id' ),
|
523 |
-
callback: 'onCheckboxOtherOptionPlaceholderChangeCallback'
|
524 |
-
};
|
525 |
-
|
526 |
-
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
527 |
},
|
528 |
|
529 |
onLimitChoices: function( model, value ) {
|
@@ -539,7 +112,9 @@
|
|
539 |
refreshMinMaxChoices: function() {
|
540 |
var minChoices = this.model.get( 'limit_choices_min' );
|
541 |
var maxChoices = this.model.get( 'limit_choices_max' );
|
542 |
-
var numChoices = this.model.get( 'options' ).
|
|
|
|
|
543 |
|
544 |
var clamp = function( v, min, max ) {
|
545 |
return Math.min( Math.max( v, min ), max );
|
@@ -560,78 +135,4 @@
|
|
560 |
},
|
561 |
} );
|
562 |
|
563 |
-
happyForms.previewer = _.extend( happyForms.previewer, {
|
564 |
-
onCheckboxDisplayTypeChangeCallback: function( id, html, options ) {
|
565 |
-
var part = this.getPartModel( id );
|
566 |
-
var $part = this.getPartElement( html );
|
567 |
-
|
568 |
-
if ( 'block' === part.get( 'display_type' ) ) {
|
569 |
-
$part.addClass( 'display-type--block' );
|
570 |
-
} else {
|
571 |
-
$part.removeClass( 'display-type--block' );
|
572 |
-
}
|
573 |
-
},
|
574 |
-
|
575 |
-
onCheckboxItemLabelChangeCallback: function( id, html, options ) {
|
576 |
-
var part = this.getPartModel( id );
|
577 |
-
var $part = this.getPartElement( html );
|
578 |
-
var option = part.get( 'options' ).get( options.itemID );
|
579 |
-
var $option = $( '#' + options.itemID, $part );
|
580 |
-
|
581 |
-
this.$( 'span.label', $option ).text( option.get( 'label' ) );
|
582 |
-
},
|
583 |
-
|
584 |
-
onCheckboxItemDefaultChangeCallback: function( id, html, options ) {
|
585 |
-
var part = this.getPartModel( id );
|
586 |
-
var $part = this.getPartElement( html );
|
587 |
-
var option = part.get( 'options' ).get( options.itemID );
|
588 |
-
var $option = $( '#' + options.itemID, $part );
|
589 |
-
|
590 |
-
this.$( 'input', $option ).prop( 'checked', option.get( 'is_default' ) );
|
591 |
-
},
|
592 |
-
|
593 |
-
onCheckboxItemDescriptionChangeCallback: function( id, html, options ) {
|
594 |
-
var part = this.getPartModel( id );
|
595 |
-
var $part = this.getPartElement( html );
|
596 |
-
var option = part.get( 'options' ).get( options.itemID );
|
597 |
-
var $option = $( '#' + options.itemID, $part );
|
598 |
-
|
599 |
-
this.$( '.happyforms-part-option__description', $option ).text( option.get( 'description' ) );
|
600 |
-
},
|
601 |
-
|
602 |
-
onCheckboxItemDeleteCallback: function( id, html, options ) {
|
603 |
-
var part = this.getPartModel( id );
|
604 |
-
var $part = this.getPartElement( html );
|
605 |
-
var $option = $( '#' + options.itemID, $part );
|
606 |
-
|
607 |
-
$option.remove();
|
608 |
-
},
|
609 |
-
|
610 |
-
onCheckboxOtherOptionLabelChangeCallback: function( id, html, options ) {
|
611 |
-
var part = this.getPartModel( id );
|
612 |
-
var $part = this.getPartElement( html );
|
613 |
-
var $otherOptionLabel = $( '.happyforms-part-option--other .label', $part );
|
614 |
-
|
615 |
-
$otherOptionLabel.text( part.get( 'other_option_label' ) );
|
616 |
-
},
|
617 |
-
|
618 |
-
onCheckboxOtherOptionPlaceholderChangeCallback: function( id, html, options ) {
|
619 |
-
var part = this.getPartModel( id );
|
620 |
-
var $part = this.getPartElement( html );
|
621 |
-
var $otherOptionInput = $( '.happyforms-part-option--other input[type=text]', $part );
|
622 |
-
|
623 |
-
$otherOptionInput.attr( 'placeholder', part.get( 'other_option_placeholder' ) );
|
624 |
-
},
|
625 |
-
|
626 |
-
onCheckboxHeadingLabelChangeCallback: function( id, html, options ) {
|
627 |
-
var part = this.getPartModel( id );
|
628 |
-
var $part = this.getPartElement( html );
|
629 |
-
var option = part.get( 'options' ).get( options.itemID );
|
630 |
-
var $option = $( '#' + options.itemID, $part );
|
631 |
-
|
632 |
-
this.$( 'label.heading-label', $option ).text( option.get( 'label' ) );
|
633 |
-
},
|
634 |
-
|
635 |
-
} );
|
636 |
-
|
637 |
} ) ( jQuery, _, Backbone, wp.customize, _happyFormsSettings );
|
36 |
model: OptionModel,
|
37 |
} );
|
38 |
|
39 |
+
var OptionItemView = happyForms.classes.views.OptionItem.extend( {
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
40 |
template: '#customize-happyforms-checkbox-item-template',
|
41 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
42 |
onItemDefaultChange: function( e ) {
|
43 |
var $target = $( e.target );
|
44 |
|
52 |
|
53 |
var data = {
|
54 |
id: this.part.get( 'id' ),
|
55 |
+
callback: 'onOptionDefaultChangeCallback',
|
56 |
options: {
|
57 |
itemID: this.model.get( 'id' ),
|
58 |
}
|
62 |
},
|
63 |
} );
|
64 |
|
65 |
+
var OptionHeadingView = happyForms.classes.views.OptionHeading.extend( {
|
66 |
+
template: '#customize-happyforms-checkbox-item-heading-template',
|
67 |
+
} );
|
68 |
|
69 |
+
happyForms.classes.views.parts.checkbox = happyForms.classes.views.ChoiceField.extend( {
|
70 |
+
template: '#customize-happyforms-checkbox-template',
|
|
|
|
|
|
|
|
|
|
|
71 |
|
72 |
+
events: _.extend( {}, happyForms.classes.views.ChoiceField.prototype.events, {
|
73 |
'change [data-bind=limit_choices_min]': 'refreshMinMaxChoices',
|
74 |
'change [data-bind=limit_choices_max]': 'refreshMinMaxChoices',
|
75 |
} ),
|
76 |
|
77 |
initialize: function() {
|
78 |
+
happyForms.classes.views.ChoiceField.prototype.initialize.apply( this, arguments );
|
|
|
|
|
79 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
80 |
this.listenTo( this.model, 'change:limit_choices', this.onLimitChoices );
|
81 |
this.listenTo( this.model.get( 'options' ), 'add remove', this.refreshMinMaxChoices );
|
82 |
},
|
83 |
|
84 |
+
getOptionItemView: function( optionModel, options ) {
|
85 |
+
var view = new OptionItemView( _.extend( {
|
86 |
+
model: optionModel,
|
87 |
+
part: this.model,
|
88 |
+
}, options ) );
|
|
|
|
|
|
|
89 |
|
90 |
+
return view;
|
|
|
|
|
|
|
91 |
},
|
92 |
|
93 |
+
getOptionHeadingView: function( optionModel, options ) {
|
94 |
+
var view = new OptionHeadingView( _.extend( {
|
95 |
+
model: optionModel,
|
96 |
+
part: this.model,
|
97 |
+
}, options ) );
|
98 |
|
99 |
+
return view;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
100 |
},
|
101 |
|
102 |
onLimitChoices: function( model, value ) {
|
112 |
refreshMinMaxChoices: function() {
|
113 |
var minChoices = this.model.get( 'limit_choices_min' );
|
114 |
var maxChoices = this.model.get( 'limit_choices_max' );
|
115 |
+
var numChoices = this.model.get( 'options' ).filter( function( option ) {
|
116 |
+
return ! option.get( 'is_heading' );
|
117 |
+
} ).length;
|
118 |
|
119 |
var clamp = function( v, min, max ) {
|
120 |
return Math.min( Math.max( v, min ), max );
|
135 |
},
|
136 |
} );
|
137 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
138 |
} ) ( jQuery, _, Backbone, wp.customize, _happyFormsSettings );
|
core/assets/js/parts/part-field-choice.js
ADDED
@@ -0,0 +1,572 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
( function( $, _, Backbone, api, settings ) {
|
2 |
+
|
3 |
+
happyForms.classes.views.Option = Backbone.View.extend( {
|
4 |
+
events: {
|
5 |
+
'click .happyforms-delete-item': 'onDeleteClick',
|
6 |
+
'click .happyforms-duplicate-item': 'onDuplicateClick',
|
7 |
+
'click .happyforms-advanced-option-action': 'onAdvancedOptionClick',
|
8 |
+
},
|
9 |
+
|
10 |
+
initialize: function( options ) {
|
11 |
+
this.template = _.template( $( this.template ).text() );
|
12 |
+
this.part = options.part;
|
13 |
+
this.listenTo( this, 'ready', this.onReady );
|
14 |
+
this.listenTo( this.model, 'open-widget', this.onAddOpenWidget );
|
15 |
+
},
|
16 |
+
|
17 |
+
onReady: function() {
|
18 |
+
// noop
|
19 |
+
},
|
20 |
+
|
21 |
+
render: function() {
|
22 |
+
this.setElement( this.template( this.model.toJSON() ) );
|
23 |
+
|
24 |
+
return this;
|
25 |
+
},
|
26 |
+
|
27 |
+
onDuplicateClick: function( e ) {
|
28 |
+
e.preventDefault();
|
29 |
+
|
30 |
+
this.$el.trigger( 'item-duplicate', this.model );
|
31 |
+
},
|
32 |
+
|
33 |
+
closeOpenWidgets: function( $currentElement ) {
|
34 |
+
var $openWidgets = $( '.happyforms-choice-item-widget').not( $currentElement );
|
35 |
+
|
36 |
+
$openWidgets.removeClass( 'happyforms-widget-choice-expanded' );
|
37 |
+
$openWidgets.find( '.happyforms-part-item-advanced' ).slideUp( 200, function() {
|
38 |
+
var $toggleIndicator = $openWidgets.find( '.toggle-indicator' );
|
39 |
+
$toggleIndicator.removeClass( 'opened' );
|
40 |
+
} );
|
41 |
+
},
|
42 |
+
|
43 |
+
onAddOpenWidget: function( e ) {
|
44 |
+
var $el = this.$el;
|
45 |
+
|
46 |
+
$el.toggleClass( 'happyforms-widget-choice-expanded' );
|
47 |
+
this.closeOpenWidgets( $el );
|
48 |
+
|
49 |
+
$( '.happyforms-part-item-advanced', this.$el ).slideToggle( 200, function() {
|
50 |
+
if ( $el.hasClass( 'happyforms-widget-choice-expanded' ) ) {
|
51 |
+
$( 'input[data-option-attribute=label]', $el ).trigger( 'focus' );
|
52 |
+
}
|
53 |
+
} );
|
54 |
+
|
55 |
+
$( '.toggle-indicator', $el ).toggleClass( 'opened' );
|
56 |
+
},
|
57 |
+
|
58 |
+
onAdvancedOptionClick: function( e ) {
|
59 |
+
e.preventDefault();
|
60 |
+
|
61 |
+
var $el = this.$el;
|
62 |
+
$el.toggleClass( 'happyforms-widget-choice-expanded' );
|
63 |
+
this.closeOpenWidgets( $el );
|
64 |
+
|
65 |
+
$( '.happyforms-part-item-advanced', this.$el ).slideToggle( 200, function() {
|
66 |
+
if ( $el.hasClass( 'happyforms-widget-choice-expanded' ) ) {
|
67 |
+
$( 'input[data-option-attribute=label]', $el ).trigger( 'focus' );
|
68 |
+
}
|
69 |
+
} );
|
70 |
+
|
71 |
+
$( '.toggle-indicator', $el ).toggleClass( 'opened' );
|
72 |
+
},
|
73 |
+
|
74 |
+
onDeleteClick: function( e ) {
|
75 |
+
e.preventDefault();
|
76 |
+
|
77 |
+
var self = this;
|
78 |
+
|
79 |
+
$( '.happyforms-part-item-advanced', this.$el ).slideUp( 'fast', function() {
|
80 |
+
self.model.collection.remove( self.model );
|
81 |
+
} );
|
82 |
+
|
83 |
+
},
|
84 |
+
} );
|
85 |
+
|
86 |
+
happyForms.classes.views.OptionHeading = happyForms.classes.views.Option.extend( {
|
87 |
+
events: _.extend( {}, happyForms.classes.views.Option.prototype.events, {
|
88 |
+
'keyup [name=label]': 'onLabelChange',
|
89 |
+
'change [name=label]': 'onLabelChange',
|
90 |
+
} ),
|
91 |
+
|
92 |
+
onReady: function() {
|
93 |
+
$( '.in-widget-title[name=label]', this.$el ).trigger( 'focus' );
|
94 |
+
},
|
95 |
+
|
96 |
+
onLabelChange: function( e ) {
|
97 |
+
var label = $( e.target ).val();
|
98 |
+
this.model.set( 'label', label );
|
99 |
+
this.part.trigger( 'change' );
|
100 |
+
$('.happyforms-item-choice-widget-title h3 .choice-in-widget-title span', this.$el ).text( label );
|
101 |
+
|
102 |
+
var data = {
|
103 |
+
id: this.part.get( 'id' ),
|
104 |
+
callback: 'onOptionHeadingLabelChangeCallback',
|
105 |
+
options: {
|
106 |
+
itemID: this.model.get( 'id' ),
|
107 |
+
}
|
108 |
+
};
|
109 |
+
|
110 |
+
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
111 |
+
},
|
112 |
+
} );
|
113 |
+
|
114 |
+
happyForms.classes.views.OptionItem = happyForms.classes.views.Option.extend( {
|
115 |
+
events: _.extend( {}, happyForms.classes.views.Option.prototype.events, {
|
116 |
+
'keyup [name=label]': 'onItemLabelChange',
|
117 |
+
'change [name=label]': 'onItemLabelChange',
|
118 |
+
'keyup [name=description]': 'onItemDescriptionChange',
|
119 |
+
'change [name=is_default]': 'onItemDefaultChange',
|
120 |
+
'keyup [name=limit_submissions_amount]': 'onItemLimitSubmissionsAmountChange',
|
121 |
+
'change [name=limit_submissions_amount]': 'onItemLimitSubmissionsAmountChange',
|
122 |
+
} ),
|
123 |
+
|
124 |
+
initialize: function( options ) {
|
125 |
+
happyForms.classes.views.Option.prototype.initialize.apply( this, arguments );
|
126 |
+
|
127 |
+
this.listenTo( this.model, 'change:limit_submissions_amount', this.onChangeMaxSubmissionsAmount );
|
128 |
+
},
|
129 |
+
|
130 |
+
onReady: function() {
|
131 |
+
$( '.in-widget-title[name=label]', this.$el ).trigger( 'focus' );
|
132 |
+
},
|
133 |
+
|
134 |
+
onItemLabelChange: function( e ) {
|
135 |
+
var label = $( e.target ).val();
|
136 |
+
this.model.set( 'label', label );
|
137 |
+
this.part.trigger( 'change' );
|
138 |
+
$('.happyforms-item-choice-widget-title h3 .choice-in-widget-title span', this.$el ).text( label );
|
139 |
+
|
140 |
+
var data = {
|
141 |
+
id: this.part.get( 'id' ),
|
142 |
+
callback: 'onOptionLabelChangeCallback',
|
143 |
+
options: {
|
144 |
+
itemID: this.model.get( 'id' ),
|
145 |
+
}
|
146 |
+
};
|
147 |
+
|
148 |
+
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
149 |
+
},
|
150 |
+
|
151 |
+
onItemDescriptionChange: function( e ) {
|
152 |
+
this.model.set( 'description', $( e.target ).val() );
|
153 |
+
this.part.trigger( 'change' );
|
154 |
+
|
155 |
+
if ( '' == this.model.previousAttributes().description || '' == this.model.get( 'description' ) ) {
|
156 |
+
var self = this;
|
157 |
+
this.part.fetchHtml( function( response ) {
|
158 |
+
var data = {
|
159 |
+
id: self.part.get( 'id' ),
|
160 |
+
html: response,
|
161 |
+
};
|
162 |
+
|
163 |
+
happyForms.previewSend( 'happyforms-form-part-refresh', data );
|
164 |
+
} );
|
165 |
+
} else {
|
166 |
+
var data = {
|
167 |
+
id: this.part.get( 'id' ),
|
168 |
+
callback: 'onOptionDescriptionChangeCallback',
|
169 |
+
options: {
|
170 |
+
itemID: this.model.get( 'id' ),
|
171 |
+
}
|
172 |
+
};
|
173 |
+
|
174 |
+
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
175 |
+
}
|
176 |
+
},
|
177 |
+
|
178 |
+
onItemDefaultChange: function( e ) {
|
179 |
+
var isChecked = $( e.target ).is( ':checked' );
|
180 |
+
|
181 |
+
this.model.collection.forEach( function( item ) {
|
182 |
+
item.set( 'is_default', 0 );
|
183 |
+
} );
|
184 |
+
|
185 |
+
$( '[name=is_default]', this.$el.siblings() ).prop( 'checked', false );
|
186 |
+
|
187 |
+
if ( isChecked ) {
|
188 |
+
this.model.set( 'is_default', 1 );
|
189 |
+
$( e.target ).prop( 'checked', true );
|
190 |
+
}
|
191 |
+
|
192 |
+
var data = {
|
193 |
+
id: this.part.get( 'id' ),
|
194 |
+
callback: 'onOptionDefaultChangeCallback',
|
195 |
+
options: {
|
196 |
+
itemID: this.model.get( 'id' ),
|
197 |
+
}
|
198 |
+
};
|
199 |
+
|
200 |
+
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
201 |
+
},
|
202 |
+
|
203 |
+
onChangeMaxSubmissionsAmount: function( e ) {
|
204 |
+
var model = this.part;
|
205 |
+
|
206 |
+
this.part.fetchHtml( function( response ) {
|
207 |
+
var data = {
|
208 |
+
id: model.get( 'id' ),
|
209 |
+
html: response,
|
210 |
+
};
|
211 |
+
|
212 |
+
happyForms.previewSend( 'happyforms-form-part-refresh', data );
|
213 |
+
} );
|
214 |
+
},
|
215 |
+
|
216 |
+
onItemLimitSubmissionsAmountChange: function( e ) {
|
217 |
+
var value = $( '[name="limit_submissions_amount"]', this.$el ).val();
|
218 |
+
|
219 |
+
if ( 0 > value ) {
|
220 |
+
$( '[name="limit_submissions_amount"]', this.$el ).val( '' );
|
221 |
+
return;
|
222 |
+
}
|
223 |
+
|
224 |
+
this.model.set( 'limit_submissions_amount', $( e.target ).val() );
|
225 |
+
this.part.trigger( 'change' );
|
226 |
+
},
|
227 |
+
|
228 |
+
} );
|
229 |
+
|
230 |
+
happyForms.classes.views.ChoiceField = happyForms.classes.views.Part.extend( {
|
231 |
+
events: _.extend( {}, happyForms.classes.views.Part.prototype.events, {
|
232 |
+
'click .add-option': 'onAddOptionClick',
|
233 |
+
'click .add-heading': 'onAddHeadingClick',
|
234 |
+
'item-duplicate': 'onOptionDuplicate',
|
235 |
+
'change [data-bind=display_type]': 'onDisplayTypeChange',
|
236 |
+
} ),
|
237 |
+
|
238 |
+
initialize: function() {
|
239 |
+
happyForms.classes.views.Part.prototype.initialize.apply( this, arguments );
|
240 |
+
|
241 |
+
this.optionViews = new Backbone.Collection();
|
242 |
+
this.listenTo( this.model.get( 'options' ), 'add', this.onOptionModelAdd );
|
243 |
+
this.listenTo( this.model.get( 'options' ), 'change', this.onOptionModelChange );
|
244 |
+
this.listenTo( this.model.get( 'options' ), 'remove', this.onOptionModelRemove );
|
245 |
+
this.listenTo( this.model.get( 'options' ), 'reset', this.onOptionModelsSorted );
|
246 |
+
this.listenTo( this.optionViews, 'add', this.onOptionViewAdd );
|
247 |
+
this.listenTo( this.optionViews, 'remove', this.onOptionViewRemove );
|
248 |
+
this.listenTo( this.optionViews, 'reset', this.onOptionViewsSorted );
|
249 |
+
this.listenTo( this, 'sort-stop', this.onOptionSortStop );
|
250 |
+
this.listenTo( this, 'ready', this.onReady );
|
251 |
+
this.listenTo( this.model, 'change:other_option', this.onAddOtherOption );
|
252 |
+
this.listenTo( this.model, 'change:other_option_label', this.onOtherOptionLabelChange );
|
253 |
+
this.listenTo( this.model, 'change:other_option_placeholder', this.onOtherOptionPlaceholderChange );
|
254 |
+
},
|
255 |
+
|
256 |
+
onReady: function() {
|
257 |
+
this.model.get( 'options' ).each( function( optionModel ) {
|
258 |
+
this.addOptionItemView( optionModel );
|
259 |
+
}, this );
|
260 |
+
|
261 |
+
$( '.option-list', this.$el ).sortable( {
|
262 |
+
handle: '.happyforms-part-item-handle',
|
263 |
+
helper: 'clone',
|
264 |
+
|
265 |
+
stop: function ( e, ui ) {
|
266 |
+
this.trigger( 'sort-stop', e, ui );
|
267 |
+
}.bind( this ),
|
268 |
+
} );
|
269 |
+
},
|
270 |
+
|
271 |
+
getOptionModelID: function() {
|
272 |
+
var prefix = this.model.get( 'id' ) + '_option_';
|
273 |
+
var collection = this.model.get( 'options' );
|
274 |
+
var timestamp = new Date().getTime();
|
275 |
+
var id = prefix + timestamp;
|
276 |
+
|
277 |
+
return id;
|
278 |
+
},
|
279 |
+
|
280 |
+
onAddOptionClick: function( e ) {
|
281 |
+
e.preventDefault();
|
282 |
+
|
283 |
+
var itemID = this.getOptionModelID();
|
284 |
+
var modelClass = this.model.get( 'options' ).model;
|
285 |
+
var itemModel = new modelClass( { id: itemID } );
|
286 |
+
this.model.get( 'options' ).add( itemModel );
|
287 |
+
this.model.get( 'options' ).findWhere( { id: itemID } ).trigger( 'open-widget' );
|
288 |
+
},
|
289 |
+
|
290 |
+
onAddHeadingClick: function( e ) {
|
291 |
+
e.preventDefault();
|
292 |
+
|
293 |
+
var itemID = this.getOptionModelID();
|
294 |
+
var modelClass = this.model.get( 'options' ).model;
|
295 |
+
var itemModel = new modelClass( { id: itemID, is_heading: 1 } );
|
296 |
+
this.model.get( 'options' ).add( itemModel );
|
297 |
+
this.model.get( 'options' ).findWhere( { id: itemID } ).trigger( 'open-widget' );
|
298 |
+
},
|
299 |
+
|
300 |
+
onOptionDuplicate: function( e, fieldChoice ) {
|
301 |
+
e.preventDefault();
|
302 |
+
|
303 |
+
var attrs = fieldChoice.toJSON();
|
304 |
+
var index = this.model.get( 'options' ).indexOf( fieldChoice );
|
305 |
+
index = index + 1;
|
306 |
+
attrs.id = this.getOptionModelID();
|
307 |
+
var modelClass = this.model.get( 'options' ).model;
|
308 |
+
var clonedModel = new modelClass( attrs );
|
309 |
+
this.model.get( 'options' ).add( clonedModel, { at: index } );
|
310 |
+
this.model.get( 'options' ).findWhere( { id: attrs.id } ).trigger( 'open-widget' );
|
311 |
+
},
|
312 |
+
|
313 |
+
onDisplayTypeChange: function(e) {
|
314 |
+
var $input = $( e.target );
|
315 |
+
var attribute = $input.data( 'bind' );
|
316 |
+
var value = $input.val();
|
317 |
+
|
318 |
+
this.model.set( attribute, value );
|
319 |
+
|
320 |
+
var data = {
|
321 |
+
id: this.model.get( 'id' ),
|
322 |
+
callback: 'onChoiceFieldDisplayTypeChangeCallback',
|
323 |
+
};
|
324 |
+
|
325 |
+
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
326 |
+
},
|
327 |
+
|
328 |
+
onOptionModelAdd: function( optionModel, optionsCollection, options ) {
|
329 |
+
this.model.trigger( 'change' );
|
330 |
+
this.addOptionItemView( optionModel, options );
|
331 |
+
|
332 |
+
var model = this.model;
|
333 |
+
|
334 |
+
if ( options.refresh !== false ) {
|
335 |
+
this.model.fetchHtml( function( response ) {
|
336 |
+
var data = {
|
337 |
+
id: model.get( 'id' ),
|
338 |
+
html: response,
|
339 |
+
};
|
340 |
+
|
341 |
+
happyForms.previewSend( 'happyforms-form-part-refresh', data );
|
342 |
+
} );
|
343 |
+
}
|
344 |
+
},
|
345 |
+
|
346 |
+
onOptionModelChange: function( optionModel ) {
|
347 |
+
this.model.trigger( 'change' );
|
348 |
+
},
|
349 |
+
|
350 |
+
onOptionModelRemove: function( optionModel ) {
|
351 |
+
this.model.trigger( 'change' );
|
352 |
+
|
353 |
+
var optionViewModel = this.optionViews.find( function( viewModel ) {
|
354 |
+
return viewModel.get( 'view' ).model.id === optionModel.id;
|
355 |
+
}, this );
|
356 |
+
|
357 |
+
this.optionViews.remove( optionViewModel );
|
358 |
+
|
359 |
+
if ( this.model.get( 'options' ).length == 0 ) {
|
360 |
+
$( '.options ul', this.$el ).html( '' );
|
361 |
+
}
|
362 |
+
|
363 |
+
var data = {
|
364 |
+
id: this.model.get( 'id' ),
|
365 |
+
callback: 'onOptionDeleteCallback',
|
366 |
+
options: {
|
367 |
+
itemID: optionModel.id,
|
368 |
+
}
|
369 |
+
};
|
370 |
+
|
371 |
+
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
372 |
+
},
|
373 |
+
|
374 |
+
onOptionModelsSorted: function() {
|
375 |
+
this.optionViews.reset( _.map( this.model.get( 'options' ).pluck( 'id' ), function( id ) {
|
376 |
+
return this.optionViews.get( id );
|
377 |
+
}, this ) );
|
378 |
+
this.model.trigger( 'change' );
|
379 |
+
|
380 |
+
var model = this.model;
|
381 |
+
|
382 |
+
this.model.fetchHtml( function( response ) {
|
383 |
+
var data = {
|
384 |
+
id: model.get( 'id' ),
|
385 |
+
html: response,
|
386 |
+
};
|
387 |
+
|
388 |
+
happyForms.previewSend( 'happyforms-form-part-refresh', data );
|
389 |
+
} );
|
390 |
+
},
|
391 |
+
|
392 |
+
addOptionItemView: function( optionModel, options ) {
|
393 |
+
var optionView = null;
|
394 |
+
var optionAttributes = optionModel.attributes;
|
395 |
+
var isHeading = 'undefined' !== typeof optionAttributes.is_heading && 1 == optionAttributes.is_heading;
|
396 |
+
var optionView = (
|
397 |
+
isHeading ?
|
398 |
+
this.getOptionHeadingView( optionModel ) :
|
399 |
+
this.getOptionItemView( optionModel )
|
400 |
+
);
|
401 |
+
var optionViewModel = new Backbone.Model( {
|
402 |
+
id: optionModel.id,
|
403 |
+
view: optionView,
|
404 |
+
} );
|
405 |
+
|
406 |
+
this.optionViews.add( optionViewModel, options );
|
407 |
+
},
|
408 |
+
|
409 |
+
getOptionItemView: function( optionModel, options ) {
|
410 |
+
var view = new happyForms.classes.views.OptionItem( _.extend( {
|
411 |
+
model: optionModel,
|
412 |
+
part: this.model,
|
413 |
+
}, options ) );
|
414 |
+
|
415 |
+
return view;
|
416 |
+
},
|
417 |
+
|
418 |
+
getOptionHeadingView: function( optionModel, options ) {
|
419 |
+
var view = new happyForms.classes.views.OptionHeading( _.extend( {
|
420 |
+
model: optionModel,
|
421 |
+
part: this.model,
|
422 |
+
}, options ) );
|
423 |
+
|
424 |
+
return view;
|
425 |
+
},
|
426 |
+
|
427 |
+
onOptionViewAdd: function( viewModel, collection, options ) {
|
428 |
+
var optionView = viewModel.get( 'view' );
|
429 |
+
|
430 |
+
if ( 'undefined' === typeof( options.index ) ) {
|
431 |
+
$( '.option-list', this.$el ).append( optionView.render().$el );
|
432 |
+
} else if ( 0 === options.index ) {
|
433 |
+
$( '.option-list', this.$el ).prepend( optionView.render().$el );
|
434 |
+
} else {
|
435 |
+
$( '.happyforms-choice-item-widget:nth-child(' + options.index + ')', this.$el ).after( optionView.render().$el );
|
436 |
+
}
|
437 |
+
|
438 |
+
optionView.trigger( 'ready' );
|
439 |
+
},
|
440 |
+
|
441 |
+
onOptionViewRemove: function( viewModel ) {
|
442 |
+
var optionView = viewModel.get( 'view' );
|
443 |
+
optionView.remove();
|
444 |
+
},
|
445 |
+
|
446 |
+
onOptionSortStop: function( e, ui ) {
|
447 |
+
var $sortable = $( '.option-list', this.$el );
|
448 |
+
var ids = $sortable.sortable( 'toArray', { attribute: 'data-option-id' } );
|
449 |
+
|
450 |
+
this.model.get( 'options' ).reset( _.map( ids, function( id ) {
|
451 |
+
return this.model.get( 'options' ).get( id );
|
452 |
+
}, this ) );
|
453 |
+
},
|
454 |
+
|
455 |
+
onOptionViewsSorted: function( optionViews ) {
|
456 |
+
var $stage = $( '.option-list', this.$el );
|
457 |
+
|
458 |
+
optionViews.forEach( function( optionViewModel ) {
|
459 |
+
var optionView = optionViewModel.get( 'view' );
|
460 |
+
var $optionViewEl = optionView.$el;
|
461 |
+
$optionViewEl.detach();
|
462 |
+
$stage.append( $optionViewEl );
|
463 |
+
optionView.trigger( 'refresh' );
|
464 |
+
}, this );
|
465 |
+
},
|
466 |
+
|
467 |
+
onAddOtherOption: function( model, value ) {
|
468 |
+
var $otherOptionOptions = $( '.happyforms-nested-settings[data-trigger="other_option"]', this.$el );
|
469 |
+
|
470 |
+
if ( 1 == value ) {
|
471 |
+
$otherOptionOptions.show();
|
472 |
+
} else {
|
473 |
+
$otherOptionOptions.hide();
|
474 |
+
}
|
475 |
+
|
476 |
+
this.refreshPart();
|
477 |
+
},
|
478 |
+
|
479 |
+
onOtherOptionLabelChange: function() {
|
480 |
+
var data = {
|
481 |
+
id: this.model.get( 'id' ),
|
482 |
+
callback: 'onOtherOptionLabelChangeCallback'
|
483 |
+
};
|
484 |
+
|
485 |
+
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
486 |
+
},
|
487 |
+
|
488 |
+
onOtherOptionPlaceholderChange: function() {
|
489 |
+
var data = {
|
490 |
+
id: this.model.get( 'id' ),
|
491 |
+
callback: 'onOtherOptionPlaceholderChangeCallback'
|
492 |
+
};
|
493 |
+
|
494 |
+
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
495 |
+
},
|
496 |
+
|
497 |
+
} );
|
498 |
+
|
499 |
+
happyForms.previewer = _.extend( happyForms.previewer, {
|
500 |
+
onOptionDeleteCallback: function( id, html, options ) {
|
501 |
+
var part = this.getPartModel( id );
|
502 |
+
var $part = this.getPartElement( html );
|
503 |
+
var $option = $( '#' + options.itemID, $part );
|
504 |
+
|
505 |
+
$option.remove();
|
506 |
+
},
|
507 |
+
|
508 |
+
onOptionLabelChangeCallback: function( id, html, options ) {
|
509 |
+
var part = this.getPartModel( id );
|
510 |
+
var $part = this.getPartElement( html );
|
511 |
+
var option = part.get( 'options' ).get( options.itemID );
|
512 |
+
var $option = $( '#' + options.itemID, $part );
|
513 |
+
|
514 |
+
this.$( 'span.label', $option ).text( option.get( 'label' ) );
|
515 |
+
},
|
516 |
+
|
517 |
+
onOptionDescriptionChangeCallback: function( id, html, options ) {
|
518 |
+
var part = this.getPartModel( id );
|
519 |
+
var $part = this.getPartElement( html );
|
520 |
+
var option = part.get( 'options' ).get( options.itemID );
|
521 |
+
var $option = $( '#' + options.itemID, $part );
|
522 |
+
|
523 |
+
this.$( '.happyforms-part-option__description', $option ).text( option.get( 'description' ) );
|
524 |
+
},
|
525 |
+
|
526 |
+
onOptionDefaultChangeCallback: function( id, html, options ) {
|
527 |
+
var part = this.getPartModel( id );
|
528 |
+
var $part = this.getPartElement( html );
|
529 |
+
var option = part.get( 'options' ).get( options.itemID );
|
530 |
+
var $option = $( '#' + options.itemID, $part );
|
531 |
+
|
532 |
+
this.$( 'input', $option ).prop( 'checked', option.get( 'is_default' ) );
|
533 |
+
},
|
534 |
+
|
535 |
+
onOtherOptionLabelChangeCallback: function( id, html, options ) {
|
536 |
+
var part = this.getPartModel( id );
|
537 |
+
var $part = this.getPartElement( html );
|
538 |
+
var $otherOptionLabel = $( '.happyforms-part-option--other .label', $part );
|
539 |
+
|
540 |
+
$otherOptionLabel.text( part.get( 'other_option_label' ) );
|
541 |
+
},
|
542 |
+
|
543 |
+
onOtherOptionPlaceholderChangeCallback: function( id, html, options ) {
|
544 |
+
var part = this.getPartModel( id );
|
545 |
+
var $part = this.getPartElement( html );
|
546 |
+
var $otherOptionInput = $( '.happyforms-part-option--other input[type=text]', $part );
|
547 |
+
|
548 |
+
$otherOptionInput.attr( 'placeholder', part.get( 'other_option_placeholder' ) );
|
549 |
+
},
|
550 |
+
|
551 |
+
onOptionHeadingLabelChangeCallback: function( id, html, options ) {
|
552 |
+
var part = this.getPartModel( id );
|
553 |
+
var $part = this.getPartElement( html );
|
554 |
+
var option = part.get( 'options' ).get( options.itemID );
|
555 |
+
var $option = $( '#' + options.itemID, $part );
|
556 |
+
|
557 |
+
this.$( 'label.heading-label', $option ).text( option.get( 'label' ) );
|
558 |
+
},
|
559 |
+
|
560 |
+
onChoiceFieldDisplayTypeChangeCallback: function( id, html, options ) {
|
561 |
+
var part = this.getPartModel( id );
|
562 |
+
var $part = this.getPartElement( html );
|
563 |
+
|
564 |
+
if ( 'block' === part.get( 'display_type' ) ) {
|
565 |
+
$part.addClass( 'display-type--block' );
|
566 |
+
} else {
|
567 |
+
$part.removeClass( 'display-type--block' );
|
568 |
+
}
|
569 |
+
},
|
570 |
+
} );
|
571 |
+
|
572 |
+
} ) ( jQuery, _, Backbone, wp.customize, _happyFormsSettings );
|
core/assets/js/parts/part-radio.js
CHANGED
@@ -36,562 +36,38 @@
|
|
36 |
model: OptionModel,
|
37 |
} );
|
38 |
|
39 |
-
happyForms.classes.views.
|
40 |
-
template: '#customize-happyforms-checkbox-item-heading-template',
|
41 |
-
|
42 |
-
events: {
|
43 |
-
'click .delete-heading': 'onDeleteHeadingClick',
|
44 |
-
'keyup [name=label]': 'onHeadingLabelChange',
|
45 |
-
'change [name=label]': 'onHeadingLabelChange',
|
46 |
-
},
|
47 |
-
|
48 |
-
initialize: function( options ) {
|
49 |
-
this.template = _.template( $( this.template ).text() );
|
50 |
-
this.part = options.part;
|
51 |
-
|
52 |
-
this.listenTo( this, 'ready', this.onReady );
|
53 |
-
},
|
54 |
-
|
55 |
-
render: function() {
|
56 |
-
this.setElement( this.template( this.model.toJSON() ) );
|
57 |
-
|
58 |
-
return this;
|
59 |
-
},
|
60 |
-
|
61 |
-
onReady: function() {
|
62 |
-
$( '[name=label]', this.$el ).trigger( 'focus' );
|
63 |
-
},
|
64 |
-
|
65 |
-
onDeleteHeadingClick: function( e ) {
|
66 |
-
e.preventDefault();
|
67 |
-
|
68 |
-
this.model.collection.remove( this.model );
|
69 |
-
},
|
70 |
-
|
71 |
-
onHeadingLabelChange: function( e ) {
|
72 |
-
this.model.set( 'label', $( e.target ).val() );
|
73 |
-
this.part.trigger( 'change' );
|
74 |
-
|
75 |
-
var data = {
|
76 |
-
id: this.part.get( 'id' ),
|
77 |
-
callback: 'onRadioHeadingLabelChangeCallback',
|
78 |
-
options: {
|
79 |
-
itemID: this.model.get( 'id' ),
|
80 |
-
}
|
81 |
-
};
|
82 |
-
|
83 |
-
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
84 |
-
},
|
85 |
-
} );
|
86 |
-
|
87 |
-
happyForms.classes.views.parts.radioOption = Backbone.View.extend( {
|
88 |
template: '#customize-happyforms-radio-item-template',
|
|
|
89 |
|
90 |
-
|
91 |
-
|
92 |
-
'click .delete-option': 'onDeleteOptionClick',
|
93 |
-
'keyup [name=label]': 'onItemLabelChange',
|
94 |
-
'change [name=label]': 'onItemLabelChange',
|
95 |
-
'keyup [name=description]': 'onItemDescriptionChange',
|
96 |
-
'change [name=is_default]': 'onItemDefaultChange',
|
97 |
-
|
98 |
-
'keyup [name=limit_submissions_amount]': 'onItemLimitSubmissionsAmountChange',
|
99 |
-
'change [name=limit_submissions_amount]': 'onItemLimitSubmissionsAmountChange',
|
100 |
-
},
|
101 |
-
|
102 |
-
initialize: function( options ) {
|
103 |
-
this.template = _.template( $( this.template ).text() );
|
104 |
-
this.part = options.part;
|
105 |
-
|
106 |
-
this.listenTo( this, 'ready', this.onReady );
|
107 |
-
this.listenTo( this.model, 'change:limit_submissions_amount', this.onChangeMaxSubmissionsAmount );
|
108 |
-
},
|
109 |
-
|
110 |
-
render: function() {
|
111 |
-
this.setElement( this.template( this.model.toJSON() ) );
|
112 |
-
return this;
|
113 |
-
},
|
114 |
-
|
115 |
-
onReady: function() {
|
116 |
-
$( '[name=label]', this.$el ).trigger( 'focus' );
|
117 |
-
},
|
118 |
-
|
119 |
-
onAdvancedOptionClick: function( e ) {
|
120 |
-
e.preventDefault();
|
121 |
-
|
122 |
-
$( '.happyforms-part-item-advanced', this.$el ).slideToggle( 300, function() {
|
123 |
-
$( e.target ).toggleClass( 'opened' );
|
124 |
-
} );
|
125 |
-
},
|
126 |
-
|
127 |
-
onDeleteOptionClick: function( e ) {
|
128 |
-
e.preventDefault();
|
129 |
-
this.model.collection.remove( this.model );
|
130 |
-
},
|
131 |
-
|
132 |
-
onItemLabelChange: function( e ) {
|
133 |
-
this.model.set( 'label', $( e.target ).val() );
|
134 |
-
this.part.trigger( 'change' );
|
135 |
-
|
136 |
-
var data = {
|
137 |
-
id: this.part.get( 'id' ),
|
138 |
-
callback: 'onRadioItemLabelChangeCallback',
|
139 |
-
options: {
|
140 |
-
itemID: this.model.get( 'id' ),
|
141 |
-
}
|
142 |
-
};
|
143 |
-
|
144 |
-
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
145 |
-
},
|
146 |
-
|
147 |
-
onItemDescriptionChange: function( e ) {
|
148 |
-
this.model.set( 'description', $( e.target ).val() );
|
149 |
-
this.part.trigger( 'change' );
|
150 |
-
|
151 |
-
if ( '' == this.model.previousAttributes().description || '' == this.model.get( 'description' ) ) {
|
152 |
-
var self = this;
|
153 |
-
this.part.fetchHtml( function( response ) {
|
154 |
-
var data = {
|
155 |
-
id: self.part.get( 'id' ),
|
156 |
-
html: response,
|
157 |
-
};
|
158 |
-
|
159 |
-
happyForms.previewSend( 'happyforms-form-part-refresh', data );
|
160 |
-
} );
|
161 |
-
} else {
|
162 |
-
var data = {
|
163 |
-
id: this.part.get( 'id' ),
|
164 |
-
callback: 'onRadioItemDescriptionChangeCallback',
|
165 |
-
options: {
|
166 |
-
itemID: this.model.get( 'id' ),
|
167 |
-
}
|
168 |
-
};
|
169 |
-
|
170 |
-
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
171 |
-
|
172 |
-
}
|
173 |
-
},
|
174 |
-
|
175 |
-
onItemDefaultChange: function( e ) {
|
176 |
-
var isChecked = $( e.target ).is( ':checked' );
|
177 |
-
|
178 |
-
this.model.collection.forEach( function( item ) {
|
179 |
-
item.set( 'is_default', 0 );
|
180 |
-
} );
|
181 |
-
|
182 |
-
$( '[name=is_default]', this.$el.siblings() ).prop( 'checked', false );
|
183 |
-
|
184 |
-
if ( isChecked ) {
|
185 |
-
this.model.set( 'is_default', 1 );
|
186 |
-
$( e.target ).prop( 'checked', true );
|
187 |
-
}
|
188 |
-
|
189 |
-
var data = {
|
190 |
-
id: this.part.get( 'id' ),
|
191 |
-
callback: 'onRadioItemDefaultChangeCallback',
|
192 |
-
options: {
|
193 |
-
itemID: this.model.get( 'id' ),
|
194 |
-
}
|
195 |
-
};
|
196 |
-
|
197 |
-
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
198 |
-
},
|
199 |
-
|
200 |
-
onChangeMaxSubmissionsAmount: function( e ) {
|
201 |
-
|
202 |
-
var model = this.part;
|
203 |
-
|
204 |
-
if ( '' == this.model.get('limit_submissions_amount') ) {
|
205 |
-
return;
|
206 |
-
}
|
207 |
-
|
208 |
-
this.part.fetchHtml( function( response ) {
|
209 |
-
var data = {
|
210 |
-
id: model.get( 'id' ),
|
211 |
-
html: response,
|
212 |
-
};
|
213 |
-
|
214 |
-
happyForms.previewSend( 'happyforms-form-part-refresh', data );
|
215 |
-
|
216 |
-
} );
|
217 |
-
},
|
218 |
-
|
219 |
-
onItemLimitSubmissionsAmountChange: function( e ) {
|
220 |
-
var value = $( '[name="limit_submissions_amount"]', this.$el ).val();
|
221 |
-
|
222 |
-
if ( 0 > value ) {
|
223 |
-
$( '[name="limit_submissions_amount"]', this.$el ).val( '' );
|
224 |
-
return;
|
225 |
-
}
|
226 |
-
|
227 |
-
this.model.set( 'limit_submissions_amount', $( e.target ).val() );
|
228 |
-
this.part.trigger( 'change' );
|
229 |
-
},
|
230 |
-
|
231 |
} );
|
232 |
|
233 |
-
happyForms.classes.views.parts.radio = happyForms.classes.views.
|
234 |
template: '#customize-happyforms-radio-template',
|
235 |
|
236 |
-
events: _.extend( {}, happyForms.classes.views.
|
237 |
-
'click .add-option': 'onAddOptionClick',
|
238 |
-
'click .add-heading': 'onAddHeadingClick',
|
239 |
-
'click .import-option': 'onImportOptionClick',
|
240 |
-
'click .import-options': 'onImportOptionsClick',
|
241 |
-
'click .add-options': 'onAddOptionsClick',
|
242 |
'change [data-bind=display_type]': 'onDisplayTypeChange',
|
243 |
} ),
|
244 |
|
245 |
-
|
246 |
-
|
247 |
-
|
248 |
-
|
249 |
-
|
250 |
-
this.listenTo( this.model.get( 'options' ), 'add', this.onOptionModelAdd );
|
251 |
-
this.listenTo( this.model.get( 'options' ), 'change', this.onOptionModelChange );
|
252 |
-
this.listenTo( this.model.get( 'options' ), 'remove', this.onOptionModelRemove );
|
253 |
-
this.listenTo( this.model.get( 'options' ), 'reset', this.onOptionModelsSorted );
|
254 |
-
this.listenTo( this.optionViews, 'add', this.onOptionViewAdd );
|
255 |
-
this.listenTo( this.optionViews, 'remove', this.onOptionViewRemove );
|
256 |
-
this.listenTo( this.optionViews, 'reset', this.onOptionViewsSorted );
|
257 |
-
this.listenTo( this, 'sort-stop', this.onOptionSortStop );
|
258 |
-
this.listenTo( this, 'ready', this.onReady );
|
259 |
-
|
260 |
-
this.listenTo( this.model, 'change:other_option', this.onAddOtherOption );
|
261 |
-
this.listenTo( this.model, 'change:other_option_label', this.onOtherOptionLabelChange );
|
262 |
-
this.listenTo( this.model, 'change:other_option_placeholder', this.onOtherOptionPlaceholderChange );
|
263 |
-
},
|
264 |
-
|
265 |
-
onReady: function() {
|
266 |
-
this.model.get( 'options' ).each( function( optionModel ) {
|
267 |
-
this.addOptionView( optionModel );
|
268 |
-
}, this );
|
269 |
-
|
270 |
-
$( '.option-list', this.$el ).sortable( {
|
271 |
-
handle: '.happyforms-part-item-handle',
|
272 |
-
helper: 'clone',
|
273 |
-
|
274 |
-
stop: function ( e, ui ) {
|
275 |
-
this.trigger( 'sort-stop', e, ui );
|
276 |
-
}.bind( this ),
|
277 |
-
} );
|
278 |
-
},
|
279 |
-
|
280 |
-
onOptionModelAdd: function( optionModel, optionsCollection, options ) {
|
281 |
-
this.model.trigger( 'change' );
|
282 |
-
this.addOptionView( optionModel, options );
|
283 |
-
|
284 |
-
var model = this.model;
|
285 |
-
|
286 |
-
if ( options.refresh !== false ) {
|
287 |
-
this.model.fetchHtml( function( response ) {
|
288 |
-
var data = {
|
289 |
-
id: model.get( 'id' ),
|
290 |
-
html: response,
|
291 |
-
};
|
292 |
-
|
293 |
-
happyForms.previewSend( 'happyforms-form-part-refresh', data );
|
294 |
-
} );
|
295 |
-
}
|
296 |
-
},
|
297 |
-
|
298 |
-
onOptionModelChange: function( optionModel ) {
|
299 |
-
this.model.trigger( 'change' );
|
300 |
-
},
|
301 |
-
|
302 |
-
onOptionModelRemove: function( optionModel ) {
|
303 |
-
this.model.trigger( 'change' );
|
304 |
-
|
305 |
-
var optionViewModel = this.optionViews.find( function( viewModel ) {
|
306 |
-
return viewModel.get( 'view' ).model.id === optionModel.id;
|
307 |
-
}, this );
|
308 |
-
|
309 |
-
this.optionViews.remove( optionViewModel );
|
310 |
-
|
311 |
-
if ( this.model.get( 'options' ).length == 0 ) {
|
312 |
-
$( '.options ul', this.$el ).html( '' );
|
313 |
-
}
|
314 |
-
|
315 |
-
var data = {
|
316 |
-
id: this.model.get( 'id' ),
|
317 |
-
callback: 'onRadioItemDeleteCallback',
|
318 |
-
options: {
|
319 |
-
itemID: optionModel.id,
|
320 |
-
}
|
321 |
-
};
|
322 |
-
|
323 |
-
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
324 |
-
},
|
325 |
-
|
326 |
-
onOptionModelsSorted: function() {
|
327 |
-
this.optionViews.reset( _.map( this.model.get( 'options' ).pluck( 'id' ), function( id ) {
|
328 |
-
return this.optionViews.get( id );
|
329 |
-
}, this ) );
|
330 |
-
this.model.trigger( 'change' );
|
331 |
-
|
332 |
-
var model = this.model;
|
333 |
-
|
334 |
-
this.model.fetchHtml( function( response ) {
|
335 |
-
var data = {
|
336 |
-
id: model.get( 'id' ),
|
337 |
-
html: response,
|
338 |
-
};
|
339 |
-
|
340 |
-
happyForms.previewSend( 'happyforms-form-part-refresh', data );
|
341 |
-
} );
|
342 |
-
},
|
343 |
-
|
344 |
-
addOptionView: function( optionModel, options ) {
|
345 |
-
var optionView = null;
|
346 |
-
var optionAttributes = optionModel.attributes;
|
347 |
-
var isHeading = 'undefined' !== typeof optionAttributes.is_heading && 1 == optionAttributes.is_heading;
|
348 |
-
|
349 |
-
if ( isHeading ) {
|
350 |
-
optionView = new happyForms.classes.views.parts.radioOptionHeading( _.extend( {
|
351 |
-
model: optionModel,
|
352 |
-
part: this.model,
|
353 |
-
}, options ) );
|
354 |
-
} else {
|
355 |
-
optionView = new happyForms.classes.views.parts.radioOption( _.extend( {
|
356 |
-
model: optionModel,
|
357 |
-
part: this.model,
|
358 |
-
}, options ) );
|
359 |
-
}
|
360 |
-
|
361 |
-
var optionViewModel = new Backbone.Model( {
|
362 |
-
id: optionModel.id,
|
363 |
-
view: optionView,
|
364 |
-
} );
|
365 |
-
|
366 |
-
this.optionViews.add( optionViewModel, options );
|
367 |
-
},
|
368 |
-
|
369 |
-
onOptionViewAdd: function( viewModel, collection, options ) {
|
370 |
-
var optionView = viewModel.get( 'view' );
|
371 |
-
$( '.option-list', this.$el ).append( optionView.render().$el );
|
372 |
-
optionView.trigger( 'ready' );
|
373 |
-
},
|
374 |
-
|
375 |
-
onOptionViewRemove: function( viewModel ) {
|
376 |
-
var optionView = viewModel.get( 'view' );
|
377 |
-
optionView.remove();
|
378 |
-
},
|
379 |
-
|
380 |
-
onOptionSortStop: function( e, ui ) {
|
381 |
-
var $sortable = $( '.option-list', this.$el );
|
382 |
-
var ids = $sortable.sortable( 'toArray', { attribute: 'data-option-id' } );
|
383 |
-
|
384 |
-
this.model.get( 'options' ).reset( _.map( ids, function( id ) {
|
385 |
-
return this.model.get( 'options' ).get( id );
|
386 |
-
}, this ) );
|
387 |
-
},
|
388 |
-
|
389 |
-
onOptionViewsSorted: function( optionViews ) {
|
390 |
-
var $stage = $( '.option-list', this.$el );
|
391 |
-
|
392 |
-
optionViews.forEach( function( optionViewModel ) {
|
393 |
-
var optionView = optionViewModel.get( 'view' );
|
394 |
-
var $optionViewEl = optionView.$el;
|
395 |
-
$optionViewEl.detach();
|
396 |
-
$stage.append( $optionViewEl );
|
397 |
-
optionView.trigger( 'refresh' );
|
398 |
-
}, this );
|
399 |
-
},
|
400 |
-
|
401 |
-
getOptionModelID: function() {
|
402 |
-
var prefix = this.model.get( 'id' ) + '_option_';
|
403 |
-
var collection = this.model.get( 'options' );
|
404 |
-
var timestamp = new Date().getTime();
|
405 |
-
var id = prefix + timestamp;
|
406 |
-
|
407 |
-
return id;
|
408 |
-
},
|
409 |
-
|
410 |
-
onAddOptionClick: function( e ) {
|
411 |
-
e.preventDefault();
|
412 |
-
|
413 |
-
var itemID = this.getOptionModelID();
|
414 |
-
var itemModel = new OptionModel( { id: itemID } );
|
415 |
-
this.model.get( 'options' ).add( itemModel );
|
416 |
-
},
|
417 |
-
|
418 |
-
onAddHeadingClick: function( e ) {
|
419 |
-
e.preventDefault();
|
420 |
-
|
421 |
-
var itemID = this.getOptionModelID();
|
422 |
-
var itemModel = new OptionModel( { id: itemID, is_heading: 1 } );
|
423 |
-
this.model.get( 'options' ).add( itemModel );
|
424 |
-
},
|
425 |
-
|
426 |
-
onDisplayTypeChange: function(e) {
|
427 |
-
var $input = $( e.target );
|
428 |
-
var attribute = $input.data( 'bind' );
|
429 |
-
var value = $input.val();
|
430 |
-
|
431 |
-
this.model.set( attribute, value );
|
432 |
-
|
433 |
-
var data = {
|
434 |
-
id: this.model.get( 'id' ),
|
435 |
-
callback: 'onRadioDisplayTypeChangeCallback',
|
436 |
-
};
|
437 |
-
|
438 |
-
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
439 |
-
},
|
440 |
-
|
441 |
-
onImportOptionsClick: function( e ) {
|
442 |
-
e.preventDefault();
|
443 |
-
|
444 |
-
$( '.options', this.$el ).hide();
|
445 |
-
$( '.options-import', this.$el ).show();
|
446 |
-
$( '.links.mode-manual', this.$el ).hide();
|
447 |
-
$( '.links.mode-import', this.$el ).show();
|
448 |
-
$( '.option-import-area', this.$el ).trigger( 'focus' );
|
449 |
-
},
|
450 |
-
|
451 |
-
onAddOptionsClick: function( e ) {
|
452 |
-
e.preventDefault();
|
453 |
-
|
454 |
-
$( '.options', this.$el ).show();
|
455 |
-
$( '.options-import', this.$el ).hide();
|
456 |
-
$( '.links.mode-import', this.$el ).hide();
|
457 |
-
$( '.links.mode-manual', this.$el ).show();
|
458 |
-
$( '.option-import-area', this.$el ).val( '' );
|
459 |
-
},
|
460 |
-
|
461 |
-
onImportOptionClick: function( e ) {
|
462 |
-
e.preventDefault();
|
463 |
-
|
464 |
-
var $textarea = $( '.option-import-area', this.$el );
|
465 |
-
var list = $textarea.val();
|
466 |
-
var self = this;
|
467 |
-
|
468 |
-
var models = list
|
469 |
-
.split( /[\r\n]+/g )
|
470 |
-
.map( function( s ) {
|
471 |
-
return s.trim();
|
472 |
-
} )
|
473 |
-
.filter( function( s ) {
|
474 |
-
return s;
|
475 |
-
} )
|
476 |
-
.forEach( function( label, i, list ) {
|
477 |
-
_.delay( function() {
|
478 |
-
var itemID = self.getOptionModelID();
|
479 |
-
var item = new OptionModel( {
|
480 |
-
id: itemID,
|
481 |
-
label: label
|
482 |
-
} );
|
483 |
-
|
484 |
-
self.model.get( 'options' ).add( item, { refresh: ( list.length - 1 === i ) } );
|
485 |
-
}, i );
|
486 |
-
} );
|
487 |
-
|
488 |
-
$textarea.val( '' );
|
489 |
-
$( '.add-options', this.$el ).trigger( 'click' );
|
490 |
-
},
|
491 |
-
|
492 |
-
onAddOtherOption: function( model, value ) {
|
493 |
-
var $otherOptionOptions = $( '.happyforms-nested-settings[data-trigger="other_option"]', this.$el );
|
494 |
-
|
495 |
-
if ( 1 == value ) {
|
496 |
-
$otherOptionOptions.show();
|
497 |
-
} else {
|
498 |
-
$otherOptionOptions.hide();
|
499 |
-
}
|
500 |
-
|
501 |
-
this.refreshPart();
|
502 |
-
},
|
503 |
-
|
504 |
-
onOtherOptionLabelChange: function() {
|
505 |
-
var data = {
|
506 |
-
id: this.model.get( 'id' ),
|
507 |
-
callback: 'onRadioOtherOptionLabelChangeCallback'
|
508 |
-
};
|
509 |
-
|
510 |
-
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
511 |
-
},
|
512 |
-
|
513 |
-
onOtherOptionPlaceholderChange: function() {
|
514 |
-
var data = {
|
515 |
-
id: this.model.get( 'id' ),
|
516 |
-
callback: 'onRadioOtherOptionPlaceholderChangeCallback'
|
517 |
-
};
|
518 |
-
|
519 |
-
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
520 |
-
},
|
521 |
-
|
522 |
-
} );
|
523 |
-
|
524 |
-
happyForms.previewer = _.extend( happyForms.previewer, {
|
525 |
-
onRadioItemDeleteCallback: function( id, html, options ) {
|
526 |
-
var part = this.getPartModel( id );
|
527 |
-
var $part = this.getPartElement( html );
|
528 |
-
var $option = $( '#' + options.itemID, $part );
|
529 |
-
|
530 |
-
$option.remove();
|
531 |
-
},
|
532 |
-
|
533 |
-
onRadioDisplayTypeChangeCallback: function( id, html, options ) {
|
534 |
-
var part = this.getPartModel( id );
|
535 |
-
var $part = this.getPartElement( html );
|
536 |
-
|
537 |
-
if ( 'block' === part.get( 'display_type' ) ) {
|
538 |
-
$part.addClass( 'display-type--block' );
|
539 |
-
} else {
|
540 |
-
$part.removeClass( 'display-type--block' );
|
541 |
-
}
|
542 |
-
},
|
543 |
-
|
544 |
-
onRadioItemLabelChangeCallback: function( id, html, options ) {
|
545 |
-
var part = this.getPartModel( id );
|
546 |
-
var $part = this.getPartElement( html );
|
547 |
-
var option = part.get( 'options' ).get( options.itemID );
|
548 |
-
var $option = $( '#' + options.itemID, $part );
|
549 |
-
|
550 |
-
this.$( 'span.label', $option ).text( option.get( 'label' ) );
|
551 |
-
},
|
552 |
-
|
553 |
-
onRadioItemDescriptionChangeCallback: function( id, html, options ) {
|
554 |
-
var part = this.getPartModel( id );
|
555 |
-
var $part = this.getPartElement( html );
|
556 |
-
var option = part.get( 'options' ).get( options.itemID );
|
557 |
-
var $option = $( '#' + options.itemID, $part );
|
558 |
-
|
559 |
-
this.$( '.happyforms-part-option__description', $option ).text( option.get( 'description' ) );
|
560 |
-
},
|
561 |
-
|
562 |
-
onRadioItemDefaultChangeCallback: function( id, html, options ) {
|
563 |
-
var part = this.getPartModel( id );
|
564 |
-
var $part = this.getPartElement( html );
|
565 |
-
var option = part.get( 'options' ).get( options.itemID );
|
566 |
-
var $option = $( '#' + options.itemID, $part );
|
567 |
-
|
568 |
-
this.$( 'input', $option ).prop( 'checked', option.get( 'is_default' ) );
|
569 |
-
},
|
570 |
-
|
571 |
-
onRadioOtherOptionLabelChangeCallback: function( id, html, options ) {
|
572 |
-
var part = this.getPartModel( id );
|
573 |
-
var $part = this.getPartElement( html );
|
574 |
-
var $otherOptionLabel = $( '.happyforms-part-option--other .label', $part );
|
575 |
-
|
576 |
-
$otherOptionLabel.text( part.get( 'other_option_label' ) );
|
577 |
-
},
|
578 |
-
|
579 |
-
onRadioOtherOptionPlaceholderChangeCallback: function( id, html, options ) {
|
580 |
-
var part = this.getPartModel( id );
|
581 |
-
var $part = this.getPartElement( html );
|
582 |
-
var $otherOptionInput = $( '.happyforms-part-option--other input[type=text]', $part );
|
583 |
|
584 |
-
|
585 |
},
|
586 |
|
587 |
-
|
588 |
-
var
|
589 |
-
|
590 |
-
|
591 |
-
|
592 |
|
593 |
-
|
594 |
},
|
595 |
} );
|
596 |
|
597 |
-
} ) ( jQuery, _, Backbone, wp.customize, _happyFormsSettings );
|
36 |
model: OptionModel,
|
37 |
} );
|
38 |
|
39 |
+
var OptionItemView = happyForms.classes.views.OptionItem.extend( {
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
40 |
template: '#customize-happyforms-radio-item-template',
|
41 |
+
} );
|
42 |
|
43 |
+
var OptionHeadingView = happyForms.classes.views.OptionHeading.extend( {
|
44 |
+
template: '#customize-happyforms-radio-item-heading-template',
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
45 |
} );
|
46 |
|
47 |
+
happyForms.classes.views.parts.radio = happyForms.classes.views.ChoiceField.extend( {
|
48 |
template: '#customize-happyforms-radio-template',
|
49 |
|
50 |
+
events: _.extend( {}, happyForms.classes.views.ChoiceField.prototype.events, {
|
|
|
|
|
|
|
|
|
|
|
51 |
'change [data-bind=display_type]': 'onDisplayTypeChange',
|
52 |
} ),
|
53 |
|
54 |
+
getOptionItemView: function( optionModel, options ) {
|
55 |
+
var view = new OptionItemView( _.extend( {
|
56 |
+
model: optionModel,
|
57 |
+
part: this.model,
|
58 |
+
}, options ) );
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
59 |
|
60 |
+
return view;
|
61 |
},
|
62 |
|
63 |
+
getOptionHeadingView: function( optionModel, options ) {
|
64 |
+
var view = new OptionHeadingView( _.extend( {
|
65 |
+
model: optionModel,
|
66 |
+
part: this.model,
|
67 |
+
}, options ) );
|
68 |
|
69 |
+
return view;
|
70 |
},
|
71 |
} );
|
72 |
|
73 |
+
} ) ( jQuery, _, Backbone, wp.customize, _happyFormsSettings );
|
core/assets/js/parts/part-select.js
CHANGED
@@ -35,117 +35,45 @@
|
|
35 |
model: OptionModel,
|
36 |
} );
|
37 |
|
38 |
-
happyForms.classes.views.
|
39 |
template: '#customize-happyforms-select-item-heading-template',
|
40 |
|
41 |
-
|
42 |
-
|
43 |
-
'
|
44 |
-
'change
|
45 |
-
|
46 |
-
|
47 |
-
initialize: function( options ) {
|
48 |
-
this.template = _.template( $( this.template ).text() );
|
49 |
-
this.part = options.part;
|
50 |
-
|
51 |
-
this.listenTo( this, 'ready', this.onReady );
|
52 |
-
},
|
53 |
-
|
54 |
-
render: function() {
|
55 |
-
this.setElement( this.template( this.model.toJSON() ) );
|
56 |
-
|
57 |
-
return this;
|
58 |
-
},
|
59 |
-
|
60 |
-
onReady: function() {
|
61 |
-
$( '[name=label]', this.$el ).trigger( 'focus' );
|
62 |
-
},
|
63 |
-
|
64 |
-
onDeleteHeadingClick: function( e ) {
|
65 |
-
e.preventDefault();
|
66 |
-
|
67 |
-
this.model.collection.remove( this.model );
|
68 |
-
},
|
69 |
-
|
70 |
-
onHeadingLabelChange: function( e ) {
|
71 |
-
this.model.set( 'label', $( e.target ).val() );
|
72 |
-
var self = this;
|
73 |
|
74 |
-
|
75 |
-
|
76 |
-
|
77 |
-
|
78 |
-
|
|
|
|
|
79 |
|
80 |
-
|
81 |
-
} );
|
82 |
},
|
83 |
} );
|
84 |
|
85 |
-
happyForms.classes.views.
|
86 |
template: '#customize-happyforms-select-item-template',
|
87 |
|
88 |
-
events: {
|
89 |
-
'click .advanced-option': 'onAdvancedOptionClick',
|
90 |
-
'click .delete-option': 'onDeleteOptionClick',
|
91 |
-
'keyup [name=label]': 'onItemLabelKeyup',
|
92 |
-
'change [name=label]': 'onItemLabelChange',
|
93 |
-
'change [name=is_default]': 'onItemDefaultChange',
|
94 |
-
'keyup [name=limit_submissions_amount]': 'onItemLimitSubmissionsAmountChange',
|
95 |
-
'change [name=limit_submissions_amount]': 'onItemLimitSubmissionsAmountChange',
|
96 |
-
},
|
97 |
-
|
98 |
-
initialize: function( options ) {
|
99 |
-
this.template = _.template( $( this.template ).text() );
|
100 |
-
this.part = options.part;
|
101 |
-
|
102 |
-
this.listenTo( this, 'ready', this.onReady );
|
103 |
-
this.listenTo( this.model, 'change:limit_submissions_amount', this.onChangeMaxSubmissionsAmount );
|
104 |
-
},
|
105 |
-
|
106 |
-
render: function() {
|
107 |
-
this.setElement( this.template( this.model.toJSON() ) );
|
108 |
-
return this;
|
109 |
-
},
|
110 |
-
|
111 |
-
onReady: function() {
|
112 |
-
$( '[name=label]', this.$el ).trigger( 'focus' );
|
113 |
-
},
|
114 |
-
|
115 |
-
onAdvancedOptionClick: function( e ) {
|
116 |
-
e.preventDefault();
|
117 |
-
|
118 |
-
$( '.happyforms-part-item-advanced', this.$el ).slideToggle( 300, function() {
|
119 |
-
$( e.target ).toggleClass( 'opened' );
|
120 |
-
} );
|
121 |
-
},
|
122 |
-
|
123 |
-
onDeleteOptionClick: function( e ) {
|
124 |
-
e.preventDefault();
|
125 |
-
this.model.collection.remove( this.model );
|
126 |
-
},
|
127 |
-
|
128 |
-
onItemLabelKeyup: function( e ) {
|
129 |
-
if ( 'Enter' === e.key ) {
|
130 |
-
$( '.add-option', this.$el ).trigger( 'click' );
|
131 |
-
return;
|
132 |
-
}
|
133 |
-
|
134 |
-
this.model.set( 'label', $( e.target ).val() );
|
135 |
-
this.part.trigger( 'change' );
|
136 |
-
},
|
137 |
-
|
138 |
onItemLabelChange: function( e ) {
|
139 |
-
var
|
|
|
|
|
|
|
140 |
|
141 |
-
|
142 |
-
|
143 |
-
|
144 |
-
|
145 |
-
|
|
|
|
|
146 |
|
147 |
-
|
148 |
-
} );
|
149 |
},
|
150 |
|
151 |
onItemDefaultChange: function( e ) {
|
@@ -167,254 +95,39 @@
|
|
167 |
callback: 'onSelectItemDefaultChangeCallback',
|
168 |
options: {
|
169 |
itemID: this.model.get( 'id' ),
|
|
|
170 |
}
|
171 |
};
|
172 |
|
173 |
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
174 |
},
|
175 |
-
|
176 |
-
onItemLimitSubmissionsAmountChange: function( e ) {
|
177 |
-
var value = $( '[name="limit_submissions_amount"]', this.$el ).val();
|
178 |
-
|
179 |
-
if ( 0 > value ) {
|
180 |
-
$( '[name="limit_submissions_amount"]', this.$el ).val( '' );
|
181 |
-
return;
|
182 |
-
}
|
183 |
-
|
184 |
-
this.model.set( 'limit_submissions_amount', $( e.target ).val() );
|
185 |
-
this.part.trigger( 'change' );
|
186 |
-
},
|
187 |
-
|
188 |
-
onChangeMaxSubmissionsAmount: function( e ) {
|
189 |
-
|
190 |
-
var model = this.part;
|
191 |
-
|
192 |
-
if ( '' == this.model.get('limit_submissions_amount') ) {
|
193 |
-
return;
|
194 |
-
}
|
195 |
-
|
196 |
-
this.part.fetchHtml( function( response ) {
|
197 |
-
var data = {
|
198 |
-
id: model.get( 'id' ),
|
199 |
-
html: response,
|
200 |
-
};
|
201 |
-
|
202 |
-
happyForms.previewSend( 'happyforms-form-part-refresh', data );
|
203 |
-
|
204 |
-
} );
|
205 |
-
},
|
206 |
} );
|
207 |
|
208 |
-
happyForms.classes.views.parts.select = happyForms.classes.views.
|
209 |
template: '#customize-happyforms-select-template',
|
210 |
|
211 |
-
events: _.extend( {}, happyForms.classes.views.Part.prototype.events, {
|
212 |
-
'click .add-option': 'onAddOptionClick',
|
213 |
-
'click .add-heading': 'onAddHeadingClick',
|
214 |
-
'click .import-option': 'onImportOptionClick',
|
215 |
-
'click .import-options': 'onImportOptionsClick',
|
216 |
-
'click .add-options': 'onAddOptionsClick',
|
217 |
-
'click .show-all-options': 'onShowAllOptionsClick',
|
218 |
-
|
219 |
-
'change [data-bind=other_option_label]': 'onOtherSelectOptionLabelChange',
|
220 |
-
} ),
|
221 |
-
|
222 |
initialize: function() {
|
223 |
-
happyForms.classes.views.
|
224 |
-
|
225 |
-
this.optionViews = new Backbone.Collection();
|
226 |
|
227 |
this.listenTo( this.model, 'change:placeholder', this.onPlaceholderChange );
|
228 |
-
this.listenTo( this.model, 'change:required', this.onRequiredChange );
|
229 |
-
this.listenTo( this.model.get( 'options' ), 'add', this.onOptionModelAdd );
|
230 |
-
this.listenTo( this.model.get( 'options' ), 'change', this.onOptionModelChange );
|
231 |
-
this.listenTo( this.model.get( 'options' ), 'remove', this.onOptionModelRemove );
|
232 |
-
this.listenTo( this.model.get( 'options' ), 'reset', this.onOptionModelsSorted );
|
233 |
-
this.listenTo( this.optionViews, 'add', this.onOptionViewAdd );
|
234 |
-
this.listenTo( this.optionViews, 'remove', this.onOptionViewRemove );
|
235 |
-
this.listenTo( this.optionViews, 'reset', this.onOptionViewsSorted );
|
236 |
-
this.listenTo( this, 'sort-stop', this.onOptionSortStop );
|
237 |
-
this.listenTo( this, 'ready', this.onReady );
|
238 |
-
|
239 |
-
this.listenTo( this.model, 'change:other_option', this.onAddOtherOption );
|
240 |
-
this.listenTo( this.model, 'change:other_option_label', this.onOtherOptionLabelChange );
|
241 |
-
this.listenTo( this.model, 'change:other_option_placeholder', this.onOtherOptionPlaceholderChange );
|
242 |
},
|
243 |
|
244 |
-
|
245 |
-
|
246 |
-
|
247 |
-
|
|
|
248 |
|
249 |
-
|
250 |
-
handle: '.happyforms-part-item-handle',
|
251 |
-
helper: 'clone',
|
252 |
-
|
253 |
-
stop: function ( e, ui ) {
|
254 |
-
this.trigger( 'sort-stop', e, ui );
|
255 |
-
}.bind( this ),
|
256 |
-
} );
|
257 |
},
|
258 |
|
259 |
-
|
260 |
-
|
261 |
-
|
|
|
|
|
262 |
|
263 |
-
|
264 |
-
|
265 |
-
if ( options.refresh !== false ) {
|
266 |
-
this.model.fetchHtml( function( response ) {
|
267 |
-
var data = {
|
268 |
-
id: model.get( 'id' ),
|
269 |
-
html: response,
|
270 |
-
};
|
271 |
-
|
272 |
-
happyForms.previewSend( 'happyforms-form-part-refresh', data );
|
273 |
-
} );
|
274 |
-
}
|
275 |
-
},
|
276 |
-
|
277 |
-
onOptionModelChange: function( optionModel ) {
|
278 |
-
this.model.trigger( 'change' );
|
279 |
-
},
|
280 |
-
|
281 |
-
onOptionModelRemove: function( optionModel ) {
|
282 |
-
this.model.trigger( 'change' );
|
283 |
-
|
284 |
-
var optionViewModel = this.optionViews.find( function( viewModel ) {
|
285 |
-
return viewModel.get( 'view' ).model.id === optionModel.id;
|
286 |
-
}, this );
|
287 |
-
|
288 |
-
if ( 1 == optionModel.get( 'is_default' ) ) {
|
289 |
-
$( '[name=is_default]', optionViewModel.$el ).prop( 'checked', false ).trigger( 'change' );
|
290 |
-
}
|
291 |
-
|
292 |
-
this.optionViews.remove( optionViewModel );
|
293 |
-
|
294 |
-
if ( this.model.get( 'options' ).length == 0 ) {
|
295 |
-
$( '.options ul', this.$el ).html( '' );
|
296 |
-
}
|
297 |
-
|
298 |
-
var data = {
|
299 |
-
id: this.model.get( 'id' ),
|
300 |
-
callback: 'onSelectItemDeleteCallback',
|
301 |
-
options: {
|
302 |
-
itemID: optionModel.id,
|
303 |
-
}
|
304 |
-
};
|
305 |
-
|
306 |
-
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
307 |
-
},
|
308 |
-
|
309 |
-
onOptionModelsSorted: function() {
|
310 |
-
this.optionViews.reset( _.map( this.model.get( 'options' ).pluck( 'id' ), function( id ) {
|
311 |
-
return this.optionViews.get( id );
|
312 |
-
}, this ) );
|
313 |
-
|
314 |
-
this.model.trigger( 'change' );
|
315 |
-
|
316 |
-
var model = this.model;
|
317 |
-
|
318 |
-
this.model.fetchHtml( function( response ) {
|
319 |
-
var data = {
|
320 |
-
id: model.get( 'id' ),
|
321 |
-
html: response,
|
322 |
-
};
|
323 |
-
|
324 |
-
happyForms.previewSend( 'happyforms-form-part-refresh', data );
|
325 |
-
} );
|
326 |
-
},
|
327 |
-
|
328 |
-
onOptionsChange: function() {
|
329 |
-
this.model.trigger( 'change' );
|
330 |
-
},
|
331 |
-
|
332 |
-
addOptionView: function( optionModel, options ) {
|
333 |
-
var optionView = null;
|
334 |
-
var optionAttributes = optionModel.attributes;
|
335 |
-
var isHeading = 'undefined' !== typeof optionAttributes.is_heading && 1 == optionAttributes.is_heading;
|
336 |
-
|
337 |
-
if ( isHeading ) {
|
338 |
-
optionView = new happyForms.classes.views.parts.selectOptionHeading( _.extend( {
|
339 |
-
model: optionModel,
|
340 |
-
part: this.model,
|
341 |
-
}, options ) );
|
342 |
-
} else {
|
343 |
-
optionView = new happyForms.classes.views.parts.selectOption( _.extend( {
|
344 |
-
model: optionModel,
|
345 |
-
part: this.model,
|
346 |
-
}, options ) );
|
347 |
-
}
|
348 |
-
|
349 |
-
var optionViewModel = new Backbone.Model( {
|
350 |
-
id: optionModel.id,
|
351 |
-
view: optionView,
|
352 |
-
} );
|
353 |
-
|
354 |
-
this.optionViews.add( optionViewModel, options );
|
355 |
-
},
|
356 |
-
|
357 |
-
onOptionViewAdd: function( viewModel, collection, options ) {
|
358 |
-
var optionView = viewModel.get( 'view' );
|
359 |
-
$( '.options ul', this.$el ).append( optionView.render().$el );
|
360 |
-
optionView.trigger( 'ready' );
|
361 |
-
},
|
362 |
-
|
363 |
-
onOptionViewRemove: function( viewModel ) {
|
364 |
-
var optionView = viewModel.get( 'view' );
|
365 |
-
optionView.remove();
|
366 |
-
},
|
367 |
-
|
368 |
-
onOptionSortStop: function( e, ui ) {
|
369 |
-
var $sortable = $( '.option-list', this.$el );
|
370 |
-
var ids = $sortable.sortable( 'toArray', { attribute: 'data-option-id' } );
|
371 |
-
|
372 |
-
this.model.get( 'options' ).reset( _.map( ids, function( id ) {
|
373 |
-
return this.model.get( 'options' ).get( id );
|
374 |
-
}, this ) );
|
375 |
-
},
|
376 |
-
|
377 |
-
onOptionViewsSorted: function( optionViews ) {
|
378 |
-
var $stage = $( '.option-list', this.$el );
|
379 |
-
|
380 |
-
optionViews.forEach( function( optionViewModel ) {
|
381 |
-
var optionView = optionViewModel.get( 'view' );
|
382 |
-
var $optionViewEl = optionView.$el;
|
383 |
-
$optionViewEl.detach();
|
384 |
-
$stage.append( $optionViewEl );
|
385 |
-
optionView.trigger( 'refresh' );
|
386 |
-
}, this );
|
387 |
-
},
|
388 |
-
|
389 |
-
getOptionModelID: function() {
|
390 |
-
var prefix = this.model.get( 'id' ) + '_option_';
|
391 |
-
var collection = this.model.get( 'options' );
|
392 |
-
var timestamp = new Date().getTime();
|
393 |
-
var id = prefix + timestamp;
|
394 |
-
|
395 |
-
return id;
|
396 |
-
},
|
397 |
-
|
398 |
-
onAddOptionClick: function( e ) {
|
399 |
-
e.preventDefault();
|
400 |
-
|
401 |
-
var itemID = this.getOptionModelID();
|
402 |
-
var itemModel = new OptionModel( { id: itemID } );
|
403 |
-
this.model.get( 'options' ).add( itemModel );
|
404 |
-
},
|
405 |
-
|
406 |
-
onAddHeadingClick: function( e ) {
|
407 |
-
e.preventDefault();
|
408 |
-
|
409 |
-
var itemID = this.getOptionModelID();
|
410 |
-
var itemModel = new OptionModel( { id: itemID, is_heading: 1 } );
|
411 |
-
this.model.get( 'options' ).add( itemModel );
|
412 |
-
},
|
413 |
-
|
414 |
-
onShowAllOptionsClick: function(e) {
|
415 |
-
var $link = $(e.target);
|
416 |
-
this.$el.find('.happyforms-part-widget--sub').show();
|
417 |
-
$link.hide();
|
418 |
},
|
419 |
|
420 |
onPlaceholderChange: function( model, value ) {
|
@@ -429,92 +142,27 @@
|
|
429 |
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
430 |
},
|
431 |
|
432 |
-
|
433 |
-
|
434 |
-
|
435 |
-
|
436 |
-
|
437 |
-
};
|
438 |
-
|
439 |
-
happyForms.previewSend('happyforms-form-part-refresh', data);
|
440 |
-
} );
|
441 |
-
},
|
442 |
-
|
443 |
-
onImportOptionsClick: function( e ) {
|
444 |
-
e.preventDefault();
|
445 |
-
|
446 |
-
$( '.options', this.$el ).hide();
|
447 |
-
$( '.options-import', this.$el ).show();
|
448 |
-
$( '.links.mode-manual', this.$el ).hide();
|
449 |
-
$( '.links.mode-import', this.$el ).show();
|
450 |
-
$( '.option-import-area', this.$el ).trigger( 'focus' );
|
451 |
-
},
|
452 |
-
|
453 |
-
onAddOptionsClick: function( e ) {
|
454 |
-
e.preventDefault();
|
455 |
-
|
456 |
-
$( '.options', this.$el ).show();
|
457 |
-
$( '.options-import', this.$el ).hide();
|
458 |
-
$( '.links.mode-import', this.$el ).hide();
|
459 |
-
$( '.links.mode-manual', this.$el ).show();
|
460 |
-
$( '.option-import-area', this.$el ).val( '' );
|
461 |
-
},
|
462 |
|
463 |
-
|
464 |
-
e.preventDefault();
|
465 |
-
|
466 |
-
var $textarea = $( '.option-import-area', this.$el );
|
467 |
-
var list = $textarea.val();
|
468 |
-
var self = this;
|
469 |
-
|
470 |
-
var models = list
|
471 |
-
.split( /[\r\n]+/g )
|
472 |
-
.map( function( s ) {
|
473 |
-
return s.trim();
|
474 |
-
} )
|
475 |
-
.filter( function( s ) {
|
476 |
-
return s;
|
477 |
-
} )
|
478 |
-
.forEach( function( label, i, list ) {
|
479 |
-
_.delay( function() {
|
480 |
-
var itemID = self.getOptionModelID();
|
481 |
-
var item = new OptionModel( {
|
482 |
-
id: itemID,
|
483 |
-
label: label
|
484 |
-
} );
|
485 |
-
|
486 |
-
self.model.get( 'options' ).add( item, { refresh: ( list.length - 1 === i ) } );
|
487 |
-
}, i );
|
488 |
-
} );
|
489 |
-
|
490 |
-
$textarea.val( '' );
|
491 |
-
$( '.add-options', this.$el ).trigger( 'click' );
|
492 |
},
|
493 |
|
494 |
-
|
495 |
-
var $otherOptionOptions = $( '.happyforms-nested-settings[data-trigger="other_option"]', this.$el );
|
496 |
-
var model = this.model;
|
497 |
-
|
498 |
-
if ( 1 == value ) {
|
499 |
-
$otherOptionOptions.show();
|
500 |
-
} else {
|
501 |
-
$otherOptionOptions.hide();
|
502 |
-
}
|
503 |
-
|
504 |
this.model.trigger( 'change' );
|
505 |
|
506 |
-
this.
|
507 |
-
|
508 |
-
|
509 |
-
html: response,
|
510 |
-
};
|
511 |
|
512 |
-
|
513 |
-
} );
|
514 |
-
},
|
515 |
|
516 |
-
|
517 |
-
|
|
|
518 |
|
519 |
var model = this.model;
|
520 |
|
@@ -527,45 +175,23 @@
|
|
527 |
happyForms.previewSend( 'happyforms-form-part-refresh', data );
|
528 |
} );
|
529 |
},
|
530 |
-
|
531 |
-
onOtherOptionLabelChange: function() {
|
532 |
-
var data = {
|
533 |
-
id: this.model.get( 'id' ),
|
534 |
-
callback: 'onSelectOtherOptionLabelChangeCallback'
|
535 |
-
};
|
536 |
-
|
537 |
-
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
538 |
-
},
|
539 |
-
|
540 |
-
onOtherOptionPlaceholderChange: function() {
|
541 |
-
var data = {
|
542 |
-
id: this.model.get( 'id' ),
|
543 |
-
callback: 'onSelectOtherOptionPlaceholderChangeCallback'
|
544 |
-
};
|
545 |
-
|
546 |
-
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
547 |
-
},
|
548 |
-
|
549 |
} );
|
550 |
|
551 |
happyForms.previewer = _.extend( happyForms.previewer, {
|
552 |
-
|
|
|
553 |
var $part = this.getPartElement( html );
|
|
|
554 |
|
555 |
-
this.$( '.
|
556 |
},
|
557 |
|
558 |
-
|
559 |
var part = this.getPartModel( id );
|
560 |
var $part = this.getPartElement( html );
|
561 |
var option = part.get( 'options' ).get( options.itemID );
|
562 |
-
var $option = $( '[data-option-id=' + options.itemID + ']', $part );
|
563 |
-
|
564 |
-
$option.text( option.get( 'label' ) );
|
565 |
|
566 |
-
|
567 |
-
$( 'input', $part ).val( option.get( 'label' ) );
|
568 |
-
}
|
569 |
},
|
570 |
|
571 |
onSelectItemDefaultChangeCallback: function( id, html, options, $ ) {
|
@@ -573,52 +199,25 @@
|
|
573 |
var $part = this.getPartElement( html );
|
574 |
var option = part.get( 'options' ).get( options.itemID );
|
575 |
|
576 |
-
|
577 |
|
578 |
-
if (
|
579 |
-
|
580 |
}
|
581 |
},
|
582 |
|
583 |
-
onSelectItemDeleteCallback: function( id, html, options ) {
|
584 |
-
var $part = this.getPartElement( html );
|
585 |
-
var $option = $( '[data-option-id=' + options.itemID + ']', $part );
|
586 |
-
|
587 |
-
$option.remove();
|
588 |
-
},
|
589 |
-
|
590 |
onSelectPlaceholderChangeCallback: function( id, html, options, $ ) {
|
591 |
var $part = this.getPartElement( html );
|
592 |
|
593 |
$( 'select option.happyforms-placeholder-option', $part ).text( options.label );
|
594 |
},
|
595 |
|
596 |
-
|
597 |
-
var part = this.getPartModel( id );
|
598 |
-
var $part = this.getPartElement( html );
|
599 |
-
var $otherOptionLabel = $( '.happyforms-custom-select-dropdown [data-value="999"]', $part );
|
600 |
-
|
601 |
-
$otherOptionLabel.text( part.get( 'other_option_label' ) );
|
602 |
-
$otherOptionLabel.attr( 'data-label', part.get( 'other_option_label' ) );
|
603 |
-
},
|
604 |
-
|
605 |
-
onSelectOtherOptionPlaceholderChangeCallback: function( id, html, options ) {
|
606 |
var part = this.getPartModel( id );
|
607 |
var $part = this.getPartElement( html );
|
608 |
-
var $otherOptionInput = $( '.happyforms-part-option--other input[type=text]', $part );
|
609 |
|
610 |
-
|
611 |
},
|
612 |
-
|
613 |
-
onSelectHeadingLabelChangeCallback: function( id, html, options ) {
|
614 |
-
var part = this.getPartModel( id );
|
615 |
-
var $part = this.getPartElement( html );
|
616 |
-
var option = part.get( 'options' ).get( options.itemID );
|
617 |
-
var $option = $( '#' + options.itemID, $part );
|
618 |
-
|
619 |
-
this.$( 'label.heading-label', $option ).text( option.get( 'label' ) );
|
620 |
-
},
|
621 |
-
|
622 |
} );
|
623 |
|
624 |
} ) ( jQuery, _, Backbone, wp.customize, _happyFormsSettings );
|
35 |
model: OptionModel,
|
36 |
} );
|
37 |
|
38 |
+
var OptionHeadingView = happyForms.classes.views.OptionHeading.extend( {
|
39 |
template: '#customize-happyforms-select-item-heading-template',
|
40 |
|
41 |
+
onLabelChange: function( e ) {
|
42 |
+
var label = $( e.target ).val();
|
43 |
+
this.model.set( 'label', label );
|
44 |
+
this.part.trigger( 'change' );
|
45 |
+
$('.happyforms-item-choice-widget-title h3 .choice-in-widget-title span', this.$el ).text( label );
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
46 |
|
47 |
+
var data = {
|
48 |
+
id: this.part.get( 'id' ),
|
49 |
+
callback: 'onSelectItemHeadingLabelChangeCallback',
|
50 |
+
options: {
|
51 |
+
itemID: this.model.get( 'id' ),
|
52 |
+
}
|
53 |
+
};
|
54 |
|
55 |
+
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
|
|
56 |
},
|
57 |
} );
|
58 |
|
59 |
+
var OptionItemView = happyForms.classes.views.OptionItem.extend( {
|
60 |
template: '#customize-happyforms-select-item-template',
|
61 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
62 |
onItemLabelChange: function( e ) {
|
63 |
+
var label = $( e.target ).val();
|
64 |
+
this.model.set( 'label', label );
|
65 |
+
this.part.trigger( 'change' );
|
66 |
+
$('.happyforms-item-choice-widget-title h3 .choice-in-widget-title span', this.$el ).text( label );
|
67 |
|
68 |
+
var data = {
|
69 |
+
id: this.part.get( 'id' ),
|
70 |
+
callback: 'onSelectItemLabelChangeCallback',
|
71 |
+
options: {
|
72 |
+
itemID: this.model.get( 'id' ),
|
73 |
+
}
|
74 |
+
};
|
75 |
|
76 |
+
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
|
|
77 |
},
|
78 |
|
79 |
onItemDefaultChange: function( e ) {
|
95 |
callback: 'onSelectItemDefaultChangeCallback',
|
96 |
options: {
|
97 |
itemID: this.model.get( 'id' ),
|
98 |
+
checked: isChecked
|
99 |
}
|
100 |
};
|
101 |
|
102 |
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
103 |
},
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
104 |
} );
|
105 |
|
106 |
+
happyForms.classes.views.parts.select = happyForms.classes.views.ChoiceField.extend( {
|
107 |
template: '#customize-happyforms-select-template',
|
108 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
109 |
initialize: function() {
|
110 |
+
happyForms.classes.views.ChoiceField.prototype.initialize.apply( this, arguments );
|
|
|
|
|
111 |
|
112 |
this.listenTo( this.model, 'change:placeholder', this.onPlaceholderChange );
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
113 |
},
|
114 |
|
115 |
+
getOptionItemView: function( optionModel, options ) {
|
116 |
+
var view = new OptionItemView( _.extend( {
|
117 |
+
model: optionModel,
|
118 |
+
part: this.model,
|
119 |
+
}, options ) );
|
120 |
|
121 |
+
return view;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
122 |
},
|
123 |
|
124 |
+
getOptionHeadingView: function( optionModel, options ) {
|
125 |
+
var view = new OptionHeadingView( _.extend( {
|
126 |
+
model: optionModel,
|
127 |
+
part: this.model,
|
128 |
+
}, options ) );
|
129 |
|
130 |
+
return view;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
131 |
},
|
132 |
|
133 |
onPlaceholderChange: function( model, value ) {
|
142 |
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
143 |
},
|
144 |
|
145 |
+
onOtherOptionLabelChange: function() {
|
146 |
+
var data = {
|
147 |
+
id: this.model.get( 'id' ),
|
148 |
+
callback: 'onSelectOtherLabelChangeCallback'
|
149 |
+
};
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
150 |
|
151 |
+
happyForms.previewSend( 'happyforms-part-dom-update', data );
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
152 |
},
|
153 |
|
154 |
+
onOptionModelRemove: function( optionModel ) {
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
155 |
this.model.trigger( 'change' );
|
156 |
|
157 |
+
var optionViewModel = this.optionViews.find( function( viewModel ) {
|
158 |
+
return viewModel.get( 'view' ).model.id === optionModel.id;
|
159 |
+
}, this );
|
|
|
|
|
160 |
|
161 |
+
this.optionViews.remove( optionViewModel );
|
|
|
|
|
162 |
|
163 |
+
if ( this.model.get( 'options' ).length == 0 ) {
|
164 |
+
$( '.options ul', this.$el ).html( '' );
|
165 |
+
}
|
166 |
|
167 |
var model = this.model;
|
168 |
|
175 |
happyForms.previewSend( 'happyforms-form-part-refresh', data );
|
176 |
} );
|
177 |
},
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
178 |
} );
|
179 |
|
180 |
happyForms.previewer = _.extend( happyForms.previewer, {
|
181 |
+
onSelectItemLabelChangeCallback: function( id, html, options ) {
|
182 |
+
var part = this.getPartModel( id );
|
183 |
var $part = this.getPartElement( html );
|
184 |
+
var option = part.get( 'options' ).get( options.itemID );
|
185 |
|
186 |
+
this.$( '#' + options.itemID, $part ).text( option.get( 'label' ) );
|
187 |
},
|
188 |
|
189 |
+
onSelectItemHeadingLabelChangeCallback: function( id, html, options ) {
|
190 |
var part = this.getPartModel( id );
|
191 |
var $part = this.getPartElement( html );
|
192 |
var option = part.get( 'options' ).get( options.itemID );
|
|
|
|
|
|
|
193 |
|
194 |
+
this.$( '#' + options.itemID, $part ).attr( 'label', option.get( 'label' ) );
|
|
|
|
|
195 |
},
|
196 |
|
197 |
onSelectItemDefaultChangeCallback: function( id, html, options, $ ) {
|
199 |
var $part = this.getPartElement( html );
|
200 |
var option = part.get( 'options' ).get( options.itemID );
|
201 |
|
202 |
+
this.$( 'select option', $part ).removeAttr( 'selected' );
|
203 |
|
204 |
+
if ( options.checked ) {
|
205 |
+
this.$( '#' + options.itemID, $part ).prop( 'selected', 'selected' );
|
206 |
}
|
207 |
},
|
208 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
209 |
onSelectPlaceholderChangeCallback: function( id, html, options, $ ) {
|
210 |
var $part = this.getPartElement( html );
|
211 |
|
212 |
$( 'select option.happyforms-placeholder-option', $part ).text( options.label );
|
213 |
},
|
214 |
|
215 |
+
onSelectOtherLabelChangeCallback: function( id, html, options ) {
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
216 |
var part = this.getPartModel( id );
|
217 |
var $part = this.getPartElement( html );
|
|
|
218 |
|
219 |
+
this.$( '.happyforms-select option#other-option', $part ).text( part.get( 'other_option_label' ) );
|
220 |
},
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
221 |
} );
|
222 |
|
223 |
} ) ( jQuery, _, Backbone, wp.customize, _happyFormsSettings );
|
core/classes/class-form-admin.php
CHANGED
@@ -678,6 +678,34 @@ class HappyForms_Form_Admin {
|
|
678 |
}
|
679 |
}
|
680 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
681 |
add_filter( 'get_edit_post_link', array( $this, 'get_edit_post_link' ), 10, 3 );
|
682 |
}
|
683 |
|
678 |
}
|
679 |
}
|
680 |
|
681 |
+
// check if added to templates
|
682 |
+
if ( current_theme_supports( 'block-templates' ) ) {
|
683 |
+
$templates = get_block_templates( array(), 'wp_template' );
|
684 |
+
$template_parts = get_block_templates( array(), 'wp_template_part' );
|
685 |
+
|
686 |
+
$theme_templates = array_merge( $templates, $template_parts );
|
687 |
+
|
688 |
+
foreach ( $theme_templates as $template ) {
|
689 |
+
$edit_url = add_query_arg(
|
690 |
+
array(
|
691 |
+
'postType' => $template->type,
|
692 |
+
'postId' => $template->id,
|
693 |
+
),
|
694 |
+
admin_url( 'site-editor.php' )
|
695 |
+
);
|
696 |
+
|
697 |
+
$link_data = array(
|
698 |
+
'content' => $template->content,
|
699 |
+
'label' => $template->title,
|
700 |
+
'edit_url' => $edit_url,
|
701 |
+
'type' => $template->type,
|
702 |
+
);
|
703 |
+
|
704 |
+
$this->create_added_to_link( $link_data, $regex_block );
|
705 |
+
$this->create_added_to_link( $link_data, $regex_shortcode );
|
706 |
+
}
|
707 |
+
}
|
708 |
+
|
709 |
add_filter( 'get_edit_post_link', array( $this, 'get_edit_post_link' ), 10, 3 );
|
710 |
}
|
711 |
|
core/classes/class-form-controller.php
CHANGED
@@ -564,10 +564,10 @@ class HappyForms_Form_Controller {
|
|
564 |
// Double slash to preserve useful slashes in values
|
565 |
$update_data = wp_slash( $update_data );
|
566 |
|
567 |
-
$
|
568 |
|
569 |
-
if ( is_wp_error( $
|
570 |
-
return $
|
571 |
}
|
572 |
|
573 |
// Update parts
|
@@ -583,16 +583,16 @@ class HappyForms_Form_Controller {
|
|
583 |
if ( ! is_wp_error( $validated_part ) ) {
|
584 |
$part_id = $part_data['id'];
|
585 |
$part_layout[] = $part_id;
|
586 |
-
happyforms_update_meta( $
|
587 |
}
|
588 |
}
|
589 |
|
590 |
-
happyforms_update_meta( $
|
591 |
}
|
592 |
|
593 |
// Cleanup stale parts
|
594 |
-
$part_layout = happyforms_get_meta( $
|
595 |
-
$form_meta = happyforms_unprefix_meta( get_post_meta( $
|
596 |
$form_meta = array_diff_key( $form_meta, $this->get_meta_fields() );
|
597 |
$stale_parts = array_diff_key( $form_meta, array_flip( $part_layout ) );
|
598 |
$part_library = happyforms_get_part_library();
|
@@ -610,17 +610,21 @@ class HappyForms_Form_Controller {
|
|
610 |
$stale_parts = array_keys( $stale_parts );
|
611 |
|
612 |
foreach ( $stale_parts as $part_meta ) {
|
613 |
-
delete_post_meta( $
|
|
|
|
|
|
|
|
|
614 |
}
|
615 |
|
616 |
// Cleanup stale parts array meta
|
617 |
-
delete_post_meta( $
|
618 |
|
619 |
-
$
|
620 |
|
621 |
-
do_action( 'happyforms_form_updated', $
|
622 |
|
623 |
-
return $
|
624 |
}
|
625 |
|
626 |
/**
|
564 |
// Double slash to preserve useful slashes in values
|
565 |
$update_data = wp_slash( $update_data );
|
566 |
|
567 |
+
$form_id = wp_update_post( $update_data, true );
|
568 |
|
569 |
+
if ( is_wp_error( $form_id ) ) {
|
570 |
+
return $form_id;
|
571 |
}
|
572 |
|
573 |
// Update parts
|
583 |
if ( ! is_wp_error( $validated_part ) ) {
|
584 |
$part_id = $part_data['id'];
|
585 |
$part_layout[] = $part_id;
|
586 |
+
happyforms_update_meta( $form_id, $part_id, $validated_part );
|
587 |
}
|
588 |
}
|
589 |
|
590 |
+
happyforms_update_meta( $form_id, 'layout', $part_layout );
|
591 |
}
|
592 |
|
593 |
// Cleanup stale parts
|
594 |
+
$part_layout = happyforms_get_meta( $form_id, 'layout', true );
|
595 |
+
$form_meta = happyforms_unprefix_meta( get_post_meta( $form_id ) );
|
596 |
$form_meta = array_diff_key( $form_meta, $this->get_meta_fields() );
|
597 |
$stale_parts = array_diff_key( $form_meta, array_flip( $part_layout ) );
|
598 |
$part_library = happyforms_get_part_library();
|
610 |
$stale_parts = array_keys( $stale_parts );
|
611 |
|
612 |
foreach ( $stale_parts as $part_meta ) {
|
613 |
+
delete_post_meta( $form_id, $part_meta );
|
614 |
+
}
|
615 |
+
|
616 |
+
if ( ! empty( $stale_parts ) ) {
|
617 |
+
do_action( 'happyforms_stale_fields_deleted', $stale_parts, $form_id );
|
618 |
}
|
619 |
|
620 |
// Cleanup stale parts array meta
|
621 |
+
delete_post_meta( $form_id, '_happyforms_parts' );
|
622 |
|
623 |
+
$form = $this->to_array( get_post( $form_id ) );
|
624 |
|
625 |
+
do_action( 'happyforms_form_updated', $form );
|
626 |
|
627 |
+
return $form;
|
628 |
}
|
629 |
|
630 |
/**
|
core/classes/class-form-email.php
CHANGED
@@ -17,6 +17,7 @@ class HappyForms_Form_Email {
|
|
17 |
public function hook() {
|
18 |
add_filter( 'happyforms_meta_fields', array( $this, 'meta_fields' ) );
|
19 |
add_action( 'happyforms_do_email_control', array( happyforms_get_setup(), 'do_control' ), 10, 3 );
|
|
|
20 |
}
|
21 |
|
22 |
public function get_fields() {
|
@@ -27,6 +28,10 @@ class HappyForms_Form_Email {
|
|
27 |
'default' => 1,
|
28 |
'sanitize' => 'happyforms_sanitize_checkbox'
|
29 |
),
|
|
|
|
|
|
|
|
|
30 |
'email_recipient' => array(
|
31 |
'default' => ( $current_user->user_email ) ? $current_user->user_email : '',
|
32 |
'sanitize' => 'happyforms_sanitize_emails',
|
@@ -47,6 +52,10 @@ class HappyForms_Form_Email {
|
|
47 |
'default' => __( 'You received a new message', 'happyforms' ),
|
48 |
'sanitize' => 'sanitize_text_field',
|
49 |
),
|
|
|
|
|
|
|
|
|
50 |
'send_confirmation_email' => array(
|
51 |
'default' => 1,
|
52 |
'sanitize' => 'happyforms_sanitize_checkbox'
|
@@ -91,16 +100,27 @@ class HappyForms_Form_Email {
|
|
91 |
'type' => 'group_start',
|
92 |
'trigger' => 'receive_email_alerts'
|
93 |
),
|
|
|
94 |
350 => array(
|
95 |
'type' => 'text',
|
96 |
-
'label' => __( '
|
97 |
'field' => 'email_recipient',
|
98 |
),
|
99 |
-
|
100 |
'type' => 'text',
|
101 |
-
'label' => __( '
|
102 |
'field' => 'email_bccs',
|
103 |
),
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
104 |
440 => array(
|
105 |
'type' => 'text',
|
106 |
'label' => __( 'Email display name', 'happyforms' ),
|
@@ -123,12 +143,12 @@ class HappyForms_Form_Email {
|
|
123 |
'type' => 'group_start',
|
124 |
'trigger' => 'send_confirmation_email'
|
125 |
),
|
126 |
-
|
127 |
'type' => 'text',
|
128 |
'label' => __( 'From email address', 'happyforms' ),
|
129 |
'field' => 'confirmation_email_sender_address',
|
130 |
),
|
131 |
-
|
132 |
'type' => 'text',
|
133 |
'label' => __( 'Reply email address', 'happyforms' ),
|
134 |
'field' => 'confirmation_email_reply_to',
|
@@ -165,6 +185,14 @@ class HappyForms_Form_Email {
|
|
165 |
return $controls;
|
166 |
}
|
167 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
168 |
/**
|
169 |
* Filter: add fields to form meta.
|
170 |
*
|
17 |
public function hook() {
|
18 |
add_filter( 'happyforms_meta_fields', array( $this, 'meta_fields' ) );
|
19 |
add_action( 'happyforms_do_email_control', array( happyforms_get_setup(), 'do_control' ), 10, 3 );
|
20 |
+
add_action( 'happyforms_do_email_control', array( $this, 'do_control' ), 10, 3 );
|
21 |
}
|
22 |
|
23 |
public function get_fields() {
|
28 |
'default' => 1,
|
29 |
'sanitize' => 'happyforms_sanitize_checkbox'
|
30 |
),
|
31 |
+
'alert_email_from_address' => array(
|
32 |
+
'default' => ( $current_user->user_email ) ? $current_user->user_email : '',
|
33 |
+
'sanitize' => 'happyforms_sanitize_emails',
|
34 |
+
),
|
35 |
'email_recipient' => array(
|
36 |
'default' => ( $current_user->user_email ) ? $current_user->user_email : '',
|
37 |
'sanitize' => 'happyforms_sanitize_emails',
|
52 |
'default' => __( 'You received a new message', 'happyforms' ),
|
53 |
'sanitize' => 'sanitize_text_field',
|
54 |
),
|
55 |
+
'alert_email_reply_to' => array(
|
56 |
+
'default' => '',
|
57 |
+
'sanitize' => 'sanitize_text_field',
|
58 |
+
),
|
59 |
'send_confirmation_email' => array(
|
60 |
'default' => 1,
|
61 |
'sanitize' => 'happyforms_sanitize_checkbox'
|
100 |
'type' => 'group_start',
|
101 |
'trigger' => 'receive_email_alerts'
|
102 |
),
|
103 |
+
|
104 |
350 => array(
|
105 |
'type' => 'text',
|
106 |
+
'label' => __( 'To email address', 'happyforms' ),
|
107 |
'field' => 'email_recipient',
|
108 |
),
|
109 |
+
351 => array(
|
110 |
'type' => 'text',
|
111 |
+
'label' => __( 'To Bcc email address', 'happyforms' ),
|
112 |
'field' => 'email_bccs',
|
113 |
),
|
114 |
+
352 => array(
|
115 |
+
'type' => 'text',
|
116 |
+
'label' => __( 'From email address', 'happyforms' ),
|
117 |
+
'field' => 'alert_email_from_address',
|
118 |
+
),
|
119 |
+
353 => array(
|
120 |
+
'type' => 'email-parts-list',
|
121 |
+
'label' => __( 'Reply email address', 'happyforms' ),
|
122 |
+
'field' => 'alert_email_reply_to',
|
123 |
+
),
|
124 |
440 => array(
|
125 |
'type' => 'text',
|
126 |
'label' => __( 'Email display name', 'happyforms' ),
|
143 |
'type' => 'group_start',
|
144 |
'trigger' => 'send_confirmation_email'
|
145 |
),
|
146 |
+
631 => array(
|
147 |
'type' => 'text',
|
148 |
'label' => __( 'From email address', 'happyforms' ),
|
149 |
'field' => 'confirmation_email_sender_address',
|
150 |
),
|
151 |
+
632 => array(
|
152 |
'type' => 'text',
|
153 |
'label' => __( 'Reply email address', 'happyforms' ),
|
154 |
'field' => 'confirmation_email_reply_to',
|
185 |
return $controls;
|
186 |
}
|
187 |
|
188 |
+
public function do_control( $control, $field, $index ) {
|
189 |
+
$type = $control['type'];
|
190 |
+
|
191 |
+
if ('email-parts-list' == $type ) {
|
192 |
+
require( happyforms_get_core_folder() . '/templates/customize-controls/email/email-parts-list.php' );
|
193 |
+
}
|
194 |
+
}
|
195 |
+
|
196 |
/**
|
197 |
* Filter: add fields to form meta.
|
198 |
*
|
core/classes/class-form-messages.php
CHANGED
@@ -48,11 +48,11 @@ class HappyForms_Form_Messages {
|
|
48 |
'sanitize' => 'sanitize_text_field',
|
49 |
),
|
50 |
'number_min_invalid' => array(
|
51 |
-
'default' => __( "
|
52 |
'sanitize' => 'sanitize_text_field',
|
53 |
),
|
54 |
'number_max_invalid' => array(
|
55 |
-
'default' => __( '
|
56 |
'sanitize' => 'sanitize_text_field',
|
57 |
),
|
58 |
'optional_part_label' => array(
|
@@ -64,11 +64,11 @@ class HappyForms_Form_Messages {
|
|
64 |
'sanitize' => 'sanitize_text_field'
|
65 |
),
|
66 |
'select_less_choices' => array(
|
67 |
-
'default' => __( '
|
68 |
'sanitize' => 'sanitize_text_field',
|
69 |
),
|
70 |
'select_more_choices' => array(
|
71 |
-
'default' => __( '
|
72 |
'sanitize' => 'sanitize_text_field',
|
73 |
),
|
74 |
'submissions_left_label' => array(
|
48 |
'sanitize' => 'sanitize_text_field',
|
49 |
),
|
50 |
'number_min_invalid' => array(
|
51 |
+
'default' => __( "This number isn't big enough.", 'happyforms' ),
|
52 |
'sanitize' => 'sanitize_text_field',
|
53 |
),
|
54 |
'number_max_invalid' => array(
|
55 |
+
'default' => __( 'This number is too big.', 'happyforms' ),
|
56 |
'sanitize' => 'sanitize_text_field',
|
57 |
),
|
58 |
'optional_part_label' => array(
|
64 |
'sanitize' => 'sanitize_text_field'
|
65 |
),
|
66 |
'select_less_choices' => array(
|
67 |
+
'default' => __( 'Too many choices are selected.', 'happyforms' ),
|
68 |
'sanitize' => 'sanitize_text_field',
|
69 |
),
|
70 |
'select_more_choices' => array(
|
71 |
+
'default' => __( 'Not enough choices are selected.', 'happyforms' ),
|
72 |
'sanitize' => 'sanitize_text_field',
|
73 |
),
|
74 |
'submissions_left_label' => array(
|
core/classes/class-form-option-limiter.php
CHANGED
@@ -200,9 +200,8 @@ class HappyForms_Form_Option_Limiter {
|
|
200 |
|
201 |
public function try_migrate_limit_count_options( $form ) {
|
202 |
$form_id = $form['ID'];
|
203 |
-
$meta_counters = happyforms_get_meta( $form_id, $this->counter_key, true );
|
204 |
|
205 |
-
if ( 0 == $form_id ||
|
206 |
return;
|
207 |
}
|
208 |
|
@@ -245,12 +244,25 @@ class HappyForms_Form_Option_Limiter {
|
|
245 |
|
246 |
$meta_counters = [];
|
247 |
$message_controller = happyforms_get_message_controller();
|
248 |
-
$messages = $message_controller->get_by_form( $form_id );
|
249 |
-
|
250 |
-
foreach( $messages as $message ){
|
251 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
252 |
foreach( $parts_with_limits as $part_name => $part ) {
|
253 |
-
$request_value = $message
|
254 |
|
255 |
if ( ! isset( $request_value[ $part_name ] ) ) {
|
256 |
continue;
|
200 |
|
201 |
public function try_migrate_limit_count_options( $form ) {
|
202 |
$form_id = $form['ID'];
|
|
|
203 |
|
204 |
+
if ( 0 == $form_id || happyforms_meta_exists( $form_id, $this->counter_key ) ) {
|
205 |
return;
|
206 |
}
|
207 |
|
244 |
|
245 |
$meta_counters = [];
|
246 |
$message_controller = happyforms_get_message_controller();
|
|
|
|
|
|
|
247 |
|
248 |
+
global $wpdb;
|
249 |
+
|
250 |
+
$messages = $wpdb->get_results( $wpdb->prepare( "
|
251 |
+
SELECT f.meta_value
|
252 |
+
FROM $wpdb->postmeta f
|
253 |
+
JOIN $wpdb->postmeta p ON f.post_id = p.post_id
|
254 |
+
WHERE p.meta_key = '_happyforms_form_id'
|
255 |
+
AND p.meta_value = %d
|
256 |
+
AND f.meta_key = '_happyforms_request';
|
257 |
+
", $form_id ), ARRAY_A );
|
258 |
+
|
259 |
+
$messages = array_map( function( $message ) {
|
260 |
+
return maybe_unserialize( $message['meta_value'] );
|
261 |
+
}, $messages );
|
262 |
+
|
263 |
+
foreach( $messages as $message ) {
|
264 |
foreach( $parts_with_limits as $part_name => $part ) {
|
265 |
+
$request_value = $message;
|
266 |
|
267 |
if ( ! isset( $request_value[ $part_name ] ) ) {
|
268 |
continue;
|
core/classes/class-form-part-library.php
CHANGED
@@ -144,7 +144,13 @@ class HappyForms_Form_Part_Library {
|
|
144 |
* @return void
|
145 |
*/
|
146 |
public function customize_enqueue_scripts() {
|
147 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
148 |
|
149 |
foreach ( $this->parts as $part ) {
|
150 |
$part->customize_enqueue_scripts( $deps );
|
144 |
* @return void
|
145 |
*/
|
146 |
public function customize_enqueue_scripts() {
|
147 |
+
wp_register_script(
|
148 |
+
'part-field-choice',
|
149 |
+
happyforms_get_plugin_url() . 'core/assets/js/parts/part-field-choice.js',
|
150 |
+
'happyforms-customize', happyforms_get_version(), true
|
151 |
+
);
|
152 |
+
|
153 |
+
$deps = array( 'happyforms-customize', 'part-field-choice' );
|
154 |
|
155 |
foreach ( $this->parts as $part ) {
|
156 |
$part->customize_enqueue_scripts( $deps );
|
core/classes/class-validation-messages.php
CHANGED
@@ -103,23 +103,23 @@ class HappyForms_Validation_Messages {
|
|
103 |
|
104 |
$fields = array(
|
105 |
'field_invalid' => array(
|
106 |
-
'default' => __( "
|
107 |
'sanitize' => 'sanitize_text_field',
|
108 |
),
|
109 |
'field_empty' => array(
|
110 |
-
'default' => __( '
|
111 |
'sanitize' => 'sanitize_text_field',
|
112 |
),
|
113 |
'no_selection' => array(
|
114 |
-
'default' => __( '
|
115 |
'sanitize' => 'sanitize_text_field',
|
116 |
),
|
117 |
'message_too_long' => array(
|
118 |
-
'default' => __( '
|
119 |
'sanitize' => 'sanitize_text_field',
|
120 |
),
|
121 |
'message_too_short' => array(
|
122 |
-
'default' => __( "
|
123 |
'sanitize' => 'sanitize_text_field',
|
124 |
),
|
125 |
// TODO remove this field once deprecated global messages is fully removed
|
103 |
|
104 |
$fields = array(
|
105 |
'field_invalid' => array(
|
106 |
+
'default' => __( "Looks like there's a mistake here.", 'happyforms' ),
|
107 |
'sanitize' => 'sanitize_text_field',
|
108 |
),
|
109 |
'field_empty' => array(
|
110 |
+
'default' => __( 'Please answer this question.', 'happyforms' ),
|
111 |
'sanitize' => 'sanitize_text_field',
|
112 |
),
|
113 |
'no_selection' => array(
|
114 |
+
'default' => __( 'Please make a selection.', 'happyforms' ),
|
115 |
'sanitize' => 'sanitize_text_field',
|
116 |
),
|
117 |
'message_too_long' => array(
|
118 |
+
'default' => __( 'This answer is too long.', 'happyforms' ),
|
119 |
'sanitize' => 'sanitize_text_field',
|
120 |
),
|
121 |
'message_too_short' => array(
|
122 |
+
'default' => __( "This answer isn't long enough.", 'happyforms' ),
|
123 |
'sanitize' => 'sanitize_text_field',
|
124 |
),
|
125 |
// TODO remove this field once deprecated global messages is fully removed
|
core/templates/customize-controls/email/email-parts-list.php
ADDED
@@ -0,0 +1,17 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<div class="customize-control" id="customize-control-<?php echo $control['field']; ?>">
|
2 |
+
<?php do_action( "happyforms_setup_control_{$control['field']}_before", $control ); ?>
|
3 |
+
|
4 |
+
<label for="<?php echo $control['field']; ?>" class="customize-control-title"><?php echo $control['label']; ?></label>
|
5 |
+
<select id="<?php echo $control['field']; ?>" data-attribute="<?php echo $control['field']; ?>">
|
6 |
+
<%
|
7 |
+
var options = _( parts ).where( { type: 'email' } );
|
8 |
+
|
9 |
+
options.forEach( function( option ) { %>
|
10 |
+
<option value="<%= option.id %>"<%= ( option.id === <?php echo $control['field']; ?> ) ? ' selected' : '' %>>"<%= option.label %>" <?php _e( 'field', 'happyforms' ); ?></option>
|
11 |
+
<% } ); %>
|
12 |
+
|
13 |
+
<option value="all"<%= ( 'all' === <?php echo $control['field']; ?> ) ? ' selected' : '' %>><?php _e( 'All Email fields', 'happyforms' ); ?></option>
|
14 |
+
</select>
|
15 |
+
|
16 |
+
<?php do_action( "happyforms_setup_control_{$control['field']}_after", $control ); ?>
|
17 |
+
</div>
|
core/templates/parts/customize-checkbox.php
CHANGED
@@ -26,7 +26,7 @@
|
|
26 |
<div class="options">
|
27 |
<ul class="option-list"></ul>
|
28 |
<h3><?php _e( 'Choices', 'happyforms' ); ?></h3>
|
29 |
-
<p class="no-options description"><?php _e( '
|
30 |
</div>
|
31 |
<div class="options-import">
|
32 |
<h3><?php _e( 'Choices', 'happyforms' ); ?></h3>
|
@@ -35,15 +35,6 @@
|
|
35 |
<p class="links mode-manual">
|
36 |
<a href="#" class="button add-heading"><?php _e( 'Add heading', 'happyforms' ); ?></a>
|
37 |
<a href="#" class="button add-option centered"><?php _e( 'Add choice', 'happyforms' ); ?></a>
|
38 |
-
<span class="centered">
|
39 |
-
<a href="#" class="import-options"><?php _e( 'Or, bulk add choices', 'happyforms' ); ?></a>
|
40 |
-
</span>
|
41 |
-
</p>
|
42 |
-
<p class="links mode-import">
|
43 |
-
<a href="#" class="button import-option"><?php _e( 'Add choices', 'happyforms' ); ?></a>
|
44 |
-
<span class="centered">
|
45 |
-
<a href="#" class="add-options"><?php _e( 'Cancel', 'happyforms' ); ?></a>
|
46 |
-
</span>
|
47 |
</p>
|
48 |
|
49 |
<?php do_action( 'happyforms_part_customize_checkbox_after_options' ); ?>
|
@@ -124,14 +115,25 @@
|
|
124 |
<?php happyforms_customize_part_footer(); ?>
|
125 |
</script>
|
126 |
<script type="text/template" id="customize-happyforms-checkbox-item-template">
|
127 |
-
<li data-option-id="<%= id %>">
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
128 |
<div class="happyforms-part-item-body">
|
129 |
-
<div class="happyforms-part-item-handle"></div>
|
130 |
-
<label>
|
131 |
-
<?php _e( 'Label', 'happyforms' ); ?>:
|
132 |
-
<input type="text" class="widefat" name="label" value="<%= label %>">
|
133 |
-
</label>
|
134 |
<div class="happyforms-part-item-advanced">
|
|
|
|
|
|
|
|
|
|
|
|
|
135 |
<p>
|
136 |
<label>
|
137 |
<?php _e( 'Hint', 'happyforms' ); ?>:
|
@@ -149,24 +151,38 @@
|
|
149 |
<input type="checkbox" name="is_default" value="1" <% if (is_default == 1) { %> checked="checked"<% } %>> <?php _e( 'Make this choice default', 'happyforms' ); ?>
|
150 |
</label>
|
151 |
</p>
|
152 |
-
|
153 |
-
|
154 |
-
|
155 |
-
|
156 |
</div>
|
157 |
</div>
|
158 |
</li>
|
159 |
</script>
|
160 |
<script type="text/template" id="customize-happyforms-checkbox-item-heading-template">
|
161 |
-
<li data-option-id="<%= id %>" data-is-heading="yes">
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
162 |
<div class="happyforms-part-item-body">
|
163 |
-
<div class="happyforms-part-item-
|
164 |
-
|
165 |
-
|
166 |
-
|
167 |
-
|
168 |
-
|
169 |
-
|
|
|
|
|
|
|
|
|
170 |
</div>
|
171 |
</div>
|
172 |
</li>
|
26 |
<div class="options">
|
27 |
<ul class="option-list"></ul>
|
28 |
<h3><?php _e( 'Choices', 'happyforms' ); ?></h3>
|
29 |
+
<p class="no-options description"><?php _e( 'It doesn\'t look like your field has any choices yet. Want to add one? Click the "Add Choice" button to start.', 'happyforms' ); ?></p>
|
30 |
</div>
|
31 |
<div class="options-import">
|
32 |
<h3><?php _e( 'Choices', 'happyforms' ); ?></h3>
|
35 |
<p class="links mode-manual">
|
36 |
<a href="#" class="button add-heading"><?php _e( 'Add heading', 'happyforms' ); ?></a>
|
37 |
<a href="#" class="button add-option centered"><?php _e( 'Add choice', 'happyforms' ); ?></a>
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
38 |
</p>
|
39 |
|
40 |
<?php do_action( 'happyforms_part_customize_checkbox_after_options' ); ?>
|
115 |
<?php happyforms_customize_part_footer(); ?>
|
116 |
</script>
|
117 |
<script type="text/template" id="customize-happyforms-checkbox-item-template">
|
118 |
+
<li data-option-id="<%= id %>" class="happyforms-choice-item-widget">
|
119 |
+
<div class="happyforms-part-item-handle">
|
120 |
+
<div class="happyforms-part-item-advanced-option">
|
121 |
+
<button type="button" class="happyforms-advanced-option-action">
|
122 |
+
<span class="toggle-indicator"></span>
|
123 |
+
</button>
|
124 |
+
</div>
|
125 |
+
<div class="happyforms-item-choice-widget-title">
|
126 |
+
<h3><?php _e( 'Choice', 'happyforms' ); ?><span class="choice-in-widget-title">: <span><%= label %></span></span></h3>
|
127 |
+
</div>
|
128 |
+
</div>
|
129 |
<div class="happyforms-part-item-body">
|
|
|
|
|
|
|
|
|
|
|
130 |
<div class="happyforms-part-item-advanced">
|
131 |
+
<p>
|
132 |
+
<label>
|
133 |
+
<?php _e( 'Label', 'happyforms' ); ?>:
|
134 |
+
<input type="text" class="widefat" name="label" value="<%= label %>" data-option-attribute="label">
|
135 |
+
</label>
|
136 |
+
</p>
|
137 |
<p>
|
138 |
<label>
|
139 |
<?php _e( 'Hint', 'happyforms' ); ?>:
|
151 |
<input type="checkbox" name="is_default" value="1" <% if (is_default == 1) { %> checked="checked"<% } %>> <?php _e( 'Make this choice default', 'happyforms' ); ?>
|
152 |
</label>
|
153 |
</p>
|
154 |
+
<div class="option-actions">
|
155 |
+
<a href="#" class="happyforms-delete-item"><?php _e( 'Delete', 'happyforms' ); ?></a> |
|
156 |
+
<a href="#" class="happyforms-duplicate-item"><?php _e( 'Duplicate', 'happyforms' ); ?></a>
|
157 |
+
</div>
|
158 |
</div>
|
159 |
</div>
|
160 |
</li>
|
161 |
</script>
|
162 |
<script type="text/template" id="customize-happyforms-checkbox-item-heading-template">
|
163 |
+
<li data-option-id="<%= id %>" class="happyforms-choice-item-widget" data-is-heading="yes">
|
164 |
+
<div class="happyforms-part-item-handle">
|
165 |
+
<div class="happyforms-part-item-advanced-option">
|
166 |
+
<button type="button" class="happyforms-advanced-option-action">
|
167 |
+
<span class="toggle-indicator"></span>
|
168 |
+
</button>
|
169 |
+
</div>
|
170 |
+
<div class="happyforms-item-choice-widget-title">
|
171 |
+
<h3><?php _e( 'Heading', 'happyforms' ); ?><span class="choice-in-widget-title">: <span><%= label %></span></span></h3>
|
172 |
+
</div>
|
173 |
+
</div>
|
174 |
<div class="happyforms-part-item-body">
|
175 |
+
<div class="happyforms-part-item-advanced">
|
176 |
+
<p>
|
177 |
+
<label>
|
178 |
+
<?php _e( 'Label', 'happyforms' ); ?>:
|
179 |
+
<input type="text" class="widefat" name="label" value="<%= label %>" data-option-attribute="label">
|
180 |
+
</label>
|
181 |
+
</p>
|
182 |
+
<div class="option-actions">
|
183 |
+
<a href="#" class="happyforms-delete-item"><?php _e( 'Delete', 'happyforms' ); ?></a> |
|
184 |
+
<a href="#" class="happyforms-duplicate-item"><?php _e( 'Duplicate', 'happyforms' ); ?></a>
|
185 |
+
</div>
|
186 |
</div>
|
187 |
</div>
|
188 |
</li>
|
core/templates/parts/customize-radio.php
CHANGED
@@ -26,24 +26,12 @@
|
|
26 |
<div class="options">
|
27 |
<ul class="option-list"></ul>
|
28 |
<h3><?php _e( 'Choices', 'happyforms' ); ?></h3>
|
29 |
-
<p class="no-options description"><?php _e( '
|
30 |
-
|
31 |
-
<div class="options-import">
|
32 |
-
<h3><?php _e( 'Choices', 'happyforms' ); ?></h3>
|
33 |
-
<textarea class="option-import-area" cols="30" rows="10" placeholder="<?php _e( 'Type or paste your choices here, adding each on a new line.' ); ?>"></textarea>
|
34 |
</div>
|
35 |
<p class="links mode-manual">
|
36 |
<a href="#" class="button add-heading"><?php _e( 'Add heading', 'happyforms' ); ?></a>
|
37 |
<a href="#" class="button add-option centered"><?php _e( 'Add choice', 'happyforms' ); ?></a>
|
38 |
-
<span class="centered">
|
39 |
-
<a href="#" class="import-options"><?php _e( 'Or, bulk add choices', 'happyforms' ); ?></a>
|
40 |
-
</span>
|
41 |
-
</p>
|
42 |
-
<p class="links mode-import">
|
43 |
-
<a href="#" class="button import-option"><?php _e( 'Add choices', 'happyforms' ); ?></a>
|
44 |
-
<span class="centered">
|
45 |
-
<a href="#" class="add-options"><?php _e( 'Cancel', 'happyforms' ); ?></a>
|
46 |
-
</span>
|
47 |
</p>
|
48 |
|
49 |
<?php do_action( 'happyforms_part_customize_radio_after_options' ); ?>
|
@@ -109,14 +97,25 @@
|
|
109 |
<?php happyforms_customize_part_footer(); ?>
|
110 |
</script>
|
111 |
<script type="text/template" id="customize-happyforms-radio-item-template">
|
112 |
-
<li data-option-id="<%= id %>">
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
113 |
<div class="happyforms-part-item-body">
|
114 |
-
<div class="happyforms-part-item-handle"></div>
|
115 |
-
<label>
|
116 |
-
<?php _e( 'Label', 'happyforms' ); ?>:
|
117 |
-
<input type="text" class="widefat" name="label" value="<%= label %>" data-option-attribute="label">
|
118 |
-
</label>
|
119 |
<div class="happyforms-part-item-advanced">
|
|
|
|
|
|
|
|
|
|
|
|
|
120 |
<p>
|
121 |
<label>
|
122 |
<?php _e( 'Hint', 'happyforms' ); ?>:
|
@@ -134,24 +133,38 @@
|
|
134 |
<input type="checkbox" name="is_default" value="1" class="default-option-switch"<% if (is_default == 1) { %> checked="checked"<% } %>> <?php _e( 'Make this choice default', 'happyforms' ); ?>
|
135 |
</label>
|
136 |
</p>
|
137 |
-
|
138 |
-
|
139 |
-
|
140 |
-
|
141 |
</div>
|
142 |
</div>
|
143 |
</li>
|
144 |
</script>
|
145 |
<script type="text/template" id="customize-happyforms-radio-item-heading-template">
|
146 |
-
<li data-option-id="<%= id %>" data-is-heading="yes">
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
147 |
<div class="happyforms-part-item-body">
|
148 |
-
<div class="happyforms-part-item-
|
149 |
-
|
150 |
-
|
151 |
-
|
152 |
-
|
153 |
-
|
154 |
-
|
|
|
|
|
|
|
|
|
155 |
</div>
|
156 |
</div>
|
157 |
</li>
|
26 |
<div class="options">
|
27 |
<ul class="option-list"></ul>
|
28 |
<h3><?php _e( 'Choices', 'happyforms' ); ?></h3>
|
29 |
+
<p class="no-options description"><?php _e( 'It doesn\'t look like your field has any choices yet. Want to add one?
|
30 |
+
Click the "Add Choice" button to start.', 'happyforms' ); ?></p>
|
|
|
|
|
|
|
31 |
</div>
|
32 |
<p class="links mode-manual">
|
33 |
<a href="#" class="button add-heading"><?php _e( 'Add heading', 'happyforms' ); ?></a>
|
34 |
<a href="#" class="button add-option centered"><?php _e( 'Add choice', 'happyforms' ); ?></a>
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
35 |
</p>
|
36 |
|
37 |
<?php do_action( 'happyforms_part_customize_radio_after_options' ); ?>
|
97 |
<?php happyforms_customize_part_footer(); ?>
|
98 |
</script>
|
99 |
<script type="text/template" id="customize-happyforms-radio-item-template">
|
100 |
+
<li data-option-id="<%= id %>" class="happyforms-choice-item-widget">
|
101 |
+
<div class="happyforms-part-item-handle">
|
102 |
+
<div class="happyforms-part-item-advanced-option">
|
103 |
+
<button type="button" class="happyforms-advanced-option-action">
|
104 |
+
<span class="toggle-indicator"></span>
|
105 |
+
</button>
|
106 |
+
</div>
|
107 |
+
<div class="happyforms-item-choice-widget-title">
|
108 |
+
<h3><?php _e( 'Choice', 'happyforms' ); ?><span class="choice-in-widget-title">: <span><%= label %></span></span></h3>
|
109 |
+
</div>
|
110 |
+
</div>
|
111 |
<div class="happyforms-part-item-body">
|
|
|
|
|
|
|
|
|
|
|
112 |
<div class="happyforms-part-item-advanced">
|
113 |
+
<p>
|
114 |
+
<label>
|
115 |
+
<?php _e( 'Label', 'happyforms' ); ?>:
|
116 |
+
<input type="text" class="widefat" name="label" value="<%= label %>" data-option-attribute="label">
|
117 |
+
</label>
|
118 |
+
</p>
|
119 |
<p>
|
120 |
<label>
|
121 |
<?php _e( 'Hint', 'happyforms' ); ?>:
|
133 |
<input type="checkbox" name="is_default" value="1" class="default-option-switch"<% if (is_default == 1) { %> checked="checked"<% } %>> <?php _e( 'Make this choice default', 'happyforms' ); ?>
|
134 |
</label>
|
135 |
</p>
|
136 |
+
<div class="option-actions">
|
137 |
+
<a href="#" class="happyforms-delete-item"><?php _e( 'Delete', 'happyforms' ); ?></a> |
|
138 |
+
<a href="#" class="happyforms-duplicate-item"><?php _e( 'Duplicate', 'happyforms' ); ?></a>
|
139 |
+
</div>
|
140 |
</div>
|
141 |
</div>
|
142 |
</li>
|
143 |
</script>
|
144 |
<script type="text/template" id="customize-happyforms-radio-item-heading-template">
|
145 |
+
<li data-option-id="<%= id %>" class="happyforms-choice-item-widget" data-is-heading="yes">
|
146 |
+
<div class="happyforms-part-item-handle">
|
147 |
+
<div class="happyforms-part-item-advanced-option">
|
148 |
+
<button type="button" class="happyforms-advanced-option-action">
|
149 |
+
<span class="toggle-indicator"></span>
|
150 |
+
</button>
|
151 |
+
</div>
|
152 |
+
<div class="happyforms-item-choice-widget-title">
|
153 |
+
<h3><?php _e( 'Heading', 'happyforms' ); ?><span class="choice-in-widget-title">: <span><%= label %></span></span></h3>
|
154 |
+
</div>
|
155 |
+
</div>
|
156 |
<div class="happyforms-part-item-body">
|
157 |
+
<div class="happyforms-part-item-advanced">
|
158 |
+
<p>
|
159 |
+
<label>
|
160 |
+
<?php _e( 'Label', 'happyforms' ); ?>:
|
161 |
+
<input type="text" class="widefat" name="label" value="<%= label %>" data-option-attribute="label">
|
162 |
+
</label>
|
163 |
+
</p>
|
164 |
+
<div class="option-actions">
|
165 |
+
<a href="#" class="happyforms-delete-item"><?php _e( 'Delete', 'happyforms' ); ?></a> |
|
166 |
+
<a href="#" class="happyforms-duplicate-item"><?php _e( 'Duplicate', 'happyforms' ); ?></a>
|
167 |
+
</div>
|
168 |
</div>
|
169 |
</div>
|
170 |
</li>
|
core/templates/parts/customize-select.php
CHANGED
@@ -30,24 +30,11 @@
|
|
30 |
<div class="options">
|
31 |
<ul class="option-list"></ul>
|
32 |
<h3><?php _e( 'Choices', 'happyforms' ); ?></h3>
|
33 |
-
<p class="no-options description"><?php _e( '
|
34 |
-
</div>
|
35 |
-
<div class="options-import">
|
36 |
-
<h3><?php _e( 'Choices', 'happyforms' ); ?></h3>
|
37 |
-
<textarea class="option-import-area" cols="30" rows="10" placeholder="<?php _e( 'Type or paste your choices here, adding each on a new line.' ); ?>"></textarea>
|
38 |
</div>
|
39 |
<p class="links mode-manual">
|
40 |
<a href="#" class="button add-heading"><?php _e( 'Add heading', 'happyforms' ); ?></a>
|
41 |
<a href="#" class="button add-option centered"><?php _e( 'Add choice', 'happyforms' ); ?></a>
|
42 |
-
<span class="centered">
|
43 |
-
<a href="#" class="import-options"><?php _e( 'Or, bulk add choices', 'happyforms' ); ?></a>
|
44 |
-
</span>
|
45 |
-
</p>
|
46 |
-
<p class="links mode-import">
|
47 |
-
<a href="#" class="button import-option"><?php _e( 'Add choices', 'happyforms' ); ?></a>
|
48 |
-
<span class="centered">
|
49 |
-
<a href="#" class="add-options"><?php _e( 'Cancel', 'happyforms' ); ?></a>
|
50 |
-
</span>
|
51 |
</p>
|
52 |
|
53 |
<% if ( instance.other_option ) { %>
|
@@ -101,14 +88,25 @@
|
|
101 |
<?php happyforms_customize_part_footer(); ?>
|
102 |
</script>
|
103 |
<script type="text/template" id="customize-happyforms-select-item-template">
|
104 |
-
<li data-option-id="<%= id %>">
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
105 |
<div class="happyforms-part-item-body">
|
106 |
-
<div class="happyforms-part-item-handle"></div>
|
107 |
-
<label>
|
108 |
-
<?php _e( 'Label', 'happyforms' ); ?>:
|
109 |
-
<input type="text" class="widefat" name="label" value="<%= label %>" data-option-attribute="label">
|
110 |
-
</label>
|
111 |
<div class="happyforms-part-item-advanced">
|
|
|
|
|
|
|
|
|
|
|
|
|
112 |
<p>
|
113 |
<label>
|
114 |
<?php _e( 'Max number of submissions', 'happyforms' ); ?>:
|
@@ -120,24 +118,38 @@
|
|
120 |
<input type="checkbox" name="is_default" value="1" class="default-option-switch"<% if (is_default == 1) { %> checked="checked"<% } %>> <?php _e( 'Make this choice default', 'happyforms' ); ?>
|
121 |
</label>
|
122 |
</p>
|
123 |
-
|
124 |
-
|
125 |
-
|
126 |
-
|
127 |
</div>
|
128 |
</div>
|
129 |
</li>
|
130 |
</script>
|
131 |
<script type="text/template" id="customize-happyforms-select-item-heading-template">
|
132 |
-
<li data-option-id="<%= id %>" data-is-heading="yes">
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
133 |
<div class="happyforms-part-item-body">
|
134 |
-
<div class="happyforms-part-item-
|
135 |
-
|
136 |
-
|
137 |
-
|
138 |
-
|
139 |
-
|
140 |
-
|
|
|
|
|
|
|
|
|
141 |
</div>
|
142 |
</div>
|
143 |
</li>
|
30 |
<div class="options">
|
31 |
<ul class="option-list"></ul>
|
32 |
<h3><?php _e( 'Choices', 'happyforms' ); ?></h3>
|
33 |
+
<p class="no-options description"><?php _e( 'It doesn\'t look like your field has any choices yet. Want to add one? Click the "Add Choice" button to start.', 'happyforms' ); ?></p>
|
|
|
|
|
|
|
|
|
34 |
</div>
|
35 |
<p class="links mode-manual">
|
36 |
<a href="#" class="button add-heading"><?php _e( 'Add heading', 'happyforms' ); ?></a>
|
37 |
<a href="#" class="button add-option centered"><?php _e( 'Add choice', 'happyforms' ); ?></a>
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
38 |
</p>
|
39 |
|
40 |
<% if ( instance.other_option ) { %>
|
88 |
<?php happyforms_customize_part_footer(); ?>
|
89 |
</script>
|
90 |
<script type="text/template" id="customize-happyforms-select-item-template">
|
91 |
+
<li data-option-id="<%= id %>" class="happyforms-choice-item-widget">
|
92 |
+
<div class="happyforms-part-item-handle">
|
93 |
+
<div class="happyforms-part-item-advanced-option">
|
94 |
+
<button type="button" class="happyforms-advanced-option-action">
|
95 |
+
<span class="toggle-indicator"></span>
|
96 |
+
</button>
|
97 |
+
</div>
|
98 |
+
<div class="happyforms-item-choice-widget-title">
|
99 |
+
<h3><?php _e( 'Choice', 'happyforms' ); ?><span class="choice-in-widget-title">: <span><%= label %></span></span></h3>
|
100 |
+
</div>
|
101 |
+
</div>
|
102 |
<div class="happyforms-part-item-body">
|
|
|
|
|
|
|
|
|
|
|
103 |
<div class="happyforms-part-item-advanced">
|
104 |
+
<p>
|
105 |
+
<label>
|
106 |
+
<?php _e( 'Label', 'happyforms' ); ?>:
|
107 |
+
<input type="text" class="widefat" name="label" value="<%= label %>" data-option-attribute="label">
|
108 |
+
</label>
|
109 |
+
</p>
|
110 |
<p>
|
111 |
<label>
|
112 |
<?php _e( 'Max number of submissions', 'happyforms' ); ?>:
|
118 |
<input type="checkbox" name="is_default" value="1" class="default-option-switch"<% if (is_default == 1) { %> checked="checked"<% } %>> <?php _e( 'Make this choice default', 'happyforms' ); ?>
|
119 |
</label>
|
120 |
</p>
|
121 |
+
<div class="option-actions">
|
122 |
+
<a href="#" class="happyforms-delete-item"><?php _e( 'Delete', 'happyforms' ); ?></a> |
|
123 |
+
<a href="#" class="happyforms-duplicate-item"><?php _e( 'Duplicate', 'happyforms' ); ?></a>
|
124 |
+
</div>
|
125 |
</div>
|
126 |
</div>
|
127 |
</li>
|
128 |
</script>
|
129 |
<script type="text/template" id="customize-happyforms-select-item-heading-template">
|
130 |
+
<li data-option-id="<%= id %>" class="happyforms-choice-item-widget" data-is-heading="yes">
|
131 |
+
<div class="happyforms-part-item-handle">
|
132 |
+
<div class="happyforms-part-item-advanced-option">
|
133 |
+
<button type="button" class="happyforms-advanced-option-action">
|
134 |
+
<span class="toggle-indicator"></span>
|
135 |
+
</button>
|
136 |
+
</div>
|
137 |
+
<div class="happyforms-item-choice-widget-title">
|
138 |
+
<h3><?php _e( 'Heading', 'happyforms' ); ?><span class="choice-in-widget-title">: <span><%= label %></span></span></h3>
|
139 |
+
</div>
|
140 |
+
</div>
|
141 |
<div class="happyforms-part-item-body">
|
142 |
+
<div class="happyforms-part-item-advanced">
|
143 |
+
<p>
|
144 |
+
<label>
|
145 |
+
<?php _e( 'Label', 'happyforms' ); ?>:
|
146 |
+
<input type="text" class="widefat" name="label" value="<%= label %>" data-option-attribute="label">
|
147 |
+
</label>
|
148 |
+
</p>
|
149 |
+
<div class="option-actions">
|
150 |
+
<a href="#" class="happyforms-delete-item"><?php _e( 'Delete', 'happyforms' ); ?></a> |
|
151 |
+
<a href="#" class="happyforms-duplicate-item"><?php _e( 'Duplicate', 'happyforms' ); ?></a>
|
152 |
+
</div>
|
153 |
</div>
|
154 |
</div>
|
155 |
</li>
|
core/templates/parts/frontend-select.php
CHANGED
@@ -29,13 +29,6 @@
|
|
29 |
<div class="happyforms-part__select-wrap">
|
30 |
<?php
|
31 |
$other_select = ( !empty( $part['other_option'] ) ) ? $part['other_option_label'] : '';
|
32 |
-
|
33 |
-
if ( !empty( $other_select ) ) {
|
34 |
-
$options[] = array(
|
35 |
-
'value' => 999,
|
36 |
-
'label' => $other_select,
|
37 |
-
);
|
38 |
-
}
|
39 |
?>
|
40 |
<select name="<?php happyforms_the_part_name( $part, $form ); ?>" data-serialize class='happyforms-select' required>
|
41 |
<option disabled hidden <?php echo ( $value === '' ) ? ' selected' : ''; ?> value='' class="happyforms-placeholder-option"><?php echo $placeholder_text; ?></option>
|
@@ -46,7 +39,7 @@
|
|
46 |
if ( $is_grouped ) : ?>
|
47 |
</optgroup>
|
48 |
<?php endif; ?>
|
49 |
-
<optgroup label="<?php echo esc_attr( $option['label'] ); ?>">
|
50 |
<?php
|
51 |
$is_grouped = true;
|
52 |
continue;
|
@@ -57,11 +50,14 @@
|
|
57 |
$selected = ( $value != '' && $value == $option_value ) ? ' selected' : '';
|
58 |
$disabled = ( '' != $option['limit_submissions_amount'] && $option['submissions_left'] == 0 ) ? ' disabled' : '';
|
59 |
?>
|
60 |
-
<option value="<?php echo $option_value; ?>" <?php echo $selected; ?> <?php echo $disabled;
|
61 |
<?php endforeach; ?>
|
62 |
<?php if ( $is_grouped ) : ?>
|
63 |
</optgroup>
|
64 |
<?php endif; ?>
|
|
|
|
|
|
|
65 |
</select>
|
66 |
</div>
|
67 |
</div>
|
29 |
<div class="happyforms-part__select-wrap">
|
30 |
<?php
|
31 |
$other_select = ( !empty( $part['other_option'] ) ) ? $part['other_option_label'] : '';
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
32 |
?>
|
33 |
<select name="<?php happyforms_the_part_name( $part, $form ); ?>" data-serialize class='happyforms-select' required>
|
34 |
<option disabled hidden <?php echo ( $value === '' ) ? ' selected' : ''; ?> value='' class="happyforms-placeholder-option"><?php echo $placeholder_text; ?></option>
|
39 |
if ( $is_grouped ) : ?>
|
40 |
</optgroup>
|
41 |
<?php endif; ?>
|
42 |
+
<optgroup label="<?php echo esc_attr( $option['label'] ); ?>" id="<?php echo esc_attr( $option['id'] ); ?>">
|
43 |
<?php
|
44 |
$is_grouped = true;
|
45 |
continue;
|
50 |
$selected = ( $value != '' && $value == $option_value ) ? ' selected' : '';
|
51 |
$disabled = ( '' != $option['limit_submissions_amount'] && $option['submissions_left'] == 0 ) ? ' disabled' : '';
|
52 |
?>
|
53 |
+
<option value="<?php echo $option_value; ?>" <?php echo $selected; ?> <?php echo $disabled; ?> id="<?php echo esc_attr( $option['id'] ); ?>"><?php echo esc_attr( $option['label'] ); ?><?php echo $submissions_left_label; ?></option>
|
54 |
<?php endforeach; ?>
|
55 |
<?php if ( $is_grouped ) : ?>
|
56 |
</optgroup>
|
57 |
<?php endif; ?>
|
58 |
+
<?php if ( !empty( $other_select ) ) : ?>
|
59 |
+
<option id="other-option" value="<?php echo '999';?>"><?php echo $other_select; ?></option>
|
60 |
+
<?php endif; ?>
|
61 |
</select>
|
62 |
</div>
|
63 |
</div>
|
happyforms.php
CHANGED
@@ -5,7 +5,7 @@
|
|
5 |
* Plugin URI: https://happyforms.io
|
6 |
* Description: We're changin' WordPress forms.
|
7 |
* Author: Happyforms
|
8 |
-
* Version: 1.15.
|
9 |
* Author URI: https://happyforms.io
|
10 |
* Upgrade URI: https://happyforms.io/upgrade
|
11 |
*/
|
@@ -22,7 +22,7 @@ if ( defined( 'HAPPYFORMS_UPGRADE_VERSION' ) ) {
|
|
22 |
/**
|
23 |
* The current version of the plugin.
|
24 |
*/
|
25 |
-
define( 'HAPPYFORMS_VERSION', '1.15.
|
26 |
|
27 |
if ( ! function_exists( 'happyforms_get_version' ) ):
|
28 |
|
5 |
* Plugin URI: https://happyforms.io
|
6 |
* Description: We're changin' WordPress forms.
|
7 |
* Author: Happyforms
|
8 |
+
* Version: 1.15.4
|
9 |
* Author URI: https://happyforms.io
|
10 |
* Upgrade URI: https://happyforms.io/upgrade
|
11 |
*/
|
22 |
/**
|
23 |
* The current version of the plugin.
|
24 |
*/
|
25 |
+
define( 'HAPPYFORMS_VERSION', '1.15.4' );
|
26 |
|
27 |
if ( ! function_exists( 'happyforms_get_version' ) ):
|
28 |
|
inc/assets/js/customize.js
CHANGED
@@ -1707,7 +1707,6 @@
|
|
1707 |
'change [data-attribute="characters_label_max"]': 'onCharLimitMaxCharsChange',
|
1708 |
'keyup [data-attribute="no_results_label"]': 'onNoResultsLabelChange',
|
1709 |
'change [data-attribute="no_results_label"]': 'onNoResultsLabelChange',
|
1710 |
-
'keyup [data-attribute="submissions_left_label"]': 'onSubmissionsLeftLabelChange',
|
1711 |
'click [data-reset]': 'resetDefaultMessage',
|
1712 |
'keyup input[data-attribute]': 'onMessageValueChange',
|
1713 |
} ),
|
@@ -1717,6 +1716,10 @@
|
|
1717 |
|
1718 |
initialize: function() {
|
1719 |
classes.views.Base.prototype.initialize.apply( this, arguments );
|
|
|
|
|
|
|
|
|
1720 |
},
|
1721 |
|
1722 |
render: function() {
|
@@ -1918,17 +1921,19 @@
|
|
1918 |
|
1919 |
|
1920 |
var partsWithLimitedOptions = happyForms.form.get( 'parts' ).filter( function( part ) {
|
1921 |
-
|
1922 |
-
|
1923 |
-
|
1924 |
-
|
1925 |
-
|
1926 |
-
|
1927 |
-
|
1928 |
-
|
|
|
|
|
|
|
|
|
1929 |
return hasLimitedOptions;
|
1930 |
-
}
|
1931 |
-
return false;
|
1932 |
} );
|
1933 |
|
1934 |
if ( partsWithLimitedOptions.length ) {
|
@@ -2012,6 +2017,30 @@
|
|
2012 |
};
|
2013 |
|
2014 |
happyForms.previewSend( 'happyforms-form-dom-update', data );
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2015 |
},
|
2016 |
} );
|
2017 |
|
1707 |
'change [data-attribute="characters_label_max"]': 'onCharLimitMaxCharsChange',
|
1708 |
'keyup [data-attribute="no_results_label"]': 'onNoResultsLabelChange',
|
1709 |
'change [data-attribute="no_results_label"]': 'onNoResultsLabelChange',
|
|
|
1710 |
'click [data-reset]': 'resetDefaultMessage',
|
1711 |
'keyup input[data-attribute]': 'onMessageValueChange',
|
1712 |
} ),
|
1716 |
|
1717 |
initialize: function() {
|
1718 |
classes.views.Base.prototype.initialize.apply( this, arguments );
|
1719 |
+
|
1720 |
+
this.listenTo( this.model, 'change:submissions_left_label', _.debounce( function( model, value ) {
|
1721 |
+
this.onSubmissionsLeftLabelChange( model, value );
|
1722 |
+
}, 800 ) );
|
1723 |
},
|
1724 |
|
1725 |
render: function() {
|
1921 |
|
1922 |
|
1923 |
var partsWithLimitedOptions = happyForms.form.get( 'parts' ).filter( function( part ) {
|
1924 |
+
var hasOptions = [ 'radio', 'checkbox', 'select' ].includes( part.get( 'type' ) );
|
1925 |
+
|
1926 |
+
if ( ! hasOptions ) {
|
1927 |
+
return false;
|
1928 |
+
}
|
1929 |
+
|
1930 |
+
var hasLimitedOptions = part.get( 'options' ).find( function( option ) {
|
1931 |
+
var limitSubmissionAmount = option.get( 'limit_submissions_amount' );
|
1932 |
+
|
1933 |
+
return typeof limitSubmissionAmount !== 'undefined' && limitSubmissionAmount != '';
|
1934 |
+
} );
|
1935 |
+
|
1936 |
return hasLimitedOptions;
|
|
|
|
|
1937 |
} );
|
1938 |
|
1939 |
if ( partsWithLimitedOptions.length ) {
|
2017 |
};
|
2018 |
|
2019 |
happyForms.previewSend( 'happyforms-form-dom-update', data );
|
2020 |
+
|
2021 |
+
var dropdowns = happyForms.form.get( 'parts' ).filter( function( part ) {
|
2022 |
+
if ( 'select' != part.get( 'type' ) ) {
|
2023 |
+
return false;
|
2024 |
+
}
|
2025 |
+
|
2026 |
+
var hasLimitedOptions = part.get( 'options' ).find( function( option ) {
|
2027 |
+
var limitSubmissionAmount = option.get( 'limit_submissions_amount' );
|
2028 |
+
return typeof limitSubmissionAmount !== 'undefined' && limitSubmissionAmount != '';
|
2029 |
+
} );
|
2030 |
+
|
2031 |
+
return hasLimitedOptions;
|
2032 |
+
} );
|
2033 |
+
|
2034 |
+
dropdowns.forEach( function( dropdown ) {
|
2035 |
+
dropdown.fetchHtml( function( response ) {
|
2036 |
+
var data = {
|
2037 |
+
id: dropdown.get( 'id' ),
|
2038 |
+
html: response,
|
2039 |
+
};
|
2040 |
+
|
2041 |
+
happyForms.previewSend( 'happyforms-form-part-refresh', data );
|
2042 |
+
} );
|
2043 |
+
} );
|
2044 |
},
|
2045 |
} );
|
2046 |
|
inc/classes/class-happyforms.php
CHANGED
@@ -172,7 +172,7 @@ class HappyForms extends HappyForms_Core {
|
|
172 |
'label' => __( 'Include referral web address', 'happyforms' ),
|
173 |
);
|
174 |
|
175 |
-
$controls[
|
176 |
'type' => 'email-parts-list_dummy',
|
177 |
'dummy_id' => 'confirmation_email_respondent_address',
|
178 |
'label' => __( 'To email address', 'happyforms' ),
|
172 |
'label' => __( 'Include referral web address', 'happyforms' ),
|
173 |
);
|
174 |
|
175 |
+
$controls[630] = array(
|
176 |
'type' => 'email-parts-list_dummy',
|
177 |
'dummy_id' => 'confirmation_email_respondent_address',
|
178 |
'label' => __( 'To email address', 'happyforms' ),
|
inc/classes/class-message-controller.php
CHANGED
@@ -385,6 +385,10 @@ class HappyForms_Message_Controller {
|
|
385 |
$name = $form['alert_email_from_name'];
|
386 |
$to = explode( ',', $form['email_recipient'] );
|
387 |
|
|
|
|
|
|
|
|
|
388 |
$email_message->set_from_name( $name );
|
389 |
$email_message->set_to( $to[0] );
|
390 |
|
@@ -400,11 +404,33 @@ class HappyForms_Message_Controller {
|
|
400 |
|
401 |
$email_message->set_subject( $subject );
|
402 |
|
403 |
-
$
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
404 |
|
405 |
-
if ( false !== $email_part ) {
|
406 |
-
$email_part_id = $email_part['id'];
|
407 |
-
$reply_to = happyforms_get_message_part_value( $message[$email_part_id], $email_part );
|
408 |
$email_message->set_reply_to( $reply_to );
|
409 |
}
|
410 |
|
385 |
$name = $form['alert_email_from_name'];
|
386 |
$to = explode( ',', $form['email_recipient'] );
|
387 |
|
388 |
+
$from_address = happyforms_get_form_property( $form, 'alert_email_from_address' );
|
389 |
+
$from_address = explode( ',', $from_address );
|
390 |
+
|
391 |
+
$email_message->set_from( $from_address[0] );
|
392 |
$email_message->set_from_name( $name );
|
393 |
$email_message->set_to( $to[0] );
|
394 |
|
404 |
|
405 |
$email_message->set_subject( $subject );
|
406 |
|
407 |
+
$email_reply_to_id = happyforms_get_form_property( $form, 'alert_email_reply_to' );
|
408 |
+
$email_reply_parts = array();
|
409 |
+
|
410 |
+
if ( 'all' === $email_reply_to_id ) {
|
411 |
+
$email_reply_parts = happyforms_get_form_controller()->get_parts_by_type( $form, 'email' );
|
412 |
+
} else {
|
413 |
+
$email_part = happyforms_get_form_controller()->get_part_by_id( $form, $email_reply_to_id );
|
414 |
+
|
415 |
+
if ( ! $email_part ) {
|
416 |
+
$email_part = happyforms_get_form_controller()->get_first_part_by_type( $form, 'email' );
|
417 |
+
}
|
418 |
+
|
419 |
+
if ( $email_part ) {
|
420 |
+
$email_reply_parts[] = $email_part;
|
421 |
+
}
|
422 |
+
}
|
423 |
+
|
424 |
+
if ( ! empty( $email_reply_parts ) ) {
|
425 |
+
$reply_to = array_map( function( $email_part ) use( $message ) {
|
426 |
+
$part_id = $email_part['id'];
|
427 |
+
$part_value = happyforms_get_message_part_value( $message[$part_id], $email_part );
|
428 |
+
|
429 |
+
return $part_value;
|
430 |
+
}, $email_reply_parts );
|
431 |
+
|
432 |
+
$reply_to = array_values( array_filter( array_map( 'trim', $reply_to ) ) );
|
433 |
|
|
|
|
|
|
|
434 |
$email_message->set_reply_to( $reply_to );
|
435 |
}
|
436 |
|
inc/templates/customize-controls/email-parts-list-dummy.php
CHANGED
@@ -1,5 +1,5 @@
|
|
1 |
<div class="customize-control customize-control-email-parts-list_dummy" id="customize-control-<?php echo $control['dummy_id']; ?>">
|
2 |
-
<label for="<?php echo $control['dummy_id']; ?>" class="customize-control-title"><?php echo $control['label'];
|
3 |
<select id="<?php echo $control['dummy_id']; ?>">
|
4 |
<%
|
5 |
var options = _( parts ).where( { type: 'email' } );
|
1 |
<div class="customize-control customize-control-email-parts-list_dummy" id="customize-control-<?php echo $control['dummy_id']; ?>">
|
2 |
+
<label for="<?php echo $control['dummy_id']; ?>" class="customize-control-title"><?php echo $control['label']; ?></label> <span class="members-only"><?php _e( 'Members Only', 'happyforms') ?></span>
|
3 |
<select id="<?php echo $control['dummy_id']; ?>">
|
4 |
<%
|
5 |
var options = _( parts ).where( { type: 'email' } );
|
languages/happyforms.pot
CHANGED
@@ -2,16 +2,16 @@
|
|
2 |
# This file is distributed under the same license as the Happyforms (free) plugin.
|
3 |
msgid ""
|
4 |
msgstr ""
|
5 |
-
"Project-Id-Version: Happyforms (free) 1.15.
|
6 |
"Report-Msgid-Bugs-To: https://wordpress.org/support/plugin/happyforms/\n"
|
7 |
"Last-Translator: The Theme Foundry\n"
|
8 |
"Language-Team: The Theme Foundry\n"
|
9 |
"MIME-Version: 1.0\n"
|
10 |
"Content-Type: text/plain; charset=UTF-8\n"
|
11 |
"Content-Transfer-Encoding: 8bit\n"
|
12 |
-
"POT-Creation-Date: 2022-
|
13 |
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
|
14 |
-
"X-Generator: WP-CLI 2.
|
15 |
"X-Domain: happyforms\n"
|
16 |
|
17 |
#. Plugin Name of the plugin
|
@@ -80,6 +80,12 @@ msgstr ""
|
|
80 |
#: core/classes/class-form-admin.php:454
|
81 |
#: core/templates/customize-form-item.php:27
|
82 |
#: core/templates/customize-form-part-footer.php:4
|
|
|
|
|
|
|
|
|
|
|
|
|
83 |
msgid "Duplicate"
|
84 |
msgstr ""
|
85 |
|
@@ -129,7 +135,6 @@ msgstr ""
|
|
129 |
|
130 |
#: core/classes/class-form-controller.php:82
|
131 |
#: core/assets/jsx/build/admin/block.js:144
|
132 |
-
#: core/assets/jsx/src/admin/block.js:32
|
133 |
msgid "No forms found."
|
134 |
msgstr ""
|
135 |
|
@@ -148,63 +153,64 @@ msgstr ""
|
|
148 |
msgid "(no title)"
|
149 |
msgstr ""
|
150 |
|
151 |
-
#: core/classes/class-form-controller.php:
|
152 |
msgid " Copy"
|
153 |
msgstr ""
|
154 |
|
155 |
-
#: core/classes/class-form-email.php:
|
156 |
msgid "You received a new message"
|
157 |
msgstr ""
|
158 |
|
159 |
-
#: core/classes/class-form-email.php:
|
160 |
msgid "We received your message"
|
161 |
msgstr ""
|
162 |
|
163 |
-
#: core/classes/class-form-email.php:
|
164 |
msgid "Your message has been successfully sent. We appreciate you contacting us and we’ll be in touch soon."
|
165 |
msgstr ""
|
166 |
|
167 |
-
#: core/classes/class-form-email.php:
|
168 |
msgid "Email me a copy of each submission"
|
169 |
msgstr ""
|
170 |
|
171 |
-
#: core/classes/class-form-email.php:
|
172 |
-
#: inc/
|
173 |
-
|
174 |
-
msgid "Email address"
|
175 |
msgstr ""
|
176 |
|
177 |
-
#: core/classes/class-form-email.php:
|
178 |
-
msgid "
|
179 |
msgstr ""
|
180 |
|
181 |
-
#: core/classes/class-form-email.php:
|
182 |
-
#: core/classes/class-form-email.php:
|
183 |
-
msgid "
|
184 |
msgstr ""
|
185 |
|
186 |
-
#: core/classes/class-form-email.php:
|
187 |
-
#: core/classes/class-form-email.php:
|
188 |
-
msgid "
|
189 |
msgstr ""
|
190 |
|
191 |
-
#: core/classes/class-form-email.php:
|
192 |
-
|
|
|
193 |
msgstr ""
|
194 |
|
195 |
-
#: core/classes/class-form-email.php:
|
196 |
-
|
|
|
197 |
msgstr ""
|
198 |
|
199 |
-
#: core/classes/class-form-email.php:
|
200 |
-
msgid "
|
201 |
msgstr ""
|
202 |
|
203 |
-
#: core/classes/class-form-email.php:
|
204 |
msgid "Email content"
|
205 |
msgstr ""
|
206 |
|
207 |
-
#: core/classes/class-form-email.php:
|
208 |
msgid "Include submitted values"
|
209 |
msgstr ""
|
210 |
|
@@ -235,11 +241,11 @@ msgid "Nothing found"
|
|
235 |
msgstr ""
|
236 |
|
237 |
#: core/classes/class-form-messages.php:51
|
238 |
-
msgid "
|
239 |
msgstr ""
|
240 |
|
241 |
#: core/classes/class-form-messages.php:55
|
242 |
-
msgid "
|
243 |
msgstr ""
|
244 |
|
245 |
#: core/classes/class-form-messages.php:59
|
@@ -247,11 +253,11 @@ msgid "(optional)"
|
|
247 |
msgstr ""
|
248 |
|
249 |
#: core/classes/class-form-messages.php:67
|
250 |
-
msgid "
|
251 |
msgstr ""
|
252 |
|
253 |
#: core/classes/class-form-messages.php:71
|
254 |
-
msgid "
|
255 |
msgstr ""
|
256 |
|
257 |
#: core/classes/class-form-messages.php:75
|
@@ -338,7 +344,7 @@ msgstr ""
|
|
338 |
msgid "Remaining submissions"
|
339 |
msgstr ""
|
340 |
|
341 |
-
#: core/classes/class-form-part-library.php:
|
342 |
msgid "Missing validation callback for field %s"
|
343 |
msgstr ""
|
344 |
|
@@ -685,14 +691,17 @@ msgstr ""
|
|
685 |
|
686 |
#: core/classes/class-form-styles.php:716
|
687 |
#: core/templates/parts/customize-checkbox.php:4
|
688 |
-
#: core/templates/parts/customize-checkbox.php:
|
|
|
689 |
#: core/templates/parts/customize-email.php:4
|
690 |
#: core/templates/parts/customize-multi-line-text.php:4
|
691 |
#: core/templates/parts/customize-number.php:4
|
692 |
#: core/templates/parts/customize-radio.php:4
|
693 |
-
#: core/templates/parts/customize-radio.php:
|
|
|
694 |
#: core/templates/parts/customize-select.php:4
|
695 |
-
#: core/templates/parts/customize-select.php:
|
|
|
696 |
#: core/templates/parts/customize-single-line-text.php:4
|
697 |
msgid "Label"
|
698 |
msgstr ""
|
@@ -712,12 +721,12 @@ msgstr ""
|
|
712 |
|
713 |
#: core/classes/class-form-styles.php:731
|
714 |
#: core/templates/parts/customize-checkbox.php:20
|
715 |
-
#: core/templates/parts/customize-checkbox.php:
|
716 |
#: core/templates/parts/customize-email.php:28
|
717 |
#: core/templates/parts/customize-multi-line-text.php:28
|
718 |
#: core/templates/parts/customize-number.php:28
|
719 |
#: core/templates/parts/customize-radio.php:20
|
720 |
-
#: core/templates/parts/customize-radio.php:
|
721 |
#: core/templates/parts/customize-select.php:24
|
722 |
#: core/templates/parts/customize-single-line-text.php:28
|
723 |
msgid "Hint"
|
@@ -824,8 +833,8 @@ msgstr ""
|
|
824 |
|
825 |
#: core/classes/class-happyforms-core.php:210
|
826 |
#: core/classes/class-happyforms-core.php:211
|
827 |
-
#: inc/classes/class-message-controller.php:
|
828 |
-
#: inc/classes/class-message-controller.php:
|
829 |
msgid "Activity"
|
830 |
msgstr ""
|
831 |
|
@@ -838,7 +847,6 @@ msgstr ""
|
|
838 |
#: core/classes/class-happyforms-core.php:228
|
839 |
#: core/classes/class-happyforms-core.php:229
|
840 |
#: core/assets/jsx/build/admin/block.js:173
|
841 |
-
#: core/assets/jsx/src/admin/block.js:61
|
842 |
msgid "Settings"
|
843 |
msgstr ""
|
844 |
|
@@ -875,23 +883,23 @@ msgid "Not enough words/characters typed"
|
|
875 |
msgstr ""
|
876 |
|
877 |
#: core/classes/class-validation-messages.php:106
|
878 |
-
msgid "
|
879 |
msgstr ""
|
880 |
|
881 |
#: core/classes/class-validation-messages.php:110
|
882 |
-
msgid "
|
883 |
msgstr ""
|
884 |
|
885 |
#: core/classes/class-validation-messages.php:114
|
886 |
-
msgid "
|
887 |
msgstr ""
|
888 |
|
889 |
#: core/classes/class-validation-messages.php:118
|
890 |
-
msgid "
|
891 |
msgstr ""
|
892 |
|
893 |
#: core/classes/class-validation-messages.php:122
|
894 |
-
msgid "
|
895 |
msgstr ""
|
896 |
|
897 |
#: core/classes/class-wp-customize-form-manager.php:162
|
@@ -2631,10 +2639,18 @@ msgstr ""
|
|
2631 |
|
2632 |
#: core/templates/admin-form-modal.php:12
|
2633 |
#: core/assets/jsx/build/admin/block.js:158
|
2634 |
-
#: core/assets/jsx/src/admin/block.js:41
|
2635 |
msgid "Insert"
|
2636 |
msgstr ""
|
2637 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2638 |
#: core/templates/customize-controls/messages/text.php:7
|
2639 |
msgid "Reset"
|
2640 |
msgstr ""
|
@@ -2691,12 +2707,12 @@ msgstr ""
|
|
2691 |
|
2692 |
#: core/templates/customize-form-item.php:33
|
2693 |
#: core/templates/customize-form-part-footer.php:3
|
2694 |
-
#: core/templates/parts/customize-checkbox.php:
|
2695 |
-
#: core/templates/parts/customize-checkbox.php:
|
2696 |
-
#: core/templates/parts/customize-radio.php:
|
2697 |
-
#: core/templates/parts/customize-radio.php:
|
2698 |
-
#: core/templates/parts/customize-select.php:
|
2699 |
-
#: core/templates/parts/customize-select.php:
|
2700 |
msgid "Delete"
|
2701 |
msgstr ""
|
2702 |
|
@@ -2784,138 +2800,117 @@ msgstr ""
|
|
2784 |
#: core/templates/parts/customize-checkbox.php:28
|
2785 |
#: core/templates/parts/customize-checkbox.php:32
|
2786 |
#: core/templates/parts/customize-radio.php:28
|
2787 |
-
#: core/templates/parts/customize-radio.php:32
|
2788 |
#: core/templates/parts/customize-select.php:32
|
2789 |
-
#: core/templates/parts/customize-select.php:36
|
2790 |
msgid "Choices"
|
2791 |
msgstr ""
|
2792 |
|
2793 |
#: core/templates/parts/customize-checkbox.php:29
|
2794 |
-
#: core/templates/parts/customize-radio.php:29
|
2795 |
#: core/templates/parts/customize-select.php:33
|
2796 |
-
msgid "
|
2797 |
msgstr ""
|
2798 |
|
2799 |
#: core/templates/parts/customize-checkbox.php:36
|
2800 |
-
#: core/templates/parts/customize-radio.php:
|
2801 |
-
#: core/templates/parts/customize-select.php:
|
2802 |
msgid "Add heading"
|
2803 |
msgstr ""
|
2804 |
|
2805 |
#: core/templates/parts/customize-checkbox.php:37
|
2806 |
-
#: core/templates/parts/customize-radio.php:
|
2807 |
-
#: core/templates/parts/customize-select.php:
|
2808 |
msgid "Add choice"
|
2809 |
msgstr ""
|
2810 |
|
2811 |
-
#: core/templates/parts/customize-checkbox.php:
|
2812 |
-
#: core/templates/parts/customize-radio.php:
|
2813 |
#: core/templates/parts/customize-select.php:43
|
2814 |
-
msgid "Or, bulk add choices"
|
2815 |
-
msgstr ""
|
2816 |
-
|
2817 |
-
#: core/templates/parts/customize-checkbox.php:43
|
2818 |
-
#: core/templates/parts/customize-radio.php:43
|
2819 |
-
#: core/templates/parts/customize-select.php:47
|
2820 |
-
msgid "Add choices"
|
2821 |
-
msgstr ""
|
2822 |
-
|
2823 |
-
#: core/templates/parts/customize-checkbox.php:45
|
2824 |
-
#: core/templates/parts/customize-radio.php:45
|
2825 |
-
#: core/templates/parts/customize-select.php:49
|
2826 |
-
msgid "Cancel"
|
2827 |
-
msgstr ""
|
2828 |
-
|
2829 |
-
#: core/templates/parts/customize-checkbox.php:56
|
2830 |
-
#: core/templates/parts/customize-radio.php:56
|
2831 |
-
#: core/templates/parts/customize-select.php:56
|
2832 |
msgid "Add 'other' choice"
|
2833 |
msgstr ""
|
2834 |
|
2835 |
-
#: core/templates/parts/customize-checkbox.php:
|
2836 |
-
#: core/templates/parts/customize-radio.php:
|
2837 |
-
#: core/templates/parts/customize-select.php:
|
2838 |
msgid "'Other' label"
|
2839 |
msgstr ""
|
2840 |
|
2841 |
-
#: core/templates/parts/customize-checkbox.php:
|
2842 |
-
#: core/templates/parts/customize-radio.php:
|
2843 |
-
#: core/templates/parts/customize-select.php:
|
2844 |
msgid "'Other' placeholder"
|
2845 |
msgstr ""
|
2846 |
|
2847 |
-
#: core/templates/parts/customize-checkbox.php:
|
2848 |
-
#: core/templates/parts/customize-radio.php:
|
2849 |
-
#: core/templates/parts/customize-select.php:
|
2850 |
msgid "Shuffle order of choices"
|
2851 |
msgstr ""
|
2852 |
|
2853 |
-
#: core/templates/parts/customize-checkbox.php:
|
2854 |
msgid "Limit choices"
|
2855 |
msgstr ""
|
2856 |
|
2857 |
-
#: core/templates/parts/customize-checkbox.php:
|
2858 |
msgid "Min choices"
|
2859 |
msgstr ""
|
2860 |
|
2861 |
-
#: core/templates/parts/customize-checkbox.php:
|
2862 |
msgid "Max choices"
|
2863 |
msgstr ""
|
2864 |
|
2865 |
-
#: core/templates/parts/customize-checkbox.php:
|
2866 |
-
#: core/templates/parts/customize-radio.php:
|
2867 |
msgid "Align choices"
|
2868 |
msgstr ""
|
2869 |
|
2870 |
-
#: core/templates/parts/customize-checkbox.php:
|
2871 |
-
#: core/templates/parts/customize-radio.php:
|
2872 |
msgid "Vertically"
|
2873 |
msgstr ""
|
2874 |
|
2875 |
-
#: core/templates/parts/customize-checkbox.php:
|
2876 |
-
#: core/templates/parts/customize-radio.php:
|
2877 |
msgid "Horizontally"
|
2878 |
msgstr ""
|
2879 |
|
2880 |
-
#: core/templates/parts/customize-checkbox.php:
|
2881 |
#: core/templates/parts/customize-email.php:48
|
2882 |
#: core/templates/parts/customize-multi-line-text.php:61
|
2883 |
#: core/templates/parts/customize-number.php:76
|
2884 |
-
#: core/templates/parts/customize-radio.php:
|
2885 |
-
#: core/templates/parts/customize-select.php:
|
2886 |
#: core/templates/parts/customize-single-line-text.php:47
|
2887 |
msgid "Require an answer"
|
2888 |
msgstr ""
|
2889 |
|
2890 |
-
#: core/templates/parts/customize-checkbox.php:
|
2891 |
#: core/templates/parts/customize-email.php:57
|
2892 |
#: core/templates/parts/customize-multi-line-text.php:70
|
2893 |
#: core/templates/parts/customize-number.php:83
|
2894 |
-
#: core/templates/parts/customize-radio.php:
|
2895 |
-
#: core/templates/parts/customize-select.php:
|
2896 |
#: core/templates/parts/customize-single-line-text.php:56
|
2897 |
msgid "Additional CSS class(es)"
|
2898 |
msgstr ""
|
2899 |
|
2900 |
-
#: core/templates/parts/customize-checkbox.php:
|
2901 |
-
|
|
|
|
|
2902 |
msgstr ""
|
2903 |
|
2904 |
-
#: core/templates/parts/customize-checkbox.php:
|
2905 |
-
|
2906 |
-
#: core/templates/parts/customize-select.php:120
|
2907 |
-
msgid "Make this choice default"
|
2908 |
msgstr ""
|
2909 |
|
2910 |
-
#: core/templates/parts/customize-checkbox.php:
|
2911 |
-
#: core/templates/parts/customize-radio.php:
|
2912 |
-
#: core/templates/parts/customize-select.php:
|
2913 |
-
msgid "
|
2914 |
msgstr ""
|
2915 |
|
2916 |
-
#: core/templates/parts/customize-checkbox.php:
|
2917 |
-
#: core/templates/parts/customize-radio.php:
|
2918 |
-
#: core/templates/parts/customize-select.php:
|
2919 |
#: inc/classes/parts/class-part-layout-title-dummy.php:8
|
2920 |
msgid "Heading"
|
2921 |
msgstr ""
|
@@ -2975,8 +2970,14 @@ msgstr ""
|
|
2975 |
msgid "Decimal"
|
2976 |
msgstr ""
|
2977 |
|
2978 |
-
#: core/templates/parts/customize-radio.php:
|
2979 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
2980 |
#: inc/classes/class-happyforms.php:138
|
2981 |
msgid "Max number of submissions"
|
2982 |
msgstr ""
|
@@ -3033,10 +3034,6 @@ msgstr ""
|
|
3033 |
msgid "Include referral web address"
|
3034 |
msgstr ""
|
3035 |
|
3036 |
-
#: inc/classes/class-happyforms.php:178
|
3037 |
-
msgid "To email address"
|
3038 |
-
msgstr ""
|
3039 |
-
|
3040 |
#: inc/classes/class-happyforms.php:184
|
3041 |
msgid "Send abandonment email"
|
3042 |
msgstr ""
|
@@ -3069,12 +3066,12 @@ msgstr ""
|
|
3069 |
msgid "Spam"
|
3070 |
msgstr ""
|
3071 |
|
3072 |
-
#: inc/classes/class-message-controller.php:
|
3073 |
-
#: inc/classes/class-message-controller.php:
|
3074 |
msgid "All Activity"
|
3075 |
msgstr ""
|
3076 |
|
3077 |
-
#: inc/classes/class-message-controller.php:
|
3078 |
msgid "No activity found."
|
3079 |
msgstr ""
|
3080 |
|
@@ -3226,10 +3223,6 @@ msgstr ""
|
|
3226 |
msgid "For formatted site URLs."
|
3227 |
msgstr ""
|
3228 |
|
3229 |
-
#: inc/templates/customize-controls/email-parts-list-dummy.php:8
|
3230 |
-
msgid "field"
|
3231 |
-
msgstr ""
|
3232 |
-
|
3233 |
#: integrations/classes/class-integrations-page-controller.php:26
|
3234 |
msgid "ActiveCampaign"
|
3235 |
msgstr ""
|
@@ -3468,22 +3461,18 @@ msgid "Publishable key"
|
|
3468 |
msgstr ""
|
3469 |
|
3470 |
#: core/assets/jsx/build/admin/block.js:127
|
3471 |
-
#: core/assets/jsx/src/admin/block.js:15
|
3472 |
msgid "Choose"
|
3473 |
msgstr ""
|
3474 |
|
3475 |
#: core/assets/jsx/build/admin/block.js:144
|
3476 |
-
#: core/assets/jsx/src/admin/block.js:27
|
3477 |
msgid "The form previously added has been trashed or deleted."
|
3478 |
msgstr ""
|
3479 |
|
3480 |
#: core/assets/jsx/build/admin/block.js:144
|
3481 |
-
#: core/assets/jsx/src/admin/block.js:31
|
3482 |
msgid "Pick a form to display on your site."
|
3483 |
msgstr ""
|
3484 |
|
3485 |
#: core/assets/jsx/build/admin/block.js:175
|
3486 |
-
#: core/assets/jsx/src/admin/block.js:63
|
3487 |
msgid "Pick a form"
|
3488 |
msgstr ""
|
3489 |
|
@@ -3497,6 +3486,11 @@ msgstr ""
|
|
3497 |
msgid "We'll occasionally send you emails about plugin updates. And don't sweat it, you can unsubscribe anytime."
|
3498 |
msgstr ""
|
3499 |
|
|
|
|
|
|
|
|
|
|
|
3500 |
#: inc/assets/jsx/build/admin/dashboard-modals.js:223
|
3501 |
#: inc/assets/jsx/src/admin/dashboard-modals.js:54
|
3502 |
msgid "Continue"
|
2 |
# This file is distributed under the same license as the Happyforms (free) plugin.
|
3 |
msgid ""
|
4 |
msgstr ""
|
5 |
+
"Project-Id-Version: Happyforms (free) 1.15.4\n"
|
6 |
"Report-Msgid-Bugs-To: https://wordpress.org/support/plugin/happyforms/\n"
|
7 |
"Last-Translator: The Theme Foundry\n"
|
8 |
"Language-Team: The Theme Foundry\n"
|
9 |
"MIME-Version: 1.0\n"
|
10 |
"Content-Type: text/plain; charset=UTF-8\n"
|
11 |
"Content-Transfer-Encoding: 8bit\n"
|
12 |
+
"POT-Creation-Date: 2022-06-13T07:21:30+00:00\n"
|
13 |
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
|
14 |
+
"X-Generator: WP-CLI 2.4.0\n"
|
15 |
"X-Domain: happyforms\n"
|
16 |
|
17 |
#. Plugin Name of the plugin
|
80 |
#: core/classes/class-form-admin.php:454
|
81 |
#: core/templates/customize-form-item.php:27
|
82 |
#: core/templates/customize-form-part-footer.php:4
|
83 |
+
#: core/templates/parts/customize-checkbox.php:156
|
84 |
+
#: core/templates/parts/customize-checkbox.php:184
|
85 |
+
#: core/templates/parts/customize-radio.php:138
|
86 |
+
#: core/templates/parts/customize-radio.php:166
|
87 |
+
#: core/templates/parts/customize-select.php:123
|
88 |
+
#: core/templates/parts/customize-select.php:151
|
89 |
msgid "Duplicate"
|
90 |
msgstr ""
|
91 |
|
135 |
|
136 |
#: core/classes/class-form-controller.php:82
|
137 |
#: core/assets/jsx/build/admin/block.js:144
|
|
|
138 |
msgid "No forms found."
|
139 |
msgstr ""
|
140 |
|
153 |
msgid "(no title)"
|
154 |
msgstr ""
|
155 |
|
156 |
+
#: core/classes/class-form-controller.php:644
|
157 |
msgid " Copy"
|
158 |
msgstr ""
|
159 |
|
160 |
+
#: core/classes/class-form-email.php:52
|
161 |
msgid "You received a new message"
|
162 |
msgstr ""
|
163 |
|
164 |
+
#: core/classes/class-form-email.php:76
|
165 |
msgid "We received your message"
|
166 |
msgstr ""
|
167 |
|
168 |
+
#: core/classes/class-form-email.php:80
|
169 |
msgid "Your message has been successfully sent. We appreciate you contacting us and we’ll be in touch soon."
|
170 |
msgstr ""
|
171 |
|
172 |
+
#: core/classes/class-form-email.php:96
|
173 |
msgid "Email me a copy of each submission"
|
174 |
msgstr ""
|
175 |
|
176 |
+
#: core/classes/class-form-email.php:106
|
177 |
+
#: inc/classes/class-happyforms.php:178
|
178 |
+
msgid "To email address"
|
|
|
179 |
msgstr ""
|
180 |
|
181 |
+
#: core/classes/class-form-email.php:111
|
182 |
+
msgid "To Bcc email address"
|
183 |
msgstr ""
|
184 |
|
185 |
+
#: core/classes/class-form-email.php:116
|
186 |
+
#: core/classes/class-form-email.php:148
|
187 |
+
msgid "From email address"
|
188 |
msgstr ""
|
189 |
|
190 |
+
#: core/classes/class-form-email.php:121
|
191 |
+
#: core/classes/class-form-email.php:153
|
192 |
+
msgid "Reply email address"
|
193 |
msgstr ""
|
194 |
|
195 |
+
#: core/classes/class-form-email.php:126
|
196 |
+
#: core/classes/class-form-email.php:158
|
197 |
+
msgid "Email display name"
|
198 |
msgstr ""
|
199 |
|
200 |
+
#: core/classes/class-form-email.php:131
|
201 |
+
#: core/classes/class-form-email.php:163
|
202 |
+
msgid "Email subject"
|
203 |
msgstr ""
|
204 |
|
205 |
+
#: core/classes/class-form-email.php:139
|
206 |
+
msgid "Email respondent a copy of their submission"
|
207 |
msgstr ""
|
208 |
|
209 |
+
#: core/classes/class-form-email.php:168
|
210 |
msgid "Email content"
|
211 |
msgstr ""
|
212 |
|
213 |
+
#: core/classes/class-form-email.php:173
|
214 |
msgid "Include submitted values"
|
215 |
msgstr ""
|
216 |
|
241 |
msgstr ""
|
242 |
|
243 |
#: core/classes/class-form-messages.php:51
|
244 |
+
msgid "This number isn't big enough."
|
245 |
msgstr ""
|
246 |
|
247 |
#: core/classes/class-form-messages.php:55
|
248 |
+
msgid "This number is too big."
|
249 |
msgstr ""
|
250 |
|
251 |
#: core/classes/class-form-messages.php:59
|
253 |
msgstr ""
|
254 |
|
255 |
#: core/classes/class-form-messages.php:67
|
256 |
+
msgid "Too many choices are selected."
|
257 |
msgstr ""
|
258 |
|
259 |
#: core/classes/class-form-messages.php:71
|
260 |
+
msgid "Not enough choices are selected."
|
261 |
msgstr ""
|
262 |
|
263 |
#: core/classes/class-form-messages.php:75
|
344 |
msgid "Remaining submissions"
|
345 |
msgstr ""
|
346 |
|
347 |
+
#: core/classes/class-form-part-library.php:233
|
348 |
msgid "Missing validation callback for field %s"
|
349 |
msgstr ""
|
350 |
|
691 |
|
692 |
#: core/classes/class-form-styles.php:716
|
693 |
#: core/templates/parts/customize-checkbox.php:4
|
694 |
+
#: core/templates/parts/customize-checkbox.php:133
|
695 |
+
#: core/templates/parts/customize-checkbox.php:178
|
696 |
#: core/templates/parts/customize-email.php:4
|
697 |
#: core/templates/parts/customize-multi-line-text.php:4
|
698 |
#: core/templates/parts/customize-number.php:4
|
699 |
#: core/templates/parts/customize-radio.php:4
|
700 |
+
#: core/templates/parts/customize-radio.php:115
|
701 |
+
#: core/templates/parts/customize-radio.php:160
|
702 |
#: core/templates/parts/customize-select.php:4
|
703 |
+
#: core/templates/parts/customize-select.php:106
|
704 |
+
#: core/templates/parts/customize-select.php:145
|
705 |
#: core/templates/parts/customize-single-line-text.php:4
|
706 |
msgid "Label"
|
707 |
msgstr ""
|
721 |
|
722 |
#: core/classes/class-form-styles.php:731
|
723 |
#: core/templates/parts/customize-checkbox.php:20
|
724 |
+
#: core/templates/parts/customize-checkbox.php:139
|
725 |
#: core/templates/parts/customize-email.php:28
|
726 |
#: core/templates/parts/customize-multi-line-text.php:28
|
727 |
#: core/templates/parts/customize-number.php:28
|
728 |
#: core/templates/parts/customize-radio.php:20
|
729 |
+
#: core/templates/parts/customize-radio.php:121
|
730 |
#: core/templates/parts/customize-select.php:24
|
731 |
#: core/templates/parts/customize-single-line-text.php:28
|
732 |
msgid "Hint"
|
833 |
|
834 |
#: core/classes/class-happyforms-core.php:210
|
835 |
#: core/classes/class-happyforms-core.php:211
|
836 |
+
#: inc/classes/class-message-controller.php:561
|
837 |
+
#: inc/classes/class-message-controller.php:562
|
838 |
msgid "Activity"
|
839 |
msgstr ""
|
840 |
|
847 |
#: core/classes/class-happyforms-core.php:228
|
848 |
#: core/classes/class-happyforms-core.php:229
|
849 |
#: core/assets/jsx/build/admin/block.js:173
|
|
|
850 |
msgid "Settings"
|
851 |
msgstr ""
|
852 |
|
883 |
msgstr ""
|
884 |
|
885 |
#: core/classes/class-validation-messages.php:106
|
886 |
+
msgid "Looks like there's a mistake here."
|
887 |
msgstr ""
|
888 |
|
889 |
#: core/classes/class-validation-messages.php:110
|
890 |
+
msgid "Please answer this question."
|
891 |
msgstr ""
|
892 |
|
893 |
#: core/classes/class-validation-messages.php:114
|
894 |
+
msgid "Please make a selection."
|
895 |
msgstr ""
|
896 |
|
897 |
#: core/classes/class-validation-messages.php:118
|
898 |
+
msgid "This answer is too long."
|
899 |
msgstr ""
|
900 |
|
901 |
#: core/classes/class-validation-messages.php:122
|
902 |
+
msgid "This answer isn't long enough."
|
903 |
msgstr ""
|
904 |
|
905 |
#: core/classes/class-wp-customize-form-manager.php:162
|
2639 |
|
2640 |
#: core/templates/admin-form-modal.php:12
|
2641 |
#: core/assets/jsx/build/admin/block.js:158
|
|
|
2642 |
msgid "Insert"
|
2643 |
msgstr ""
|
2644 |
|
2645 |
+
#: core/templates/customize-controls/email/email-parts-list.php:10
|
2646 |
+
#: inc/templates/customize-controls/email-parts-list-dummy.php:8
|
2647 |
+
msgid "field"
|
2648 |
+
msgstr ""
|
2649 |
+
|
2650 |
+
#: core/templates/customize-controls/email/email-parts-list.php:13
|
2651 |
+
msgid "All Email fields"
|
2652 |
+
msgstr ""
|
2653 |
+
|
2654 |
#: core/templates/customize-controls/messages/text.php:7
|
2655 |
msgid "Reset"
|
2656 |
msgstr ""
|
2707 |
|
2708 |
#: core/templates/customize-form-item.php:33
|
2709 |
#: core/templates/customize-form-part-footer.php:3
|
2710 |
+
#: core/templates/parts/customize-checkbox.php:155
|
2711 |
+
#: core/templates/parts/customize-checkbox.php:183
|
2712 |
+
#: core/templates/parts/customize-radio.php:137
|
2713 |
+
#: core/templates/parts/customize-radio.php:165
|
2714 |
+
#: core/templates/parts/customize-select.php:122
|
2715 |
+
#: core/templates/parts/customize-select.php:150
|
2716 |
msgid "Delete"
|
2717 |
msgstr ""
|
2718 |
|
2800 |
#: core/templates/parts/customize-checkbox.php:28
|
2801 |
#: core/templates/parts/customize-checkbox.php:32
|
2802 |
#: core/templates/parts/customize-radio.php:28
|
|
|
2803 |
#: core/templates/parts/customize-select.php:32
|
|
|
2804 |
msgid "Choices"
|
2805 |
msgstr ""
|
2806 |
|
2807 |
#: core/templates/parts/customize-checkbox.php:29
|
|
|
2808 |
#: core/templates/parts/customize-select.php:33
|
2809 |
+
msgid "It doesn't look like your field has any choices yet. Want to add one? Click the \"Add Choice\" button to start."
|
2810 |
msgstr ""
|
2811 |
|
2812 |
#: core/templates/parts/customize-checkbox.php:36
|
2813 |
+
#: core/templates/parts/customize-radio.php:33
|
2814 |
+
#: core/templates/parts/customize-select.php:36
|
2815 |
msgid "Add heading"
|
2816 |
msgstr ""
|
2817 |
|
2818 |
#: core/templates/parts/customize-checkbox.php:37
|
2819 |
+
#: core/templates/parts/customize-radio.php:34
|
2820 |
+
#: core/templates/parts/customize-select.php:37
|
2821 |
msgid "Add choice"
|
2822 |
msgstr ""
|
2823 |
|
2824 |
+
#: core/templates/parts/customize-checkbox.php:47
|
2825 |
+
#: core/templates/parts/customize-radio.php:44
|
2826 |
#: core/templates/parts/customize-select.php:43
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2827 |
msgid "Add 'other' choice"
|
2828 |
msgstr ""
|
2829 |
|
2830 |
+
#: core/templates/parts/customize-checkbox.php:52
|
2831 |
+
#: core/templates/parts/customize-radio.php:49
|
2832 |
+
#: core/templates/parts/customize-select.php:49
|
2833 |
msgid "'Other' label"
|
2834 |
msgstr ""
|
2835 |
|
2836 |
+
#: core/templates/parts/customize-checkbox.php:56
|
2837 |
+
#: core/templates/parts/customize-radio.php:53
|
2838 |
+
#: core/templates/parts/customize-select.php:53
|
2839 |
msgid "'Other' placeholder"
|
2840 |
msgstr ""
|
2841 |
|
2842 |
+
#: core/templates/parts/customize-checkbox.php:63
|
2843 |
+
#: core/templates/parts/customize-radio.php:60
|
2844 |
+
#: core/templates/parts/customize-select.php:65
|
2845 |
msgid "Shuffle order of choices"
|
2846 |
msgstr ""
|
2847 |
|
2848 |
+
#: core/templates/parts/customize-checkbox.php:68
|
2849 |
msgid "Limit choices"
|
2850 |
msgstr ""
|
2851 |
|
2852 |
+
#: core/templates/parts/customize-checkbox.php:73
|
2853 |
msgid "Min choices"
|
2854 |
msgstr ""
|
2855 |
|
2856 |
+
#: core/templates/parts/customize-checkbox.php:77
|
2857 |
msgid "Max choices"
|
2858 |
msgstr ""
|
2859 |
|
2860 |
+
#: core/templates/parts/customize-checkbox.php:82
|
2861 |
+
#: core/templates/parts/customize-radio.php:64
|
2862 |
msgid "Align choices"
|
2863 |
msgstr ""
|
2864 |
|
2865 |
+
#: core/templates/parts/customize-checkbox.php:86
|
2866 |
+
#: core/templates/parts/customize-radio.php:68
|
2867 |
msgid "Vertically"
|
2868 |
msgstr ""
|
2869 |
|
2870 |
+
#: core/templates/parts/customize-checkbox.php:90
|
2871 |
+
#: core/templates/parts/customize-radio.php:72
|
2872 |
msgid "Horizontally"
|
2873 |
msgstr ""
|
2874 |
|
2875 |
+
#: core/templates/parts/customize-checkbox.php:96
|
2876 |
#: core/templates/parts/customize-email.php:48
|
2877 |
#: core/templates/parts/customize-multi-line-text.php:61
|
2878 |
#: core/templates/parts/customize-number.php:76
|
2879 |
+
#: core/templates/parts/customize-radio.php:78
|
2880 |
+
#: core/templates/parts/customize-select.php:70
|
2881 |
#: core/templates/parts/customize-single-line-text.php:47
|
2882 |
msgid "Require an answer"
|
2883 |
msgstr ""
|
2884 |
|
2885 |
+
#: core/templates/parts/customize-checkbox.php:105
|
2886 |
#: core/templates/parts/customize-email.php:57
|
2887 |
#: core/templates/parts/customize-multi-line-text.php:70
|
2888 |
#: core/templates/parts/customize-number.php:83
|
2889 |
+
#: core/templates/parts/customize-radio.php:85
|
2890 |
+
#: core/templates/parts/customize-select.php:76
|
2891 |
#: core/templates/parts/customize-single-line-text.php:56
|
2892 |
msgid "Additional CSS class(es)"
|
2893 |
msgstr ""
|
2894 |
|
2895 |
+
#: core/templates/parts/customize-checkbox.php:126
|
2896 |
+
#: core/templates/parts/customize-radio.php:108
|
2897 |
+
#: core/templates/parts/customize-select.php:99
|
2898 |
+
msgid "Choice"
|
2899 |
msgstr ""
|
2900 |
|
2901 |
+
#: core/templates/parts/customize-checkbox.php:145
|
2902 |
+
msgid "Max submissions"
|
|
|
|
|
2903 |
msgstr ""
|
2904 |
|
2905 |
+
#: core/templates/parts/customize-checkbox.php:151
|
2906 |
+
#: core/templates/parts/customize-radio.php:133
|
2907 |
+
#: core/templates/parts/customize-select.php:118
|
2908 |
+
msgid "Make this choice default"
|
2909 |
msgstr ""
|
2910 |
|
2911 |
+
#: core/templates/parts/customize-checkbox.php:171
|
2912 |
+
#: core/templates/parts/customize-radio.php:153
|
2913 |
+
#: core/templates/parts/customize-select.php:138
|
2914 |
#: inc/classes/parts/class-part-layout-title-dummy.php:8
|
2915 |
msgid "Heading"
|
2916 |
msgstr ""
|
2970 |
msgid "Decimal"
|
2971 |
msgstr ""
|
2972 |
|
2973 |
+
#: core/templates/parts/customize-radio.php:29
|
2974 |
+
msgid ""
|
2975 |
+
"It doesn't look like your field has any choices yet. Want to add one?\n"
|
2976 |
+
"Click the \"Add Choice\" button to start."
|
2977 |
+
msgstr ""
|
2978 |
+
|
2979 |
+
#: core/templates/parts/customize-radio.php:127
|
2980 |
+
#: core/templates/parts/customize-select.php:112
|
2981 |
#: inc/classes/class-happyforms.php:138
|
2982 |
msgid "Max number of submissions"
|
2983 |
msgstr ""
|
3034 |
msgid "Include referral web address"
|
3035 |
msgstr ""
|
3036 |
|
|
|
|
|
|
|
|
|
3037 |
#: inc/classes/class-happyforms.php:184
|
3038 |
msgid "Send abandonment email"
|
3039 |
msgstr ""
|
3066 |
msgid "Spam"
|
3067 |
msgstr ""
|
3068 |
|
3069 |
+
#: inc/classes/class-message-controller.php:563
|
3070 |
+
#: inc/classes/class-message-controller.php:564
|
3071 |
msgid "All Activity"
|
3072 |
msgstr ""
|
3073 |
|
3074 |
+
#: inc/classes/class-message-controller.php:565
|
3075 |
msgid "No activity found."
|
3076 |
msgstr ""
|
3077 |
|
3223 |
msgid "For formatted site URLs."
|
3224 |
msgstr ""
|
3225 |
|
|
|
|
|
|
|
|
|
3226 |
#: integrations/classes/class-integrations-page-controller.php:26
|
3227 |
msgid "ActiveCampaign"
|
3228 |
msgstr ""
|
3461 |
msgstr ""
|
3462 |
|
3463 |
#: core/assets/jsx/build/admin/block.js:127
|
|
|
3464 |
msgid "Choose"
|
3465 |
msgstr ""
|
3466 |
|
3467 |
#: core/assets/jsx/build/admin/block.js:144
|
|
|
3468 |
msgid "The form previously added has been trashed or deleted."
|
3469 |
msgstr ""
|
3470 |
|
3471 |
#: core/assets/jsx/build/admin/block.js:144
|
|
|
3472 |
msgid "Pick a form to display on your site."
|
3473 |
msgstr ""
|
3474 |
|
3475 |
#: core/assets/jsx/build/admin/block.js:175
|
|
|
3476 |
msgid "Pick a form"
|
3477 |
msgstr ""
|
3478 |
|
3486 |
msgid "We'll occasionally send you emails about plugin updates. And don't sweat it, you can unsubscribe anytime."
|
3487 |
msgstr ""
|
3488 |
|
3489 |
+
#: inc/assets/jsx/build/admin/dashboard-modals.js:213
|
3490 |
+
#: inc/assets/jsx/src/admin/dashboard-modals.js:49
|
3491 |
+
msgid "Email address"
|
3492 |
+
msgstr ""
|
3493 |
+
|
3494 |
#: inc/assets/jsx/build/admin/dashboard-modals.js:223
|
3495 |
#: inc/assets/jsx/src/admin/dashboard-modals.js:54
|
3496 |
msgid "Continue"
|
readme.txt
CHANGED
@@ -5,7 +5,7 @@ Tags: contact form, contact form plugin, forms, form builder, custom form, intak
|
|
5 |
Requires at least: 5.0
|
6 |
Tested up to: 6.0
|
7 |
Requires PHP: 7.0
|
8 |
-
Stable tag: 1.15.
|
9 |
License: GPLv2 or later
|
10 |
License URI: http://www.gnu.org/licenses/gpl-2.0.html
|
11 |
|
@@ -34,11 +34,11 @@ https://www.youtube.com/watch?v=X1snk2vJbXI
|
|
34 |
* Easily add forms anywhere to your pages, posts and widget areas.
|
35 |
* Add multiple forms to the same page.
|
36 |
* Completely mobile responsive forms.
|
37 |
-
* Unlimited forms, fields, emails and
|
38 |
* Create multi-column layouts with a single click.
|
39 |
* Easily duplicate forms.
|
40 |
* Confirmation message on submission.
|
41 |
-
* Confirmation email sent to
|
42 |
* One-click HoneyPot spam prevention.
|
43 |
* Over 50 styles controls built-in.
|
44 |
* GDPR and 508 compliant forms and secure forms.
|
@@ -56,22 +56,16 @@ https://www.youtube.com/watch?v=X1snk2vJbXI
|
|
56 |
= Upgraded Happyforms Features: =
|
57 |
|
58 |
* Access to all 20+ form fields.
|
59 |
-
* Manage unlimited
|
60 |
-
* Let
|
61 |
* Redirect to any webpage after the form is submitted.
|
62 |
-
* Multi-page forms with
|
63 |
-
*
|
64 |
-
* Limit the number of responses per form.
|
65 |
* Google ReCaptcha spam prevention integration.
|
66 |
-
*
|
67 |
-
*
|
68 |
-
* Inherit theme styles option.
|
69 |
-
* Preview values before submission.
|
70 |
* Log IP address automatically.
|
71 |
-
*
|
72 |
-
* Randomize form fields and values to avoid biases.
|
73 |
-
* Advanced filtering of responses.
|
74 |
-
* Fade submit button until valid.
|
75 |
* Unlimited personal and client use plans.
|
76 |
* No-nonsense support team, happy to help over email.
|
77 |
|
@@ -81,19 +75,19 @@ https://www.youtube.com/watch?v=X1snk2vJbXI
|
|
81 |
|
82 |
= Can you read my replies? =
|
83 |
|
84 |
-
Heck nah! No one likes peepers. All
|
85 |
|
86 |
Note: you'll need to upgrade to our paid contact form builder plugin to get some of the best goodies mentioned here.
|
87 |
|
88 |
= Can I translate forms into my language? =
|
89 |
|
90 |
-
Absolutely! Every last word read by your
|
91 |
|
92 |
Note: you'll need to upgrade to our paid contact form builder plugin to get some of the best goodies mentioned here.
|
93 |
|
94 |
= Is Happyforms GDPR and CCPA ready? =
|
95 |
|
96 |
-
Yep! We have a special field for collecting
|
97 |
|
98 |
Note: you'll need to upgrade to our paid contact form builder plugin to get some of the best goodies mentioned here.
|
99 |
|
@@ -101,7 +95,7 @@ Note: you'll need to upgrade to our paid contact form builder plugin to get some
|
|
101 |
|
102 |
Our competitors claim to be HIPAA compliant, but that’s misleading. Those dodgy buggers! Why have a compliant form if your site’s server, connected services and chosen inbox aren’t?
|
103 |
|
104 |
-
To keep things simple, we say to disable Happyforms from saving
|
105 |
|
106 |
It’s easier than it sounds. Promise. Hit us up if you have questions.
|
107 |
|
@@ -151,11 +145,17 @@ Aw, honestly, the thought that you're writing about our contact form builder is
|
|
151 |
|
152 |
== Changelog ==
|
153 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
154 |
= 1.15.3 =
|
155 |
* New feature: Submissions are checked against headless browsers for better antispam protection.
|
156 |
* Improvement: Field choices preserves its shuffled state when a validation occurs on submission for better usability.
|
157 |
* Improvement: Better wording and style fixes in the form builder.
|
158 |
-
* Bugfix: Opt-In Choice field label spacing was off.
|
159 |
|
160 |
= 1.15.2 =
|
161 |
* New feature: "Screen Options" tab now includes "View mode" for better consistency with core WordPress.
|
@@ -944,6 +944,9 @@ Aw, honestly, the thought that you're writing about our contact form builder is
|
|
944 |
|
945 |
== Upgrade Notice ==
|
946 |
|
|
|
|
|
|
|
947 |
= 1.15.3 =
|
948 |
* Improved antispam protection, better shuffling of field choices, miscellaneous improvements and bugfixes.
|
949 |
|
@@ -1017,7 +1020,7 @@ Aw, honestly, the thought that you're writing about our contact form builder is
|
|
1017 |
* Improved honeypot and asset loading, miscellaneous bugfixes.
|
1018 |
|
1019 |
= 1.12.9 =
|
1020 |
-
* Jetpack synchronization was triggering a fatal error.
|
1021 |
|
1022 |
= 1.12.8 =
|
1023 |
* Safer builder controls internal API.
|
5 |
Requires at least: 5.0
|
6 |
Tested up to: 6.0
|
7 |
Requires PHP: 7.0
|
8 |
+
Stable tag: 1.15.4
|
9 |
License: GPLv2 or later
|
10 |
License URI: http://www.gnu.org/licenses/gpl-2.0.html
|
11 |
|
34 |
* Easily add forms anywhere to your pages, posts and widget areas.
|
35 |
* Add multiple forms to the same page.
|
36 |
* Completely mobile responsive forms.
|
37 |
+
* Unlimited forms, fields, emails and submissions.
|
38 |
* Create multi-column layouts with a single click.
|
39 |
* Easily duplicate forms.
|
40 |
* Confirmation message on submission.
|
41 |
+
* Confirmation email sent to submitter.
|
42 |
* One-click HoneyPot spam prevention.
|
43 |
* Over 50 styles controls built-in.
|
44 |
* GDPR and 508 compliant forms and secure forms.
|
56 |
= Upgraded Happyforms Features: =
|
57 |
|
58 |
* Access to all 20+ form fields.
|
59 |
+
* Manage unlimited submissions easily in the dashboard.
|
60 |
+
* Let submitters upload files to your forms.
|
61 |
* Redirect to any webpage after the form is submitted.
|
62 |
+
* Multi-page forms with step indicator.
|
63 |
+
* Limit the number of submissions per form.
|
|
|
64 |
* Google ReCaptcha spam prevention integration.
|
65 |
+
* Enable people to save and resume their submission.
|
66 |
+
* Preview submission before submitting.
|
|
|
|
|
67 |
* Log IP address automatically.
|
68 |
+
* Shuffle form fields and choices to avoid biases.
|
|
|
|
|
|
|
69 |
* Unlimited personal and client use plans.
|
70 |
* No-nonsense support team, happy to help over email.
|
71 |
|
75 |
|
76 |
= Can you read my replies? =
|
77 |
|
78 |
+
Heck nah! No one likes peepers. All submissions are saved in your WordPress database or sent to your inbox.
|
79 |
|
80 |
Note: you'll need to upgrade to our paid contact form builder plugin to get some of the best goodies mentioned here.
|
81 |
|
82 |
= Can I translate forms into my language? =
|
83 |
|
84 |
+
Absolutely! Every last word read by your submitters can be translated — just type and replace. No extra plugins. No code changes. No fuss.
|
85 |
|
86 |
Note: you'll need to upgrade to our paid contact form builder plugin to get some of the best goodies mentioned here.
|
87 |
|
88 |
= Is Happyforms GDPR and CCPA ready? =
|
89 |
|
90 |
+
Yep! We have a special field for collecting submitters' consent for things just like this.
|
91 |
|
92 |
Note: you'll need to upgrade to our paid contact form builder plugin to get some of the best goodies mentioned here.
|
93 |
|
95 |
|
96 |
Our competitors claim to be HIPAA compliant, but that’s misleading. Those dodgy buggers! Why have a compliant form if your site’s server, connected services and chosen inbox aren’t?
|
97 |
|
98 |
+
To keep things simple, we say to disable Happyforms from saving submissions and instead point replies to an email address hosted by an end-to-end encrypted email service like ProtonMail.
|
99 |
|
100 |
It’s easier than it sounds. Promise. Hit us up if you have questions.
|
101 |
|
145 |
|
146 |
== Changelog ==
|
147 |
|
148 |
+
= 1.15.4 =
|
149 |
+
* New feature: "To email address" control under "Email me a copy of each submission" allows for more granular control of email settings.
|
150 |
+
* New feature: "Reply email address" control under "Email me a copy of each submission" for easier exchanges with submitting users.
|
151 |
+
* Improvement: "Added to" column in Forms screen now lists templates and reusable blocks for better integration with WordPress.
|
152 |
+
* Improvement: Interface of choices in all choice-based fields has been redesigned for better usability and clarity.
|
153 |
+
* Bugfix: Display of fields with limited choices wasn't updating correctly in builder's preview screen.
|
154 |
+
|
155 |
= 1.15.3 =
|
156 |
* New feature: Submissions are checked against headless browsers for better antispam protection.
|
157 |
* Improvement: Field choices preserves its shuffled state when a validation occurs on submission for better usability.
|
158 |
* Improvement: Better wording and style fixes in the form builder.
|
|
|
159 |
|
160 |
= 1.15.2 =
|
161 |
* New feature: "Screen Options" tab now includes "View mode" for better consistency with core WordPress.
|
944 |
|
945 |
== Upgrade Notice ==
|
946 |
|
947 |
+
= 1.15.4 =
|
948 |
+
* New email controls, redesigned choice interface, miscellaneous improvements and bugfixes.
|
949 |
+
|
950 |
= 1.15.3 =
|
951 |
* Improved antispam protection, better shuffling of field choices, miscellaneous improvements and bugfixes.
|
952 |
|
1020 |
* Improved honeypot and asset loading, miscellaneous bugfixes.
|
1021 |
|
1022 |
= 1.12.9 =
|
1023 |
+
* Jetpack synchronization was triggering a fatal error.
|
1024 |
|
1025 |
= 1.12.8 =
|
1026 |
* Safer builder controls internal API.
|