Statistics
| Revision:

gvsig-vectorediting / org.gvsig.vectorediting / trunk / org.gvsig.vectorediting / org.gvsig.vectorediting.lib / org.gvsig.vectorediting.lib.prov / org.gvsig.vectorediting.lib.prov.reversedirection / src / main / java / org / gvsig / vectorediting / lib / prov / reversedirection / ReverseDirectionEditingProvider.java @ 2616

History | View | Annotate | Download (10.2 KB)

1
/* gvSIG. Desktop Geographic Information System.
2
 *
3
 * Copyright ? 2007-2015 gvSIG Association
4
 *
5
 * This program is free software; you can redistribute it and/or
6
 * modify it under the terms of the GNU General Public License
7
 * as published by the Free Software Foundation; either version 2
8
 * of the License, or (at your option) any later version.
9
 *
10
 * This program is distributed in the hope that it will be useful,
11
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13
 * GNU General Public License for more details.
14
 *
15
 * You should have received a copy of the GNU General Public License
16
 * along with this program; if not, write to the Free Software
17
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
18
 * MA  02110-1301, USA.
19
 *
20
 * For any additional information, do not hesitate to contact us
21
 * at info AT gvsig.com, or visit our website www.gvsig.com.
22
 */
23
package org.gvsig.vectorediting.lib.prov.reversedirection;
24

    
25
import java.util.ArrayList;
26
import java.util.List;
27
import org.gvsig.fmap.dal.exception.DataException;
28
import org.gvsig.fmap.dal.feature.EditableFeature;
29
import org.gvsig.fmap.dal.feature.Feature;
30
import org.gvsig.fmap.dal.feature.FeatureSelection;
31
import org.gvsig.fmap.dal.feature.FeatureStore;
32
import org.gvsig.fmap.geom.Geometry;
33
import org.gvsig.fmap.geom.Geometry.TYPES;
34
import org.gvsig.fmap.geom.GeometryException;
35
import org.gvsig.fmap.geom.GeometryLocator;
36
import org.gvsig.fmap.geom.GeometryManager;
37
import org.gvsig.fmap.geom.aggregate.MultiCurve;
38
import org.gvsig.fmap.geom.operation.GeometryOperationException;
39
import org.gvsig.fmap.geom.operation.GeometryOperationNotSupportedException;
40
import org.gvsig.fmap.geom.primitive.Curve;
41
import org.gvsig.fmap.geom.primitive.Line;
42
import org.gvsig.fmap.geom.primitive.Point;
43
import org.gvsig.fmap.geom.primitive.Spline;
44
import org.gvsig.fmap.geom.type.GeometryType;
45
import org.gvsig.tools.ToolsLocator;
46
import org.gvsig.tools.dispose.DisposeUtils;
47
import org.gvsig.tools.dynobject.DynObject;
48
import org.gvsig.tools.exception.BaseException;
49
import org.gvsig.tools.service.spi.ProviderServices;
50
import org.gvsig.vectorediting.lib.api.DrawingStatus;
51
import org.gvsig.vectorediting.lib.api.EditingServiceParameter;
52
import org.gvsig.vectorediting.lib.api.EditingServiceParameter.TYPE;
53
import org.gvsig.vectorediting.lib.api.exceptions.DrawServiceException;
54
import org.gvsig.vectorediting.lib.api.exceptions.FinishServiceException;
55
import org.gvsig.vectorediting.lib.api.exceptions.InvalidEntryException;
56
import org.gvsig.vectorediting.lib.api.exceptions.StartServiceException;
57
import org.gvsig.vectorediting.lib.api.exceptions.StopServiceException;
58
import org.gvsig.vectorediting.lib.spi.AbstractEditingProvider;
59
import org.gvsig.vectorediting.lib.spi.DefaultEditingServiceParameter;
60
import org.gvsig.vectorediting.lib.spi.EditingProvider;
61
import org.gvsig.vectorediting.lib.spi.EditingProviderFactory;
62
import org.gvsig.vectorediting.lib.spi.EditingProviderServices;
63

    
64
/**
65
 *
66
 * @author <a href="mailto:lmarques@disid.com">Lluis Marques</a>
67
 *
68
 */
