[OpenLayers-Users] how to best extend drawing tools to includemeasure

Pierre GIRAUD bluecarto at gmail.com
Thu May 17 13:07:53 EDT 2007


I played around to get something working for your needs.
This may be another way to get what you want. What I wanted to show is
another way to get custom controls with less code. Though, it is
surely not the best way.
And you probably need to compute the distance in a different way than
the simple getLength().

--------------------------------
var p = new OpenLayers.Control.Panel({'displayClass':
'olControlEditingToolbar'});

var distance = new OpenLayers.Control();
OpenLayers.Util.extend(distance, {
    geometry: null,
    draw: function() {
    	this.geometry = new OpenLayers.Geometry.LineString();
    	this.handler = new OpenLayers.Handler.Path(distance, {"point":
this.pointAdded, "done": this.geometryDone});
    },
    displayClass: 'olControlDrawFeaturePath', // should be something
like olControlDistance
    pointAdded: function(point) {
		this.geometry.addPoint(point.clone());
    	$('distance').innerHTML = this.geometry.getLength();
    }
});

p.addControls([ new OpenLayers.Control.Navigation(), distance ]);

map.addControl(p);
p.activateControl(p.controls[0]);
------------------------------------

Regards

Pierre

On 5/16/07, Mike Quentel <mikequentel at yahoo.com> wrote:
> Bob,
>
> Thanks very much for sharing your code and ideas.
>
> What I've done to add the distance measure functionality to a line drawing tool (in addition to the code I attached in my previous email) is the following:
>
> 1.  I created another handler class called OpenLayers.Handler.MeasureTool, with essentially the same implementation as the Path.js, with a few modifications.
>
> 2.  In MeasureTool, I added a class member representing the Measure control, as in:
>
> measure: null,
>
> 3.  In MeasureTool, I overrided the setMap function of OpenLayers.Control, so that the class member measure is added to the map, as in:
>
> setMap: function() {
>   OpenLayers.Control.prototype.setMap.apply(this, arguments);
>     this.map.addControl(this.measure);
> },
>
> 4.  In the MeasureTool (which is almost identical to Path.js), I added the following to the drawGeometry function:
>
> drawGeometry: function() {
>    this.layer.renderer.drawGeometry(this.line, this.style);
>    this.layer.renderer.drawGeometry(this.point, this.style);
>
>    // here is the call to the Measure control...
>    this.measure.showDistance(this.line);
>
> },
>
> Not clear what I'd have to do to change the functionality if I'm using WGS84, lat/lon.  Doesn't the Vincenty formula work acceptably for lat/lon values?
>
> Many thanks for your help.
>
> Mike Quentel
>
>
> ----- Original Message ----
> From: "Cicconetti, Bob" <BCicconetti at dnr.state.md.us>
> To: Mike Quentel <mikequentel at yahoo.com>; OpenLayers Users <users at openlayers.org>
> Sent: Wednesday, 16 May, 2007 10:50:23 AM
> Subject: RE: [OpenLayers-Users] how to best extend drawing tools to includemeasure
>
> What I've done is fairly similar, but use the much simpler getArea and
> getLength calls. My maps are set in State Plane Nad83m, and you may have
> to change a few things if you're in lat/lon.
>
> R C
>
> 1) First, extend the drawing controls div to allow for more buttons, and
> define the buttons. Copy or create new buttons in gimp/whatever.
>
> --- theme/default/style.css     (revision 3151)
> +++ theme/default/style.css     (working copy)
> @@ -108,7 +108,7 @@
>      float:right;
>      right: 0px;
>      height: 30px;
> -    width: 200px;
> +    width: 270px;
>  }
>  .olControlEditingToolbar div {
>    float:right;
> @@ -148,3 +148,15 @@
>    background-image: url("img/draw_polygon_on.png");
>    background-repeat: no-repeat;
>  }
> +.olControlEditingToolbar .olControlSelectFeatureItemInactive {
> +  background-image: url("img/info_off.png");
> +}
> +.olControlEditingToolbar .olControlSelectFeatureItemActive {
> +  background-image: url("img/info_on.png");
> +}
> +.olControlEditingToolbar .olControlDeleteFeatureItemInactive {
> +  background-image: url("img/delete_off.png");
> +}
> +.olControlEditingToolbar .olControlDeleteFeatureItemActive {
> +  background-image: url("img/delete_on.png");
> +}
>
> 2) Add this to my javascript:
> [...]
>   // Extend the edit tool bar to allow deleting features, and gather
>   // info about them.
>   var selectTool = new OpenLayers.Control.SelectFeature(vlayer,
>         {
>         onSelect:feature_info,
>         onUnselect:clear_feature_info
>         });
>
>   var deleteTool = new OpenLayers.Control.SelectFeature(vlayer,
>         {
>         onSelect:deleteFeature,
>         onUnselect:clear_feature_info
>         });
>
>   var editToolBar = new OpenLayers.Control.EditingToolbar(vlayer);
>
>   var myControls = [ selectTool, deleteTool ];
>   // Fun with gimp. Be sure to use patched style.css.
>   myControls[0].displayClass = 'olControlSelectFeature';
>   myControls[1].displayClass = 'olControlDeleteFeature';
>
>   editToolBar.addControls(myControls);
>   map.addControl(editToolBar);
>
> [...]
>
>   function feature_info(feature) {
>    //Extend to allow string length as well.
>       if (feature.geometry.CLASS_NAME == "OpenLayers.Geometry.Polygon")
>         {
>
>         var str = feature.geometry.getArea();
>         // Assume units are meters, for now.
>         // Magic numbers are evil, but ah well.
>         var sqft = str / 0.09290304;
>         var acres = str / 4046.856422;
>
>         // FIXME: Round and truncate. 8 sig figs?
>         if (sqft < 4000)
>          str = "Area: (sq ft.) " + sqft;
>         else
>          str = "Area: (acres) " + acres;
>
>         document.getElementById('area').innerHTML = str;
>
>         }
>       else if (feature.geometry.CLASS_NAME ==
> "OpenLayers.Geometry.LineString")
>         {
>         var str = feature.geometry.getLength();
>         var feet = str / 0.3048;
>         var miles = str / 1609.344;
>
>         if (feet < 2000)
>          str = "Length: (feet) " + feet;
>         else
>          str = "Length: (miles) " + miles;
>
>         document.getElementById('area').innerHTML = str;
>         }
>
>   }
>
>   function clear_feature_info(geometry) {
>         document.getElementById('area').innerHTML = "Select Feature for
> Area or
> Length.";
>   }
>
>   function deleteFeature(geometry) {
>         this.layer.removeFeatures(geometry);
>         }
>
> > -----Original Message-----
> > From: users-bounces at openlayers.org
> [mailto:users-bounces at openlayers.org]
> > On Behalf Of Mike Quentel
> > Sent: Tuesday, May 15, 2007 3:56 PM
> > To: OpenLayers Users
> > Subject: [OpenLayers-Users] how to best extend drawing tools to
> > includemeasure
> >
> > I created a measure control (OpenLayers.Control.Measure) that uses a
> div
> > (like the mouse position control) to display distance.
> >
> > So far, I have an example where the user can select a drawn line, and
> get
> > back the total distance of the line.  It employs the
> > OpenLayers.Util.distVincenty function to calculate the distances of
> the
> > components of the geometry, adding up the results.  It also handles
> > situations like the user attempting to measure the entire globe
> (handles
> > situation if the pixel clicks exceed what they should for a
> hemisphere).
> > This is still in its raw state, so if you see bugs, please let me
> know.
> > The attached example seems to work well.
> >
> > Please, need advice...I would like to add this functionality to the
> > drawing tools, such that when the user draws a line, the total
> distance is
> > displayed in the measure control.  I am not sure how to go about doing
> > this.  Would it be best to include this control in the
> > OpenLayers.Handler.Path handler class?
> >
> > Attached is Measure.js, which represents OpenLayers.Control.Measure,
> as
> > well as measure.html, to show an example.
> >
> > If you want to add this control to your OL directory tree.....
> >
> > The style.css would include the following:
> >
> > div.olControlMeasure {
> >       background-color: #FFFFFF;
> >     top: 30px;
> >     left: 400px;
> >     display: block;
> >     position: absolute;
> >     font-family: Arial;
> >     font-size: smaller;
> >     font-weight: bold;
> > }
> >
> > The base OpenLayers class would need to include the Measure.js in its
> JS
> > files array:
> >
> > var jsfiles=new Array(
> > ...
> > "OpenLayers/Control/Measure.js"
> > );
> >
> >
> >
> >
> >
> >
> >
> >
> >
> >       ___________________________________________________________
> > Yahoo! Mail is the world's favourite email. Don't settle for less,
> sign up
> > for
> > your free account today
> >
> http://uk.rd.yahoo.com/evt=44106/*http://uk.docs.yahoo.com/mail/winter07
> .h
> > tml
>
>
>
>
>
>
>
>
> ___________________________________________________________
> New Yahoo! Mail is the ultimate force in competitive emailing. Find out more at the Yahoo! Mail Championships. Plus: play games and win prizes.
> http://uk.rd.yahoo.com/evt=44106/*http://mail.yahoo.net/uk
> _______________________________________________
> Users mailing list
> Users at openlayers.org
> http://openlayers.org/mailman/listinfo/users
>



More information about the Users mailing list