ThinkGeo.com    |     Documentation    |     Premium Support

Add marker and remove marker

Hi,


I have referred many codes from this forum. Now I ahve a problem.


I want to add and remove the marker from map using JavaScript.


Could you please help me.


Thanks in Advance.


Thanks:


Kam



Kamal,



Actually, web edition integrate OpenLayers Library which you can refer to the following address for detail:

dev.openlayers.org/releases/...rs-js.html



On the other hand, we attached a simple sample to satisfy your requirement, please let us know if you have more queries.



Thanks,

Howard



1249-Post6348.zip (96.7 KB)

Thanks a lot Howard for this help.Actually I am trying to implement on click on map to create  multiple markers and to rempve the same. 


Thanks:


Kamal



Kamal,



It refers to many OpenLayers functions; please see the following JavaScript for detail.

var tgMap = null;
var OnMapCreated = function(map) {
    tgMap = map;
    map.events.register('click', map, addMarker);
}

var addMarker = function(evt) {
    var lonlat = this.getLonLatFromViewPortPx(evt.xy);
    var markerOverlay = this.getLayer('SimpleMarkerOverlay');
    var size = new OpenLayers.Size(21, 25);
    var offset = new OpenLayers.Pixel(-(size.w / 2), -size.h);
    var icon = new OpenLayers.Icon('theme/default/img/marker.gif', size, offset);
    var marker = new OpenLayers.Marker(lonlat, icon);
    marker.events.register('click', { overlay: markerOverlay, marker: marker }, function(evt) {
        this.overlay.removeMarker(this.marker);
        this.marker.destroy();
    })
    markerOverlay.addMarker(marker);



Please let me know if you have any questions.



Thanks,

Howard



Thank You Howard. 
 I never used popup in marker. I m facing below problem. 
 When user clicks on map the marker will be created that is done successfuly with above code.Now I have to show a popup window to user to fill the place name when he clicks on marker.That marker infomation will be stored in database for history purpose. If he again clicks on same marker that information will be shown. 
 I m trying to implement it with popup in mapping openlayer javascript. 
 Could u please help me.

Kamal,



It's simple to implement follow my last reply; the longitude and latitude is known currently; what you need to do is to new an OpenLayers Popup and add it into the map. Please see the code below. I think you need to do some validation before adding into your application. Also OpenLayers support several kind of Popups which you can find at dev.openlayers.org/releases/OpenLayers-2.8/doc/apidocs/files/OpenLayers/Popup-js.html. 

var tgMap = null;

var OnMapCreated = function(map) {
    tgMap = map;
    map.events.register('click', map, addMarker);
}

var addMarker = function(evt) {
    var lonlat = this.getLonLatFromViewPortPx(evt.xy);
    var markerOverlay = this.getLayer('SimpleMarkerOverlay');
    var size = new OpenLayers.Size(21, 25);
    var offset = new OpenLayers.Pixel(-(size.w / 2), -size.h);
    var icon = new OpenLayers.Icon('theme/default/img/marker.gif', size, offset);
    var marker = new OpenLayers.Marker(lonlat, icon);
    marker.events.register('click', { overlay: markerOverlay, marker: marker }, function(evt) {
        var popup = new OpenLayers.Popup("chicken",
           lonlat,
           new OpenLayers.Size(200, 200),
           "example popup",
           true);

        tgMap.addPopup(popup);
    })
    markerOverlay.addMarker(marker);
}



Thanks,

Howard



Thanks a lot Howard. 
 I have one very basic problem. I m trying but not working. 
 I want to add one textbox and button in popup window so if user will click on map, he will able to enter his place name in that textbox on clcik of button and this name with latlong will store in database or reuse. 
 could u pls help me. 
  
 Thanks: 
 Kamal

Kamal, 



In my last reply, there is a string "example popup" which supports inner html; that means you can input "<input type="text" />" instead; in this way, you can deploy your html control inside of the Popup control. 



The rest stuff is to implement sever event from html control. You can choose postback or callback to implement your requirement. I think you can find many article for your issue. Such as IPostBackEventHandler or ICallbackEventHandler etc. 



Please let me know if you have any questions. 



Thanks, 

Howard



Thanks Howard. Now it is working. 
 I have below problems: 
 1. When I m populating the marker on map it populates but when I just move map or zoon in or zoom out those markers are go out. Is there any way to retain those markers on map after zoom or moving of map. 
 2. I am trying to get the approximate location name using lat lon from database .  
 Could you please help me in these issues.

Thanks Howard. Now it is working. 
 I have below problems: 
 1. When I m populating the marker on map it populates but when I just move map or zoon in or zoom out those markers are go out. Is there any way to retain those markers on map after zoom or moving of map. 
 2. I am trying to get the approximate location name using lat lon from database .  
 Could you please help me in these issues. 
 Thanks: 
 Kam

Kam,



The marker's location cannot be changed after zooming in and out. It might be the location problem you set. If possible, please send me your code so that I can recreate your issue easily.



We have query tools to find the feature by the longitude/latitude. Please see the code below.
Collection<Feature> features = worldLayer.QueryTools.GetFeaturesNearestTo(new Feature(clickLocation), GeographyUnit.DecimalDegree, 1, ReturningColumnsType.NoColumns);
Please let me know if you have any questions.



Thanks,

Howard





 



Hi Howard,


Please find below code for add,remove marker.


 var lonlat = null;

        var tgMap = null;

        var popup = null;

        var OnMapCreated = function(map) {

            tgMap = map;

            map.events.register('click', map, addMarker);

        }


        var addMarker = function(evt) {//Opening var addMarker


            lonlat = this.getLonLatFromViewPortPx(evt.xy);


            //This is for just refernce of Lanlot 

            document.getElementById("txtlon").value = lonlat.lon;

            document.getElementById("txtlat").value = lonlat.lat;

            document.getElementById("txtlonlat").value = document.formXenolith.txtlon.value + document.formXenolith.txtlat.value//.getElementById("txtlon").tostring() + document.getElementById("txtlat").tostring();

            //This is for just refernce of Lanlot


            var markerOverlay = this.getLayer('Moving_Marker');

            var size = new OpenLayers.Size(21, 25);

            var offset = new OpenLayers.Pixel(-(size.w / 2), -size.h);

            var icon = new OpenLayers.Icon('/images/SmallPinGreen.png', size, offset);

            var marker = new OpenLayers.Marker(lonlat, icon);


            if (document.getElementById("Radio1").checked == true) {


                marker.events.register('click', { overlay: markerOverlay, marker: marker }, function(evt) {

                    this.overlay.removeMarker(this.marker);

                    this.marker.destroy();


                })

                markerOverlay.addMarker(marker);

            }


            else if (document.getElementById("Radio2").checked == true) {

                marker.events.register('click', { overlay: markerOverlay, marker: marker }, function(evt) {

                    document.getElementById("txtforExistLonLat").value = document.formXenolith.txtlon.value + document.formXenolith.txtlat.value//.getElementById("txtlon").tostring() + document.getElementById("txtlat").tostring();

                    popup = new OpenLayers.Popup("komal", lonlat, new OpenLayers.Size(150, 100), s, true);

                    tgMap.addPopup(popup);

                })

                markerOverlay.addMarker(marker);


            }


            else {


                markerOverlay.addMarker(marker);

            }

        }  //Closing var addMarker


 


Thanks:


Kamal



Kamal, 
  
 I guess the markerOverlay you use is InMemoryMarkerOverlay which is designed only for maintaining markers on server side; it refreshes server markers when zooming or panning around; so the client markers you added will be removed. Please use SimpleMarkerOverlay on server side instead. 
  
 If there is any misunderstanding, please let us know. 
  
 Thanks, 
 Howard

Thanks Howard. I used simple marker overlayer. It is working fine.


CollectionB<Feature> features = worldLayer.QueryTools.GetFeaturesNearestTo (new Feature(clickLocation), GeographyUnit.DecimalDegree, 1, ReturningColumnsType.NoColumns);

 


I am not getting from above code how to implement it. I need some sample code for getting nearest location.


Could you please provide me if you have.


Thanks:


Kam


 



Hi kamal,


I’m wondering you implement the marker overlay in server side or client side. If it is a server side marker overlay, you just need to hook the map click event and write the line of code in the map click event like this:


protected void Map1_Click(object sender, MapClickedEventArgs e)
{
    Collection<Feature> features = worldLayer.QueryTools.GetFeaturesNearestTo(new Feature(e.Position), GeographyUnit.DecimalDegree, 1, ReturningColumnsType.NoColumns);

    foreach (Feature feature in features)
    { 
        PointShape markerPointShape = (PointShape)feature.GetShape();
        simpleMarkerOverlay.Markers.Add(new Marker(markerPointShape));    
    }
}


And if you implemented the marker overlay in client side, you need to raise a call back to get the features, and the call back process is like this:
1. Raise a call back in the client side code. The argument contains a point shape as a string which is the world coordinate you clicked on;
2. On the server side you should implement a call back event handler and add your own logic to find the features:


public class MyCallBackEventHandler : System.Web.UI.ICallbackEventHandler
{
    private PointShape sourcePointShape;

    public string GetCallbackResult()
    {
        string result = string.Empty;

        // Add the Find Features logic here.
        Collection<Feature> features = worldLayer.QueryTools.GetFeaturesNearestTo(new Feature(sourcePointShape), GeographyUnit.DecimalDegree, 1, ReturningColumnsType.NoColumns);

        // Then construct the return the features as a string.
        return result;
    }

    public void RaiseCallbackEvent(string eventArgument)
    {
        // Parse the event argument to a PointShape.
    }
}


3. Add the returned features to the client side marker overlay in your call back method. Just parse the result string to some features and add them to the marker overlay in your client side.
Any more questions please let me know.
Thanks,
Sun

Thanks sun for ur quick response.


I am implementing it through server side. I m using google Map Layer. But QueryTool class is not available for this layer. I tested it. It is available with shapefile. Could you please help me.


Thanks:


Kam



Kamal, 
  
 GoogleMapsLayer is a layer which directly access google’s cached image server. It doesn’t maintain the features so that we cannot handle much. I’m not sure which layer you want to query in the Google layer. I just make an example to show you how to query features in your situations. 
  
 1) prepare the shape files you want to query such as counties or states. 
 2) create a ShapeFileFeatureLayer which maintains the shape file you want to query. Do not add it into any overlay; we only need this object for querying. 
 3) project this layer into Google’s projection then do the query as the method we attached above. 
  
 General speaking, we maintain a temporary layer for querying not directly query GoogleMapsLayer. 
  
 Hope it makes sense. 
  
 Thanks, 
 Howard

