Changes between Initial Version and Version 1 of MapGuideRfc140


Ignore:
Timestamp:
Jun 30, 2014, 9:03:57 AM (10 years ago)
Author:
jng
Comment:

--

Legend:

Unmodified
Added
Removed
Modified
  • MapGuideRfc140

    v1 v1  
     1
     2= !MapGuide RFC 140 - Shareable tile sets and XYZ tile rendering support =
     3
     4This page contains a change request (RFC) for the !MapGuide Open Source project.
     5More !MapGuide RFCs can be found on the [wiki:MapGuideRfcs RFCs] page.
     6
     7== Status ==
     8
     9||RFC Template Version||(1.0)||
     10||Submission Date||1 July 2014||
     11||Last Modified||||
     12||Author||Jackie Ng||
     13||RFC Status||draft||
     14||Implementation Status||||
     15||Proposed Milestone||3.0||
     16||Assigned PSC guide(s)||(when determined)||
     17||'''Voting History'''||(vote date)||
     18||+1||||
     19||+0||||
     20||-0||||
     21||-1||||
     22||no vote|| ||
     23
     24== Overview ==
     25
     26This RFC proposes to enhance the Tiled Map support in MapGuide with shareable tile sets and XYZ tile rendering support
     27
     28== Motivation ==
     29
     30The current tiled map support in MapGuide has several limitations:
     31
     32 * Tile rendering settings are globally bound to values defined in serverconfig.ini. It is not possible to have tiled maps of various tile sizes and image formats
     33 * Tile layers are tied to Map Definitions, preventing re-use of tile caches with other Map Definitions. Such information should ideally be defined in a separate resource.
     34 * The root directory for all tile caches is also defined by serverconfig.ini. It is not possible to use alternate paths for storage for certain tiled maps.
     35 * The current tile services are not amenable to consumption by external client libraries and applications without intricate knowledge of the MapGuide API and settings of the Map Definition / MgMap.
     36
     37== Proposed Solution ==
     38
     39This RFC proposes a multi-pronged approach to solving this problem:
     40
     41 * Introducing a new resource type: TileSetDefinition
     42 * CREATERUNTIMEMAP/DESCRIBERUNTIMEMAP update
     43 * Implementing a simple provider model to support different tile sources
     44 * New APIs to support Tile Sets
     45 * Supporting "XYZ" tile sets
     46 
     47Each component is described below
     48 
     49=== TileSetDefinition ===
     50
     51A Tile Set Definition defines a tile cache and its various properties:
     52
     53 * The bounds of the tile cache
     54 * Parameters that define how this tile cache is accesssed
     55 * The layers and groups that consititute the tile set
     56
     57Basically, the Tile Set Definition is effectively the BaseMapDefinition component of the existing Map Definiton schema separated out into its own separate resource.
     58
     59The TileSetDefinition schema is defined as follows:
     60{{{
     61<?xml version="1.0" encoding="UTF-8"?>
     62<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" elementFormDefault="qualified" attributeFormDefault="unqualified">
     63  <xs:include schemaLocation="PlatformCommon-1.0.0.xsd"/>
     64  <xs:element name="TileSetDefinition">
     65    <xs:annotation>
     66      <xs:documentation>Defines a tile cache</xs:documentation>
     67    </xs:annotation>
     68    <xs:complexType>
     69      <xs:sequence>
     70        <xs:element name="TileStoreParameters" type="TileStoreParametersType">
     71           <xs:annotation>
     72            <xs:documentation>Defines the parameters to access and describe the tile cache</xs:documentation>
     73          </xs:annotation>
     74        </xs:element>
     75        <xs:element name="Extents" type="Box2DType">
     76          <xs:annotation>
     77            <xs:documentation>A bounding box around the area of the tile cache</xs:documentation>
     78          </xs:annotation>
     79        </xs:element>
     80        <xs:element name="BaseMapLayerGroup" type="BaseMapLayerGroupCommonType" minOccurs="1" maxOccurs="unbounded">
     81          <xs:annotation>
     82            <xs:documentation>A group of layers that is used to compose a tiled layer in the HTML viewer</xs:documentation>
     83          </xs:annotation>
     84        </xs:element>
     85      </xs:sequence>
     86    </xs:complexType>
     87  </xs:element>
     88  <xs:complexType name="TileStoreParametersType">
     89    <xs:annotation>
     90      <xs:documentation>TileStoreParameters defines the parameters of this tile cache.</xs:documentation>
     91    </xs:annotation>
     92    <xs:sequence>
     93      <xs:element name="TileProvider" type="xs:string">
     94        <xs:annotation>
     95          <xs:documentation>The tile image provider</xs:documentation>
     96        </xs:annotation>
     97      </xs:element>
     98      <xs:element name="Parameter" type="NameValuePairType" minOccurs="0" maxOccurs="unbounded">
     99        <xs:annotation>
     100          <xs:documentation>Collection of name value pairs for connecting to the tile image provider</xs:documentation>
     101        </xs:annotation>
     102      </xs:element>
     103    </xs:sequence>
     104  </xs:complexType>
     105  <xs:complexType name="NameValuePairType">
     106    <xs:annotation>
     107      <xs:documentation>A type describing name and value pairs</xs:documentation>
     108    </xs:annotation>
     109    <xs:sequence>
     110      <xs:element name="Name" type="xs:string">
     111        <xs:annotation>
     112          <xs:documentation>Text for the name of parameter</xs:documentation>
     113        </xs:annotation>
     114      </xs:element>
     115      <xs:element name="Value" type="xs:string">
     116        <xs:annotation>
     117          <xs:documentation>Text for value of parameter</xs:documentation>
     118        </xs:annotation>
     119      </xs:element>
     120      <xs:element name="ExtendedData1" type="ExtendedDataType" minOccurs="0"/>
     121    </xs:sequence>
     122  </xs:complexType>
     123  <xs:complexType name="Box2DType">
     124    <xs:annotation>
     125      <xs:documentation>Box2D encapsulates the the coordinates of a box in 2-D space</xs:documentation>
     126    </xs:annotation>
     127    <xs:sequence>
     128      <xs:element name="MinX" type="xs:double">
     129        <xs:annotation>
     130          <xs:documentation>Minimum x-coordinate</xs:documentation>
     131        </xs:annotation>
     132      </xs:element>
     133      <xs:element name="MaxX" type="xs:double">
     134        <xs:annotation>
     135          <xs:documentation>Maximum x-coordinate</xs:documentation>
     136        </xs:annotation>
     137      </xs:element>
     138      <xs:element name="MinY" type="xs:double">
     139        <xs:annotation>
     140          <xs:documentation>Minimum y-coordinate</xs:documentation>
     141        </xs:annotation>
     142      </xs:element>
     143      <xs:element name="MaxY" type="xs:double">
     144        <xs:annotation>
     145          <xs:documentation>Maximum y-coordinate</xs:documentation>
     146        </xs:annotation>
     147      </xs:element>
     148    </xs:sequence>
     149  </xs:complexType>
     150  <xs:complexType name="BaseMapLayerType">
     151    <xs:annotation>
     152      <xs:documentation>BaseMapLayerType encapsulates the properties of a BaseMapLayer.</xs:documentation>
     153    </xs:annotation>
     154    <xs:sequence>
     155      <xs:element name="Name" type="xs:string">
     156        <xs:annotation>
     157          <xs:documentation>Name of the MapLayer</xs:documentation>
     158        </xs:annotation>
     159      </xs:element>
     160      <xs:element name="ResourceId" type="xs:string">
     161        <xs:annotation>
     162          <xs:documentation>ResourceId of the MapLayer</xs:documentation>
     163        </xs:annotation>
     164      </xs:element>
     165      <xs:element name="Selectable" type="xs:boolean">
     166        <xs:annotation>
     167          <xs:documentation>Whether or not the Layer can be selected</xs:documentation>
     168        </xs:annotation>
     169      </xs:element>
     170      <xs:element name="ShowInLegend" type="xs:boolean">
     171        <xs:annotation>
     172          <xs:documentation>Whether or not the Layer should be shown in the legend</xs:documentation>
     173        </xs:annotation>
     174      </xs:element>
     175      <xs:element name="LegendLabel" type="xs:string">
     176        <xs:annotation>
     177          <xs:documentation>Label to be shown for the Layer in the legend</xs:documentation>
     178        </xs:annotation>
     179      </xs:element>
     180      <xs:element name="ExpandInLegend" type="xs:boolean">
     181        <xs:annotation>
     182          <xs:documentation>Whether or not the Layer should be expanded in the legend.</xs:documentation>
     183        </xs:annotation>
     184      </xs:element>
     185    </xs:sequence>
     186  </xs:complexType>
     187  <xs:complexType name="MapLayerGroupCommonType">
     188    <xs:annotation>
     189      <xs:documentation>MapLayerGroupCommonType is a common subclass of MapLayerGroupCommonType and BaseMapLayerGroupCommonType</xs:documentation>
     190    </xs:annotation>
     191    <xs:sequence>
     192      <xs:element name="Name" type="xs:string">
     193        <xs:annotation>
     194          <xs:documentation>The name of this LayerGroup</xs:documentation>
     195        </xs:annotation>
     196      </xs:element>
     197      <xs:element name="Visible" type="xs:boolean">
     198        <xs:annotation>
     199          <xs:documentation>Whether this group's visiblity should be visible or not when it first comes into range</xs:documentation>
     200        </xs:annotation>
     201      </xs:element>
     202      <xs:element name="ShowInLegend" type="xs:boolean">
     203        <xs:annotation>
     204          <xs:documentation>Whether or not the LayerGroup should be shown in the legend</xs:documentation>
     205        </xs:annotation>
     206      </xs:element>
     207      <xs:element name="ExpandInLegend" type="xs:boolean">
     208        <xs:annotation>
     209          <xs:documentation>Whether or not the LayerGroup should be initially expanded in the legend</xs:documentation>
     210        </xs:annotation>
     211      </xs:element>
     212      <xs:element name="LegendLabel" type="xs:string">
     213        <xs:annotation>
     214          <xs:documentation>Label to be shown for the LayerGroup in the legend</xs:documentation>
     215        </xs:annotation>
     216      </xs:element>
     217    </xs:sequence>
     218  </xs:complexType>
     219  <xs:complexType name="BaseMapLayerGroupCommonType">
     220    <xs:annotation>
     221      <xs:documentation>BaseMapLayerGroupCommonType encapsulates the properties of a BaseMapLayerGroup. It extends MapLayerGroupCommonType by holding the layers in the group.  The base map layer groups defines what layers are used to render a tile set in the HTML viewer.</xs:documentation>
     222    </xs:annotation>
     223    <xs:complexContent>
     224      <xs:extension base="MapLayerGroupCommonType">
     225        <xs:sequence>
     226          <xs:element name="BaseMapLayer" type="BaseMapLayerType" minOccurs="0" maxOccurs="unbounded">
     227            <xs:annotation>
     228              <xs:documentation>The layers that are part of this group. The order of the layers represents the draw order, layers first is the list are drawn over top of layers later in the list.</xs:documentation>
     229            </xs:annotation>
     230          </xs:element>
     231        </xs:sequence>
     232      </xs:extension>
     233    </xs:complexContent>
     234  </xs:complexType>
     235</xs:schema>
     236}}}
     237
     238An example tile set definition would look like this:
     239
     240{{{
     241<?xml version="1.0" encoding="UTF-8"?>
     242<TileSetDefinition xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="TileSetDefinition-3.0.0.xsd">
     243  <TileStoreParameters>
     244    <TileProvider>Default</TileProvider>
     245    <Parameter>
     246      <Name>TilePath</Name>
     247      <Value>%MG_TILE_CACHE_PATH%</Value>
     248    </Parameter>
     249    <Parameter>
     250      <Name>TileWidth</Name>
     251      <Value>256</Value>
     252    </Parameter>
     253    <Parameter>
     254      <Name>TileHeight</Name>
     255      <Value>256</Value>
     256    </Parameter>
     257    <Parameter>
     258      <Name>TileFormat</Name>
     259      <Value>PNG</Value>
     260    </Parameter>
     261    <Parameter>
     262      <Name>FiniteScaleList</Name>
     263      <Value>200000,100000,50000,25000,12500,6250,3125,1562.5,781.25,390.625</Value>
     264    </Parameter>
     265    <Parameter>
     266      <Name>CoordinateSystem</Name>
     267      <Value>GEOGCS["LL84",DATUM["WGS 84",SPHEROID["WGS 84",6378137,298.25722293287],TOWGS84[0,0,0,0,0,0,0]],PRIMEM["Greenwich",0],UNIT["Degrees",0.01745329252]]</Value>
     268    </Parameter>
     269  </TileStoreParameters>
     270  <Extents>
     271    <MinX>-87.79786601383196</MinX>
     272    <MaxX>-87.66452777186925</MaxX>
     273    <MinY>43.6868578621819</MinY>
     274    <MaxY>43.8037962206133</MaxY>
     275  </Extents>
     276  <BaseMapLayerGroup>
     277    <Name>Base Layer Group</Name>
     278    <Visible>true</Visible>
     279    <ShowInLegend>true</ShowInLegend>
     280    <ExpandInLegend>true</ExpandInLegend>
     281    <LegendLabel>Tiled Layers</LegendLabel>
     282    <BaseMapLayer>
     283      <Name>Roads</Name>
     284      <ResourceId>Library://Samples/Sheboygan/Layers/Roads.LayerDefinition</ResourceId>
     285      <Selectable>false</Selectable>
     286      <ShowInLegend>true</ShowInLegend>
     287      <LegendLabel>Roads</LegendLabel>
     288      <ExpandInLegend>true</ExpandInLegend>
     289    </BaseMapLayer>
     290    <BaseMapLayer>
     291      <Name>Districts</Name>
     292      <ResourceId>Library://Samples/Sheboygan/Layers/Districts.LayerDefinition</ResourceId>
     293      <Selectable>false</Selectable>
     294      <ShowInLegend>true</ShowInLegend>
     295      <LegendLabel>Districts</LegendLabel>
     296      <ExpandInLegend>true</ExpandInLegend>
     297    </BaseMapLayer>
     298    <BaseMapLayer>
     299      <Name>Buildings</Name>
     300      <ResourceId>Library://Samples/Sheboygan/Layers/Buildings.LayerDefinition</ResourceId>
     301      <Selectable>false</Selectable>
     302      <ShowInLegend>true</ShowInLegend>
     303      <LegendLabel>Buildings</LegendLabel>
     304      <ExpandInLegend>true</ExpandInLegend>
     305    </BaseMapLayer>
     306    <BaseMapLayer>
     307      <Name>Parcels</Name>
     308      <ResourceId>Library://Samples/Sheboygan/Layers/Parcels.LayerDefinition</ResourceId>
     309      <Selectable>true</Selectable>
     310      <ShowInLegend>true</ShowInLegend>
     311      <LegendLabel>Parcels</LegendLabel>
     312      <ExpandInLegend>true</ExpandInLegend>
     313    </BaseMapLayer>
     314    <BaseMapLayer>
     315      <Name>Islands</Name>
     316      <ResourceId>Library://Samples/Sheboygan/Layers/Islands.LayerDefinition</ResourceId>
     317      <Selectable>false</Selectable>
     318      <ShowInLegend>true</ShowInLegend>
     319      <LegendLabel>Islands</LegendLabel>
     320      <ExpandInLegend>true</ExpandInLegend>
     321    </BaseMapLayer>
     322    <BaseMapLayer>
     323      <Name>Hydrography</Name>
     324      <ResourceId>Library://Samples/Sheboygan/Layers/Hydrography.LayerDefinition</ResourceId>
     325      <Selectable>false</Selectable>
     326      <ShowInLegend>true</ShowInLegend>
     327      <LegendLabel>Hydrography</LegendLabel>
     328      <ExpandInLegend>true</ExpandInLegend>
     329    </BaseMapLayer>
     330    <BaseMapLayer>
     331      <Name>CityLimits</Name>
     332      <ResourceId>Library://Samples/Sheboygan/Layers/CityLimits.LayerDefinition</ResourceId>
     333      <Selectable>false</Selectable>
     334      <ShowInLegend>true</ShowInLegend>
     335      <LegendLabel>CityLimits</LegendLabel>
     336      <ExpandInLegend>true</ExpandInLegend>
     337    </BaseMapLayer>
     338  </BaseMapLayerGroup>
     339</TileSetDefinition>
     340}}}
     341
     342As you can see, the structure of the document is mostly similar to the BaseMapDefinition section of a Map Definition, with one notable difference.
     343
     344The tile cache settings are defined as a set of key/value pairs for a particular Tile Provider. See the Tile Providers section for more information
     345
     346To render and access tiles in this tile set, clients can use the existing GetTile API of MgTileService, but instead of passing in a Map Definition resource id, they pass in a Tile Set Definition resource id instead. The net result will be the same for both: You will get a rendered tile for the given group/row/col/scale. The difference in this implementation is that, GetTile on the tile set definition will use the defined width/height/format as defined in the Tile Set Definition when rendering (instead of serverconfig.ini).
     347
     348This allows for different tile sets to use different width/height/format/storage settings.
     349
     350To allow for tile set re-usability, Map Definitions can now reference a Tile Set Definition so that its layers and groups can be incorporated to a MgMap as tiled layers/groups. The relevant portion of the new Map Definition schema is shown below
     351
     352{{{
     353<?xml version="1.0" encoding="UTF-8"?>
     354<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" elementFormDefault="qualified" attributeFormDefault="unqualified" version="3.0.0">
     355  <xs:include schemaLocation="WatermarkDefinition-2.4.0.xsd"/>
     356  ...
     357      <xs:element name="BaseMapDefinition" minOccurs="0">
     358        ...
     359      </xs:element>
     360      <xs:element name="TileSetSource" minOccurs="0">
     361        <xs:annotation>
     362          <xs:documentation>A reference to the tile set source to use</xs:documentation>
     363        </xs:annotation>
     364        <xs:complexType>
     365          <xs:sequence>
     366            <xs:element name="ResourceId" type="xs:string">
     367              <xs:annotation>
     368                <xs:documentation>ResourceId of the TileSetDefinition</xs:documentation>
     369              </xs:annotation>
     370            </xs:element>
     371          </xs:sequence>
     372        </xs:complexType>
     373      </xs:element>
     374      <xs:element name="Watermarks" type="WatermarkInstanceCollectionType" minOccurs="0">
     375        ...
     376      </xs:element>
     377  ...
     378</xs:schema>
     379}}}
     380
     381An example Map Definition that links to a Tile Set Definition looks like this
     382{{{
     383<?xml version="1.0" encoding="UTF-8"?>
     384<MapDefinition xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="MapDefinition-3.0.0.xsd" version="3.0.0">
     385  <Name>Base Map linked to Tile Set</Name>
     386  <CoordinateSystem>GEOGCS["WGS84 Lat/Long's, Degrees, -180 ==&gt; +180",DATUM["D_WGS_1984",SPHEROID["World_Geodetic_System_of_1984",6378137,298.257222932867]],PRIMEM["Greenwich",0],UNIT["Degree",0.017453292519943295]]</CoordinateSystem>
     387  <Extents>
     388    <MinX>-87.764986990962839</MinX>
     389    <MaxX>-87.695521510899724</MaxX>
     390    <MinY>43.691398128787782</MinY>
     391    <MaxY>43.797520000480347</MaxY>
     392  </Extents>
     393  <BackgroundColor>FFF7E1D2</BackgroundColor>
     394  <TileSetSource>
     395    <ResourceId>Library://Samples/Sheboygan/TileSets/Sheboygan.TileSetDefinition</ResourceId>
     396  </TileSetSource>
     397</MapDefinition>
     398}}}
     399
     400If for any reason a BaseMapDefinition element and TileSetSource element both exist in the Map Definition, the BaseMapDefinition takes precedence when initializing a MgMap. Authoring tools should try to ensure that only a BaseMapDefinition or TileSetSource is specified but not both.
     401
     402Since both a Tile Set Definition and Map Definition both define coordinate systems and extents. The question may arise as to which one to use when creating a MgMap. The answer is simply if a Map Definition references a Tile Set Definition, then the coordinate system of the Tile Set and the extents of the Map Definition "wins". For example, if the coordinate system of the Map Definition is LL84, and the linked Tile Set Definition is WGS84.PseudoMercator. The coordinate system of the MgMap that is created will be WGS84.PseudoMercator and the extent will be the WGS84.PseudoMercator projected version of the Map Definition's extents.
     403
     404The reason for this rule is simply it is much easier to re-project dynamic layers to the Tile Set's coordinate system rather than re-projecting tiles to the Map Definition's coordinate system. Client authoring tools should do whatever they can to communicate this fact.
     405
     406This support requires some changes to MgLayerGroupType and MgMap in order for applications to identify if it originates from a Map Definition or Tile Set Definition.
     407
     408Firstly, a new value has been defined for MgLayerGroupType to identify layer groups from Tile Sets
     409{{{
     410class MgLayerGroupType
     411{
     412PUBLISHED_API:
     413    /////////////////////////////////////////////////
     414    /// \brief
     415    /// Specifies that the layer is a base map layer from a TileSetDefinition resource
     416    ///
     417    /// \since 3.0
     418    static const INT32 BaseMapFromTileSet = 3;
     419};
     420}}}
     421
     422From a client application perspective, any MgLayerGroup that is BaseMap or BaseMapFromTileSet should be treated the same for the purposes of:
     423 a) Determining if a layer group is tiled
     424 b) If a group is suitable for GETTILE requests
     425
     426Secondly, MgMap has a new GetTileSetDefinition() method to identify the Tile Set the group originates from
     427{{{
     428class MG_PLATFORMBASE_API MgMap : public MgMapBase
     429{
     430PUBLISHED_API:
     431    //////////////////////////////////////////////////////////////////
     432    /// \brief
     433    /// Returns the resource id of the Tile Set Definition that created
     434    /// this map, or the Tile Set Definition linked from the Map Definition
     435    /// used to created this map. If it was created from a Map Definition and
     436    /// that does not link to a Tile Set Definition, then NULL is returned.
     437    ///
     438    /// <!-- Syntax in .Net, Java, and PHP -->
     439    /// \htmlinclude DotNetSyntaxTop.html
     440    /// MgResourceIdentifier GetTileSetDefinition();
     441    /// \htmlinclude SyntaxBottom.html
     442    /// \htmlinclude JavaSyntaxTop.html
     443    /// MgResourceIdentifier GetTileSetDefinition();
     444    /// \htmlinclude SyntaxBottom.html
     445    /// \htmlinclude PHPSyntaxTop.html
     446    /// MgResourceIdentifier GetTileSetDefinition();
     447    /// \htmlinclude SyntaxBottom.html
     448    ///
     449    /// \since 3.0
     450    ///
     451    /// \return
     452    /// Returns the resource id of the Tile Set Definition. NULL if created from a Map Definition that does not link
     453    /// to a Tile Set
     454    MgResourceIdentifier* GetTileSetDefinition();
     455};
     456}}}
     457
     458The existing Create() method of MgMap now also supports Tile Set Definitions meaning it is now possible to create MgMap instances from a Tile Set Definition or a Map Definition. This was done out of necessity as the server implementation of the Tile Service needs to be able to make an MgMap instance to pass to the RenderTile rendering method. For this RFC, we will apply some limitations on what Tile Set Definitions can be passed to MgMap::Create(). See Implications for more information.
     459
     460=== CREATERUNTIMEMAP/DESCRIBERUNTIMEMAP update ===
     461
     462This new information also needs to be passed down to whatever responses we send to the client application, so CREATERUNTIMEMAP/DESCRIBERUNTIMEMAP have been updated to include this information:
     463
     464 * The Tile Set Definition that the Map Definition links to. If the Map Definition doesn't link to a Tile Set, this element is omitted.
     465 * The tile width. If the Map Definition doesn't link to a Tile Set, this element is omitted.
     466 * The tile height. If the Map Definition doesn't link to a Tile Set, this element is omitted.
     467
     468The new RuntimeMap XML schema is shown below
     469
     470{{{
     471<?xml version="1.0" encoding="UTF-8"?>
     472<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" elementFormDefault="qualified" attributeFormDefault="unqualified">
     473  <xs:element name="RuntimeMap">
     474    <xs:annotation>
     475      <xs:documentation>Describes information about a Runtime Map, so that client applications can interact with it</xs:documentation>
     476    </xs:annotation>
     477    <xs:complexType>
     478      <xs:sequence>
     479        <xs:element name="SiteVersion" type="xs:string">
     480          <xs:annotation>
     481            <xs:documentation>The MapGuide Site Version</xs:documentation>
     482          </xs:annotation>
     483        </xs:element>
     484        <xs:element name="Name" type="xs:string">
     485          <xs:annotation>
     486            <xs:documentation>The name of the runtime map. This is the value required for any mapagent operation that require a MAPNAME parameter</xs:documentation>
     487          </xs:annotation>
     488        </xs:element>
     489        <xs:element name="MapDefinition" type="xs:string">
     490          <xs:annotation>
     491            <xs:documentation>The resource id of the Map Definition from which this runtime map was created from</xs:documentation>
     492          </xs:annotation>
     493        </xs:element>
     494        <xs:element name="TileSetDefinition" type="xs:string" minOccurs="0">
     495          <xs:annotation>
     496            <xs:documentation>The resource id of the Tile Set Definition that this Map Definition is linked from. If this Map Definition does not link to a tile set, this element is omitted</xs:documentation>
     497          </xs:annotation>
     498        </xs:element>
     499        <xs:element name="TileWidth" type="xs:string" minOccurs="0">
     500          <xs:annotation>
     501            <xs:documentation>The tile width as defined by the settings in the Tile Set Definition. If this Map Definition does not link to a tile set, this element is omitted</xs:documentation>
     502          </xs:annotation>
     503        </xs:element>
     504        <xs:element name="TileHeight" type="xs:string" minOccurs="0">
     505          <xs:annotation>
     506            <xs:documentation>The tile height as defined by the settings in the Tile Set Definition. If this Map Definition does not link to a tile set, this element is omitted</xs:documentation>
     507          </xs:annotation>
     508        </xs:element>
     509        <xs:element name="BackgroundColor" type="xs:string">
     510          <xs:annotation>
     511            <xs:documentation>The map's background color in ARGB hex string format</xs:documentation>
     512          </xs:annotation>
     513        </xs:element>
     514        <xs:element name="DisplayDpi" type="xs:integer">
     515          <xs:annotation>
     516            <xs:documentation>The number of dots per inch of the map display</xs:documentation>
     517          </xs:annotation>
     518        </xs:element>
     519        <xs:element name="IconMimeType" type="xs:string" minOccurs="0">
     520          <xs:annotation>
     521            <xs:documentation>The mime type of all inline icons</xs:documentation>
     522          </xs:annotation>
     523        </xs:element>
     524        <xs:element name="CoordinateSystem" type="CoordinateSystemType" />
     525        <xs:element name="Extents" type="Envelope" />
     526        <xs:element name="Group" type="RuntimeMapGroup" minOccurs="0" maxOccurs="unbounded" />
     527        <xs:element name="Layer" type="RuntimeMapLayer" minOccurs="0" maxOccurs="unbounded" />
     528        <xs:element name="FiniteDisplayScale" type="xs:double" minOccurs="0" maxOccurs="unbounded" />
     529        <xs:attribute name="version" type="xs:string" use="required" fixed="3.0.0"/>
     530      </xs:sequence>
     531    </xs:complexType>
     532  </xs:element>
     533  <xs:complexType name="CoordinateSystemType">
     534    <xs:annotation>
     535      <xs:documentation>Describes the coordinate system of the runtime map</xs:documentation>
     536    </xs:annotation>
     537    <xs:sequence>
     538      <xs:element name="Wkt" type="xs:string">
     539        <xs:annotation>
     540          <xs:documentation>The WKT string of the coordinate system</xs:documentation>
     541        </xs:annotation>
     542      </xs:element>
     543      <xs:element name="MentorCode" type="xs:string">
     544        <xs:annotation>
     545          <xs:documentation>The CS-Map code of the coordinate system</xs:documentation>
     546        </xs:annotation>
     547      </xs:element>
     548      <xs:element name="EpsgCode" type="xs:string">
     549        <xs:annotation>
     550          <xs:documentation>The EPSG code of the coordinate system</xs:documentation>
     551        </xs:annotation>
     552      </xs:element>
     553      <xs:element name="MetersPerUnit" type="xs:double">
     554        <xs:annotation>
     555          <xs:documentation>The meters-per-unit value of the coordinate system</xs:documentation>
     556        </xs:annotation>
     557      </xs:element>
     558    </xs:sequence>
     559  </xs:complexType>
     560  <xs:complexType name="RuntimeMapGroup">
     561    <xs:annotation>
     562      <xs:documentation>Describes a group of Runtime Map Layers</xs:documentation>
     563    </xs:annotation>
     564    <xs:sequence>
     565      <xs:element name="Name" type="xs:string">
     566        <xs:annotation>
     567          <xs:documentation>The name of the group</xs:documentation>
     568        </xs:annotation>
     569      </xs:element>
     570      <xs:element name="Type" type="xs:integer">
     571        <xs:annotation>
     572          <xs:documentation>The type of this group. Can be tiled or dynamic. Uses the value of MgLayerGroupType</xs:documentation>
     573        </xs:annotation>
     574      </xs:element>
     575      <xs:element name="LegendLabel" type="xs:string">
     576        <xs:annotation>
     577          <xs:documentation>The group's legend label</xs:documentation>
     578        </xs:annotation>
     579      </xs:element>
     580      <xs:element name="ObjectId" type="xs:string">
     581        <xs:annotation>
     582          <xs:documentation>The group's unique id. Use this value for turning on/off this group in a GETDYNAMICMAPOVERLAYIMAGE request</xs:documentation>
     583        </xs:annotation>
     584      </xs:element>
     585      <xs:element name="ParentId" type="xs:string" minOccurs="0">
     586        <xs:annotation>
     587          <xs:documentation>The group's parent group id. Use this value for determining parent-child relationships when building a layer/group hierarchy</xs:documentation>
     588        </xs:annotation>
     589      </xs:element>
     590      <xs:element name="DisplayInLegend" type="xs:boolean">
     591        <xs:annotation>
     592          <xs:documentation>Indicates whether this group should be displayed in the legend</xs:documentation>
     593        </xs:annotation>
     594      </xs:element>
     595      <xs:element name="ExpandInLegend" type="xs:boolean">
     596        <xs:annotation>
     597          <xs:documentation>Indicates whether this group should be initially expanded in the legend</xs:documentation>
     598        </xs:annotation>
     599      </xs:element>
     600      <xs:element name="Visible" type="xs:boolean">
     601        <xs:annotation>
     602          <xs:documentation>Indicates whether this group is potentially visible. Note that this may be true even though the group is not visible. This will occur if one of the groups this group is organized within is not visible.</xs:documentation>
     603        </xs:annotation>
     604      </xs:element>
     605      <xs:element name="ActuallyVisible" type="xs:boolean">
     606        <xs:annotation>
     607          <xs:documentation>Indicates the actual visibility of the group. The visibility depends on the visible property of the group, and the visible property of each group this group is organized within.</xs:documentation>
     608        </xs:annotation>
     609      </xs:element>
     610    </xs:sequence>
     611  </xs:complexType>
     612  <xs:complexType name="RuntimeMapLayer">
     613    <xs:annotation>
     614      <xs:documentation>Describes a runtime instance of a Layer Definition</xs:documentation>
     615    </xs:annotation>
     616    <xs:sequence>
     617      <xs:element name="Name" type="xs:string">
     618        <xs:annotation>
     619          <xs:documentation>The name of the layer</xs:documentation>
     620        </xs:annotation>
     621      </xs:element>
     622      <xs:element name="Type" type="xs:integer">
     623        <xs:annotation>
     624          <xs:documentation>The type of this layer. Can be tiled or dynamic. Uses the value of MgLayerType</xs:documentation>
     625        </xs:annotation>
     626      </xs:element>
     627      <xs:element name="LegendLabel" type="xs:string">
     628        <xs:annotation>
     629          <xs:documentation>The layer's legend label</xs:documentation>
     630        </xs:annotation>
     631      </xs:element>
     632      <xs:element name="ObjectId" type="xs:string">
     633        <xs:annotation>
     634          <xs:documentation>The layer's unique id. Use this value for turning on/off this layer in a GETDYNAMICMAPOVERLAYIMAGE request</xs:documentation>
     635        </xs:annotation>
     636      </xs:element>
     637      <xs:element name="ParentId" type="xs:string" minOccurs="0">
     638        <xs:annotation>
     639          <xs:documentation>The layer's parent group id. Use this value for determining parent-child relationships when building a layer/group hierarchy</xs:documentation>
     640        </xs:annotation>
     641      </xs:element>
     642      <xs:element name="DisplayInLegend" type="xs:boolean">
     643        <xs:annotation>
     644          <xs:documentation>Indicates whether this layer should be displayed in the legend</xs:documentation>
     645        </xs:annotation>
     646      </xs:element>
     647      <xs:element name="ExpandInLegend" type="xs:boolean">
     648        <xs:annotation>
     649          <xs:documentation>Indicates whether this layer should be initially expanded (if layer is themed) in the legend</xs:documentation>
     650        </xs:annotation>
     651      </xs:element>
     652      <xs:element name="Visible" type="xs:boolean">
     653        <xs:annotation>
     654          <xs:documentation>Indicates whether this layer is potentially visible. Note that this may be true even though the layer is not visible. This will occur if the visible flag of one of the groups this layer is organized within is not visible or when the current viewScale property of the map is outside the scale ranges defined for this layer.</xs:documentation>
     655        </xs:annotation>
     656      </xs:element>
     657      <xs:element name="ActuallyVisible" type="xs:boolean">
     658        <xs:annotation>
     659          <xs:documentation>Indicates the actual visibility of the layer. The visibility depends on the visible property of the group, and the visible property of each group this group is organized within.</xs:documentation>
     660        </xs:annotation>
     661      </xs:element>
     662      <xs:element name="LayerDefinition" type="xs:string">
     663        <xs:annotation>
     664          <xs:documentation>The Layer Definition from which this runtime layer was created from</xs:documentation>
     665        </xs:annotation>
     666      </xs:element>
     667      <xs:element name="FeatureSource" type="FeatureSourceInfo" minOccurs="0" />
     668      <xs:element name="ScaleRange" type="ScaleRangeInfo" minOccurs="0" maxOccurs="unbounded" />
     669    </xs:sequence>
     670  </xs:complexType>
     671  <xs:complexType name="FeatureSourceInfo">
     672    <xs:annotation>
     673      <xs:documentation>Describe the Feature Source information for a runtime layer</xs:documentation>
     674    </xs:annotation>
     675    <xs:sequence>
     676      <xs:element name="ResourceId" type="xs:string">
     677        <xs:annotation>
     678          <xs:documentation>The Feature Source resource id</xs:documentation>
     679        </xs:annotation>
     680      </xs:element>
     681      <xs:element name="ClassName" type="xs:string">
     682        <xs:annotation>
     683          <xs:documentation>The qualified FDO class name</xs:documentation>
     684        </xs:annotation>
     685      </xs:element>
     686      <xs:element name="Geometry" type="xs:string">
     687        <xs:annotation>
     688          <xs:documentation>The name of the default Geometry property</xs:documentation>
     689        </xs:annotation>
     690      </xs:element>
     691    </xs:sequence>
     692  </xs:complexType>
     693  <xs:complexType name="ScaleRangeInfo">
     694    <xs:annotation>
     695      <xs:documentation>Describes a scale range of the runtime layer</xs:documentation>
     696    </xs:annotation>
     697    <xs:sequence>
     698      <xs:element name="MinScale" type="xs:double">
     699        <xs:annotation>
     700          <xs:documentation>The minimum scale of this scale range</xs:documentation>
     701        </xs:annotation>
     702      </xs:element>
     703      <xs:element name="MaxScale" type="xs:double">
     704        <xs:annotation>
     705          <xs:documentation>The maximum scale of this scale range</xs:documentation>
     706        </xs:annotation>
     707      </xs:element>
     708      <xs:element name="FeatureStyle" type="FeatureStyleInfo" minOccurs="0" maxOccurs="unbounded">
     709        <xs:annotation>
     710          <xs:documentation>The feature style for a given geometry type.</xs:documentation>
     711        </xs:annotation>
     712      </xs:element>
     713    </xs:sequence>
     714  </xs:complexType>
     715  <xs:complexType name="FeatureStyleInfo">
     716    <xs:annotation>
     717      <xs:documentation>Defines the style rules for a given geometry type</xs:documentation>
     718    </xs:annotation>
     719    <xs:sequence>
     720      <xs:element name="Type" type="xs:integer">
     721        <xs:annotation>
     722          <xs:documentation>The geometry type that this rule is applicable to (1=point, 2=line, 3=area, 4=composite)</xs:documentation>
     723        </xs:annotation>
     724      </xs:element>
     725      <xs:element name="Rule" type="RuleInfo" minOccurs="0" maxOccurs="unbounded" />
     726    </xs:sequence>
     727  </xs:complexType>
     728  <xs:complexType name="RuleInfo">
     729    <xs:annotation>
     730      <xs:documentation>Describes a stylization rule in a layer's scale range</xs:documentation>
     731    </xs:annotation>
     732    <xs:sequence>
     733      <xs:element name="LegendLabel" type="xs:string">
     734        <xs:annotation>
     735          <xs:documentation>The legend label for this rule</xs:documentation>
     736        </xs:annotation>
     737      </xs:element>
     738      <xs:element name="Filter" type="xs:string">
     739        <xs:annotation>
     740          <xs:documentation>The FDO filter that features must match in order for them to be stylized using this particular rule</xs:documentation>
     741        </xs:annotation>
     742      </xs:element>
     743      <xs:element name="Icon" type="xs:string" minOccurs="0">
     744        <xs:annotation>
     745          <xs:documentation>Defines the icon for this rule. The icon's image content is in base64 format</xs:documentation>
     746        </xs:annotation>
     747      </xs:element>
     748    </xs:sequence>
     749  </xs:complexType>
     750  <xs:complexType name="Envelope">
     751    <xs:annotation>
     752      <xs:documentation>Specifies an envelope (a rectangle) using two corner points.</xs:documentation>
     753    </xs:annotation>
     754    <xs:sequence>
     755      <xs:element name="LowerLeftCoordinate">
     756        <xs:annotation>
     757          <xs:documentation>Specifies the lower left corner of the envelope.</xs:documentation>
     758        </xs:annotation>
     759        <xs:complexType>
     760          <xs:sequence>
     761            <xs:element name="X" type="xs:string"/>
     762            <xs:element name="Y" type="xs:string"/>
     763          </xs:sequence>
     764        </xs:complexType>
     765      </xs:element>
     766      <xs:element name="UpperRightCoordinate">
     767        <xs:annotation>
     768          <xs:documentation>Specifies the upper right corner of the envelope.</xs:documentation>
     769        </xs:annotation>
     770        <xs:complexType>
     771          <xs:sequence>
     772            <xs:element name="X" type="xs:string"/>
     773            <xs:element name="Y" type="xs:string"/>
     774          </xs:sequence>
     775        </xs:complexType>
     776      </xs:element>
     777    </xs:sequence>
     778  </xs:complexType>
     779</xs:schema>
     780}}}
     781
     782The CREATERUNTIMEMAP/DESCRIBERUNTIMEMAP operations can now return either the v2.6 response (for compatibility) or the v3.0 response based on the operation version supplied. Fusion will use the 3.0.0 operation version by default. Other client applications are recommended to use this new version.
     783
     784=== Tile Providers ===
     785
     786Tile sets are currently managed by MapGuide using globally defined settings in serverconfig.ini. Introducing the concept of Tile Providers allows us to abstract out rendering and tile access specifics to different Tile Providers. An easy way to think about this is FDO for tile access, storage and management with the Tile Set Definition akin to a "Feature Source" for a tile set.
     787
     788For this RFC, we will introduce 2 Tile Providers that can be used by Tile Set Definitions:
     789
     790 * Default
     791 * XYZ
     792
     793The "Default" provider implements the existing tile rendering and access mechanism. The following parameters can be specified to a "Default" tile provider:
     794
     795 * TilePath - Defines where rendered tiles will be cached. This can be any path of your choice or %MG_TILE_CACHE_PATH% to use the MapGuide-designated tile cache path.
     796 * TileWidth - Defines the width of tiles that are rendered. Default value is 300.
     797 * TileHeight - Defines the height of tiles that are rendered. Default value is 300.
     798 * TileFormat - Defines the image format of rendered tiles. Default value is PNG.
     799 * RenderOnly - Defines whether tiles rendered for this tile set will be cached or not. Default value is false.
     800 * CoordinateSystem - Defines the coordinate system of this tile set. Any layers in this tile set will be re-projected to this coordinate system when rendering if their coordinate system is not the same.
     801 * FiniteScaleList - Defines the discrete set of zoom levels for this tile set.
     802
     803The "XYZ" provider implements tile rendering and access using the XYZ tiling scheme. Coordinate System is always LL84 and size of rendered tiles are locked at 256x256 pixels. See XYZ support below for more information. "XYZ" provider also uses a simplified directory structure for storing tiles `<basepath>/<group>/<z>/<x>/<y>.<format>` allowing for easy and intuitive external access if the tile cache was exposed by a web server. The following parameters can be specified to a "XYZ" tile provider:
     804
     805 * TilePath - Defines where rendered tiles will be cached. This can be any path of your choice or %MG_TILE_CACHE_PATH% to use the MapGuide-designated tile cache path.
     806 * TileFormat - Defines the image format of rendered tiles. Default value is PNG.
     807 * RenderOnly - Defines whether tiles rendered for this tile set will be cached or not. Default value is false.
     808
     809Tile access is the same for both Default and XYZ tile providers. For XYZ, the terminology for tile access is as follows:
     810 * X = row
     811 * Y = column
     812 * Z = scale index
     813
     814A new GetTileProviders API is added to MgTileService to return this information:
     815
     816{{{
     817class MG_MAPGUIDE_API MgTileService : public MgService
     818{
     819PUBLISHED_API:
     820    //////////////////////////////////////////////////////////////////
     821    /// \brief
     822    /// Returns the list of available tile providers, along with supported connection parameters
     823    ///
     824    /// \since 3.0
     825    virtual MgByteReader* GetTileProviders() = 0;
     826};
     827}}}
     828
     829The response is similar to the GetFeatureProvider API in MgFeatureService, providing enough information for client applications like Maestro or Studio to build rich editor user interfaces around. The current response looks like this:
     830
     831{{{
     832<?xml version="1.0" encoding="UTF-8"?>
     833<TileProviderList>
     834  <TileProvider>
     835    <Name>Default</Name>
     836    <DisplayName>Default Tile Provider</DisplayName>
     837    <Description>Default tile access provided by MapGuide. Supports MapGuide-managed tile path or user-defined path</Description>
     838    <ConnectionProperties>
     839      <ConnectionProperty Enumerable="false" Protected="false" Required="true">
     840        <Name>TilePath</Name>
     841        <LocalizedName>Tile Path</LocalizedName>
     842        <DefaultValue>%MG_TILE_CACHE_PATH%</DefaultValue>
     843      </ConnectionProperty>
     844      <ConnectionProperty Enumerable="false" Protected="false" Required="true">
     845        <Name>TileWidth</Name>
     846        <LocalizedName>Tile Width</LocalizedName>
     847        <DefaultValue>300</DefaultValue>
     848      </ConnectionProperty>
     849      <ConnectionProperty Enumerable="false" Protected="false" Required="true">
     850        <Name>TileHeight</Name>
     851        <LocalizedName>Tile Height</LocalizedName>
     852        <DefaultValue>300</DefaultValue>
     853      </ConnectionProperty>
     854      <ConnectionProperty Enumerable="true" Protected="false" Required="true">
     855        <Name>TileFormat</Name>
     856        <LocalizedName>Tile Format</LocalizedName>
     857        <DefaultValue>PNG</DefaultValue>
     858        <Value>PNG</Value>
     859        <Value>PNG8</Value>
     860        <Value>JPG</Value>
     861        <Value>GIF</Value>
     862      </ConnectionProperty>
     863      <ConnectionProperty Enumerable="false" Protected="false" Required="false">
     864        <Name>RenderOnly</Name>
     865        <LocalizedName>Render Tiles Only (do not cache)</LocalizedName>
     866        <DefaultValue>false</DefaultValue>
     867      </ConnectionProperty>
     868      <ConnectionProperty Enumerable="false" Protected="false" Required="true">
     869        <Name>CoordinateSystem</Name>
     870        <LocalizedName>Coordinate System</LocalizedName>
     871        <DefaultValue/>
     872      </ConnectionProperty>
     873      <ConnectionProperty Enumerable="false" Protected="false" Required="true">
     874        <Name>FiniteScaleList</Name>
     875        <LocalizedName>Finite Display Scale List</LocalizedName>
     876        <DefaultValue/>
     877      </ConnectionProperty>
     878    </ConnectionProperties>
     879  </TileProvider>
     880  <TileProvider>
     881    <Name>XYZ</Name>
     882    <DisplayName>XYZ Tile Provider</DisplayName>
     883    <Description>XYZ tile access provided by MapGuide. Grid scheme is compatible with Google Maps and Open Street Map. Rendered tiles are 256x256. Layers must be convertible from lat/lon coordinates. Under this scheme, Row = X, Column = Y, Scale = Z for accessing tiles. Supports MapGuide-managed tile path or user-defined path</Description>
     884    <ConnectionProperties>
     885      <ConnectionProperty Enumerable="false" Protected="false" Required="true">
     886        <Name>TilePath</Name>
     887        <LocalizedName>Tile Path</LocalizedName>
     888        <DefaultValue>%MG_TILE_CACHE_PATH%</DefaultValue>
     889      </ConnectionProperty>
     890      <ConnectionProperty Enumerable="true" Protected="false" Required="true">
     891        <Name>TileFormat</Name>
     892        <LocalizedName>Tile Format</LocalizedName>
     893        <DefaultValue>PNG</DefaultValue>
     894        <Value>PNG</Value>
     895        <Value>PNG8</Value>
     896        <Value>JPG</Value>
     897        <Value>GIF</Value>
     898      </ConnectionProperty>
     899      <ConnectionProperty Enumerable="false" Protected="false" Required="false">
     900        <Name>RenderOnly</Name>
     901        <LocalizedName>Render Tiles Only (do not cache)</LocalizedName>
     902        <DefaultValue>false</DefaultValue>
     903      </ConnectionProperty>
     904    </ConnectionProperties>
     905  </TileProvider>
     906</TileProviderList>
     907}}}
     908
     909These tile providers are implemented inside the server implementation of the Tile Service and new initialization logic in MgMap is currently hard-coded against these two providers. There is no scope in this RFC to define a formal plugin API where external Tile Providers can be defined and registered.
     910
     911=== XYZ support ===
     912
     913XYZ is a tiling scheme used by Google Maps and OpenStreetMap among others that is notable for its ease of consumption by external 3rd party clients with easy to understand rules and methods for determining the values of X,Y and Z to retrieve tiles at any given map viewport.
     914
     915Adding XYZ tile set support to MapGuide increases the accessibility of tiled maps to external 3rd party clients that can access map tiles without needing to know information about the Map Definition itself (eg. meters-per-unit, coordinate system, tile size) in order to know what row/col/scale to issue with GETTILE requests.
     916
     917The existing RenderTile API is not suitable for rendering XYZ tiles. We will introduce a new API to MgRenderingService for this purpose.
     918
     919{{{
     920class MG_MAPGUIDE_API MgRenderingService : public MgService
     921{
     922PUBLISHED_API:
     923    /////////////////////////////////////////////////////////////////
     924    /// \brief
     925    /// Returns the specified map tile for the given map. Tile structure is
     926    /// based on the XYZ tiling scheme used by Google Maps, OpenStreetMap, and
     927    /// others
     928    ///
     929    /// \param map
     930    /// Input
     931    /// map object containing current state of map.
     932    /// \param baseMapLayerGroupName
     933    /// Input
     934    /// Specifies the name of the baseMapLayerGroup for which to render the tile.
     935    /// \param x
     936    /// Input
     937    /// Specifies the row index of the tile to return.
     938    /// \param y
     939    /// Input
     940    /// Specifies the column index of the tile to return.
     941    /// \param z
     942    /// Input
     943    /// Specifies the zoom level of the tile to return.
     944    ///
     945    /// \return
     946    /// A byte reader containing the rendered tile image.
     947    ///
     948    virtual MgByteReader* RenderTileXYZ(
     949        MgMap* map,
     950        CREFSTRING baseMapLayerGroupName,
     951        INT32 x,
     952        INT32 y,
     953        INT32 z) = 0;
     954};
     955}}}
     956
     957Based on the given x, y and z values, [http://wiki.openstreetmap.org/wiki/Slippy_map_tilenames we use defined mathematical forumlae] to convert this to a lat/lon bounding box. If the coordinate system of the tile set is already lat/lon, the map tile will be rendered for these bounds. Otherwise the bounds will be transformed to the tile set's coordinate system before doing the rendering.
     958
     959Tile Set Definitions using the XYZ provider will be using this API for the actual tile rendering.
     960
     961=== APIs to support tile sets ===
     962
     963As mentioned above, the raw tile access primitive of GetTile in MgTileService and the v1.2 GETTILE mapagent request requires no modification. The existing method signature satisfies our requirements for tile access via Tile Set Definitions. The API documentation only needs to be updated to specify that the MgResourceIdentifier can now be a Map Definition or a Tile Set Definition.
     964
     965Other APIs in MgTileService will need new overloads to work with tile sets:
     966
     967{{{
     968class MG_MAPGUIDE_API MgTileService : public MgService
     969{
     970PUBLISHED_API:
     971    //////////////////////////////////////////////////////////////////
     972    /// \brief
     973    /// Clears the entire tile cache for the given tile set.  Tiles for all base
     974    /// map layer groups and finite scales will be removed.
     975    ///
     976    /// \param map
     977    /// Input
     978    /// Specifies the map whose tile cache will be cleared.
     979    ///
     980    /// \since 3.0
     981    virtual void ClearCache(MgResourceIdentifier* tileSet) = 0;
     982   
     983    //////////////////////////////////////////////////////////////////
     984    /// \brief
     985    /// Returns the default width of a tile.
     986    ///
     987    /// \param tileSet
     988    /// Input
     989    /// Specifies the resource id of the tile set
     990    ///
     991    /// \return
     992    /// Default width of a tile in pixels.
     993    ///
     994    /// \since 3.0
     995    virtual INT32 GetDefaultTileSizeX(MgResourceIdentifier* tileSet) = 0;
     996
     997    //////////////////////////////////////////////////////////////////
     998    /// \brief
     999    /// Returns the default height of a tile.
     1000    ///
     1001    /// \param tileSet
     1002    /// Input
     1003    /// Specifies the resource id of the tile set
     1004    ///
     1005    /// \return
     1006    /// Default height of a tile in pixels.
     1007    ///
     1008    /// \since 3.0
     1009    virtual INT32 GetDefaultTileSizeY(MgResourceIdentifier* tileSet) = 0;
     1010};
     1011}}}
     1012
     1013== Implications ==
     1014
     1015Existing tiled Map Definitions and tile access methods will behave as before using globally defined settings in serverconfig.ini.
     1016
     1017An important thing to note as well is that invoking GETTILE on a Map Definition that is linked to a tile set *will not* use the settings defined in that tile set. This is because the server-side does not properly handle the case of a Map Definition that links to a tile set. Any Map Definition resource id is automatically delegated to the existing tile rendering and management code path. A solution does exist to address this, but it appears to be too complex to feasibly make it into this initial implementation. For the sake of simplicity, the API story of GETTILE is:
     1018
     1019 * If used with a Map Definition, serverconfig.ini settings will always be used regardless of whether the Map Definition links to a Tile Set or not.
     1020 * If used with a Tile Set Definition, settings from that resource will be used.
     1021
     1022Client applications have already been modified to handle this expectation.
     1023
     1024An important constraint of the XYZ tiling scheme is that XYZ resolves to lat/lon coordinates. Therefore any map you wish to make available as an XYZ tileset must be in a coordinate system that is either LL84 or transformable from LL84. Maps based on arbitrary coordinate systems cannot be served as XYZ tile sets.
     1025
     1026As mentioned above, the MgMap::Create() method now supports Tile Set Definitions. However for the public API, the method will only support Tile Set Definitions using the "Default" tile provider. The reason for this is that when creating a MgMap, it also needs to be initalized with the coordinate system and finite scale lists, and only Tile Set Definitions using the "Default" tile provider can provide this information. It is not possible to create a MgMap using a Tile Set Definition that uses the XYZ provider. Such attempts will throw a MgUnsupportedTileProviderException.
     1027
     1028For simplicity, much of the new MgMap initialization logic is hard-coded against the 2 tile providers introduced in this RFC. No formal "plugin" model exists for adding additional tile provider support. Defining a formal plugin API would be the scope of another RFC.
     1029
     1030Although a Tile Set Definition is sort of a Map Definition and a MgMap can be created from a Tile Set Definition in certain cases, the AJAX and Fusion viewers *will not* be modified to support Web/Flexible Layouts that reference Tile Set Definitions instead of Map Definitions. Authoring tools can and should maintain the constraint that a Web/Flexible Layout must reference a Map Definition.
     1031
     1032Tile Set Definitions will still be susceptible to shotgun cache invalidation when an upstream resource is saved. No mechanism exists in this RFC to prevent this from happening. But since such information is now separated out into a separate resource, it can pave the way for future API work where tile sets can be locked/unlocked to prevent/allow edits of upstream dependent resources.
     1033
     1034== Test Plan ==
     1035
     1036Add new MdfModel tests to exercise the new TileSetDefinition schema and ensure all elements are properly read in from sample documents.
     1037
     1038Add new tile service tests to exercise MgMap creation from Tile Set Definitions and linked Map Definitions and GetTile to TileSetDefinition resources in a multi-threaded fashion.
     1039
     1040== Funding / Resources ==
     1041
     1042Community