How to Retrieve Attribute values of a shapefile using Sharpmap?

Topics: SharpMap Project
Oct 15, 2009 at 9:47 PM

Hi,

I have drawn a shapefile in QGIS and assigned attribute values to this shapefile objects.

I have drawn polygons with Attribute name ="Name" of type string. I am trying to display only those polygons of my shapefile which match attribute value entered by user. I am using C# and sharpmap for this.

E.g. If user enters string as "11" then only those polygons having their Name=11 should be displayed in my picturebox.

I can display whole shapefile in picturebox but cant display individual parts of shapefile based on their attributes..

Does anybody know how to achieve above task?

Please let me know if anybody has any idea about it.

 

 

Coordinator
Oct 15, 2009 at 10:56 PM
Edited Oct 16, 2009 at 3:13 PM

Hi siddhesh123, you can use the FilterDelegate property of the shapefile provider to assign a filter

something like

Shapefile shp = .....
shp.FilterDelegate = row => row["Name"] == "11";
or
Shapefile shp = ....
shp.FilterDelegate = delegate(FeatureDataRow row){

return row["Name"] == "11";
};
hth jd
Oct 16, 2009 at 3:30 PM

Hi,

Thanks for the reply,

Can you please explain what is above delegate doing?

I actually didnt understand above code. In the first code, is row defined as FeatureDataRow?

Thanks

 

Coordinator
Oct 17, 2009 at 12:27 PM

Hi siddhesh123, the two methods are equivalent, the top one uses lambda syntax from c# 3.0 whereas the bottom one uses the older anonymous method syntax, if you prefer you could also use an instance or static method as long as it matches the signature of Shapefile.FilterMethod.

In essence Shapefile.FilterDelegate is a method that is called for each row in the dataset and returns a boolean which controls whether the record is included or excluded in the result set. It is called during Shapefile.ExecuteIntersectionQuery and also when enumerating all records.
In our example above the delegate is testing whether the FeatureDataRow provided in the argument contains a "Name" attribute with the value "11" - if it does it returns true and the row is included in the results.


Other uses for the Shapefile.FilterDelegate property include 'true intersection testing' as by default the shapefile provider only tests bounding boxes.

hth jd 

Oct 17, 2009 at 9:23 PM

Hi,

My code is as follows-     Please correct me if i m wrong in any comments or code

Sharpmap.Map sharp;

           sharp = new SharpMap.Map(pictureBox1.Size);
            SharpMap.Layers.VectorLayer testlayer = new SharpMap.Layers.VectorLayer("TestLayer");


             ShapeFile sf = new ShapeFile(path);
             sf.Open();


            BoundingBox bx = sf.GetExtents();   // Putting all attributes in bx..
            var ds = new FeatureDataSet();             // initializing ds
             sf.ExecuteIntersectionQuery(bx, ds);  // I didnt fully understand this fun

sf.FilterDelegate = delegate(FeatureDataRow row)
             {
                 return row["Name"] == "11";
             };
             
           testlayer.DataSource = sf;
            sharp.Layers.Add(testlayer); // Adds layer to sharp object
            sharp.ZoomToExtents();
            pictureBox1.Image = sharp.GetMap(); // diplay

 

Coordinator
Oct 17, 2009 at 11:34 PM

Hi siddhesh123, you dont need to executeintersectionquery yourself unles you are trying to get the data for soe non rendering purpose..

the following should run- but I havent tested it

 

SharpMap.Map sharp = new SharpMap.Map(pictureBox1.Size); ShapeFile sf = new ShapeFile(path); sf.FilterDelegate = delegate(FeatureDataRow row) { return row["Name"] == "11"; }; SharpMap.Layers.VectorLayer testlayer = new SharpMap.Layers.VectorLayer("TestLayer"); testlayer.DataSource = sf; sharp.Layers.Add(testlayer); // Adds layer to sharp object sf.Open(); sharp.ZoomToExtents(); pictureBox1.Image = sharp.GetMap(); // diplay

 

Oct 18, 2009 at 4:51 AM

Hi,

I tried this code,

If I remove == sign and replace it with != then I get complete shapefile.

But I could not get selected polygons having "Name" attribute as 11.

What exactly is this delegate returning? Should it return those polygons which do not have "Name" attribute as 11?

 

sf.FilterDelegate = delegate(FeatureDataRow row)
            {
                return row["NAME"] != "11";
                   
            };

 

 

 

Oct 18, 2009 at 4:53 AM

hi john,

I got it. Thanks

What i did was,I used .equals property of a string

Instread of using =="11" I used return row["Name"].equals("11");

and my job was done.

I will let you know if I face any problems in this area.

Thanks again