Excellent explanation.Thanks Howard.


I will try and implement the functionality that we need (plotting and getting the location from the lattitude and longitude)using Shape Files.


Question(1)We are having issues on the map plotting when we use Shape File Layer(commented code)


The same works with Google Map Layer(uncommented code).


Any pointers on what I am missing?


Please see my code below:


*******************************************************************************************************************


           Map1.MapUnit = GeographyUnit.DecimalDegree;


            //ShapeFileFeatureLayer states = new ShapeFileFeatureLayer(MapPath("~/App_Data/STATES.SHP"));

            //states.ZoomLevelSet.ZoomLevel01.DefaultAreaStyle = AreaStyles.State2;

            //states.ZoomLevelSet.ZoomLevel01.ApplyUntilZoomLevel = ApplyUntilZoomLevel.Level20;


            //LayerOverlay stateOverlay = new LayerOverlay();

            //stateOverlay.Layers.Add(states);

            //Map1.CustomOverlays.Add(stateOverlay);


            GoogleOverlay google = new GoogleOverlay();

            google.GoogleMapType = GoogleMapType.Normal;

            google.JavaScriptLibraryUri = new Uri(ConfigurationManager.AppSettings["googleuri"].ToString());


            Map1.CustomOverlays.Add(google);




            // You should create a marker overlay first, and add the overlay into the 

            //CustomOverlays.If you just want to use default marker overlay of map1, 

            //you need to initialize the properties of that marker overlay to ensure 

            //it will be created at client side.


            InMemoryMarkerOverlay markerOverlay = new InMemoryMarkerOverlay("SimpleMarkerOverlay");

           // markerOverlay.ZoomLevelSet.ZoomLevel01.DefaultMarkerStyle.WebImage = new WebImage  ("theme/default/img/marker_blue.gif", 21, 25);

            markerOverlay.ZoomLevelSet.ZoomLevel01.ApplyUntilZoomLevel = ApplyUntilZoomLevel.Level20;

            Map1.CustomOverlays.Add(markerOverlay);




            //SimpleMarkerOverlay markerOverlay = new SimpleMarkerOverlay("SimpleMarkerOverlay");

            //markerOverlay.IsBaseOverlay = false;

            //Map1.CustomOverlays.Add(markerOverlay);


            //states.Open();

            //Map1.CurrentExtent = states.GetBoundingBox();

            //states.Close();


