View Javadoc
1   package fr.ifremer.tutti.ui.swing.content.operation.catches.accidental;
2   
3   /*
4    * #%L
5    * Tutti :: UI
6    * %%
7    * Copyright (C) 2012 - 2014 Ifremer
8    * %%
9    * This program is free software: you can redistribute it and/or modify
10   * it under the terms of the GNU General Public License as
11   * published by the Free Software Foundation, either version 3 of the 
12   * License, or (at your option) any later version.
13   * 
14   * This program is distributed in the hope that it will be useful,
15   * but WITHOUT ANY WARRANTY; without even the implied warranty of
16   * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17   * GNU General Public License for more details.
18   * 
19   * You should have received a copy of the GNU General Public 
20   * License along with this program.  If not, see
21   * <http://www.gnu.org/licenses/gpl-3.0.html>.
22   * #L%
23   */
24  
25  import com.google.common.collect.Lists;
26  import com.google.common.collect.Sets;
27  import fr.ifremer.tutti.persistence.entities.TuttiEntities;
28  import fr.ifremer.tutti.persistence.entities.data.AccidentalBatch;
29  import fr.ifremer.tutti.persistence.entities.data.Attachment;
30  import fr.ifremer.tutti.persistence.entities.data.FishingOperation;
31  import fr.ifremer.tutti.persistence.entities.referential.Caracteristic;
32  import fr.ifremer.tutti.persistence.entities.referential.CaracteristicQualitativeValue;
33  import fr.ifremer.tutti.persistence.entities.referential.Species;
34  import fr.ifremer.tutti.service.DecoratorService;
35  import fr.ifremer.tutti.type.WeightUnit;
36  import fr.ifremer.tutti.ui.swing.content.operation.catches.AbstractTuttiBatchTableUIHandler;
37  import fr.ifremer.tutti.ui.swing.content.operation.catches.EditCatchesUI;
38  import fr.ifremer.tutti.ui.swing.content.operation.catches.EditCatchesUIHandler;
39  import fr.ifremer.tutti.ui.swing.content.operation.catches.EditCatchesUIModel;
40  import fr.ifremer.tutti.ui.swing.content.operation.catches.accidental.create.CreateAccidentalBatchUIModel;
41  import fr.ifremer.tutti.ui.swing.content.operation.catches.species.frequency.IndividualObservationBatchTableModel;
42  import fr.ifremer.tutti.ui.swing.util.TuttiBeanMonitor;
43  import fr.ifremer.tutti.ui.swing.util.TuttiUI;
44  import fr.ifremer.tutti.ui.swing.util.TuttiUIUtil;
45  import fr.ifremer.tutti.ui.swing.util.attachment.AttachmentCellEditor;
46  import fr.ifremer.tutti.ui.swing.util.attachment.AttachmentCellRenderer;
47  import fr.ifremer.tutti.ui.swing.util.caracteristics.CaracteristicMapCellComponent;
48  import fr.ifremer.tutti.ui.swing.util.caracteristics.CaracteristicMapColumnRowModel;
49  import fr.ifremer.tutti.ui.swing.util.caracteristics.CaracteristicMapColumnUIHandler;
50  import fr.ifremer.tutti.ui.swing.util.caracteristics.CaracteristicMapEditorUI;
51  import fr.ifremer.tutti.ui.swing.util.comment.CommentCellEditor;
52  import fr.ifremer.tutti.ui.swing.util.comment.CommentCellRenderer;
53  import jaxx.runtime.validator.swing.SwingValidator;
54  import org.apache.commons.logging.Log;
55  import org.apache.commons.logging.LogFactory;
56  import org.jdesktop.swingx.JXTable;
57  import org.jdesktop.swingx.table.DefaultTableColumnModelExt;
58  import org.nuiton.decorator.Decorator;
59  import org.nuiton.jaxx.application.swing.table.ColumnIdentifier;
60  import org.nuiton.validator.NuitonValidatorResult;
61  
62  import javax.swing.JComponent;
63  import java.util.List;
64  
65  /**
66   * @author Tony Chemit - chemit@codelutin.com
67   * @since 0.2
68   */
69  public class AccidentalBatchUIHandler
70          extends AbstractTuttiBatchTableUIHandler<AccidentalBatchRowModel, AccidentalBatchUIModel, AccidentalBatchTableModel, AccidentalBatchUI>
71          implements CaracteristicMapColumnUIHandler {
72  
73      /** Logger. */
74      private static final Log log =
75              LogFactory.getLog(AccidentalBatchUIHandler.class);
76  
77      /**
78       * Weight unit.
79       *
80       * @since 2.5
81       */
82      protected WeightUnit weightUnit;
83  
84      public AccidentalBatchUIHandler() {
85          super(
86                  AccidentalBatchRowModel.PROPERTY_SPECIES,
87                  AccidentalBatchRowModel.PROPERTY_GENDER,
88                  AccidentalBatchRowModel.PROPERTY_WEIGHT,
89                  AccidentalBatchRowModel.PROPERTY_SIZE,
90                  AccidentalBatchRowModel.PROPERTY_LENGTH_STEP_CARACTERISTIC,
91                  AccidentalBatchRowModel.PROPERTY_DEAD_OR_ALIVE,
92                  AccidentalBatchRowModel.PROPERTY_CARACTERISTICS,
93                  AccidentalBatchRowModel.PROPERTY_COMMENT,
94                  AccidentalBatchRowModel.PROPERTY_ATTACHMENT);
95      }
96  
97      //------------------------------------------------------------------------//
98      //-- AbstractTuttiBatchTableUIHandler methods                           --//
99      //------------------------------------------------------------------------//
100 
101     @Override
102     protected ColumnIdentifier<AccidentalBatchRowModel> getCommentIdentifier() {
103         return AccidentalBatchTableModel.COMMENT;
104     }
105 
106     @Override
107     protected ColumnIdentifier<AccidentalBatchRowModel> getAttachementIdentifier() {
108         return AccidentalBatchTableModel.ATTACHMENT;
109     }
110 
111     @Override
112     public void selectFishingOperation(FishingOperation bean) {
113 
114         boolean empty = bean == null;
115 
116         AccidentalBatchUIModel model = getModel();
117 
118         List<AccidentalBatchRowModel> rows;
119 
120         if (empty) {
121             rows = null;
122         } else {
123 
124             if (log.isDebugEnabled()) {
125                 log.debug("Get accidental batch for fishingOperation: " +
126                           bean.getId());
127             }
128             rows = Lists.newArrayList();
129 
130             if (!TuttiEntities.isNew(bean)) {
131 
132                 // get all marine litter root
133                 List<AccidentalBatch> batches =
134                         getPersistenceService().getAllAccidentalBatch(bean.getIdAsInt());
135 
136                 for (AccidentalBatch aBatch : batches) {
137                     AccidentalBatchRowModel entry = loadBatch(aBatch);
138                     rows.add(entry);
139                 }
140             }
141         }
142         model.setRows(rows);
143     }
144 
145     //------------------------------------------------------------------------//
146     //-- AbstractTuttiTableUIHandler methods                                --//
147     //------------------------------------------------------------------------//
148 
149     @Override
150     protected void beforeOpenPopup(int rowIndex, int columnIndex) {
151         super.beforeOpenPopup(rowIndex, columnIndex);
152 
153         boolean enableRemove = false;
154 
155         if (rowIndex != -1) {
156 
157             // there is a selected row
158             enableRemove = true;
159         }
160         AccidentalBatchUIModel model = getModel();
161         model.setRemoveBatchEnabled(enableRemove);
162     }
163 
164     @Override
165     public AccidentalBatchTableModel getTableModel() {
166         return (AccidentalBatchTableModel) getTable().getModel();
167     }
168 
169     @Override
170     public JXTable getTable() {
171         return ui.getTable();
172     }
173 
174     @Override
175     protected boolean isRowValid(AccidentalBatchRowModel row) {
176         AccidentalBatch batch = row.toEntity();
177         NuitonValidatorResult validator =
178                 getValidationService().validateEditAccidentalBatch(batch);
179         return !validator.hasErrorMessagess();
180     }
181 
182     @Override
183     protected void saveSelectedRowIfRequired(TuttiBeanMonitor<AccidentalBatchRowModel> rowMonitor,
184                                              AccidentalBatchRowModel row) {
185 
186         if (row != null && row.isValid() && rowMonitor.wasModified()) {
187 
188             // monitored bean was modified, save it
189             if (log.isInfoEnabled()) {
190                 log.info("Row " + row + " was modified, will save it");
191             }
192 
193             String title = buildReminderLabelTitle(row.getSpecies(),
194                                                    null,
195                                                    "Sauvegarde de la capture accidentelle : ",
196                                                    "Ligne :" + (getTableModel().getRowIndex(row) + 1));
197 
198             showInformationMessage(title);
199 
200             rowMonitor.setBean(null);
201             saveRow(row);
202             rowMonitor.setBean(row);
203 
204             // clear modified flag on the monitor
205             rowMonitor.clearModified();
206         }
207     }
208 
209     //------------------------------------------------------------------------//
210     //-- AbstractTuttiUIHandler methods                                     --//
211     //------------------------------------------------------------------------//
212 
213     @Override
214     public SwingValidator<AccidentalBatchUIModel> getValidator() {
215         return null;
216     }
217 
218     @Override
219     public void beforeInit(AccidentalBatchUI ui) {
220         super.beforeInit(ui);
221 
222         weightUnit = getConfig().getAccidentalCatchWeightUnit();
223 
224         if (log.isDebugEnabled()) {
225             log.debug("beforeInit: " + ui);
226         }
227 
228         EditCatchesUIModel catchesUIModel =
229                 ui.getContextValue(EditCatchesUIModel.class);
230 
231         AccidentalBatchUIModel model = new AccidentalBatchUIModel(catchesUIModel);
232         ui.setContextValue(model);
233     }
234 
235     @Override
236     public void afterInit(AccidentalBatchUI ui) {
237 
238         if (log.isDebugEnabled()) {
239             log.debug("afterInit: " + ui);
240         }
241 
242         initUI(ui);
243 
244         JXTable table = getTable();
245 
246         // create table column model
247         DefaultTableColumnModelExt columnModel =
248                 new DefaultTableColumnModelExt();
249 
250         Decorator<CaracteristicQualitativeValue> caracteristicQualitativeValueDecorator =
251                 getDecorator(CaracteristicQualitativeValue.class, null);
252 
253         {
254             // Id column
255 
256             addIdColumnToModel(columnModel, AccidentalBatchTableModel.ID, table);
257 
258         }
259 
260         {
261             // Species column
262 
263             Decorator<Species> speciesDecorator = getDecorator(
264                     Species.class, DecoratorService.FROM_PROTOCOL);
265             addComboDataColumnToModel(columnModel,
266                                       AccidentalBatchTableModel.SPECIES,
267                                       speciesDecorator,
268                                       getDataContext().getReferentSpecies());
269 
270         }
271 
272         { // Gender caracteristic column
273 
274             addComboDataColumnToModel(columnModel,
275                                       AccidentalBatchTableModel.GENDER,
276                                       caracteristicQualitativeValueDecorator,
277                                       getDataContext().getGenderValues());
278 
279         }
280 
281         { // Weight column
282 
283             addFloatColumnToModel(columnModel,
284                                   AccidentalBatchTableModel.WEIGHT,
285                                   weightUnit,
286                                   table);
287         }
288 
289         { // Size column
290 
291             addFloatColumnToModel(columnModel,
292                                   AccidentalBatchTableModel.SIZE,
293                                   TuttiUI.DECIMAL3_PATTERN,
294                                   table);
295         }
296 
297         { // Length step caracteristic column
298             Decorator<Caracteristic> caracteristicDecorator =
299                     getDecorator(Caracteristic.class, null);
300             addComboDataColumnToModel(columnModel,
301                                       AccidentalBatchTableModel.LENGTH_STEP_CARACTERISTIC,
302                                       caracteristicDecorator,
303                                       getDataContext().getLengthStepCaracteristics());
304 
305         }
306 
307         { // Dead or alive caracteristic column
308 
309             addComboDataColumnToModel(columnModel,
310                                       AccidentalBatchTableModel.DEAD_OR_ALIVE,
311                                       caracteristicQualitativeValueDecorator,
312                                       getDataContext().getDeadOrAliveValues());
313 
314         }
315 
316         { // Other caracteristics column
317 
318             addColumnToModel(columnModel,
319                              CaracteristicMapCellComponent.newEditor(ui, Sets.<Caracteristic>newHashSet()),
320                              CaracteristicMapCellComponent.newRender(getContext()),
321                              IndividualObservationBatchTableModel.OTHER_CARACTERISTICS);
322 
323         }
324 
325         { // Comment column
326 
327             addColumnToModel(columnModel,
328                              CommentCellEditor.newEditor(ui),
329                              CommentCellRenderer.newRender(),
330                              AccidentalBatchTableModel.COMMENT);
331         }
332 
333         { // File column
334 
335             Decorator<Attachment> decorator = getDecorator(Attachment.class, null);
336             addColumnToModel(columnModel,
337                              AttachmentCellEditor.newEditor(ui),
338                              AttachmentCellRenderer.newRender(decorator),
339                              AccidentalBatchTableModel.ATTACHMENT);
340         }
341 
342         // create table model
343         AccidentalBatchTableModel tableModel =
344                 new AccidentalBatchTableModel(weightUnit, columnModel);
345 
346         table.setModel(tableModel);
347         table.setColumnModel(columnModel);
348 
349         initBatchTable(table, columnModel, tableModel);
350     }
351 
352     @Override
353     protected JComponent getComponentToFocus() {
354         return getUI().getTable();
355     }
356 
357     @Override
358     public void onCloseUI() {
359         if (log.isDebugEnabled()) {
360             log.debug("closing: " + ui);
361         }
362         ui.getAccidentalBatchAttachmentsButton().onCloseUI();
363     }
364 
365     @Override
366     public CaracteristicMapEditorUI getCaracteristicMapEditor() {
367         EditCatchesUI parent = getParentContainer(EditCatchesUI.class);
368         return parent.getAccidentalCaracteristicMapEditor();
369     }
370 
371     @Override
372     public void showCaracteristicMapEditor(CaracteristicMapColumnRowModel editRow) {
373         EditCatchesUI parent = getParentContainer(EditCatchesUI.class);
374         parent.getHandler().setAccidentalSelectedCard(EditCatchesUIHandler.EDIT_CARACTERISTICS_CARD, editRow.getSpecies());
375     }
376 
377     @Override
378     public void hideCaracteristicMapEditor() {
379         EditCatchesUI parent = getParentContainer(EditCatchesUI.class);
380         parent.getHandler().setAccidentalSelectedCard(EditCatchesUIHandler.MAIN_CARD);
381     }
382 
383     //------------------------------------------------------------------------//
384     //-- Public methods                                                     --//
385     //------------------------------------------------------------------------//
386 
387     public void addBatch(CreateAccidentalBatchUIModel model) {
388         if (model.isValid()) {
389 
390             AccidentalBatchTableModel tableModel = getTableModel();
391 
392             AccidentalBatchRowModel newRow = tableModel.createNewRow();
393             newRow.setSpecies(model.getSpecies());
394             newRow.setGender(model.getGender());
395             newRow.setWeight(model.getWeight());
396             newRow.setSize(model.getSize());
397             newRow.setLengthStepCaracteristic(model.getLengthStepCaracteristic());
398             newRow.setDeadOrAlive(model.getDeadOrAlive());
399 
400             recomputeRowValidState(newRow);
401 
402             saveRow(newRow);
403 
404             tableModel.addNewRow(newRow);
405             TuttiUIUtil.selectFirstCellOnLastRow(getTable());
406         }
407     }
408 
409     //------------------------------------------------------------------------//
410     //-- Internal methods                                                   --//
411     //------------------------------------------------------------------------//
412 
413     protected AccidentalBatchRowModel loadBatch(AccidentalBatch aBatch) {
414 
415         AccidentalBatchRowModel newRow =
416                 new AccidentalBatchRowModel(weightUnit, aBatch);
417 
418         List<Attachment> attachments =
419                 getPersistenceService().getAllAttachments(newRow.getObjectType(),
420                                                           newRow.getObjectId());
421 
422         newRow.addAllAttachment(attachments);
423 
424         return newRow;
425     }
426 
427     protected void saveRow(AccidentalBatchRowModel row) {
428 
429         AccidentalBatch entityToSave = row.toEntity();
430 
431         FishingOperation fishingOperation = getModel().getFishingOperation();
432         entityToSave.setFishingOperation(fishingOperation);
433         if (log.isDebugEnabled()) {
434             log.debug("Selected fishingOperation: " + fishingOperation.getId());
435         }
436 
437         if (TuttiEntities.isNew(entityToSave)) {
438 
439             getPersistenceService().createAccidentalBatch(entityToSave);
440             row.setId(entityToSave.getId());
441         } else {
442             getPersistenceService().saveAccidentalBatch(entityToSave);
443         }
444 
445         fireBatchSaved(row);
446     }
447 }