ThinkGeo.com    |     Documentation    |     Premium Support

Overriden DrawCore features are not original types

I’m doing some work in overriden DrawCore() functions in some custom point style classes. The features using these styles are custom classes which inherit from Feature. However, in the DrawCore() functions, these features lose their derived type and are just Feature. Is there anything in particular that can cause this? The layer they are added to is just an InMemoryFeatureLayer, and are being added via the InternalFeatures.Add function, with a .BuildIndex() called after the .Add.

Looking at the InternalFeatures, I can confirm they are the derived type.

I am also overriding the DrawCore of that particular layer, if it matters. In the layer’s DrawCore, I’m simply doing a canvas.DrawLine, and then calling base.DrawCore(canvas, labelsInAllLayers); which leads to the style’s DrawCore function eventually.

Here’s what I can see in the stack trace:
In Style.cs, in the public void Draw( function, the features at this point are showing as the base Feature type.
I’m guessing somewhere along the line it’s using the layer’s projection converter. When I use ConvertToExternalProjection on a derived type, it always returns the base Feature type.

Hi Dan,

You are right. ConvertToExternalProjection(DerivedFeature) creates and returns a new Feature, that’s why the input derived type was lost.

A workaround would be creating the derived features from the reprojected data, to avoid the internal reprojection in the layer level, something like this:

SubFeature subFeature = new SubFeature();
foreach (var columnValue in reprojectedFeature.ColumnValues)
       subFeature.ColumnValues.Add(columnValue.Key, columnValue.Value);

subFeature.SetWellKnownBinary(reprojectedFeature.GetWellKnownBinary());
inMemoryFeatureLayer.InternalFeatures.Add(subFeature);

Background: Feature was designed to be Immutable (it was a struct at first), but over time we made it a class and add some virtual method for user to override, but in some places (such as ConvertToExternalProjection) we still treat it as an Immutable value object and returns a newly created Feature, which is the root cause here.

I think we still need to keep the current way ( creating a new Feature during layer reprojection) to avoid breaking change, but we can provide some helper methods like feature.Reproject(4326, 3857) to reproject itself. You still need to add the reprojected feature to a layer but the code would be much simpler. Let us discuss about it and will keep you posted, and just let me know if you have any suggestions.

Thanks,
Ben