Example: Create Many Locations from a Drawing

Given a drawing of points, we quickly create a folder with Locations for all of the points, allowing us to quickly pan and zoom to a local view around each point.

 

This is an introductory example, so we will illustrate every small step.   That creates very many illustrations, but the actual process can be handled in around five minutes by someone familiar with Manifold.  It is a very easy process.

 

Download the project seen below, as it is at the end of the example, create_locations_from_drawing.mxb, from the Examples page on the Manifold website.   Also download a simplified project suitable for Viewer tourism, Chateaux.mxb, from the Examples page on the Manifold website.   The downloadable examples use Bing street maps, while this topic uses OpenStreetMaps.

 

To fit into this documentation, illustrations show a small Manifold desktop, with only a few panes, docked to the right side.  In real life we use a much larger Manifold desktop, and more panes would be turned on, with panes docked to the left or to the right, or undocked, as we prefer.   Right-click a pane's tab to change where it is docked.  Manifold will remember that new arrangement for our next session.

A Drawing with Points

We have a map with a drawing layer that contains points at the locations of famous chateaux in France.

 

 

 

 

The map has an OSM streets background layer and also a Google satellite layer.

 

 

 

 

We can zoom in to the chateaux layer to see how this particular collection of chateaux is located in the valley of the river Loire.     There are hundreds of chateaux in and near the valley of the Loire, but this drawing only shows a small collection of the most famous.

 

 

 

 

Turning off the streets layer and turning on the Google satellite layer, we can see the points in the drawing layer in place over the satellite imagery.    We would like to zoom into various of the chateaux for a closer look.

 

 

 

 

We can always do that, to get a view like that above of the chateau at Chambord, by repeatedly using a right-click-and-drag to draw a zoom box.   However, even if we add a labels layer (not a bad idea in any event) to label the dots, it is still tedious to repeatedly use mouse motions to zoom in to get a view like that above.   If we want to see another chateau, we have to zoom back out and then repeat the process.

 

Much better would be to have a collection of locations, which would allow us to jump between views with a single click.    Our mission is to create such a collection of locations automatically, one for each point record in our drawing.

Prepare the Table

Opening the drawing's table, we see it is a typical table for a drawing, shown below in undocked form.

 

 

The table has a Name for each chateau, a geometry field called Geom that encodes the location, and a Description field that contains comments.    To automatically create a Location for each record in the table, we will use a script almost identical to that used in the Example: VBScript to Create Locations from a Table topic.

 

 

The text of the script illustrated above is:

 

' VBScript

Sub Main

        Set app = Manifold.Application

        Set db = app.GetDatabaseRoot() ' opened MAP file

        Set table = db.Search("locations")

        ' get list of records

        Set records = table.SearchAll(Array("Name", "Scale", "Longitude", "Latitude", "Description"))

        If (records Is Nothing) Then

                Exit Sub ' no records

        End If

        Do While records.Fetch

                ' read record values

                Set values = records.GetValues()

                name = values(0).Data

                scale = CDbl(values(1).Data)

                lon = CDbl(values(2).Data)

                lat = CDbl(values(3).Data)

                descr = values(4).Data

                ' compose location definition

                Set props = app.CreatePropertySet()

                props.SetProperty "Center", app.CreatePointObj(lon, lat)

                props.SetProperty "Scale", scale

                def = props.ToJson()

                ' create location

                created = db.Insert(name, "location")

                db.SetProperty created, "Text", def ' set location definition

                db.SetProperty created, "Folder", "Locations" ' put location into folder

                db.SetProperty created, "Description", descr ' set description

                app.Log "Created location: " & created

        Loop

        ' app.OpenLog

End Sub

 

It is identical to the script used in the Example: VBScript to Create Locations from a Table topic, except that it requires the table to have a Description text field, from which the script pulls the text to place in the Description property of the Location component it will create.   Having a Description property in the Location component will cause Manifold to show that description text in a tool tip when the mouse hovers over the Location in the Project pane.   

 

Just like the script in the Example: VBScript to Create Locations from a Table topic, in addition to the required Description field,  the above script is hard-wired to require Name, Scale, Latitude, and Longitude fields in a table called locations.     If we want to repeat this workflow with a table that uses fields like these but with different names, we can use the Edit - Schema dialog to quickly rename the fields to use the same names as our example table.

Add Fields

We already have a Name field and a Description field, so with the focus on the table we will launch the Edit - Schema dialog to create Scale, Latitude, and Longitude fields in the table.

 

 

To add a Scale field to the schema, we click the Add command button and choose Field.

 

 

In the Field dialog we use the name Scale and we choose the float64 type from the drop down menu.  

 

The initial default data type in the Type field is int32, for 32-bit integer numbers.   The Field dialog remembers the last used Type and presents that as the default until a different Type has been picked.  That makes it easy to repeatedly add new fields of the same data type.

 

Press OK to add the new Scale field to the schema.

 

To add a Latitude field to the schema, we click the Add command button and again choose Field.

 

 

In the Field dialog we use the name Latitude.  The float64 type is still in the Type box, remembered from the prior use.

 

We want to create the Latitude field as a computed field, so we press the Edit Expression button to launch the Expression dialog.  

 

 

In the expression pane, we enter the expression

 

VectorValue(GeomCoordXY([Geom], 0),1)

 

That expression uses two, simple SQL functions to extract the latitude number from the geometry field.  For a discussion of how that expression works, see the Example: Create a Geocoded Table from a Drawing topic.

 

Press OK.

 

 

Back in the Field dialog, we see the expression we added.   We press OK to add the new Latitude field to the Schema.

 

 

To add a Longitude field to the schema, we click the Add command button and choose Field.

 

 

In the Field dialog we use the name Longitude.  The float64 type is still in the Type box, remembered from the prior use.  

 