*******************************************************************************************************************


Question (2) As a different approach, is it possible through google map api to return the location name in addition to display on map control.


Currently we are aware that using the google api we can plot the location name from given latitude and longitude. We need the actual location name in addition to the plotting as well.


Any help or any sample code to achieve this will be much appreciated.


Thanks:


Kamal



Hi kamal,


For question 1, you mean the map doesn’t show correctly when you only use the shape file layer? It seems that you didn’t set the right CurrentExtent based on your code. This block of codes works fine in my machine, please have a try with it:


protected void Page_Load(object sender, EventArgs e)
{
    if (!Page.IsPostBack)
    {
        Map1.MapBackground.BackgroundBrush = new GeoSolidBrush(GeoColor.FromHtml("#B3C6D4"));
        Map1.MapUnit = GeographyUnit.DecimalDegree;

        ShapeFileFeatureLayer worldLayer = new ShapeFileFeatureLayer(MapPath("~/SampleData/USA/STATES.SHP"));
        worldLayer.ZoomLevelSet.ZoomLevel01.DefaultAreaStyle = AreaStyles.State2;
        worldLayer.ZoomLevelSet.ZoomLevel01.ApplyUntilZoomLevel = ApplyUntilZoomLevel.Level20;

        LayerOverlay stateOverlay = new LayerOverlay();
        stateOverlay.Layers.Add(worldLayer);
        Map1.CustomOverlays.Add(stateOverlay);

        SimpleMarkerOverlay markerOverlay = new SimpleMarkerOverlay("SimpleMarkerOverlay");
        markerOverlay.IsBaseOverlay = false;
        Map1.CustomOverlays.Add(markerOverlay);

        worldLayer.Open();
        Map1.CurrentExtent = worldLayer.GetBoundingBox();
        worldLayer.Close();
    }
}


