Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Raster Data Loading from FilePath in Dotspatial

I have this simple line of code in DotSpatial

var raster = Raster.OpenFile("X://Data//4mr_project.tif");

Why raster just getting null value??

I also have .aux, .ovr, .tfw files in the same directory.

EDITED:

I found that the line below works fine:

var featureSet = FeatureSet.Open("X:\\Test Data\\shap\\edited.shp")

because Dotspatial have capability to load .shp file by default. But loading raster data .tif format, Dotspatial need GDAL extensions. Now the question is how to load GDAL extensions manually in Dotspatial using C#.

like image 278
Moshi Avatar asked Feb 11 '23 15:02

Moshi


2 Answers

GDAL extensions can be supported in your own application through the use of the AppManager component. You can drag and drop this onto your form. This allows for support from the GDAL data extensions, and will also gives support to other plug-ins. Here is a basic walk through for adding the AppManager to a new project that just has a Map on the form.

1) From the Visual Studio Toolbox, right click and click on "Choose Items"

Choose Items

2) From the dialog, choose "Browse" and browse to the DotSpatial.Controls.dll library.

Dotspatial.Controls.dll

3) Click Ok as needed to close the dialogs and get back to the Toolbox.

4) Find the AppManager component you just added in the Toolbox.

AppManager

5) Drag the AppManager component onto your form. (not on the map, but on the form). A new instance should appear below your form in the non-visual components list.

6) Select this component to view it's properties in the Properties Dialog.

7) Set the map for the appManager (or other components if you are using them).

Define Map

8) The GDAL component does not even require the Map to be defined in order to work, it should just work. But you will need the GDAL extension. You can find the DotSpatial.Data.Rasters.GdalExtension in the "Windows Extensions" folder. Ensure that you have a similar folder in your output directory with the necessary GdalExtension. One method is just to ensure that this is in your final distribution folder manually.

9) (Optional) One trick you can use, to ensure you have the GDAL plugin in your release folders is to add the libraries as content. This way, regardless if you are working on a debug version or a release version, it will ensure that the GDAL data extension makes it to the output folders.

Copy Content

10) Ensure that the directory you are using (like "Windows Extensions") is listed in the Directories property of the AppManager. The image below shows the default folders which are "Application Extensions" and "Plugins". I think it originally was "Application Extensions" but got updated to "Windows Extensions" later. Unfortunately, I don't think they updated the default folder.

Directories

11) In the code somewhere (probably in the form constructor) you need to call appManager1.LoadExtensions(); If you don't call this, it will not actually load the GDAL extension even if you have the GDAL library as part of your project.

12) Add a SpatialDockManager, SpatialHeaderManager, SpatialStatusStrip to the project. Then assign these to the properties on the AppManager, the same way you did the map. For reasons that are beyond me and were implemented after I left, the previously open ended design structure has changed, and now it will throw message box errors if the program does not include these things but you try to use Extensions. The "ProgressHandler" property takes the SpatialStatusStrip.

After following all 12 of these steps (and running the project in x86 mode) the raster code you posted in the initial question works, and you can open geotifs. I also pushed the GDAL extension into the root "Application Extensions" directory while trying to get it to work, but I don't think you have to do that. It should work if it is in a subfolder.

like image 82
Ted Avatar answered Feb 25 '23 04:02

Ted


Sorry to be that late (hopefully, it's never too late), but if you wish to use the plugin without using AppManager, because you may be composing something custom and do not want to depend on the main DotSpatial application framework (note that the AppManager utilizes some slightly advanced "magic" to make it all work together), you can do yourself the following few simple tasks:

1) Add a reference to the file

(DotSpatial Release Folder)\Windows Extensions\DotSpatial.Data.Rasters.GdalExtension.dll

to your project (this is the main GdalExtension Plugin output file).

NOTE: To make sure this step is done correctly, make sure that building your library (the one that references the GdalExtension.dll) ends up copying to this project's output directory the additional files from the same folder (i.e. gdal_csharp.dll etc.).

2) This same folder also contains a gdal subfolder. Copy the folder itself, as-is, to your output path (usually ...\bin\Release\\ or ...\bin\Debug\\, depending on your configuration). Of course in your final project, you would probably like to use a post-build copy event to automate the process, or just include the folder as content in your application build output, as Ted also mentions in step 9 of his answer.

NOTE: By output folder, I am referring to the Application Output Path, not the library output path. If your application is using a library, which undertakes the task of loading rasters (through GdalExtension), the gdal folder does not need to be in the output folder of this library. It needs to end up in your final application's output folder. The reason is that the various dll files are loaded dynamically, so they have to be found in the executing application folder.

3) As early as possible in your codebase, create a new GdalRasterProvider, which should now be referenced by the dll file added in step 1. This means, add something like the following line to your project

var grp = new DotSpatial.Data.Rasters.GdalExtension.GdalRasterProvider();

Thereafter, the first line of code in your post should work as expected. So, technically, the answer to the original question is that the DefaultDataManager class did not find any suitable provider to perform the task of actually loading the Raster file. Therefore, you are left with a null variable.

Interestingly, you don't need to hold the reference anywhere (i.e. do anything with variable grp). If you check the source code, the constructor itself undertakes the task of adding itself to the DefaultDataProvider.PreferredProviders dictionary, which is eventually invoked behind the scenes in the call to Raster.Open(string) method. The only "tough-to-figure-out" part is simply to copy the gdal folder in your application output path, because the GDAL extension loads a number of references located therein upon instantiation of any provider, and the loading is based on a "gdal" subfolder located in whichever folder your application resides and is executed from.

(Note that the Plugin also contains two more providers (GdalImageProvider and OgrDataProvider). To make these two work, you need to instantiate them but also to manually add them to the PreferredProviders dictionary of the DefaultDataProvider, typically also up early in your application code)

like image 21
Vector Sigma Avatar answered Feb 25 '23 04:02

Vector Sigma