Statistics
| Revision:

svn-gvsig-desktop / trunk / org.gvsig.desktop / org.gvsig.desktop.compat.cdc / org.gvsig.fmap.dal / org.gvsig.fmap.dal.impl / src / main / java / org / gvsig / fmap / dal / feature / impl / FeatureManager.java @ 40559

History | View | Annotate | Download (11 KB)

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

    
26
import java.util.Collection;
27
import java.util.HashMap;
28
import java.util.Iterator;
29
import java.util.LinkedHashMap;
30
import java.util.LinkedHashSet;
31
import java.util.Map;
32
import java.util.NoSuchElementException;
33

    
34
import org.gvsig.fmap.dal.exception.DataException;
35
import org.gvsig.fmap.dal.feature.EditableFeature;
36
import org.gvsig.fmap.dal.feature.Feature;
37
import org.gvsig.fmap.dal.feature.FeatureAttributeDescriptor;
38
import org.gvsig.fmap.dal.feature.FeatureReference;
39
import org.gvsig.fmap.dal.feature.FeatureStore;
40
import org.gvsig.fmap.dal.feature.FeatureType;
41
import org.gvsig.fmap.dal.feature.impl.expansionadapter.ExpansionAdapter;
42

    
43

    
44
/**
45
 * DOCUMENT ME!
46
 *
47
 * @author Vicente Caballero Navarro
48
 */
