summaryrefslogtreecommitdiff
path: root/misc/openlayers/tests/Control/ModifyFeature.html
diff options
context:
space:
mode:
Diffstat (limited to 'misc/openlayers/tests/Control/ModifyFeature.html')
-rw-r--r--misc/openlayers/tests/Control/ModifyFeature.html828
1 files changed, 828 insertions, 0 deletions
diff --git a/misc/openlayers/tests/Control/ModifyFeature.html b/misc/openlayers/tests/Control/ModifyFeature.html
new file mode 100644
index 0000000..6226733
--- /dev/null
+++ b/misc/openlayers/tests/Control/ModifyFeature.html
@@ -0,0 +1,828 @@
+<html>
+<head>
+ <script src="../OLLoader.js"></script>
+ <script type="text/javascript">
+
+ function test_initialize(t) {
+ t.plan(3);
+ var layer = {
+ styleMap: {createSymbolizer: function(){}},
+ events: {
+ on: function() {},
+ un: function() {}
+ }
+ };
+ var options = {
+ documentDrag: true
+ };
+ var control = new OpenLayers.Control.ModifyFeature(layer, options);
+
+ t.ok(control.layer == layer,
+ "constructor sets layer correctly");
+ t.eq(control.handlers.drag.documentDrag, true,
+ "constructor sets options correctly on drag handler");
+ t.eq(control.mode, OpenLayers.Control.ModifyFeature.RESHAPE,
+ "constructor initializes modification mode correctly");
+ control.destroy();
+ }
+
+ function test_destroy(t) {
+ t.plan(1);
+ var map = new OpenLayers.Map("map");
+ var layer = new OpenLayers.Layer.Vector();
+ map.addLayer(layer);
+ var control = new OpenLayers.Control.ModifyFeature(layer);
+ control.destroy();
+ t.eq(control.layer, null, "Layer reference removed on destroy.");
+ map.destroy();
+ }
+
+ function test_activate(t) {
+ t.plan(2);
+ var map = new OpenLayers.Map("map");
+ var layer = new OpenLayers.Layer.Vector();
+ map.addLayer(layer);
+ var control = new OpenLayers.Control.ModifyFeature(layer);
+ map.addControl(control);
+ t.ok(!control.handlers.drag.active,
+ "drag handler is not active prior to activating control");
+ control.activate();
+ t.ok(control.handlers.drag.active,
+ "drag handler is active after activating control");
+
+ map.destroy();
+ }
+
+ function test_initDeleteCodes(t) {
+ t.plan(3);
+ var layer = new OpenLayers.Layer.Vector();
+ var control = new OpenLayers.Control.ModifyFeature(layer, {'deleteCodes': 46});
+ t.eq(control.deleteCodes[0], 46, "Delete code properly turned into an array.");
+ var control = new OpenLayers.Control.ModifyFeature(layer);
+ t.eq(control.deleteCodes[0], 46, "Default deleteCodes include delete");
+ t.eq(control.deleteCodes[1], 68, "Default deleteCodes include 'd'");
+
+ control.destroy();
+ layer.destroy();
+ }
+
+ function test_handleKeypress(t) {
+ t.plan(16);
+
+ /**
+ * There are two things that we want to test here
+ * 1) test that control.deleteCodes are respected
+ * 3) test that a vertex is properly deleted
+ *
+ * In the future, feature deletion may be added to the control.
+ */
+
+ var layer = new OpenLayers.Layer.Vector();
+ var control = new OpenLayers.Control.ModifyFeature(layer);
+ var delKey = 46;
+ var dKey = 100;
+ control.deleteCodes = [delKey, dKey];
+
+ // test that a polygon vertex is deleted for all delete codes
+ var point = new OpenLayers.Feature.Vector(
+ new OpenLayers.Geometry.Point()
+ );
+ var poly = new OpenLayers.Feature.Vector(
+ new OpenLayers.Geometry.Polygon()
+ );
+
+ // mock up vertex deletion
+ var origGetFeatureFromEvent = layer.getFeatureFromEvent;
+ layer.getFeatureFromEvent = function() { return point; };
+ control.feature = poly;
+ // we cannot use selectFeature since the control is not part of a map
+ control._originalGeometry = poly.geometry.clone();
+ control.vertices = [point];
+ point.geometry.parent = {
+ removeComponent: function(geometry) {
+ t.eq(geometry.id, point.geometry.id,
+ "vertex deletion: removeComponent called on parent with proper geometry");
+ }
+ };
+ layer.events.on({
+ "featuremodified": function(event) {
+ t.ok(event.feature.modified !== null, "modified property of feature should have been set");
+ t.eq(event.feature.id, poly.id, "vertex deletion: featuremodifed triggered");
+ },
+ "vertexremoved": function(evt) {
+ layer.events.unregister("vertexremoved", this, arguments.callee);
+ t.eq(evt.feature.id, poly.id, "vertexremoved triggered with correct feature");
+ t.eq(evt.vertex.id, point.geometry.id, "vertexremoved triggered with correct vertex");
+ t.eq(evt.pixel, "foo", "vertexremoved triggered with correct pixel");
+ }
+ });
+ layer.drawFeature = function(feature) {
+ t.eq(feature.id, poly.id,
+ "vertex deletion: drawFeature called with the proper feature");
+ };
+ control.resetVertices = function() {
+ t.ok(true, "vertex deletion: resetVertices called");
+ };
+ control.onModification = function(feature) {
+ t.eq(feature.id, poly.id,
+ "vertex deletion: onModification called with the proper feature");
+ };
+ // run the above four tests twice
+ control.handleKeypress({keyCode:delKey, xy: "foo"});
+ control.handleKeypress({keyCode:dKey});
+ t.eq(control.feature.state, OpenLayers.State.UPDATE, "feature state set to update");
+
+ // now make sure nothing happens if the vertex is mid-drag
+ control.handlers.drag.dragging = true;
+ control.handleKeypress({keyCode:delKey});
+
+ // clean up
+ layer.getFeatureFromEvent = origGetFeatureFromEvent;
+ control.destroy();
+ layer.destroy();
+ }
+
+
+ function test_onUnSelect(t) {
+ t.plan(5);
+ var layer = new OpenLayers.Layer.Vector();
+ var control = new OpenLayers.Control.ModifyFeature(layer);
+ var fakeFeature = {'id':'myid'};
+ control.vertices = 'a';
+ control.virtualVertices = 'b';
+ control.features = true;
+ layer.events.on({"afterfeaturemodified": function(event) {
+ t.eq(event.feature, fakeFeature, "afterfeaturemodified triggered");
+ }});
+ control.onModificationEnd = function (feature) { t.eq(feature.id, fakeFeature.id, "onModificationEnd got feature.") }
+ layer.removeFeatures = function(verts) {
+ t.ok(verts == 'a', "Normal verts removed correctly");
+ }
+ layer.destroyFeatures = function(verts) {
+ t.ok(verts == 'b', "Virtual verts destroyed correctly");
+ }
+ control.unselectFeature(fakeFeature);
+ t.eq(control.feature, null, "feature is set to null");
+
+ layer.destroyFeatures = function() {};
+ control.destroy();
+ layer.destroy();
+ }
+
+ function test_stop_modification(t) {
+ t.plan(1);
+ var map = new OpenLayers.Map('map');
+ var layer = new OpenLayers.Layer.Vector("Vectors!", {isBaseLayer: true});
+ var feature = new OpenLayers.Feature.Vector(
+ new OpenLayers.Geometry.Point(0, 0)
+ );
+ layer.addFeatures([feature]);
+ map.addLayer(layer);
+ map.setCenter(new OpenLayers.LonLat(0, 0));
+
+
+ // If a feature is to be modified, control.selectFeature gets called.
+ // We want this test to fail if selectFeature gets called.
+ var modified = false;
+
+ var control = new OpenLayers.Control.ModifyFeature(layer);
+ map.addControl(control);
+ control.activate();
+
+ // register a listener that will stop feature modification
+ layer.events.on({"beforefeaturemodified": function() {return false}});
+
+ // we can initiate feature modification by programmatically selecting
+ // a feature
+ control.selectFeature(feature);
+
+ if(modified) {
+ t.fail("selectFeature called, prepping feature for modification");
+ } else {
+ t.ok(true, "the beforefeaturemodified listener stopped feature modification");
+ }
+ }
+
+ function test_selectFeature(t) {
+ t.plan(12);
+ var map = new OpenLayers.Map('map');
+ var layer = new OpenLayers.Layer.Vector("Vectors!", {isBaseLayer: true});
+ map.addLayer(layer);
+ map.setCenter(new OpenLayers.LonLat(0, 0));
+ var control = new OpenLayers.Control.ModifyFeature(layer);
+ control.vertices = [];
+ control.virtualVertices = [];
+ var callback = function(obj) {
+ t.ok(obj.feature == fakeFeature, "beforefeaturemodified triggered");
+ };
+ layer.events.on({"beforefeaturemodified": callback});
+ control.onModificationStart = function(feature) { t.eq(feature.id, fakeFeature.id, "On Modification Start called with correct feature."); }
+
+ // Start of testing
+
+ control.collectVertices = function() { t.fail("Collect vertices called when geom is a point"); }
+ var fakeFeature = new OpenLayers.Feature.Vector(new OpenLayers.Geometry.Point(0, 0));
+
+ // Points don't call collectVertices
+ control.selectFeature(fakeFeature);
+ control.unselectFeature(fakeFeature);
+
+ control.collectVertices = function() {
+ t.ok(true, "collectVertices called");
+ this.vertices = 'a';
+ this.virtualVertices = 'd';
+ layer.addFeatures(this.vertices);
+ layer.addFeatures(this.virtualVertices);
+ }
+
+ layer.addFeatures = function(features) {
+ t.ok(features == 'a' || features == 'd', "features passed correctly");
+ }
+ layer.destroyFeatures = function() {};
+
+ fakeFeature.geometry = new OpenLayers.Geometry.Polygon([
+ new OpenLayers.Geometry.LinearRing([
+ new OpenLayers.Geometry.Point(0, 0),
+ new OpenLayers.Geometry.Point(1, 1)
+ ])
+ ]);
+
+ // OnSelect calls collectVertices and passes features to layer
+ control.selectFeature(fakeFeature);
+ control.unselectFeature(fakeFeature);
+ layer.destroyFeatures = OpenLayers.Layer.Vector.prototype.destroyFeatures;
+
+ control.vertices = ['a'];
+ control.virtualVertices = [{destroy: function() {}}];
+
+ layer.addFeatures = function(features) {}
+
+ layer.removeFeatures = function(features) {
+ t.eq(features.length, 1, "Correct feature length passed in");
+ }
+
+ // Features are removed whenever they exist
+ control.selectFeature(fakeFeature);
+
+ control.destroy();
+
+ // layer.destroy() will call removeFeatures with an empty array, make
+ // removeFeatures reference an empty function to prevent the above
+ // test to fail
+ layer.removeFeatures = function(features) {};
+ layer.destroy();
+ }
+
+ function test_resetVertices(t) {
+ t.plan(20);
+ var layer = new OpenLayers.Layer.Vector();
+ var control = new OpenLayers.Control.ModifyFeature(layer);
+ var point = new OpenLayers.Geometry.Point(5,6);
+ var point2 = new OpenLayers.Geometry.Point(7,8);
+ var point3 = new OpenLayers.Geometry.Point(9,10);
+
+ control.feature = new OpenLayers.Feature.Vector(point);
+ control.resetVertices();
+ t.eq(control.vertices.length, 0, "Correct vertices length");
+ t.eq(control.virtualVertices.length, 0, "Correct virtual vertices length.");
+
+ var multiPoint = new OpenLayers.Geometry.MultiPoint([point, point2]);
+ control.feature = new OpenLayers.Feature.Vector(multiPoint);
+ control.resetVertices();
+ t.eq(control.vertices.length, 2, "Correct vertices length with multipoint");
+ t.eq(control.virtualVertices.length, 0, "Correct virtual vertices length (multipoint).");
+
+ var line = new OpenLayers.Geometry.LineString([point, point2]);
+ control.feature = new OpenLayers.Feature.Vector(line);
+ control.resetVertices();
+ t.eq(control.vertices.length, 2, "Correct vertices length with line");
+ t.eq(control.virtualVertices.length, 1, "Correct virtual vertices length (linestring).");
+
+ var polygon = new OpenLayers.Geometry.Polygon([new OpenLayers.Geometry.LinearRing([point, point2, point3])]);
+ control.feature = new OpenLayers.Feature.Vector(polygon);
+ control.resetVertices();
+ t.eq(control.vertices.length, 3, "Correct vertices length with polygon");
+ t.eq(control.virtualVertices.length, 3, "Correct virtual vertices length (polygon).");
+
+ control.mode = OpenLayers.Control.ModifyFeature.DRAG;
+ control.resetVertices();
+ t.ok(control.dragHandle != null, "Drag handle is set");
+ t.eq(control.vertices.length, 0, "Correct vertices length with polygon (DRAG)");
+
+ control.mode = OpenLayers.Control.ModifyFeature.ROTATE;
+ control.resetVertices();
+ t.ok(control.radiusHandle != null, "Radius handle is set");
+ t.eq(control.vertices.length, 0, "Correct vertices length with polygon (ROTATE)");
+
+ control.mode = OpenLayers.Control.ModifyFeature.RESIZE;
+ control.resetVertices();
+ t.ok(control.radiusHandle != null, "Radius handle is set");
+ t.eq(control.vertices.length, 0, "Correct vertices length with polygon (RESIZE)");
+
+ control.mode = OpenLayers.Control.ModifyFeature.RESHAPE;
+ control.resetVertices();
+ t.ok(control.radiusHandle == null, "Radius handle is not set (RESHAPE)");
+ t.eq(control.vertices.length, 3, "Correct vertices length with polygon (RESHAPE)");
+ t.eq(control.virtualVertices.length, 3, "Correct virtual vertices length (RESHAPE)");
+
+ control.mode = OpenLayers.Control.ModifyFeature.RESIZE | OpenLayers.Control.ModifyFeature.RESHAPE;
+ control.resetVertices();
+ t.ok(control.radiusHandle != null, "Radius handle is set (RESIZE|RESHAPE)");
+ t.eq(control.vertices.length, 0, "No vertices when both resizing and reshaping (RESIZE|RESHAPE)");
+ t.eq(control.virtualVertices.length, 0, "No virtual vertices when both resizing and reshaping (RESIZE|RESHAPE)");
+
+ control.destroy();
+ layer.destroy();
+ }
+
+ function test_dragVertex(t) {
+ t.plan(8);
+ var map = new OpenLayers.Map("map", {
+ resolutions: [1]
+ });
+ var layer = new OpenLayers.Layer.Vector("foo", {
+ maxExtent: new OpenLayers.Bounds(-10, -10, 10, 10),
+ isBaseLayer: true
+ });
+ map.addLayer(layer);
+
+ var control = new OpenLayers.Control.ModifyFeature(layer);
+ map.addControl(control);
+ control.activate();
+
+ map.zoomToMaxExtent();
+
+ var log = {};
+ layer.events.on({
+ "vertexmodified": function(event) {
+ log.event = event;
+ }
+ });
+
+ // pretend to drag a point
+ var feature = new OpenLayers.Feature.Vector(
+ new OpenLayers.Geometry.Point(0, 0)
+ );
+ control.feature = feature;
+ var pixel = new OpenLayers.Pixel(-100, 100);
+ control.dragVertex(feature, pixel);
+ t.eq(log.event.type, "vertexmodified", "[drag point] vertexmodified triggered");
+ t.geom_eq(log.event.vertex, feature.geometry, "[drag point] listeners receive correct vertex");
+ t.eq(log.event.feature.id, feature.id, "[drag point] listeners receive correct feature");
+ t.ok(log.event.pixel === pixel, "[drag point] listeners receive correct pixel");
+
+ // pretend to drag vertex of a linestring
+ var vert = new OpenLayers.Feature.Vector(
+ new OpenLayers.Geometry.Point(0, 0)
+ );
+ var feature = new OpenLayers.Feature.Vector(
+ new OpenLayers.Geometry.LineString([
+ vert.geometry, new OpenLayers.Geometry.Point(10, 0)
+ ])
+ );
+ control.feature = feature;
+ var pixel = new OpenLayers.Pixel(-100, 100);
+ control.dragVertex(vert, pixel);
+ t.eq(log.event.type, "vertexmodified", "[drag vertex] vertexmodified triggered");
+ t.geom_eq(log.event.vertex, vert.geometry, "[drag vertex] listeners receive correct vertex");
+ t.eq(log.event.feature.id, feature.id, "[drag vertex] listeners receive correct feature");
+ t.ok(log.event.pixel === pixel, "[drag vertex] listeners receive correct pixel");
+
+
+ map.destroy();
+ }
+ function test_collectDragHandle(t) {
+ t.plan(4);
+ var map = new OpenLayers.Map("map", {
+ resolutions: [1]
+ });
+ var layer = new OpenLayers.Layer.Vector("foo", {
+ maxExtent: new OpenLayers.Bounds(-10, -10, 10, 10),
+ isBaseLayer: true
+ });
+ map.addLayer(layer);
+ var feature = new OpenLayers.Feature.Vector(new OpenLayers.Geometry.Point(1,1));
+ layer.addFeatures([feature]);
+ var control = new OpenLayers.Control.ModifyFeature(layer);
+ map.addControl(control);
+ control.activate();
+ control.feature = feature;
+ control.collectDragHandle();
+ t.ok(control.dragHandle != null, "Drag handle created");
+ t.ok(control.dragHandle._sketch == true, "Handle has _sketch true");
+ t.ok(control.dragHandle.renderIntent == control.vertexRenderIntent,"Render intent for handle set");
+ t.ok(control.layer.getFeatureById(control.dragHandle.id) != null, "Drag handle added to layer");
+ }
+ function test_collectRadiusHandle(t) {
+ t.plan(4);
+ var map = new OpenLayers.Map("map", {
+ resolutions: [1]
+ });
+ var layer = new OpenLayers.Layer.Vector("foo", {
+ maxExtent: new OpenLayers.Bounds(-10, -10, 10, 10),
+ isBaseLayer: true
+ });
+ map.addLayer(layer);
+ var feature = new OpenLayers.Feature.Vector(new OpenLayers.Geometry.Point(1,1));
+ layer.addFeatures([feature]);
+ var control = new OpenLayers.Control.ModifyFeature(layer);
+ map.addControl(control);
+ control.activate();
+ control.feature = feature;
+ control.collectRadiusHandle();
+ t.ok(control.radiusHandle != null, "Radius handle created");
+ t.ok(control.radiusHandle._sketch == true, "Radius has _sketch true");
+ t.ok(control.radiusHandle.renderIntent == control.vertexRenderIntent,"Render intent for handle set");
+ t.ok(control.layer.getFeatureById(control.radiusHandle.id) != null, "Drag radius added to layer");
+ }
+ function test_onDrag(t) {
+ t.plan(1);
+ t.ok(true, "onDrag not tested yet.");
+ }
+
+ function test_dragComplete(t) {
+ t.plan(8);
+ var layer = new OpenLayers.Layer.Vector();
+ var control = new OpenLayers.Control.ModifyFeature(layer);
+
+ var fakeFeature = {
+ 'geometry': { 'id':'myGeom'},
+ 'id': 'fakeFeature'
+ };
+ layer.addFeatures = function (verts) {
+ t.ok(verts == 'virtual' || verts == 'normal', verts + " verts correct");
+ }
+ layer.removeFeatures = function (verts) {
+ t.ok(verts == 'previous virtual' || verts == 'previous normal', verts + " verts correct");
+ }
+ layer.events.on({"featuremodified": function(event) {
+ t.eq(event.feature, fakeFeature, "featuremodified triggered");
+ }});
+ control.onModification = function(feat) {
+ t.eq(feat.id, fakeFeature.id, "onModification gets correct feat");
+ }
+ control.collectVertices = function() {
+ t.ok(true, "collectVertices called");
+ this.vertices = 'normal';
+ this.virtualVertices = 'virtual';
+ layer.addFeatures(this.vertices);
+ layer.addFeatures(this.virtualVertices);
+ }
+ control.feature = fakeFeature;
+ control.vertices = 'previous normal';
+ control.virtualVertices = 'previous virtual';
+ control.dragComplete();
+ t.eq(fakeFeature.state, OpenLayers.State.UPDATE, "feature state set to UPDATE");
+
+ control.destroy();
+
+ // layer.destroy() will call removeFeatures with an empty array, make
+ // removeFeatures reference an empty function to prevent the above
+ // test to fail
+ layer.removeFeatures = function(verts) {};
+ layer.destroy();
+ }
+
+ function test_deactivate(t) {
+ t.plan(2);
+ var map = new OpenLayers.Map("map");
+ var layer = new OpenLayers.Layer.Vector();
+ map.addLayer(layer);
+ var control = new OpenLayers.Control.ModifyFeature(layer);
+ map.addControl(control);
+
+ control.handlers.keyboard.deactivate = function() {
+ t.ok(true,
+ "control.deactivate calls deactivate on keyboard handler");
+ }
+ control.handlers.drag.deactivate = function() {
+ t.ok(true,
+ "control.deactivate calls deactivate on drag handler");
+ }
+ control.active = true;
+ control.deactivate();
+
+ control.handlers.keyboard.deactivate = OpenLayers.Handler.Keyboard.prototype.deactivate;
+ control.handlers.drag.deactivate = OpenLayers.Handler.Drag.prototype.deactivate;
+ map.destroy();
+ }
+
+ function test_onModificationStart(t) {
+ t.plan(5);
+ var map = new OpenLayers.Map("map");
+ var layer = new OpenLayers.Layer.Vector(null, {
+ styleMap: new OpenLayers.StyleMap({
+ "vertex": new OpenLayers.Style({foo: "bar"})
+ }, {extendDefault: false})
+ });
+ map.addLayer(layer);
+ var control = new OpenLayers.Control.ModifyFeature(layer);
+ map.addControl(control);
+ control.activate();
+
+ // make sure onModificationStart is called on feature selection
+ var testFeature = new OpenLayers.Feature.Vector(
+ OpenLayers.Geometry.fromWKT("LINESTRING(3 4,10 50,20 25)")
+ );
+ layer.addFeatures([testFeature]);
+ control.onModificationStart = function(feature) {
+ t.eq(feature.id, testFeature.id,
+ "onModificationStart called with the right feature");
+ };
+ control.selectFeature(testFeature);
+
+ // make sure styles are set correctly from default style
+ t.eq(control.virtualStyle, OpenLayers.Util.applyDefaults({
+ strokeOpacity: 0.3,
+ fillOpacity: 0.3
+ }, OpenLayers.Feature.Vector.style["default"]), "virtual style set correctly");
+ var vertex = layer.features[layer.features.length-1];
+ t.eq(vertex.renderIntent, null, "vertex style set correctly - uses default style");
+ control.unselectFeature(testFeature);
+
+ // make sure styles are set correctly with vertexRenderIntent
+ control = new OpenLayers.Control.ModifyFeature(layer, {vertexRenderIntent: "vertex"});
+ map.addControl(control);
+ control.activate();
+ control.selectFeature(testFeature);
+ t.eq(control.virtualStyle, {
+ strokeOpacity: 0.3,
+ fillOpacity: 0.3,
+ foo: "bar"
+ }, "virtual style set correctly");
+ var vertex = layer.features[layer.features.length-1];
+ t.eq(vertex.renderIntent, "vertex", "vertex style set correctly - uses 'vertex' renderIntent");
+ control.unselectFeature(testFeature);
+
+ map.destroy();
+ }
+
+ function test_onModification(t) {
+ t.plan(3);
+ var map = new OpenLayers.Map("map");
+ var layer = new OpenLayers.Layer.Vector();
+ map.addLayer(layer);
+ var control = new OpenLayers.Control.ModifyFeature(layer);
+ map.addControl(control);
+ control.activate();
+
+ // make sure onModification is called on drag complete
+ var point = new OpenLayers.Feature.Vector(
+ new OpenLayers.Geometry.Point(Math.random(), Math.random())
+ );
+ control.feature = point;
+ control.onModification = function(feature) {
+ t.eq(feature.id, point.id,
+ "onModification called with the right feature on drag complete");
+ };
+ control.dragComplete();
+
+ // make sure onModification is called on vertex deletion
+ var poly = new OpenLayers.Feature.Vector(
+ new OpenLayers.Geometry.Polygon()
+ );
+ var oldDraw = layer.drawFeature;
+ layer.drawFeature = function() {
+ return;
+ };
+ control.feature = poly;
+ control.vertices = [point];
+ layer.events.on({"featuremodified": function(event) {
+ t.eq(event.feature.id, poly.id, "featuremodified triggered");
+ }});
+
+ control.onModification = function(feature) {
+ t.eq(feature.id, poly.id,
+ "onModification called with the right feature on vertex delete");
+ };
+ point.geometry.parent = poly.geometry;
+ origGetFeatureFromEvent = layer.getFeatureFromEvent;
+ layer.getFeatureFromEvent = function() { return point; };
+ control.handleKeypress({keyCode:46});
+ layer.drawFeature = oldDraw;
+ layer.getFeatureFromEvent = origGetFeatureFromEvent;
+
+ map.destroy();
+ }
+
+ function test_onModificationEnd(t) {
+ t.plan(3);
+ var map = new OpenLayers.Map("map");
+ var layer = new OpenLayers.Layer.Vector();
+ map.addLayer(layer);
+ var control = new OpenLayers.Control.ModifyFeature(layer);
+ map.addControl(control);
+ control.activate();
+
+ // make sure onModificationEnd is called on unselect feature
+ var testFeature = new OpenLayers.Feature.Vector(
+ new OpenLayers.Geometry.Point(Math.random(), Math.random())
+ );
+ layer.events.on({"afterfeaturemodified": function(event) {
+ t.eq(event.feature.id, testFeature.id, "afterfeaturemodified triggered");
+ t.eq(event.modified, false, "afterfeaturemodified event given proper modified property (false - feature was not modified in this case)");
+ }});
+ control.onModificationEnd = function(feature) {
+ t.eq(feature.id, testFeature.id,
+ "onModificationEnd called with the right feature");
+ };
+ control.unselectFeature(testFeature);
+
+ map.destroy();
+ }
+
+ function test_events(t) {
+ t.plan(2);
+ var map = new OpenLayers.Map("map");
+ var layer = new OpenLayers.Layer.Vector();
+ map.addLayer(layer);
+ var control = new OpenLayers.Control.ModifyFeature(layer);
+ map.addControl(control);
+ control.activate();
+
+ // make sure onModificationStart is called on feature selection
+ var testFeature = new OpenLayers.Feature.Vector(
+ new OpenLayers.Geometry.Point(Math.random(), Math.random())
+ );
+
+ // test that beforefeatureselected is triggered
+ function handle_beforefeatureselected(event) {
+ t.ok(event.feature == testFeature, "beforefeatureselected called with the correct feature");
+ }
+ layer.events.on({
+ "beforefeatureselected": handle_beforefeatureselected
+ });
+ layer.events.triggerEvent("beforefeatureselected", {
+ feature: testFeature
+ });
+ layer.events.un({
+ "beforefeatureselected": handle_beforefeatureselected
+ });
+
+ // test that beforefeatureselected is triggered
+ function handle_featureselected(event) {
+ t.ok(event.feature == testFeature, "featureselected called with the correct feature");
+ }
+ layer.events.on({
+ "featureselected": handle_featureselected
+ });
+ layer.events.triggerEvent("featureselected", {
+ feature: testFeature
+ });
+ layer.events.un({
+ "featureselected": handle_featureselected
+ });
+
+ map.destroy();
+ }
+
+ function test_standalone(t) {
+
+ t.plan(17);
+ var map = new OpenLayers.Map("map");
+ var layer = new OpenLayers.Layer.Vector();
+
+ var f1 = new OpenLayers.Feature.Vector(
+ OpenLayers.Geometry.fromWKT("LINESTRING(3 4,10 50,20 25)")
+ );
+ var f2 = new OpenLayers.Feature.Vector(
+ OpenLayers.Geometry.fromWKT("POLYGON((1 1,5 1,5 5,1 5,1 1),(2 2, 3 2, 3 3, 2 3,2 2))")
+ );
+ var f3 = new OpenLayers.Feature.Vector(
+ OpenLayers.Geometry.fromWKT("POINT(10 15)")
+ );
+ var f4 = new OpenLayers.Feature.Vector(
+ OpenLayers.Geometry.fromWKT("POINT(15 10)")
+ );
+ layer.addFeatures([f1, f2, f3, f4]);
+
+ map.addLayer(layer);
+ var control = new OpenLayers.Control.ModifyFeature(layer, {standalone: true});
+ map.addControl(control);
+
+ var log = [];
+ layer.events.on({
+ beforefeaturemodified: function(evt) {
+ layer.events.unregister("beforefeaturemodified", this, arguments.callee);
+ log.push(evt);
+ },
+ featuremodified: function(evt) {
+ log.push(evt);
+ },
+ afterfeaturemodified: function(evt) {
+ log.push(evt);
+ }
+ });
+
+ // activate control
+ control.activate();
+ t.eq(control.active, true, "[activate] control activated");
+
+ // manually select feature for editing
+ control.selectFeature(f1);
+ t.eq(log.length, 1, "[select f1] beforefeaturemodified triggered");
+ t.ok(control.feature === f1, "[select f1] control.feature set to f1");
+ log = []
+
+ // manually unselect feature for editing
+ control.unselectFeature(f1);
+ t.eq(control.feature, null, "[unselect f1] control.feature set to null");
+ t.eq(log.length, 1, "[unselect f1] event logged");
+ t.eq(log[0].type, "afterfeaturemodified", "[unselect f1] afterfeaturemodified triggered");
+ t.ok(log[0].feature === f1, "[unselect f1] correct feature");
+ t.eq(log[0].modified, false, "[unselect f1] feature not actually modified");
+
+ // clear log and select new feature for editing
+ log = [];
+ control.selectFeature(f2);
+ t.ok(control.feature === f2, "[select f2] control.feature set to f2");
+
+ // deactivate control and confirm feature is unselected
+ control.deactivate();
+ t.eq(log.length, 1, "[deactivate] event logged");
+ t.eq(log[0].type, "afterfeaturemodified", "[deactivate] afterfeaturemodified triggered");
+ t.ok(log[0].feature === f2, "[deactivate] correct feature");
+ t.eq(log[0].modified, false, "[deactivate] feature not actually modified");
+
+ // select the polygon feature to make sure that we can drag vertices and
+ // virtual vertices
+ control.selectFeature(f2);
+ var origGetFeatureFromEvent = layer.getFeatureFromEvent;
+ layer.getFeatureFromEvent = function() { return control.vertices[0]; };
+ control.handlers.drag.callbacks.down.call(control, new OpenLayers.Pixel(0,0));
+ t.ok(control.vertex === control.vertices[0], "can drag vertex of feature f2");
+ t.ok(control.feature === f2, "dragging a vertex does not change the selected feature");
+ layer.getFeatureFromEvent = function() { return control.virtualVertices[0]; };
+ control.handlers.drag.callbacks.down.call(control, new OpenLayers.Pixel(0,0));
+ t.ok(control.vertex === control.virtualVertices[0], "can drag virtual vertex of feature f2");
+ t.ok(control.feature === f2, "dragging a vertex does not change the selected feature");
+ layer.getFeatureFromEvent = origGetFeatureFromEvent;
+ control.deactivate();
+
+ map.destroy();
+
+ }
+
+ function test_setFeatureState(t) {
+ t.plan(4);
+ var map = new OpenLayers.Map("map");
+ var layer = new OpenLayers.Layer.Vector("vector", {isBaseLayer: true});
+ map.addLayer(layer);
+ var feature = new OpenLayers.Feature.Vector(new OpenLayers.Geometry.Point(1,2));
+ layer.addFeatures([feature]);
+ var control = new OpenLayers.Control.ModifyFeature(layer, {standalone: true});
+ map.addControl(control);
+
+ control.selectFeature(feature);
+ var originalGeometry = feature.geometry;
+
+ t.ok(control._originalGeometry, "original geometry stored for later use in setFeatureState");
+
+ feature.geometry = new OpenLayers.Geometry.Point(2,3);
+ control.modified = true;
+ control.setFeatureState();
+
+ t.eq(feature.state, OpenLayers.State.UPDATE, "feature state set to UPDATE");
+ t.geom_eq(feature.modified.geometry, originalGeometry, "original geometry stored on the modified property");
+ t.eq(control._originalGeometry, undefined, "original geometry deleted once it is set on the modified property");
+ }
+
+ function test_createVertices(t) {
+ t.plan(2);
+ var layer = new OpenLayers.Layer.Vector();
+ var control = new OpenLayers.Control.ModifyFeature(layer, {
+ createVertices: false
+ });
+ var line = new OpenLayers.Geometry.LineString([
+ new OpenLayers.Geometry.Point(5, 6),
+ new OpenLayers.Geometry.Point(7, 8),
+ new OpenLayers.Geometry.Point(9, 10)
+ ]);
+ control.feature = new OpenLayers.Feature.Vector(line);
+ control.resetVertices();
+
+ t.eq(control.vertices.length, 3, "Correct vertices length with createVertices is false");
+ t.eq(control.virtualVertices.length, 0, "Correct virtual vertices length with createVertices is false");
+ control.destroy();
+ }
+
+ function test_moveLayerToTop_moveLayerBack(t) {
+ t.plan(2);
+ var map = new OpenLayers.Map("map");
+ var layer1 = new OpenLayers.Layer.Vector();
+ var layer2 = new OpenLayers.Layer.Vector();
+ map.addLayers([layer1, layer2]);
+ var control = new OpenLayers.Control.ModifyFeature(layer1);
+ map.addControl(control);
+ control.activate();
+ t.ok(layer1.div.style.zIndex > layer2.div.style.zIndex, "layer raised so events don't get swallowed");
+ control.deactivate();
+ t.ok(layer1.div.style.zIndex < layer2.div.style.zIndex, 'layer order restored on deactivation');
+ }
+
+ </script>
+</head>
+<body>
+ <div id="map" style="width: 400px; height: 250px;"/>
+</body>
+</html>