We want to create the Longitude field as a computed field, so we press the Edit Expression button to launch the Expression dialog.  

 

 

In the expression pane, we enter the expression

 

VectorValue(GeomCoordXY([Geom], 0),0)

 

That expression uses two, simple SQL functions to extract the longitude number from the geometry field.  For a discussion of how that expression works, see the Example: Create a Geocoded Table from a Drawing topic.

 

Press OK.

 

 

 

Back in the Field dialog, we see the expression we added.   We press OK to add the new Longitude field to the Schema.

 

 

The Schema dialog displays the new fields we have provisionally added in bluish background color.   This indicates they have been provisionally added to the table's schema, but changes have not yet been committed to the table.   To commit changes and add the fields to the table, we press Save Changes.

 

 

The fields appear in the table.  We have adjusted column widths to enable them all to fit into the illustration.   The Latitude and Longitude fields are shown with gray background color, indicating they are read-only, because they are computed fields, automatically calculating their values from whatever is in the Geom field.   

 

We have used computed fields so if we edit the drawing by moving any of the points, the latitude and longitude values will automatically be recomputed.

Populate the Scale Field

Each record should have the desired Scale value.    We can fill the Scale field with a desired value using the Transform pane's Copy template, or we can use a quick trick.  Since this documentation is full of many examples using the Transform pane, we will use a quick trick, to show an alternative method.

 

 

We double-click into the Scale cell for any of the records, enter 3000 and then press Enter.  Next we press Ctrl-A to select all records, or, we choose Edit - Select All.  

 

 

We right-click onto the cell that contains the 3000 value and choose Copy to Selection from the context menu.

 

Instantly, the Scale value for all selected records is set to 3000.   The table window also prompts for a refresh, in case any records have been modified by someone else or by some other process.  We click the prompt to clear the "data has been changed" advisory.   

 

 

We press Ctrl-I to invert the selection, that is to select none, or, we choose Edit - Select None.  

 

Except for the name of the table, the table we have prepared is ready to use with our script.  We will next change the name of the table.

Make a Table Copy called "locations"

The script we will use is hard-wired to digest a table called locations, so we will make a copy of the table we have prepared and re-name the copy locations.

 

 

 

 

Click the table to highlight it and press Ctrl-C to copy, or, press the Copy icon, or, right-click the table and choose Copy.

 

 

 

 

Press Ctrl-V to paste, or press the Paste icon, or right-click onto a blank spot in the Project pane and choose Copy.   A copy of the table appears using a default name.

 

 

 

 

Rename the copy to locations by slow-double-clicking it, entering the new name, and then pressing Enter.

Run the Script

We now have a table called locations that contains all of the fields required by the script.  Ready to go!

 

 

 

 

Right-click onto the Create Locations Description script and choose Run.

 

 

 

 

Instantly, a folder called Locations appears.   We can open it to see it contains a collection of locations, one for each record in our table.  Each location is named using the Name field for the record in the table.

Visit Locations

Now the fun part:  we can pan and zoom to any of the locations with a click.  This is not as satisfying as visiting the various chateaux in person, but visiting them this way is quicker, costs much less, and avoids crowds of tourists in the summer and rainy days in winter.

 

 

 

 

The Locations button automatically is loaded with all of the locations that are now in the project.   We can click on the Château d Amboise location to visit it.

 

 

 

 

The view instantly pans and zooms to that location, far faster than manually panning and zooming to Amboise.  In the view above, Leonardo's grave is in the chapel that partially appears just above the disabled Bing word in the tab strip.   See the chapel in the Notes to the Example: Change the Contrast of an Image topic.

 

If we position the mouse cursor over one of the locations we have created, a tooltip appears which gives the contents of the Description field.

 

 

If we right-click on one of the locations and choose Properties from the context menu, we can see the location has been created with a Description property that contains the text from the Description field in the table.   Adding a Description property is the difference between the Create Locations Description script used in this topic and the Create Locations script used in the Example: VBScript to Create Locations from a Table topic.

 

 

 

 

When there are many locations in a project, using the Locations button can become unwieldy.   We can always just right-click onto a desired location and choose View in Active Window.  

 

 

 

 

Above, we have instantly panned and zoomed to the Château d Angers.  From the description: "A massive fortress with exceptionally thick walls within the town of Angers, the site of the Apocalypse Tapestry."

Notes

See the Labels topic for a spectacular view of Chambord from ground level.  See the  the Example: Change the Contrast of an Image topic for notes on Leonardo.  Visit France if you can, and spend a few days in the valley of the Loire visiting chateaux.

Downloads

Download the create_locations_from_drawing.mxb project from the Examples page on the Manifold website.   Also download a simplified project suitable for Viewer tourism, Chateaux.mxb, from the Examples page on the Manifold website

See Also

Getting Started

 

User Interface

 

Tables

 

Maps

 

Locations

 

Selection

 

Project Pane

 

Select Pane

 

Transform Pane

 

Example: Locations - Save Locations and use saved Locations to quickly navigate to desired views in windows.

 

Example: Create a Table from Locations - Create a table that contains, as records, all of the Locations components in a project.  Each record contains the Name, Latitude, Longitude, and Scale of a location.  We use simple, point-and-click operations using the Select and Transform panes.

 

Example: Create a Geocoded Table from a Drawing - A partner example to Example: Create a Drawing from a Geocoded Table   A geocoded table has records with a latitude and longitude for each record.   This example starts with a table for a drawing of points where the geom field in the table contains geometry information for each point.   We extract the Y and X locations for each point  from the geom field to create latitude and longitude fields in the table for each record.

 

Example: VBScript to Create Locations from a Table - Use VBScript to take a table where each record has a name, scale, latitude and longitude and for each record create a Location component in the project.