49
public class FeatureManager {
50
    private ExpansionAdapter expansionAdapter;
51
    private Collection deleted = new LinkedHashSet();//<FeatureID>
52
    private int deltaSize=0;
53
        private Map added = new LinkedHashMap();
54
        private Map addedAndDeleted = new LinkedHashMap();
55
        private HashMap modifiedFromOriginal=new HashMap();
56
    
57
        public FeatureManager(ExpansionAdapter expansionAdapter){
58
            this.expansionAdapter=expansionAdapter;
59
    }
60

    
61
        /**
62
         * Deletes feature from this manager. 
63
         * @param id 
64
         * @return The deleted feature or null if the
65
         * feature had not been edited or previously added in the editing session 
66
         */
67
    public Feature delete(FeatureReference id) {
68
        deleted.add(id);
69
                Integer num = (Integer) added.remove(id);
70
        Feature feature=null;
71
        if (num == null || num.intValue() == -1) {
72
            num = (Integer) modifiedFromOriginal.remove(id);
73
            if (num != null) {
74
                feature = (Feature) expansionAdapter.getObject(num.intValue());
75
            }
76
            // if num is null here, method returns null
77
                }else{
78
                        feature = (Feature) expansionAdapter.getObject(num.intValue());
79
                        addedAndDeleted.put(id, num);
80
                }
81
        deltaSize--;
82
        return feature;
83
    }
84

    
85
    /**
86
     * DOCUMENT ME!
87
     *
88
     * @param feature DOCUMENT ME!
89
     */
90
    public void add(Feature feature) {
91
        int pos = expansionAdapter.addObject(feature);
92
        added.put(feature.getReference(),new Integer(pos));
93
        deleted.remove(feature.getReference());
94
        deltaSize++;
95
    }
96

    
97
    /**
98
     * DOCUMENT ME!
99
     * @param id DOCUMENT ME!
100
     */
101
    public Feature deleteLastFeature() {
102
        expansionAdapter.deleteLastObject();
103
        Feature feature=(Feature)expansionAdapter.getObject(expansionAdapter.getSize()-1);
104
        added.remove(feature.getReference());
105
        modifiedFromOriginal.remove(feature.getReference());
106
        deltaSize--;
107
        return feature;
108
    }
109

    
110
    /**
111
     * Returns a Feature of the default type.
112
     *
113
     * @param id
114
     *            the feature reference
115
     * @param store
116
     *            the store to get the feature from
117
     * @return a Feature with the given reference
118
     * @throws DataException
119
     *             if there is an error getting the Feature
120
     */
121
    public Feature get(FeatureReference id, FeatureStore store)
122
            throws DataException {
123
        return get(id, store, null);
124
    }
125

    
126
    /**
127
     * Returns a Feature of the given type.
128
     *
129
     * @param id
130
     *            the feature reference
131
     * @param store
132
     *            the store to get the feature from
133
     * @param featureType
134
     *            the type of the feature to return
135
     * @return a Feature with the given reference
136
     * @throws DataException
137
     *             if there is an error getting the Feature
138
     */
139
    public Feature get(FeatureReference id, FeatureStore store,
140
                        FeatureType featureType) throws DataException {
141
            // FIXME: y si el featuretype que paso esta modificado.
142
            //        Deberia buscarlo en el featuretypemanager ?
143
                //
144
            //        Si no existe feature con ese id... ? retorna null ?
145
            //        en EditedDefaultIterator se hace uso de ese comportamiento.
146
            //
147
            Integer intNum = ((Integer) added.get(id));
148
            if (intNum == null){
149
                    intNum =((Integer) modifiedFromOriginal.get(id));
150
                if (intNum == null){                        
151
                    //If the feature has been added and deleted
152
                    intNum = (Integer)addedAndDeleted.get(id);
153
                    if (intNum == null){
154
                        return null;
155
                    }
156
                }
157
            }
158
        int num = intNum.intValue();
159
        if (num==-1) {
160
                        return null;
161
                }
162
        Feature feature=(Feature)expansionAdapter.getObject(num);
163
        if (featureType== null){
164
                featureType = store.getDefaultFeatureType();
165
        }
166
               return getCorrectFeature(feature, store,featureType);
167
    }
168

    
169
    private Feature getCorrectFeature(Feature feature, FeatureStore store,
170
                        FeatureType featureType) throws DataException {
171
             Iterator iterator=featureType.iterator();
172
         EditableFeature newFeature=feature.getEditable();//store.createNewFeature(featureType, false);
173
         FeatureType orgType = feature.getType();
174
         int orgIndex;
175
         while (iterator.hasNext()) {
176
                         FeatureAttributeDescriptor fad = (FeatureAttributeDescriptor) iterator.next();
177
                         orgIndex = orgType.getIndex(fad.getName());
178
                         if (orgIndex<0){
179
                                 continue;
180
                         }
181
                         if (fad.isAutomatic() || fad.isReadOnly()
182
                                        || fad.getEvaluator() != null) {
183
                                continue;
184
                        }
185
                         Object value = feature.get(orgIndex);
186
                        if (value == null && !fad.allowNull()) {
187
                                continue;
188
                        }
189
                        newFeature.set(orgIndex, value);
190
                 }
191
        return newFeature.getNotEditableCopy();
192
        }
193

    
194
        /**
195
     * DOCUMENT ME!
196
     *
197
     * @param feature DOCUMENT ME!
198
     * @param oldFeature DOCUMENT ME!
199
     */
200
    public int update(Feature feature, Feature oldFeature) {
201
            int oldNum=-1;
202
        int num = expansionAdapter.addObject(feature);
203
        FeatureReference id=feature.getReference();
204
        if (added.containsKey(id)){
205
                oldNum=((Integer)added.get(id)).intValue();
206
                added.put(id,new Integer(num));
207
        }else{
208
                if (modifiedFromOriginal.get(id)!=null) {
209
                                oldNum=((Integer)modifiedFromOriginal.get(id)).intValue();
210
                        }
211
                modifiedFromOriginal.put(id,new Integer(num));
212
        }
213
        return oldNum;
214
    }
215

    
216
    /**
217
     * DOCUMENT ME!
218
     *
219
     * @param id DOCUMENT ME!
220
     */
221
    public void restore(FeatureReference id) {
222
        deleted.remove(id);
223
        deltaSize++;
224
    }
225
    public void restore(FeatureReference id,int num){
226
            if (added.containsKey(id)){
227
                added.put(id,new Integer(num));
228
        }else{
229
                modifiedFromOriginal.put(id,new Integer(num));
230
        }
231
    }
232

    
233

    
234
    public boolean isDeleted(Feature feature){
235
            return deleted.contains(feature.getReference());
236
    }
237

    
238
    public boolean isDeleted(FeatureReference featureID) {
239
                return deleted.contains(featureID);
240
        }
241

    
242
        public void clear() {
243
                added.clear();
244
                modifiedFromOriginal.clear();
245
            expansionAdapter.close();
246
            deleted.clear();//<FeatureID>
247
            addedAndDeleted.clear();
248
            deltaSize=0;
249
        }
250

    
251

    
252
        public boolean hasChanges() {
253
                return added.size()>0 || modifiedFromOriginal.size() > 0 || deleted.size() > 0;
254
        }
255

    
256
        public Iterator getDeleted() {
257
                return new DeletedIterator();
258

    
259
        }
260

    
261
        class DeletedIterator implements Iterator {
262
                private Boolean hasnext = null;
263
                private Iterator iter;
264
                private DefaultFeatureReference obj;
265

    
266
                public DeletedIterator(){
267
                        iter = deleted.iterator();
268
                }
269

    
270
                public boolean hasNext() {
271
                        if (hasnext != null) {
272
                                return hasnext.booleanValue();
273
                        }
274
                        hasnext = Boolean.FALSE;
275
                        while (iter.hasNext()) {
276
                                obj = (DefaultFeatureReference) iter.next();
277
                                if (obj.isNewFeature()) {
278
                                        continue;
279
                                }
280
                                hasnext = Boolean.TRUE;
281
                                break;
282
                        }
283
                        return hasnext.booleanValue();
284
                }
285

    
286
                public Object next() {
287
                        if (!hasNext()) {
288
                                throw new NoSuchElementException();
289
                        }
290

    
291
                        hasnext = null;
292
                        return obj;
293
                }
294

    
295
                public void remove() {
296
                        throw new UnsupportedOperationException();
297

    
298
                }
299

    
300
        }
301

    
302
        public Iterator getInserted() {
303
                return new InsertedIterator();
304
        }
305

    
306
        class InsertedIterator implements Iterator {
307

    
308
                private Iterator addedIter;
309
                private DefaultFeature obj;
310
                private Boolean hasnext = null;
311

    
312
                public InsertedIterator(){
313
                        addedIter = added.values().iterator();
314
                }
315

    
316
                public boolean hasNext() {
317
                        if (hasnext != null) {
318
                                return hasnext.booleanValue();
319
                        }
320
                        hasnext = Boolean.FALSE;
321
                        int pos;
322
                        while (addedIter.hasNext()) {
323
                                pos = ((Integer) addedIter.next()).intValue();
324
                                obj = (DefaultFeature) expansionAdapter.getObject(pos);
325
                                if (!deleted.contains(obj.getReference())) {
326
                                        hasnext = Boolean.TRUE;
327
                                        break;
328
                                }
329
                        }
330
                        return hasnext.booleanValue();
331
                }
332

    
333
                public Object next() {
334
                        if (!hasNext()) {
335
                                throw new NoSuchElementException();
336
                        }
337
                        hasnext = null;
338
                        return obj.getData();
339
                }
340

    
341
                public void remove() {
342
                        addedIter.remove();
343
                }
344

    
345
        }
346
        public Iterator getUpdated() {
347
                return new UpdatedIterator();
348
        }
349
        class UpdatedIterator implements Iterator{
350
                private Boolean hasnext = null;
351
                private Iterator iter;
352
                private DefaultFeature obj;
353
                private int pos;
354

    
355
                public UpdatedIterator() {
356
                        iter = expansionAdapter.iterator();
357
                        pos = -1;
358
                }
359

    
360
                public boolean hasNext() {
361
                        if (hasnext != null) {
362
                                return hasnext.booleanValue();
363
                        }
364
                        hasnext = Boolean.FALSE;
365
                        while (iter.hasNext()) {
366
                                pos++;
367
                                obj = (DefaultFeature) iter.next();
368
                                if (deleted.contains(obj.getReference())){
369
                                        continue;
370
                                }else if (!modifiedFromOriginal.containsValue(new Integer(pos))){
371
                                        continue;
372
                                }else {
373
                                        hasnext = Boolean.TRUE;
374
                                        break;
375
                                }
376
                        }
377
                        return hasnext.booleanValue();
378
                }
379

    
380
                public Object next() {
381
                        if (!hasNext()) {
382
                                throw new NoSuchElementException();
383
                        }
384
                        hasnext = null;
385
                        return obj.getData();
386
                }
387

    
388
                public void remove() {
389
                        throw new UnsupportedOperationException();
390

    
391
                }
392
        }
393

    
394
        public boolean hasNews() {
395
                return !added.isEmpty();
396
        }
397

    
398
        public long getDeltaSize() {
399
                return deltaSize;
400
        }
401
}