I wanted to get your feedback on a new PDF extension we are working on. The extension allows you to print your maps into a vector PDF. I think you will find the extension flexible and easy to use.
To implement this extension, we created a new class called PdfGeoCanvas that inherits from the abstract class GeoCanvas. We put the logic in there and because of that, we can easily draw all of our layers using this new GeoCanvas type. This is not just a cool extension for writing to PDFs, but also a fine example of how extensible the Map Suite 3.x framework is. We went from normally drawing on a bitmap in pixels to drawing to a vector PDF in points.
Downloads:
The zip file will eventually be included in the main release, but I wanted to get this into your hands as quickly as possible and get some feedback. In the zip file you will find the sample below, the source to the library we use to handle the PDF-specific stuff, and a DLL of the extension. I have also included a sample PDF as an attachment.
The sample application has two main parts. The first part is some very standard code to draw a few layers. The second part simply loops through these layers and draws them to the PDF. I think you will find it simple and easy to use.
Important:
When you load the sample application, you need to reference the MapSuiteCore.dll from any of the latest editions.
For the PDF to pop up you need to have a PDF reader associated with the .pdf extension. While the writing of the PDF has nothing to do with it, we just have some handy code in the sample that pops the PDF up when it's done drawing.
The code below is also in the zip file.
David
// This method is really standard. It is used to draw the image on the screen.
// The real magic is in the btnToPdf_Click event.
private void Sample_Load(object sender, EventArgs e)
{
bitmap = new Bitmap(map.Width, map.Height);
mapEngine = new MapEngine();
mapEngine.CurrentExtent = ExtentHelper.GetDrawingExtent(new RectangleShape(-180.0, 83.0, 180.0, -90.0), map.Width, map.Height);
mapEngine.BackgroundFillBrush = new GeoSolidBrush(GeoColor.GeographicColors.ShallowOcean);
EcwRasterLayer worldImageLayer = new EcwRasterLayer(@"..\..\SampleData\World.ecw");
ShapeFileFeatureLayer worldLayer = new ShapeFileFeatureLayer(@"..\..\SampleData\Countries02.shp");
worldLayer.ZoomLevelSet.ZoomLevel01.DefaultAreaStyle = AreaStyles.Country1;
worldLayer.ZoomLevelSet.ZoomLevel01.DefaultAreaStyle.OutlinePen.LineJoin = DrawingLineJoin.Round;
worldLayer.ZoomLevelSet.ZoomLevel01.ApplyUntilZoomLevel = ApplyUntilZoomLevel.Level20;
ShapeFileFeatureLayer usStatesLayer = new ShapeFileFeatureLayer(@"..\..\SampleData\USStates.shp");
usStatesLayer.ZoomLevelSet.ZoomLevel01.DefaultAreaStyle = AreaStyles.State2;
usStatesLayer.ZoomLevelSet.ZoomLevel01.DefaultAreaStyle.OutlinePen.LineJoin = DrawingLineJoin.Round;
usStatesLayer.ZoomLevelSet.ZoomLevel01.ApplyUntilZoomLevel = ApplyUntilZoomLevel.Level20;
ShapeFileFeatureLayer worldCapitalsLayer = new ShapeFileFeatureLayer(@"..\..\SampleData\WorldCapitals.shp");
worldCapitalsLayer.ZoomLevelSet.ZoomLevel01.DefaultPointStyle = PointStyles.Capital3;
worldCapitalsLayer.ZoomLevelSet.ZoomLevel01.ApplyUntilZoomLevel = ApplyUntilZoomLevel.Level20;
ShapeFileFeatureLayer worldCapitalsLabelsLayer = new ShapeFileFeatureLayer(@"..\..\SampleData\WorldCapitals.shp");
worldCapitalsLabelsLayer.ZoomLevelSet.ZoomLevel01.DefaultTextStyle = TextStyles.Capital3("city_name");
worldCapitalsLabelsLayer.ZoomLevelSet.ZoomLevel01.DefaultTextStyle.HaloPen = new GeoPen(GeoColor.StandardColors.White, 2);
worldCapitalsLabelsLayer.ZoomLevelSet.ZoomLevel01.DefaultTextStyle.HaloPen.LineJoin = DrawingLineJoin.Round;
worldCapitalsLabelsLayer.ZoomLevelSet.ZoomLevel01.ApplyUntilZoomLevel = ApplyUntilZoomLevel.Level20;
mapEngine.StaticLayers.Add("WorldImageLayer", worldImageLayer);
mapEngine.StaticLayers.Add("WorldLayer", worldLayer);
mapEngine.StaticLayers.Add("USStatesLayer", usStatesLayer);
mapEngine.StaticLayers.Add("WorldCapitals", worldCapitalsLayer);
mapEngine.StaticLayers.Add("WorldCapitalsLabels", worldCapitalsLabelsLayer);
DrawImage();
}
// Here we setup the PDF page and then create our PDFGeoCanvas.
// We loop through all the layers to draw and then save & pop the
// PDF
private void btnToPdf_Click(object sender, EventArgs e)
{
PdfDocument document = new PdfDocument();
PdfPage page = document.AddPage();
if (pageOrientationLandscape.Checked == true)
{
page.Orientation = PageOrientation.Landscape;
}
PdfGeoCanvas pdfGeoCanvas = new PdfGeoCanvas();
Collection<SimpleCandidate> labelsInLayers = new Collection<SimpleCandidate>();
foreach (Layer layer in mapEngine.StaticLayers)
{
pdfGeoCanvas.BeginDrawing(page, ExtentHelper.GetDrawingExtent(mapEngine.CurrentExtent, (float)(page.Width.Point), (float)(page.Height.Point)),GeographyUnit.DecimalDegree);
layer.Open();
layer.Draw(pdfGeoCanvas, labelsInLayers);
layer.Close();
pdfGeoCanvas.EndDrawing();
}
string filename = "MapSuite PDF Map.pdf";
document.Save(filename);
Process.Start(filename);
}
Downloads: