The features which are either incompatible or potentially problematic with multi-layer are:
The dataset ID is specified on the layer, which is good, but it is also specified on the top-level visualisation. This is mainly to make map visualisations work via the same code paths as other visualisation types, which all currently have a single datasetID which is specified on the same level. When a map can have more than one layer from more than one dataset, this really doesn't make sense any more.
The filters are specified on the layer level, which is good. But two layers might be made from the same dataset, and in that case we should think about how the filters will be applied on the backend, and what we expect to happen. My initial thoughts are that the user will not expect the filters defined on one layer to affect the data used to display a different layer, even if both layers are derived from the same dataset.
The legend is specified on the layer level. We should think about how multiple legends will be represented. If we want to have a single legend for the whole map, regardless of how many layers it has, one idea would be to retain the "legend" object for each layer, but move the "position" property to a new "legend" object that lives on the spec level. The idea would be that a legend has "sections" where each section is represented on the layer level, but anything applying to the legend container, like the position (and perhaps a title) would be represented directly on the spec.
How to uniquely identify layers. An intuitive option is to use the array index. I think this makes sense because layer order is important as it will determine stacking (z-index) and we will likely have to allow users to change the order of layers in the editor. We should think about if we need an immutable id for layers, or if the array index is enough.
We don't currently have types for layers. It might make sense to add them, as many options (e.g "pointSize") are specific to a layer type. We could begin with at least geopoint and geoshape (or whatever we decide the appropriate terms are).
For the new geoshape layer type, we will need some way to store i) the column used to colour a shape (similar to the pointColorColumn for geopoint layers, ii) the aggregation method (e.g. "mean", "max", "median" etc) and iii) the base colour value used to generate the spectrum of shades that will be applied to the shapes. As a very simple example, the shapeColorColumn might be c5, the shapeColorMethod might be mean and the shapeBaseColor might be #FF0000. If we imagine that column c5 measures fluoride levels, then the system would calculate the mean value of c5 for the geoshape, and then use that value to modify the shapeBaseColor to generate the display color for that geoshape. If the shapeBaseColor is #FF0000 then the generated display color might be #FFBBBB (or something else, depending on what formula we agree to generate display colors from the base color)
That being said, a "new" multilayer map spec might look like:
Context
Currently maps only support a single layer, and the visualisation spec for maps reflects this.
As we begin working on multi-layer support in the client and the backend, we first need to agree how multi-layer maps are represented.
Let's start with an example single-layer map spec (made from a mock dataset):
The features which are either incompatible or potentially problematic with multi-layer are:
The dataset ID is specified on the layer, which is good, but it is also specified on the top-level visualisation. This is mainly to make map visualisations work via the same code paths as other visualisation types, which all currently have a single datasetID which is specified on the same level. When a map can have more than one layer from more than one dataset, this really doesn't make sense any more.
The filters are specified on the layer level, which is good. But two layers might be made from the same dataset, and in that case we should think about how the filters will be applied on the backend, and what we expect to happen. My initial thoughts are that the user will not expect the filters defined on one layer to affect the data used to display a different layer, even if both layers are derived from the same dataset.
The legend is specified on the layer level. We should think about how multiple legends will be represented. If we want to have a single legend for the whole map, regardless of how many layers it has, one idea would be to retain the "legend" object for each layer, but move the "position" property to a new "legend" object that lives on the
spec
level. The idea would be that a legend has "sections" where each section is represented on the layer level, but anything applying to the legend container, like the position (and perhaps a title) would be represented directly on the spec.How to uniquely identify layers. An intuitive option is to use the array index. I think this makes sense because layer order is important as it will determine stacking (z-index) and we will likely have to allow users to change the order of layers in the editor. We should think about if we need an immutable id for layers, or if the array index is enough.
We don't currently have types for layers. It might make sense to add them, as many options (e.g "pointSize") are specific to a layer type. We could begin with at least
geopoint
andgeoshape
(or whatever we decide the appropriate terms are).For the new
geoshape
layer type, we will need some way to store i) the column used to colour a shape (similar to thepointColorColumn
for geopoint layers, ii) the aggregation method (e.g. "mean", "max", "median" etc) and iii) the base colour value used to generate the spectrum of shades that will be applied to the shapes. As a very simple example, theshapeColorColumn
might bec5
, theshapeColorMethod
might bemean
and theshapeBaseColor
might be#FF0000
. If we imagine that columnc5
measures fluoride levels, then the system would calculate the mean value ofc5
for the geoshape, and then use that value to modify theshapeBaseColor
to generate the display color for that geoshape. If theshapeBaseColor
is#FF0000
then the generated display color might be#FFBBBB
(or something else, depending on what formula we agree to generate display colors from the base color)That being said, a "new" multilayer map spec might look like:
In every instance where I've come up with a new name for something, it's just a first attempt and shouldn't be taken too seriously