]> git.agnieray.net Git - galette.git/blob - galette/templates/default/pages/transaction_form.html.twig
Add and use member dropdown form component
[galette.git] / galette / templates / default / pages / transaction_form.html.twig
1 {#
2 /**
3 * Copyright © 2003-2024 The Galette Team
4 *
5 * This file is part of Galette (https://galette.eu).
6 *
7 * Galette is free software: you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation, either version 3 of the License, or
10 * (at your option) any later version.
11 *
12 * Galette is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with Galette. If not, see <http://www.gnu.org/licenses/>.
19 */
20 #}
21 {% extends "page.html.twig" %}
22
23 {% block content %}
24 {% if members.list is defined %}
25 <form action="{% if transaction.id %}{{ url_for("editTransaction", {"id": transaction.id}) }}{% else %}{{ url_for("addTransaction") }}{% endif %}" enctype="multipart/form-data" method="post" class="ui form">
26 <div class="ui styled fluid accordion field">
27 <div class="active title">
28 <i class="jsonly displaynone icon dropdown" aria-hidden="true"></i>
29 {{ _T("Transaction details") }}
30 </div>
31 <div class="active content">
32 <div class="ui mobile reversed stackable grid">
33 <div class="{% if transaction.id %}five wide {% endif %}column">
34 <div class="field inline{% if required.trans_desc is defined and required.trans_desc == 1 %} required{% endif %}">
35 <label for="trans_desc">{{ _T("Description:") }}</label>
36 <input type="text" name="trans_desc" id="trans_desc" value="{{ transaction.description }}" maxlength="150" size="30"{% if required.trans_desc is defined and required.trans_desc == 1 %} required="required"{% endif %}/>
37 </div>
38 {% include 'components/forms/member_dropdown.html.twig' with {
39 'required': required.id_adh is defined and required.id_adh == 1,
40 'id': 'id_adh',
41 'label': _T("Originator:"),
42 'value': transaction.member,
43 'component_class': 'inline field'
44 } %}
45 <div class="field inline{% if required.trans_date is defined and required.trans_date == 1 %} required{% endif %}">
46 <label for="trans_date">{{ _T("Date:") }}</label>
47 <div class="ui calendar" id="transaction-rangestart">
48 <div class="ui input left icon">
49 <i class="calendar icon" aria-hidden="true"></i>
50 <input type="text" class="date-pick" name="trans_date" id="trans_date" value="{{ transaction.date }}" maxlength="10"{% if required.trans_date is defined and required.trans_date == 1 %} required="required"{% endif %} placeholder="{{ _T('yyyy-mm-dd format') }}" />
51 </div>
52 </div>
53 </div>
54 <div class="field inline{% if required.trans_amount is defined and required.trans_amount == 1 %} required{% endif %}">
55 <label for="trans_amount">{{ _T("Amount:") }}</label>
56 <input type="text" name="trans_amount" id="trans_amount" value="{{ transaction.amount }}" maxlength="10"{% if required.trans_amount is defined and required.trans_amount == 1 %} required="required"{% endif %}/>
57 </div>
58 <div class="field inline{% if required.trans_payment_type is defined and required.trans_payment_type == 1 %} required{% endif %}">
59 {# payment type #}
60 {% set ptype = transaction.payment_type %}
61 {% include 'components/forms/payment_types.html.twig' with {
62 'current': ptype,
63 'varname': 'type_paiement_trans',
64 'show_inline': true,
65 'empty': {
66 'label': _T("None"),
67 'value': '0'
68 }
69 } %}
70 </div>
71 {% if transaction.id == null %}
72 <div class="field inline">
73 <label class="inline" title="{{ _T("Select a contribution type to create for dispatch transaction") }}">{{ _T("Dispatch type:") }}</label>
74 <i class="circular inverted primary small icon info tooltip" title="{{ _T("Select a contribution type to create for dispatch transaction") }}" aria-hidden="true"></i>
75 <input type="radio" name="contrib_type" id="contrib_type_fee" value="{{ constant('Galette\\Entity\\Contribution::TYPE_FEE') }}"/> <label for="contrib_type_fee">{{ _T("Membership fee") }}</label>
76 <input type="radio" name="contrib_type" id="contrib_type_donation" value="{{ constant('Galette\\Entity\\Contribution::TYPE_DONATION') }}"/> <label for="contrib_type_donation">{{ _T("Donation") }}</label>
77 </div>
78 {% endif %}
79 </div>
80 {% if transaction.id %}
81 <div class="eleven wide column">
82 <div class="ui tiny header">{{ _T("Attached contributions") }}</div>
83 <table class="listing ui very compact small celled yellow table">
84 <thead>
85 <tr>
86 <th class="id_row">#</th>
87 <th class="left date_row">{{ _T("Date") }}</th>
88 <th class="left date_row">{{ _T("Begin") }}</th>
89 <th class="left date_row">{{ _T("End") }}</th>
90 <th class="left">{{ _T("Duration") }}</th>
91 {% if login.isAdmin() or login.isStaff() %}
92 <th class="left">{{ _T("Member") }}</th>
93 {% endif %}
94 <th class="left">{{ _T("Type") }}</th>
95 <th class="left">{{ _T("Amount") }}</th>
96 {% if login.isAdmin() or login.isStaff() %}
97 <th class="actions_row">{{ _T("Actions") }}</th>
98 {% endif %}
99 </tr>
100 </thead>
101 <tfoot>
102 <tr>
103 <th class="right bgfree" colspan="{% if login.isAdmin() or login.isStaff() %}7{% else %}5{% endif %}">{{ _T("Dispatched amount:") }}</th>
104 <th class="right bgfree">{{ transaction.getDispatchedAmount() }}</th>
105 <td></td>
106 </tr>
107 <tr>
108 <th class="right bgfree" colspan="{% if login.isAdmin() or login.isStaff() %}7{% else %}5{% endif %}">{{ _T("Not dispatched amount:") }}</th>
109 <th class="right bgfree">{{ transaction.getMissingAmount() }}</th>
110 <td></td>
111 </tr>
112 {% if transaction.getMissingAmount() > 0 %}
113 <tr>
114 <th colspan="{% if login.isAdmin() or login.isStaff() %}9{% else %}7{% endif %}">
115 <div class="ui basic fitted right aligned segment">
116 <a
117 href="{{ url_for("addContribution", {"type": constant('Galette\\Entity\\Contribution::TYPE_FEE')}) }}?trans_id={{ transaction.id }}"
118 class="ui icon green compact button tooltip"
119 title="{{ _T("Create a new fee that will be attached to the current transaction") }}"
120 >
121 <i class="plus tiny icon" aria-hidden="true"></i>
122 <i class="user check icon" aria-hidden="true"></i>
123 <span class="visually-hidden">{{ _T("Create a new fee that will be attached to the current transaction") }}</span>
124 </a>
125 <a
126 href="{{ url_for("addContribution", {"type": constant('Galette\\Entity\\Contribution::TYPE_DONATION')}) }}?trans_id={{ transaction.id }}"
127 class="ui icon green compact button tooltip"
128 title="{{ _T("Create a new donation that will be attached to the current transaction") }}"
129 >
130 <i class="plus tiny icon" aria-hidden="true"></i>
131 <i class="gift icon" aria-hidden="true"></i>
132 <span class="visually-hidden">{{ _T("Create a new donation that will be attached to the current transaction") }}</span>
133 </a>
134 <a
135 href="#"
136 class="ui icon blue compact button tooltip"
137 title="{{ _T("Select an existing contribution in the database, and attach it to the current transaction") }}"
138 id="contribslist"
139 >
140 <i class="receipt icon" aria-hidden="true"></i>
141 <span class="visually-hidden">{{ _T("Select an existing contribution in the database, and attach it to the current transaction") }}</span>
142 </a>
143 </div>
144 </th>
145 </tr>
146 {% endif %}
147 </tfoot>
148 <tbody>
149 {% for ordre, contrib in contribs %}
150 {% set mid = contrib.member %}
151 <tr class="{{ contrib.getRowClass() }}">
152 <td class="center">
153 {{ ordre + 1 }}
154 </td>
155 <td class="center">{{ contrib.date }}</td>
156 <td class="center">{{ contrib.begin_date }}</td>
157 <td class="center">{{ contrib.end_date }}</td>
158 <td>{{ contrib.duration }}</td>
159 {% if login.isAdmin() or login.isStaff() %}
160 <td>{{ memberName({'id': mid}) }}</td>
161 {% endif %}
162 <td>{{ contrib.type.libelle }}</td>
163 <td class="right">{{ contrib.amount }}</td>
164 {% if login.isAdmin() or login.isStaff() %}
165 <td class="actions_row">
166 <a
167 href="{{ url_for("detach_contribution", {"id": transaction.id, "cid": contrib.id}) }}"
168 class="delete"
169 >
170 <i class="ui red trash icon tooltip" aria-hidden="true"></i>
171 <span class="ui special popup">{{ _T("Detach contribution from this transaction") }}</span>
172 </a>
173 </td>
174 {% endif %}
175 </tr>
176 {% else %}
177 <tr><td colspan="{% if login.isAdmin() or login.isStaff() %}9{% else %}7{% endif %}" class="emptylist">{{ _T("no contribution") }}</td></tr>
178 {% endfor %}
179 </tbody>
180 </table>
181 </div>
182 {% endif %}
183 </div>
184 </div>
185 </div>
186
187 {% include "components/dynamic_fields.html.twig" with {'object': transaction} %}
188
189 <div class="ui basic center aligned segment">
190 <button type="submit" name="valid" class="ui labeled icon primary button action">
191 <i class="save icon" aria-hidden="true"></i> {{ _T("Save") }}
192 </button>
193 <input type="hidden" name="trans_id" value="{{ transaction.id }}"/>
194 <input type="hidden" name="valid" value="1"/>
195 {% include "components/forms/csrf.html.twig" %}
196 </div>
197 </form>
198 {% else %} {# No members #}
199 <div class="ui warning message" id="warningbox">
200 <h3>{{ _T("No member registered!") }}</h3>
201 <p>
202 {{ _T("Unfortunately, there is no member in your database yet,") }}
203 <br/>
204 <a href="{{ url_for("addMember") }}">{{ _T("please create a member") }}</a>
205 </p>
206 </div>
207 {% endif %}
208 {% endblock %}
209
210 {% block javascripts %}
211 <script type="text/javascript">
212 {% include "elements/js/choose_adh.js.twig" %}
213 document.getElementById('id_adh_input').type = 'hidden';
214
215 $(function(){
216 {% if transaction.id %}
217 {# Contributions popup #}
218 var _btnuser_mapping = function(){
219 $('#contribslist').click(function(){
220 $.ajax({
221 url: '{{ url_for("contributions", {"type": "contributions"}) }}',
222 type: "GET",
223 data: {
224 ajax: true,
225 max_amount: '{{ transaction.getMissingAmount() }}'
226 },
227 {% include "elements/js/loader.js.twig" with {
228 selector: '#contribslist',
229 loader: 'button'
230 } %},
231 success: function(res){
232 _contribs_dialog(res, '{{ transaction.getMissingAmount() }}');
233 },
234 error: function() {
235 {% include "elements/js/modal.js.twig" with {
236 modal_title_twig: _T("An error occurred displaying contributions :(")|e("js"),
237 modal_without_content: true,
238 modal_class: "mini",
239 modal_deny_only: true,
240 modal_cancel_text: _T("Close")|e("js"),
241 modal_classname: "redalert",
242 } %}
243 }
244 });
245 });
246 }
247 _btnuser_mapping();
248
249 var _contribs_dialog = function(res, max_amount){
250 {% include "elements/js/modal.js.twig" with {
251 modal_title_twig: _T("Contributions selection")|e("js"),
252 modal_content: "res",
253 modal_class: "contributions-selection fullscreen",
254 modal_content_class: "scrolling",
255 modal_deny_only: true,
256 modal_cancel_text: _T("Close")|e('js')
257 } %}
258 _contribs_ajax_mapper(res, max_amount);
259 }
260
261 var _contribs_ajax_mapper = function(res, max_amount){
262 $('.contributions-selection .filter.icon').remove();
263 $('.contributions-selection .infoline .button').remove();
264 $('.contributions-selection .contribution_row input[type=checkbox]').hide();
265
266 //Initialize Fomantic components
267 $('.contributions-selection .dropdown').dropdown();
268 {% include "elements/js/calendar.js.twig" %}
269
270 //Deactivate contributions list links
271 $('.contributions-selection tbody a').click(function(){
272 //for links in body (members links), we de nothing
273 return false;
274 });
275
276 //Use JS to send forms
277 $('.contributions-selection form').on('submit', function(){
278 var _form = $(this);
279 $.ajax({
280 url: _form.attr('action'),
281 type: "POST",
282 data: _form.serialize(),
283 {% include "elements/js/loader.js.twig" with {
284 selector: '.contributions-selection'
285 } %},
286 success: function(res){
287 $('#main-container').remove();
288 $('.contributions-selection .content').append(res);
289 _contribs_ajax_mapper(res, max_amount);
290 },
291 error: function() {
292 {% include "elements/js/modal.js.twig" with {
293 modal_title_twig: _T("An error occurred displaying contributions :(")|e("js"),
294 modal_without_content: true,
295 modal_class: "mini",
296 modal_deny_only: true,
297 modal_cancel_text: _T("Close")|e("js"),
298 modal_classname: "redalert",
299 } %}
300 }
301 });
302 return false;
303 });
304
305 _bindDropdownsAutosubmit();
306
307 //Bind pagination and ordering links
308 $('.contributions-selection .pagination a, .contributions-selection thead a').click(function() {
309 $.ajax({
310 url: this.href,
311 type: "GET",
312 data: {
313 ajax: true,
314 max_amount: max_amount
315 },
316 {% include "elements/js/loader.js.twig" with {
317 selector: '.contributions-selection'
318 } %},
319 success: function(res){
320 $('#main-container').remove();
321 $('.contributions-selection .content').append(res);
322 _contribs_ajax_mapper(res, max_amount);
323 },
324 error: function() {
325 {% include "elements/js/modal.js.twig" with {
326 modal_title_twig: _T("An error occurred displaying contributions :(")|e("js"),
327 modal_without_content: true,
328 modal_class: "mini",
329 modal_deny_only: true,
330 modal_cancel_text: _T("Close")|e("js"),
331 modal_classname: "redalert",
332 } %}
333 },
334 });
335 return false;
336 });
337
338 //Bind reset filters button
339 $('#clear_filter').click(function(event) {
340 var _this = $(this);
341 _this.closest('form').submit(function(event) {
342 var _form = $(this);
343 $.ajax({
344 url: _form.attr('action'),
345 type: "POST",
346 data: {
347 clear_filter: true
348 },
349 {% include "elements/js/loader.js.twig" with {
350 selector: '.contributions-selection'
351 } %},
352 success: function(res){
353 $('#main-container').remove();
354 $('.contributions-selection .content').append(res);
355 _contribs_ajax_mapper(res, max_amount);
356 },
357 error: function() {
358 {% include "elements/js/modal.js.twig" with {
359 modal_title_twig: _T("An error occurred displaying contributions :(")|e("js"),
360 modal_without_content: true,
361 modal_class: "mini",
362 modal_deny_only: true,
363 modal_cancel_text: _T("Close")|e("js"),
364 modal_classname: "redalert",
365 } %}
366 }
367 });
368 });
369 });
370
371 //Select a row
372 $('.contributions-selection .contribution_row').click(function(){
373 $('.contributions-selection').modal('hide');
374 var _cid = $(this).find('input[name="entries_sel[]"]').val();
375 window.location.href = '{{ url_for("attach_contribution", {"id": transaction.id, "cid": "%cid"}) }}'.replace(/%cid/, _cid);
376 }).css('cursor', 'pointer').attr('title', '{{ _T("Click on a contribution row to attach it to the current transaction")|e('js') }}');
377 }
378 {% endif %}
379 });
380 </script>
381 {% endblock %}