PluginProbe ʕ •ᴥ•ʔ
GiveWP – Donation Plugin and Fundraising Platform / 4.7.1
GiveWP – Donation Plugin and Fundraising Platform v4.7.1
4.16.2 4.16.1 4.16.0 4.15.5 4.15.4 4.15.3 4.15.2 4.15.1 4.15.0 2.3.0 2.3.1 2.3.2 2.30.0 2.31.0 2.31.1 2.32.0 2.33.0 2.33.1 2.33.2 2.33.3 2.33.4 2.33.5 2.4.0 2.4.1 2.4.2 2.4.3 2.4.4 2.4.5 2.4.6 2.4.7 2.5.0 2.5.1 2.5.10 2.5.11 2.5.12 2.5.13 2.5.2 2.5.3 2.5.4 2.5.5 2.5.6 2.5.7 2.5.8 2.5.9 2.6.0 2.6.1 2.6.2 2.6.3 2.7.0 2.7.1 2.7.2 2.7.3 2.7.4 2.7.5 2.8.0 2.8.1 2.9.0 2.9.1 2.9.2 2.9.3 2.9.4 2.9.5 2.9.6 2.9.7 3.0.0 3.0.1 3.0.2 3.0.3 3.0.4 3.1.0 3.1.1 3.1.2 3.10.0 3.11.0 3.12.0 3.12.1 3.12.2 3.12.3 3.13.0 3.14.0 3.14.1 3.14.2 3.15.0 3.15.1 3.16.0 3.16.1 3.16.2 3.16.3 3.16.4 3.16.5 3.17.0 3.17.1 3.17.2 3.18.0 3.19.0 3.19.1 3.19.2 3.19.3 3.19.4 3.2.0 3.2.1 3.2.2 3.20.0 3.21.0 3.21.1 3.22.0 3.22.1 3.22.2 3.3.0 3.3.1 3.4.0 3.4.1 3.4.2 3.5.0 3.5.1 3.6.0 3.6.1 3.6.2 3.7.0 3.8.0 3.9.0 4.0.0 4.1.0 4.1.1 4.10.0 4.10.1 4.11.0 4.12.0 4.13.0 4.13.1 4.13.2 4.14.0 4.14.1 4.14.2 4.14.3 4.14.4 4.14.5 4.14.6 4.2.0 4.2.1 4.3.0 4.3.1 4.3.2 4.4.0 4.5.0 4.6.1 4.7.0 4.7.1 4.8.0 4.8.1 4.9.0 trunk 1.9.0 2.0.0 2.0.1 2.0.2 2.0.3 2.0.4 2.0.5 2.0.6 2.0.7 2.1.0 2.1.1 2.1.2 2.1.3 2.1.4 2.1.5 2.1.6 2.1.7 2.1.8 2.10.0 2.10.1 2.10.2 2.10.3 2.10.4 2.11.0 2.11.1 2.11.2 2.11.3 2.12.0 2.12.1 2.12.2 2.12.3 2.13.0 2.13.1 2.13.2 2.13.3 2.13.4 2.14.0 2.15.0 2.16.0 2.16.1 2.17.0 2.17.1 2.17.3 2.18.0 2.18.1 2.19.1 2.19.2 2.19.3 2.19.4 2.19.5 2.19.6 2.19.7 2.19.8 2.2.0 2.2.1 2.2.2 2.2.3 2.2.4 2.2.5 2.2.6 2.20.0 2.20.1 2.20.2 2.21.0 2.21.1 2.21.2 2.21.3 2.21.4 2.22.0 2.22.1 2.22.2 2.22.3 2.23.0 2.23.1 2.23.2 2.24.0 2.24.1 2.24.2 2.25.0 2.25.1 2.25.2 2.25.3 2.26.0 2.27.0 2.27.1 2.27.2 2.27.3 2.28.0 2.29.0 2.29.1 2.29.2
give / src / FormBuilder / ViewModels / FormBuilderViewModel.php
give / src / FormBuilder / ViewModels Last commit date
FormBuilderViewModel.php 11 months ago
FormBuilderViewModel.php
414 lines
1 <?php
2
3 namespace Give\FormBuilder\ViewModels;
4
5 use Give\Campaigns\Models\Campaign;
6 use Give\DonationForms\Actions\GenerateDonationFormPreviewRouteUrl;
7 use Give\DonationForms\Models\DonationForm;
8 use Give\DonationForms\ValueObjects\GoalProgressType;
9 use Give\DonationForms\ValueObjects\GoalSource;
10 use Give\DonationForms\ValueObjects\GoalType;
11 use Give\Donations\Models\Donation;
12 use Give\Donations\ValueObjects\DonationMetaKeys;
13 use Give\Donors\Models\Donor;
14 use Give\Donors\ValueObjects\DonorMetaKeys;
15 use Give\FormBuilder\DataTransferObjects\EmailNotificationData;
16 use Give\FormBuilder\ValueObjects\FormBuilderRestRouteConfig;
17 use Give\Framework\FormDesigns\FormDesign;
18 use Give\Framework\FormDesigns\Registrars\FormDesignRegistrar;
19 use Give\Framework\PaymentGateways\PaymentGateway;
20 use Give\Framework\Support\Facades\Scripts\ScriptAsset;
21 use Give\Helpers\IntlTelInput;
22 use Give\Subscriptions\Models\Subscription;
23 use Give_License;
24
25 class FormBuilderViewModel
26 {
27 /**
28 * @since 3.12.0 Add goalProgressOptions key to the returned array
29 * @since 3.9.0 Add support to intlTelInputSettings key in the returned array
30 * @since 3.7.0 Add support to isExcerptEnabled key in the returned array
31 * @since 3.2.0 Add nameTitlePrefixes key to the returned array
32 * @since 3.0.0
33 */
34 public function storageData(int $donationFormId): array
35 {
36 /** @var DonationForm $donationForm */
37 $donationForm = DonationForm::find($donationFormId);
38
39 return [
40 'formId' => $donationFormId,
41 'resourceURL' => rest_url(FormBuilderRestRouteConfig::NAMESPACE . '/form/' . $donationFormId),
42 'previewURL' => (new GenerateDonationFormPreviewRouteUrl())($donationFormId),
43 'nonce' => wp_create_nonce('wp_rest'),
44 'blockData' => $donationForm->blocks->toJson(),
45 'settings' => $donationForm->settings->toJson(),
46 'currency' => give_get_currency(),
47 'formDesigns' => array_map(static function ($designClass) {
48 /** @var FormDesign $design */
49 $design = give($designClass);
50
51 return [
52 'id' => $design::id(),
53 'name' => $design::name(),
54 'isMultiStep' => $design->isMultiStep(),
55 ];
56 }, give(FormDesignRegistrar::class)->getDesigns()),
57 'formPage' => [
58 'isEnabled' => give_is_setting_enabled(give_get_option('forms_singular')),
59 // Note: Boolean values must be nested in an array to maintain boolean type, see \WP_Scripts::localize().
60 'permalink' => add_query_arg(['p' => $donationFormId], site_url('?post_type=give_forms')),
61 'rewriteSlug' => get_post_type_object('give_forms')->rewrite['slug'],
62 'baseUrl' => preg_replace('/^https?:\/\//', '', site_url()),
63 ],
64 'gateways' => $this->getGateways(),
65 'gatewaySettingsUrl' => admin_url('edit.php?post_type=give_forms&page=give-settings&tab=gateways'),
66 'isRecurringEnabled' => defined('GIVE_RECURRING_VERSION') ? GIVE_RECURRING_VERSION : null,
67 'recurringAddonData' => [
68 'isInstalled' => defined('GIVE_RECURRING_VERSION'),
69 ],
70 'formFieldManagerData' => [
71 'isInstalled' => defined('GIVE_FFM_VERSION'),
72 'isLicensed' => (Give_License::get_license_by_plugin_dirname('give-form-field-manager')['license'] ?? '') === 'valid',
73 ],
74 'emailTemplateTags' => $this->getEmailTemplateTags(),
75 'emailNotifications' => array_map(static function ($notification) {
76 return EmailNotificationData::fromLegacyNotification($notification);
77 }, apply_filters('give_email_notification_options_metabox_fields', [], $donationFormId)),
78 'emailPreviewURL' => rest_url('givewp/form-builder/email-preview'),
79 'emailDefaultAddress' => get_option('admin_email'),
80 'disallowedFieldNames' => $this->getDisallowedFieldNames(),
81 'donationConfirmationTemplateTags' => $this->getDonationConfirmationPageTemplateTags(),
82 'termsAndConditions' => [
83 'checkboxLabel' => give_get_option('agree_to_terms_label'),
84 'agreementText' => give_get_option('agreement_text'),
85 ],
86 'goalTypeOptions' => $this->getGoalTypeOptions(),
87 'goalSourceOptions' => $this->getGoalSourceOptions(),
88 'goalProgressOptions' => $this->getGoalProgressOptions(),
89 'nameTitlePrefixes' => give_get_option('title_prefixes', array_values(give_get_default_title_prefixes())),
90 'isExcerptEnabled' => give_is_setting_enabled(give_get_option('forms_excerpt')),
91 'intlTelInputSettings' => IntlTelInput::getSettings(),
92 'campaignColors' => $this->getCampaignColors($donationFormId),
93 'showFormGoalNotice' => !get_user_meta(get_current_user_id(), 'givewp_campaign_form_goal_notice', true),
94 ];
95 }
96
97 /**
98 * @since 3.0.0
99 */
100 public function isRecurringEnabled(): bool
101 {
102 return defined('GIVE_RECURRING_VERSION') && GIVE_RECURRING_VERSION;
103 }
104
105 /**
106 * @since 3.0.0
107 */
108 public function getGoalTypeOption(
109 string $value,
110 string $label,
111 string $description,
112 bool $isCurrency = false
113 ): array
114 {
115 return [
116 'value' => $value,
117 'label' => $label,
118 'description' => $description,
119 'isCurrency' => $isCurrency,
120 ];
121 }
122
123
124 /**
125 * @since 4.1.0
126 */
127 public function getGoalSourceOption(
128 string $value,
129 string $label,
130 string $description
131 ): array
132 {
133 return [
134 'value' => $value,
135 'label' => $label,
136 'description' => $description,
137 ];
138 }
139
140
141 /**
142 * @since 3.12.0
143 */
144 public function getGoalProgressOption(
145 string $value,
146 string $label,
147 string $description
148 ): array
149 {
150 return [
151 'value' => $value,
152 'label' => $label,
153 'description' => $description
154 ];
155 }
156
157
158 /**
159 * @since 3.0.0
160 */
161 public function getGoalTypeOptions(): array
162 {
163 $options = [
164 $this->getGoalTypeOption(
165 GoalType::AMOUNT,
166 __('Amount Raised', 'give'),
167 __('The total amount raised for the form', 'give'),
168 true
169 ),
170 $this->getGoalTypeOption(
171 GoalType::DONATIONS,
172 __('Number of Donations', 'give'),
173 __('The total number of donations made for the form', 'give')
174 ),
175 $this->getGoalTypeOption(
176 GoalType::DONORS,
177 __('Number of Donors', 'give'),
178 __('The total number of unique donors who have donated to the form', 'give')
179 ),
180 ];
181
182 if ($this->isRecurringEnabled()) {
183 return array_merge($options, [
184 $this->getGoalTypeOption(
185 GoalType::AMOUNT_FROM_SUBSCRIPTIONS,
186 __('Subscription Amount Raised', 'give'),
187 __('The total amount raised for the form through subscriptions', 'give'),
188 true
189 ),
190 $this->getGoalTypeOption(
191 GoalType::SUBSCRIPTIONS,
192 __('Number of Subscriptions', 'give'),
193 __('The total number of subscriptions made for the form', 'give')
194 ),
195 $this->getGoalTypeOption(
196 GoalType::DONORS_FROM_SUBSCRIPTIONS,
197 __('Number of Subscribers', 'give'),
198 __('The total number of unique donors who have donated to the form through subscriptions', 'give')
199 ),
200 ]);
201 }
202
203 return $options;
204 }
205
206 /**
207 * @since 4.1.0
208 */
209 public function getGoalSourceOptions(): array
210 {
211 return [
212 $this->getGoalTypeOption(
213 GoalSource::CAMPAIGN,
214 __('Campaign', 'give'),
215 __('The goal for this form will automatically adjust according to the campaign goal. Change campaign goal.', 'give')
216 ),
217 $this->getGoalTypeOption(
218 GoalSource::FORM,
219 __('Custom', 'give'),
220 __('Set the custom goal for this form', 'give')
221 ),
222 ];
223 }
224
225 /**
226 * @since 3.12.0
227 */
228 public function getGoalProgressOptions(): array
229 {
230 return [
231 $this->getGoalProgressOption(
232 GoalProgressType::ALL_TIME,
233 __('All time', 'give'),
234 __('Displays the goal progress for a lifetime, starting from when this form was published.', 'give')
235 ),
236 $this->getGoalProgressOption(
237 GoalProgressType::CUSTOM,
238 __('Custom', 'give'),
239 __('Displays the goal progress from the start date to the end date.', 'give')
240 )
241 ];
242 }
243
244 /**
245 * @since 3.0.0
246 */
247 public function getEmailTemplateTags(array $tags = []): array
248 {
249 return array_map(static function ($tag) {
250 $tag['id'] = $tag['tag'];
251 $tag['desc'] = html_entity_decode($tag['desc'], ENT_QUOTES);
252 $tag['description'] = html_entity_decode($tag['description'], ENT_QUOTES);
253
254 return $tag;
255 }, array_merge($tags, array_values(give()->email_tags->get_tags())));
256 }
257
258 /**
259 * @since 3.0.0
260 */
261 public function getDonationConfirmationPageTemplateTags(): array
262 {
263 $templateTags = $this->getEmailTemplateTags([
264 [
265 'tag' => 'first_name',
266 'desc' => __('The first name supplied by the donor during their donation.', 'give'),
267 'description' => __('The first name supplied by the donor during their donation.', 'give'),
268 'func' => null,
269 "context" => 'donation',
270 ],
271 [
272 'tag' => 'last_name',
273 'desc' => __('The last name supplied by the donor during their donation.', 'give'),
274 'description' => __('The last name supplied by the donor during their donation.', 'give'),
275 'func' => null,
276 "context" => 'donation',
277 ],
278 [
279 'tag' => 'email',
280 'desc' => __('The email supplied by the donor during their donation.', 'give'),
281 'description' => __('The email supplied by the donor during their donation.', 'give'),
282 'func' => null,
283 "context" => 'donation',
284 ],
285 ]);
286
287 $supportedContexts = [
288 "general",
289 "form",
290 "donation",
291 "donor",
292 "subscription",
293 ];
294
295 array_multisort($templateTags, SORT_ASC);
296
297 return array_values(
298 array_filter($templateTags, static function ($tag) use ($supportedContexts) {
299 return !empty($tag['description']) && in_array((string)$tag['context'], $supportedContexts, true);
300 })
301 );
302 }
303
304 /**
305 * @since 3.0.0
306 */
307 public function jsPathFromPluginRoot(): string
308 {
309 return GIVE_PLUGIN_URL . 'build/formBuilderApp.js';
310 }
311
312 /**
313 * @since 3.0.0
314 */
315 public function jsPathToRegistrars(): string
316 {
317 return GIVE_PLUGIN_URL . 'build/formBuilderRegistrars.js';
318 }
319
320 /**
321 * @since 3.0.0
322 */
323 public function jsRegistrarsDependencies(): array
324 {
325 return ScriptAsset::getDependencies(GIVE_PLUGIN_DIR . 'build/formBuilderRegistrars.asset.php');
326 }
327
328 /**
329 * @since 3.0.0
330 */
331 public function jsDependencies(): array
332 {
333 $dependencies = ScriptAsset::getDependencies(GIVE_PLUGIN_DIR . 'build/formBuilderApp.asset.php');
334
335 return array_merge($dependencies, ['@givewp/form-builder/registrars']);
336 }
337
338 /**
339 * @since 3.0.0
340 */
341 public function getGateways(): array
342 {
343 $enabledGateways = array_keys(give_get_option('gateways_v3', []));
344
345 $builderPaymentGatewayData = array_map(static function ($gatewayClass) use ($enabledGateways) {
346 /** @var PaymentGateway $gateway */
347 $gateway = give($gatewayClass);
348
349 return [
350 'id' => $gateway::id(),
351 'enabled' => in_array($gateway::id(), $enabledGateways, true),
352 'label' => give_get_gateway_checkout_label($gateway::id(), 3) ?? $gateway->getPaymentMethodLabel(),
353 'supportsSubscriptions' => $gateway->supportsSubscriptions(),
354 ];
355 }, give()->gateways->getPaymentGateways(3));
356
357 return array_values($builderPaymentGatewayData);
358 }
359
360 /**
361 * In the Form Builder custom fields have meta keys. These meta keys are used for both the field name and the meta,
362 * as not to be too confusing. This array is used to prevent the user from creating meta keys that conflict with the
363 * existing meta or field names.
364 *
365 * @since 4.3.2 Add country, state, city, zip, address1, and address2 to the disallowed field names.
366 * @since 3.0.0
367 */
368 protected function getDisallowedFieldNames(): array
369 {
370 $disallowedFieldNames = array_merge(
371 Donation::propertyKeys(),
372 array_values(DonationMetaKeys::toArray()),
373 Donor::propertyKeys(),
374 array_values(DonorMetaKeys::toArray()),
375 Subscription::propertyKeys(),
376 [
377 'fund_id',
378 'login',
379 'consent',
380 'donation-summary',
381 'country',
382 'state',
383 'city',
384 'zip',
385 'address1',
386 'address2',
387 ]
388 );
389
390 return array_values(array_unique($disallowedFieldNames));
391 }
392
393 /**
394 * @since 4.1.0
395 */
396 private function getCampaignColors(int $formId): array
397 {
398 /** @var Campaign $campaign */
399 $campaign = give()->campaigns->getByFormId($formId);
400
401 if ($campaign) {
402 return [
403 'primaryColor' => $campaign->primaryColor,
404 'secondaryColor' => $campaign->secondaryColor,
405 ];
406 }
407
408 return [
409 'primaryColor' => '',
410 'secondaryColor' => '',
411 ];
412 }
413 }
414