For question 2, I think this is a feature of Google library, please review the content in the following address to get more information about this:
code.google.com/apis/maps/do...vices.html
Any more questions please let me know.
Thanks,
Sun

Hi, 
 I have a issue with memory leak. 
 1. I am using InMemoryMarker layer in my code. There is a issue with memory leak. Is there any solution to remove this problem. 
 Code: 
                     InMemoryMarkerOverlay markerOverlay_LiveTrail = null; 
                     markerOverlay_LiveTrail = new InMemoryMarkerOverlay("markerOverlay_LiveTrail"); 
                     markerOverlay_LiveTrail.FeatureSource.Open(); 
                     markerOverlay_LiveTrail.ZoomLevelSet.ZoomLevel01.ApplyUntilZoomLevel = ApplyUntilZoomLevel.Level20; 
                     markerOverlay_LiveTrail.ZoomLevelSet.ZoomLevel01.DefaultMarkerStyle.Popup.ContentHtml = contentHtml.ToString(); 
                     markerOverlay_LiveTrail.ZoomLevelSet.ZoomLevel01.DefaultMarkerStyle.Popup.Width = 250; 
                     markerOverlay_LiveTrail.ZoomLevelSet.ZoomLevel01.DefaultMarkerStyle.Popup.Height = 50; 
                     Proj4Projection m_objProj4_for_LiveTrail = new Proj4Projection(); 
                     m_objProj4_for_LiveTrail.InternalProjectionParametersString = Proj4Projection.GetEpsgParametersString(4326); 
                     m_objProj4_for_LiveTrail.ExternalProjectionParametersString = Proj4Projection.GetGoogleMapParametersString(); 
                     m_objProj4_for_LiveTrail.Open(); 
                     markerOverlay_LiveTrail.FeatureSource.Projection = m_objProj4_for_LiveTrail; 
                     Map1.CustomOverlays.Add(markerOverlay_LiveTrail); 
 2. Do you have released any latest version which resolves the memory leak problem fro inmemorymarker layer. 
  
 Thanks 
 Kamal