PluginProbe ʕ •ᴥ•ʔ
GiveWP – Donation Plugin and Fundraising Platform / 4.16.3
GiveWP – Donation Plugin and Fundraising Platform v4.16.3
4.16.3 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 / DonationForms / OrphanedForms / resources / app.tsx
give / src / DonationForms / OrphanedForms / resources Last commit date
app.tsx 1 year ago index.tsx 1 year ago styles.module.scss 1 year ago
app.tsx
246 lines
1 import {__, _x} from '@wordpress/i18n';
2 import {useState} from 'react';
3 import apiFetch from '@wordpress/api-fetch';
4 import {Button, Card, Modal, Notice, Pagination as ListTablePagination, Spinner, Table} from '@givewp/components';
5 import {useForms} from '../../resources/utils';
6 import useCampaigns from '../../../Campaigns/Blocks/shared/hooks/useCampaigns';
7 import {format} from 'date-fns';
8 import * as locales from 'date-fns/locale';
9 import styles from './styles.module.scss';
10
11
12 const browserLanguage = navigator.language;
13 const localizedCode = browserLanguage.replace('-', '');
14 const genericCode = browserLanguage.split('-')[0];
15 const locale = locales[localizedCode] ?? locales[genericCode] ?? locales.enUS;
16 const dateFormat = _x('MM/dd/yyyy \'at\' h:mmaaa', 'Date format', 'give');
17
18 type Props = {
19 ids: number[];
20 currentPage: number;
21 showModal: boolean;
22 campaign?: number;
23 }
24
25 const OrphanedFormsListTable = () => {
26 const [state, setState] = useState<Props>({
27 ids: [],
28 currentPage: 1,
29 showModal: false,
30 });
31
32 const {forms, hasResolved, totalPages} = useForms({
33 page: state.currentPage,
34 status: ['orphaned'],
35 });
36
37 const {campaigns, hasResolved: campaignsLoaded} = useCampaigns();
38
39 const showModal = (showModal: boolean) => {
40 setState(prevState => {
41 return {
42 ...prevState,
43 showModal,
44 };
45 });
46 };
47
48 const selectForm = (selectedId: number) => {
49
50 let ids = state.ids;
51
52 if (ids.includes(selectedId)) {
53 ids = ids.filter(id => id !== selectedId);
54 } else {
55 ids.push(selectedId);
56 }
57
58 setState(prevState => {
59 return {
60 ...prevState,
61 ids,
62 };
63 });
64 };
65
66 const selectCampaign = (campaign: number) => {
67 setState(prevState => {
68 return {
69 ...prevState,
70 campaign,
71 };
72 });
73 };
74
75
76 const setCurrentPage = (currentPage: number) => {
77 setState((previousState) => {
78 return {
79 ...previousState,
80 currentPage,
81 };
82 });
83 };
84
85 const getFormName = (id: number) => {
86 //@ts-ignore
87 const form = forms.filter(form => form.id === id);
88 //@ts-ignore
89 return form[0].title;
90 };
91
92 const handleSave = () => {
93 apiFetch({
94 path: '/givewp/v3/associate-forms-with-campaign',
95 method: 'POST',
96 data: {
97 campaignId: state.campaign,
98 formIDs: state.ids,
99 },
100 }).then(() => {
101 window.location.reload();
102 });
103 };
104
105 const Pagination = () => (
106 <div className={styles.pagination}>
107 <ListTablePagination
108 currentPage={state.currentPage}
109 setPage={(page: number) => setCurrentPage(page)}
110 totalPages={totalPages}
111 disabled={!hasResolved}
112 />
113 </div>
114 );
115
116
117 const ConfirmationModal = () => {
118 return (
119 <Modal
120 type="info"
121 handleClose={() => showModal(false)}
122 >
123 <Modal.Title>
124 {__('Associate forms with campaign', 'give')}
125
126 <Modal.CloseIcon onClick={() => showModal(false)} />
127 </Modal.Title>
128
129 <div>
130 <h4>{__('Selected forms', 'give')}</h4>
131 {state.ids.map(id => (
132 <p key={id}>
133 {getFormName(id)}
134 </p>
135 ))}
136 </div>
137
138 <div className={styles.section}>
139 <h4>{__('Select campaign', 'give')}</h4>
140 <select
141 className={styles.input}
142 onChange={e => selectCampaign(Number(e.target.value))}>
143 <option>
144 {__('Select campaign', 'give')}
145 </option>
146 {campaigns.map((campaign) => (
147 <option
148 selected={state.campaign === campaign.id}
149 value={campaign.id}
150 >
151 {campaign.title}
152 </option>
153 ))}
154 </select>
155
156 </div>
157
158 <div className={styles.buttons}>
159
160 <Button
161 className="button button-primary"
162 onClick={handleSave}
163 icon={null}
164 disabled={!state.campaign}
165 >
166 {__('Associate forms ', 'give')}
167 </Button>
168
169 <Button
170 className="button button-secondary"
171 icon={null}
172 type="reset"
173 onClick={() => showModal(false)}
174 >
175 {__('Cancel', 'give')}
176 </Button>
177 </div>
178 </Modal>
179 );
180 };
181
182
183 const columns = [
184 {
185 key: 'id',
186 label: __('Donation Form', 'give'),
187 },
188 {
189 key: 'createdAt',
190 label: __('Date created', 'give'),
191 },
192 ];
193
194 const columnFilters = {
195 id: (id: number, form: {title: string}) => (
196 <div className={styles.row}>
197 <input type="checkbox" onChange={() => selectForm(id)} />
198 <div>{form.title}</div>
199 </div>
200 ),
201 createdAt: (value: {date: string}) => {
202 return format(new Date(value.date), dateFormat, {locale});
203 },
204 };
205
206 if (!hasResolved) {
207 return (
208 <Notice>
209 <Spinner />
210 <h2>{__('Loading donation forms', 'give')}</h2>
211 </Notice>
212 );
213 }
214
215 return (
216 <>
217 <Card>
218 <Table
219 columns={columns}
220 columnFilters={columnFilters}
221 data={forms ?? []}
222 isLoading={!hasResolved}
223 stripped={false}
224 isSorting={false}
225 />
226 </Card>
227
228 <div className={styles.footerRow}>
229 {hasResolved && forms && (
230 <button
231 className="button"
232 disabled={state.ids.length === 0}
233 onClick={() => showModal(true)}
234 >
235 {__('Associate forms', 'give')}
236 </button>
237 )}
238 <Pagination />
239 </div>
240 {state.showModal && campaignsLoaded && <ConfirmationModal />}
241 </>
242 );
243 };
244
245 export default OrphanedFormsListTable;
246