69
public class ReverseDirectionEditingProvider extends AbstractEditingProvider
70
    implements EditingProvider {
71

    
72
    private final EditingServiceParameter selectionParameter;
73

    
74
    private FeatureSelection selection;
75

    
76
    private final FeatureStore featureStore;
77

    
78
    public ReverseDirectionEditingProvider(ProviderServices providerServices,
79
        DynObject parameters) {
80
        super(providerServices);
81

    
82
        this.featureStore =
83
            (FeatureStore) parameters
84
                .getDynValue(EditingProviderFactory.FEATURE_STORE_FIELD);
85

    
86
        this.selectionParameter =
87
            new DefaultEditingServiceParameter("selection", "selection",
88
                TYPE.SELECTION);
89
    }
90

    
91
    @Override
92
    public EditingServiceParameter next() {
93
        if (selection == null) {
94
            return this.selectionParameter;
95
        }
96
        return null;
97
    }
98

    
99
    @Override
100
    public DrawingStatus getDrawingStatus(Point mousePosition)
101
        throws DrawServiceException {
102
        return null;
103
    }
104

    
105
    @Override
106
    public void stop() throws StopServiceException {
107
        ToolsLocator.getDisposableManager().release(selection);
108
        DisposeUtils.disposeQuietly(selection);
109
        this.selection = null;
110
    }
111

    
112
    @Override
113
    public List<EditingServiceParameter> getParameters() {
114
        List<EditingServiceParameter> parameters =
115
            new ArrayList<>();
116
        parameters.add(selectionParameter);
117
        return parameters;
118
    }
119

    
120
    @Override
121
    public void setValue(EditingServiceParameter parameter, Object value) throws InvalidEntryException {
122
        validateAndInsertValue(parameter, value);
123
    }
124

    
125
    @Override
126
    public void setValue(Object value) throws InvalidEntryException {
127
        EditingServiceParameter parameter = next();
128
        validateAndInsertValue(parameter, value);
129
    }
130

    
131
    private void validateAndInsertValue(EditingServiceParameter parameter,
132
        Object value) throws InvalidEntryException {
133

    
134
        if (parameter == selectionParameter) {
135

    
136
            if (value instanceof FeatureSelection) {
137
                FeatureSelection featureSelection = (FeatureSelection) value;
138

    
139
                if (featureSelection.getSelectedCount() > 0) {
140
                    try {
141
                        featureSelection.accept((Object obj) -> {
142
                            Feature feature = (Feature) obj;
143
                            Geometry geometry =
144
                                    feature.getDefaultGeometry();
145
                            GeometryType geometryType =
146
                                    geometry.getGeometryType();
147
                            
148
                            if (!geometryType.isTypeOf(TYPES.CURVE)
149
                                    && !geometryType.isTypeOf(TYPES.MULTICURVE)) {
150
                                throw new InvalidEntryException(null);
151
                            }
152
                        });
153
                    } catch (BaseException e) {
154
                        throw new InvalidEntryException(e);
155
                    }
156
                    ToolsLocator.getDisposableManager().bind(
157
                        (FeatureSelection) value);
158
                    this.selection = featureSelection;
159
                } else {
160
                    throw new InvalidEntryException(null);
161
                }
162
            }
163
        }
164
    }
165

    
166
    @Override
167
    public Geometry finish() throws FinishServiceException {
168
        return null;
169
    }
170

    
171
    @Override
172
    public void finishAndStore() throws FinishServiceException {
173

    
174
        if (selection != null) {
175

    
176
            final EditingProviderServices editingProviderServices =
177
                (EditingProviderServices) getProviderServices();
178

    
179
            try {
180
                selection.accept((Object obj) -> {
181
                    Feature feature = (Feature) obj;
182
                    EditableFeature eFeature = feature.getEditable();
183
                    Geometry geometry = eFeature.getDefaultGeometry();
184
                    
185
                    eFeature.setDefaultGeometry(reverseDirection(geometry));
186
                    editingProviderServices.updateFeatureInFeatureStore(
187
                            eFeature, featureStore);
188
                });
189

    
190
                ToolsLocator.getDisposableManager().release(selection);
191
                DisposeUtils.dispose(selection);
192
                featureStore.getFeatureSelection().deselectAll();
193

    
194
            } catch (BaseException e) {
195
                throw new FinishServiceException(e);
196
            }
197
        }
198
    }
199

    
200
    private Geometry reverseDirection(Geometry geometry)
201
        throws GeometryException, GeometryOperationNotSupportedException, GeometryOperationException {
202
        GeometryManager geometryManager = GeometryLocator.getGeometryManager();
203
        GeometryType geometryType = geometry.getGeometryType();
204

    
205
        if (geometryType.isTypeOf(TYPES.MULTICURVE)) {
206
            MultiCurve reversedMultiCurve =
207
                geometryManager.createMultiCurve(geometryType.getSubType());
208
            MultiCurve multicurve = (MultiCurve) geometry;
209
            for (int i = 0; i < multicurve.getPrimitivesNumber(); i++) {
210
                reversedMultiCurve.addCurve(reverseCurve(multicurve.getCurveAt(i)));
211
            }
212
            return reversedMultiCurve;
213
        } else if (geometryType.isTypeOf(TYPES.CURVE)) {
214
            return reverseCurve((Curve) geometry);
215
        } else {
216
            throw new IllegalArgumentException(String.format(
217
                "Can't reverse geometry with {} type", geometryType.getType()));
218
        }
219
    }
220

    
221
    private Curve reverseCurve(Curve curve) throws GeometryException, GeometryOperationNotSupportedException, GeometryOperationException {
222
        GeometryManager geometryManager = GeometryLocator.getGeometryManager();
223
        Curve curveToReverse = null;
224
        Curve reverseCurve = null;
225
        if(curve instanceof Line || curve instanceof Spline){
226
            reverseCurve = (Curve) curve.cloneGeometry();
227
            reverseCurve.flip();
228
        } else {
229
            curveToReverse = (Curve) curve.toLines().getPrimitiveAt(0);
230
            reverseCurve = (Curve) geometryManager.create(Geometry.TYPES.LINE, curve.getGeometryType().getSubType());
231
            for (int i = curveToReverse.getNumVertices() - 1; i >= 0; i--) {
232
                reverseCurve.addVertex(curveToReverse.getVertex(i));
233
            }
234
        }
235
        return reverseCurve;
236
    }
237

    
238
    @Override
239
    public void start() throws StartServiceException, InvalidEntryException {
240
        FeatureSelection selected = null;
241
        if (featureStore != null) {
242
            try {
243
                selected = featureStore.getFeatureSelection();
244
            } catch (DataException e) {
245
                throw new StartServiceException(e);
246
            }
247

    
248
            if (selected.getSelectedCount() > 0) {
249
                try {
250
                    setValue(selected);
251
                } catch (InvalidEntryException e) {
252
                    throw new InvalidEntryException(e);
253
                }
254
            }
255
        }
256
    }
257

    
258
    @Override
259
    public String getName() {
260
        return ReverseDirectionEditingProviderFactory.PROVIDER_NAME;
261
    }
262

    
263
    @Override
264
    public Object getValue(EditingServiceParameter parameter) {
265
        if(parameter == this.selectionParameter){
266
            return this.selection;
267
        }
268
        return null;
269
    }
270
}