2 * Copyright (C) 2018 EDIT
3 * European Distributed Institute of Taxonomy
4 * http://www.e-taxonomy.eu
6 * The contents of this file are subject to the Mozilla Public License Version 1.1
7 * See LICENSE.TXT at the top of this package for the full license terms.
9 package eu
.etaxonomy
.taxeditor
.editor
.descriptiveDataSet
.matrix
;
11 import java
.util
.ArrayList
;
12 import java
.util
.Collection
;
13 import java
.util
.List
;
15 import java
.util
.UUID
;
16 import java
.util
.stream
.Collectors
;
18 import org
.eclipse
.jface
.layout
.GridDataFactory
;
19 import org
.eclipse
.jface
.window
.Window
;
20 import org
.eclipse
.swt
.SWT
;
21 import org
.eclipse
.swt
.events
.SelectionAdapter
;
22 import org
.eclipse
.swt
.events
.SelectionEvent
;
23 import org
.eclipse
.swt
.layout
.RowLayout
;
24 import org
.eclipse
.swt
.widgets
.Button
;
25 import org
.eclipse
.swt
.widgets
.Composite
;
27 import eu
.etaxonomy
.cdm
.api
.service
.IDescriptionService
;
28 import eu
.etaxonomy
.cdm
.api
.service
.IDescriptiveDataSetService
;
29 import eu
.etaxonomy
.cdm
.api
.service
.ITaxonNodeService
;
30 import eu
.etaxonomy
.cdm
.api
.service
.UpdateResult
;
31 import eu
.etaxonomy
.cdm
.api
.service
.dto
.RowWrapperDTO
;
32 import eu
.etaxonomy
.cdm
.api
.service
.dto
.SpecimenRowWrapperDTO
;
33 import eu
.etaxonomy
.cdm
.api
.service
.dto
.TaxonRowWrapperDTO
;
34 import eu
.etaxonomy
.cdm
.common
.CdmUtils
;
35 import eu
.etaxonomy
.cdm
.model
.description
.CategoricalData
;
36 import eu
.etaxonomy
.cdm
.model
.description
.Feature
;
37 import eu
.etaxonomy
.cdm
.model
.description
.QuantitativeData
;
38 import eu
.etaxonomy
.cdm
.model
.description
.SpecimenDescription
;
39 import eu
.etaxonomy
.cdm
.model
.taxon
.Taxon
;
40 import eu
.etaxonomy
.cdm
.model
.taxon
.TaxonNode
;
41 import eu
.etaxonomy
.cdm
.persistence
.dto
.SpecimenNodeWrapper
;
42 import eu
.etaxonomy
.cdm
.persistence
.dto
.TaxonNodeDto
;
43 import eu
.etaxonomy
.taxeditor
.model
.ImageResources
;
44 import eu
.etaxonomy
.taxeditor
.model
.MessagingUtils
;
45 import eu
.etaxonomy
.taxeditor
.store
.CdmStore
;
46 import eu
.etaxonomy
.taxeditor
.ui
.dialog
.selection
.TaxonSelectionDialog
;
53 public class CharacterMatrixBottomToolbar
extends Composite
{
55 private CharacterMatrix matrix
;
57 public CharacterMatrixBottomToolbar(CharacterMatrix matrix
, int style
) {
66 setLayout(new RowLayout());
67 GridDataFactory
.fillDefaults().grab(true, false).applyTo(this);
70 * Add description button
72 Button btnAddDescription
= new Button(this, SWT
.PUSH
);
73 btnAddDescription
.setImage(ImageResources
.getImage(ImageResources
.ADD_ICON_GREEN
));
74 btnAddDescription
.addSelectionListener(new SelectionAdapter() {
76 public void widgetSelected(SelectionEvent e
) {
78 SpecimenSelectionDialog dialog
= new SpecimenSelectionDialog(matrix
.getShell(), matrix
);
79 if(dialog
.open()==Window
.OK
){
80 Collection
<SpecimenNodeWrapper
> wrappers
= dialog
.getSpecimen();
81 for (SpecimenNodeWrapper wrapper
: wrappers
) {
82 SpecimenDescription specimenDescription
= CdmStore
.getService(IDescriptiveDataSetService
.class)
83 .findSpecimenDescription(matrix
.getDescriptiveDataSet().getUuid(),
84 wrapper
.getUuidAndTitleCache().getUuid());
85 SpecimenRowWrapperDTO rowWrapper
= CdmStore
.getService(IDescriptiveDataSetService
.class)
86 .createSpecimenRowWrapper(specimenDescription
, matrix
.getDescriptiveDataSet(), true);
88 error
+= specimenDescription
;
91 //add specimen description
92 matrix
.getDescriptions().add(rowWrapper
);
93 matrix
.getDescriptiveDataSet().addDescription(specimenDescription
);
94 matrix
.getCdmEntitiySession().load(specimenDescription
, true);
96 //add taxon description
97 TaxonRowWrapperDTO taxonDescription
= rowWrapper
.getDefaultTaxonDescription();
98 matrix
.getDescriptiveDataSet().addDescription(taxonDescription
.getDescription());
99 matrix
.getCdmEntitiySession().load(taxonDescription
.getDescription(), true);
102 matrix
.getSpecimenCache().remove(wrapper
);
104 if(CdmUtils
.isNotBlank(error
)){
105 MessagingUtils
.warningDialog("Errors during row creation", this,
106 String
.format("Could not create rows for the following description:\n\n%s", error
));
112 * Remove description button
114 Button btnRemoveDescription
= new Button(this, SWT
.PUSH
);
115 btnRemoveDescription
.setImage(ImageResources
.getImage(ImageResources
.ACTIVE_DELETE_ICON
));
116 btnRemoveDescription
.addSelectionListener(new SelectionAdapter() {
118 public void widgetSelected(SelectionEvent e
) {
119 int[] fullySelectedRowPositions
= matrix
.getBodyLayer().getSelectionLayer().getFullySelectedRowPositions();
120 List
<RowWrapperDTO
> toRemove
= new ArrayList
<>();
121 for (int i
: fullySelectedRowPositions
) {
122 Object rowObject
= matrix
.getBodyDataProvider().getRowObject(i
);
123 if(rowObject
instanceof RowWrapperDTO
){
124 toRemove
.add((RowWrapperDTO
) rowObject
);
127 toRemove
.forEach(rowToRemove
->{
128 matrix
.getDescriptions().remove(rowToRemove
);
129 matrix
.getDescriptiveDataSet().removeDescription(rowToRemove
.getDescription());
137 Button btnAggregate
= new Button(this, SWT
.PUSH
);
138 btnAggregate
.setText("Aggregate");
139 btnAggregate
.addSelectionListener(new SelectionAdapter() {
141 public void widgetSelected(SelectionEvent e
) {
142 List
<TaxonNode
> taxonSubtreeFilter
= CdmStore
.getService(IDescriptiveDataSetService
.class).loadFilteredTaxonNodes(matrix
.getDescriptiveDataSet(), null);
143 List
<TaxonNodeDto
> nodeDtos
= taxonSubtreeFilter
.stream()
144 .map(node
-> new TaxonNodeDto(node
)).collect(Collectors
.toList());
145 TaxonNodeDto parentDto
= CdmStore
.getService(ITaxonNodeService
.class).findCommonParentDto(nodeDtos
);
146 UUID taxonUuid
= parentDto
.getTaxonUuid();
147 int response
= MessagingUtils
.confirmDialog(
148 "Choose location for the aggregated description",
149 String
.format("The aggregated description will be stored at "
150 + "the common parent taxon of this data set:\n%s\n\n"
151 + "Do you want to use this taxon?"
152 , parentDto
.getTaxonTitleCache()), "Yes", "Choose taxon", "Cancel");
156 else if(response
==1){
157 Taxon taxon
= TaxonSelectionDialog
.selectTaxon(getShell(), null);
161 taxonUuid
= taxon
.getUuid();
163 List
<UUID
> descriptionUuids
= new ArrayList
<>();
164 matrix
.getDescriptiveDataSet().getDescriptions().forEach(desc
->descriptionUuids
.add(desc
.getUuid()));
165 UpdateResult result
= CdmStore
.getService(IDescriptionService
.class).aggregateDescription(taxonUuid
, descriptionUuids
, matrix
.getDescriptiveDataSet().getLabel(), matrix
.getDescriptiveDataSet().getUuid());
166 matrix
.addUpdateResult(result
);
169 aggregateCategorcialHistogram(matrix
.getFeatureToHistogramMap());
170 aggregateQuantitativeSummary(matrix
.getFeatureToQuantDataStatisticsMap());
176 @SuppressWarnings("unchecked")
177 private void aggregateCategorcialHistogram(Map
<Feature
, CategoricalDataHistogram
> featureToHistogramMap
) {
178 featureToHistogramMap
.clear();
179 matrix
.getDescriptions().stream()
180 .filter(desc
->desc
instanceof SpecimenRowWrapperDTO
)
181 .forEach(o
-> ((SpecimenRowWrapperDTO
) o
).getDescription().getElements().stream()
182 .filter(descriptionElement
-> descriptionElement
instanceof CategoricalData
)
183 .forEach(categoricalData
-> {
184 Feature feature
= ((CategoricalData
) categoricalData
).getFeature();
185 CategoricalDataHistogram dataHistogram
= featureToHistogramMap
.get(feature
);
186 if(dataHistogram
==null){
187 dataHistogram
= new CategoricalDataHistogram(feature
);
189 featureToHistogramMap
.put(feature
, dataHistogram
);
190 ((CategoricalData
) categoricalData
).getStateData()
191 .forEach(stateData
-> featureToHistogramMap
.get(feature
).addState(stateData
.getState()));
195 @SuppressWarnings("unchecked")
196 private void aggregateQuantitativeSummary(Map
<Feature
, QuantitativeDataStatistics
> featureToQuantDataStatisticsMap
) {
197 featureToQuantDataStatisticsMap
.clear();
198 matrix
.getDescriptions().stream()
199 .filter(desc
->desc
instanceof SpecimenRowWrapperDTO
)
200 .forEach(o
-> ((SpecimenRowWrapperDTO
) o
).getDescription().getElements().stream()
201 .filter(descriptionElement
-> descriptionElement
instanceof QuantitativeData
)
202 .forEach(quantData
-> {
203 Feature feature
= ((QuantitativeData
) quantData
).getFeature();
204 QuantitativeDataStatistics dataStatistics
= featureToQuantDataStatisticsMap
.get(feature
);
205 if(dataStatistics
==null){
206 dataStatistics
= new QuantitativeDataStatistics();
208 featureToQuantDataStatisticsMap
.put(feature
, dataStatistics
);
209 dataStatistics
.addQuantitativeData((QuantitativeData
) quantData
);