On Aug 27, 2010, at 07:52 , Slawomir Messner wrote:
1. Is this the recommended way to work with styles or is there a better
way? Is there maybe already a tool?
You have several options, as styling has evolved in OpenLayers 2.0. For the
recommended way of client-side styling in OpenLayers, please refer to
http://trac.openlayers.org/wiki/Styles. This is all about rule based styling.
If you want to use a tool, you can go through SLD (see
http://openlayers.org/dev/examples/sld.html) and use an SLD editor. There you
have several options - I only list some that I know to be useful:
* Web-based: OpenGeo Suite Styler (http://opengeo.org/products/suite/)
* Desktop GIS: UDig (http://udig.refractions.net/)
* If you are familiar with CSS, you can try GeoServer CSS
(http://dwins.wordpress.com/2010/07/25/geoserver-css-conversion/)
Jep, we could put any value in
attributes or feature.sytle but sometimes there are more then 2000
features so we want to have as few styles as possible.
With that many features, you should not even consider rendering them at the
client. Instead, use a WMS (e.g. GeoServer or MapServer). But what I said above
about SLD is also valid here - SLD is the way to go with GeoServer. For
MapServer, the primary way to define styles is through the mapfile, which some
people prefer over SLD.
Are rule maybe
better even if harder to parse?
The functions described below are working already, but not always
together, the workflow below will be the new one and before I change
"all" our controls and loading mechanism from every source... I would
like to have some opinions.
This is because you should not mix rule based styling (i.e. layers with a
styleMap) with symbolizer based styling (i.e. features with a style).
2. The docs telling you at OL.Feature.Vector under
OpenLayers.Feature.Vector.style "OpenLayers features can have a number
of style attributes..." but it's the layer, right?
Both is true. In the old way of styling, symbolizers defined on a feature (as
style property) take precedence over the ones defined on the layer (also as
style property).
I see my style only
if I set OpenLayers.Feature.Vector.style like {'pointRadius':6,
fillColor:'#FF0000'} not OL.StyleMap({'default': {'pointRadius':6,
fillColor:'#FF0000'}, 'select': {'pointRadius':6, fillColor:'#0000FF'}
}) or {'default': {'pointRadius':6, fillColor:'#FF0000'}, 'select':
{'pointRadius':6, fillColor:'#0000FF'} }.
The OpenLayers.Style object cannot be used with features, it is part of the
rule based styling framework. Only symbolizers are supported. So what you
describe here is expected.
3. StyleMap, Style and Object are the classes you have to work with.
For rule based styling (the new way), you work with StyleMap and Style. For
symbolizer based styling (the old way) you work with symbolizer objects.
Sometimes it's ok to write attributes it into style directly and in some
cases it's better to use style.styles["default"].defaultStyle.
style.styles["default"].defaultStyle is not part of the API, so you should
never be working with that in an application. What you are referring to here is just the
base style on which rules will be applied to.
Are there
some plans to change styling or limit the way to style to make it more
clearly for OL 3.0?
As I said, vector styling went through a long evolution in OpenLayers 2.x, and
there are plans to give it an overhaul in 3.0. What exactly it will look like
is not clear yet, but the aim is to make it simpler. My prediction is that rule
based styling will be closer to SLD/CSS, and styling features individually will
also be possible (for the sake of KML support).
Something like: Every stlye attribute is a stylemap
and when it doesn't have the style you want look in it's "container"
(control)->feature->layer(or should it be feature->(control)>layer).
This is exactly what you do with the StyleMap: On the layer, you have a
StyleMap which contains Style instances for all renderIntents (default, select,
temporary etc.). If you want to style a feature individually, you create a rule
with a FeatureId filter for the desired renderIntent. A control is configured
with a renderIntent, which it will use when drawing features.
Step 1. Let's say we have some named places in a vector layer some
chosen geometries form our data. When we load them we use the common way
to style them with StyleMap in the layer also the labels, the text is
stored in an attribute so we use ${attribName}.
Step 2. Now we want to edit the style of one feature so we have to use
the style attribute of OL.Feature.Vector, right? Because we want to
change only some attributes the layer style and not to create a new
style than we have to copy the layer (default) style into the features
style attribute before editing:
feature.style =
OpenLayers.Util.extend({},layer.style.styles["default"].defaultStyle);
Nope. If you wanted to get the style that the feature is currently rendered
with, you would do
layer.styleMap.createSymbolizer(feature, "default");
But we do not want to do that here. Let's say you want to change the fillColor
of the feature, then you would create a symbolizer with it:
var symbolizer = {fillColor: "#FF32CC"};
Now you add a rule with a FeatureId filter to the Style for the "default"
renderIntent:
layer.styleMap.styles["default"].addRules([new OpenLayers.Rule({
filter: new OpenLayers.Filter.FeatureId({fids: [feature.id]}),
symbolizer: symbolizer
})]);
If your features have a fid (e.g. because they came from a GML format), you should replace
"feature.id" above with "feature.fid".
Step 2b. Because some attributes are calculated from attributes so the
attributes of feature.style are replaced by the values if there is
something like this ${attribName}. Nearly all style attributes should be
editable labels, graphics, strokes, fill, radius...
If you create a FeatureId filter like above, you still can do that by using
${whatever} in the symbolizer.
But now we lost the ability to mark this feature as selected, it doesn't
work by the select style of the layer.
If you do like described above, selecting by rendering the feature with a
"select" intent will still work, because you did not set a style property on
the feature.
Expect we define a selectStyle in
the SelectFeature control, but this style would be same for every
feature so i.e. we cannot keep the different labels.
No need to use a selectStyle in the above scenario.
Step 3. Editing of attributes or moving features. For editing style it's
not so important to have a select style but when you use the layer with
other controls, like an attribute editor. What would we do if a user
changes in a feature with edited style the attribute for the label? We
have to read it again and put it into feature.style like in 2b.
Not with the above scenario, unless you allowed the user to hard-code a new
label by setting a label property in the symbolizer.
Step 4. Adding new features.
A user expects that he can do Step 2,3 and 4 not in the row and multiple
times.
Still no problem. Add new rules with featureId filters with only the
symbolizers properties that the user has edited.
Step 5. Now the user should be able to save the resulting map with style
and attributes. so for every edited feature we have to save the style
attribute for the others the layer.style.styles["default"].defaultStyle
or mark them as "layerStyled" and save the default Style to reuse it as
layer style the next time a user loads his layer.
Nope. Just use Format.SLD to write an SLD. And the good thing is: this will
also work if your features were never rendered on the client, but by your WMS.
I'm looking forward for your critics, tipps and other helping things.
I think there were many in my post.
Regards,
Andreas.
I'm open for questions and so on.
Thx and Regards,
Slawomir
--
-----------------------------------------------
Slawomir Messner
Forschungszentrum "Deutscher Sprachatlas"
_______________________________________________
Users mailing list
[email protected]
http://openlayers.org/mailman/listinfo/users