Hi Andreas, Thanks for the feedback. I did strike a few issues with the TreeNodeUI not being an Ext.Component so your approach sounds like the way to go. I'll get back in touch once I have something working.
Cheers Adam On Mon, Aug 16, 2010 at 8:09 PM, Andreas Hocevar <[email protected]> wrote: > Hi, > > although your progress here is impressive, I think it would have been simpler > to add the VectorLegend as a component, after creating a generic tree node > that can render an Ext.Component (which the VectorLegend is). This is covered > by http://trac.geoext.org/ticket/139, and there is a working patch already. > My objection to this patch was that extending nodes with different mixins can > become complicated, so I proposed http://trac.geoext.org/ticket/185, which > also has a working patch, plus patches from others that show how node > additions can be created easily based on my patch. > > If you want to try this approach, I'll gladly assist. > > Regards, > Andreas. > > On Aug 16, 2010, at 01:44 , Adam Ratcliffe wrote: > >> Hi Andreas, >> >> I had sometime over the weekend to start looking into how to implement >> this. Below is my initial attempt, which while working, I'm not >> completely happy with. Maybe you or somebody on the else on the list >> can suggest some improvements? >> >> Some of the issues that I had were: >> >> - My class duplicates code from GeoExt.VectorLegend >> >> - I needed to override GeoExt.FeatureRenderer.onRender() so that the >> wrapper element that's created for the legend swatch is an inline >> element rather than a block-level element. It would be helpful if >> GeoExt.FeatureRenderer allowed the element type to be specified via >> the 'autoEl' config option like other ExtJS components. >> >> - I had issues with vertical alignment of the legend swatch relative >> to the node checkbox and label text. I was able to align these >> elements satisfactorily under FF and Safari using the styles below - I >> haven't tested in IE yet. >> >> Styles >> ---------- >> >> .x-tree-node-legend { >> height: 18px; >> } >> >> .x-tree-node-legend input { >> margin-left: 2px !important; >> vertical-align: top !important; >> } >> >> .x-tree-node-legend .x-tree-node-anchor span { >> vertical-align: top !important; >> } >> >> Script >> --------- >> >> GeoExt.tree.VectorLayerNodeUI = Ext.extend(GeoExt.tree.LayerNodeUI, { >> >> constructor: function(config) { >> GeoExt.tree.VectorLayerNodeUI.superclass.constructor.apply(this, >> arguments); >> >> if (!this.symbolType) { >> if (this.feature) { >> this.symbolType = this.symbolTypeFromFeature(this.feature); >> } else if (this.node.layer) { >> if (this.node.layer.geometryType) { >> this.symbolType = >> this.symbolTypeFromGeometry(this.node.layer.geometryType); >> } else if (this.node.layer.features.length > 0) { >> var feature = this.node.layer.features[0].clone(); >> feature.attributes = {}; >> this.feature = feature; >> this.symbolType = >> this.symbolTypeFromFeature(this.feature); >> } else { >> this.node.layer.events.on({ >> featuresadded: this.onFeaturesAdded, >> scope: this >> }); >> } >> } >> } >> >> this.setRules(); >> }, >> >> symbolTypeFromGeometry: function(geometry) { >> var symbolType = geometry.prototype.CLASS_NAME.split('.').pop(); >> return (symbolType == 'LineString') ? 'Line' : symbolType; >> }, >> >> symbolTypeFromFeature: function(feature) { >> var match = feature.geometry.CLASS_NAME.match(/Point|Line|Polygon/); >> return (match && match[0]) || "Point"; >> }, >> >> onFeaturesAdded: function() { >> this.node.layer.events.un({ >> featuresadded: this.onFeaturesAdded, >> scope: this >> }); >> var feature = this.node.layer.features[0].clone(); >> feature.attributes = {}; >> this.feature = feature; >> this.symbolType = this.symbolTypeFromFeature(this.feature); >> if (!this.rules) { >> this.setRules(); >> } >> this.update(); >> }, >> >> update: function() { >> if (this.symbolType && this.rules) { >> this.createRuleRenderer(this.rules[0], >> this.legendWrap).render(this.elNode, 2); >> } >> }, >> >> setRules: function() { >> var style = this.node.layer.styleMap && >> this.node.layer.styleMap.styles["default"]; >> if (!style) { >> style = new OpenLayers.Style(); >> } >> if (style.rules.length === 0) { >> this.rules = [ >> new OpenLayers.Rule({ >> symbolizer: style.createSymbolizer(this.feature) >> }) >> ]; >> } else { >> this.rules = style.rules; >> } >> }, >> >> createRuleRenderer: function(rule) { >> var symbolizer = rule.symbolizer; >> if (symbolizer[this.symbolType]) { >> symbolizer = symbolizer[this.symbolType]; >> } >> return new GeoExt.FeatureRenderer({ >> resolution: 1, >> width: 18, >> height: 18, >> symbolType: this.symbolType, >> symbolizers: [symbolizer], >> // override onRender() so that the vector element can >> // be wrapped with an inline element in place of a block element >> onRender: function(ct, position) { >> if(!this.el) { >> this.el = document.createElement('span'); >> this.el.className = 'legend-wrap'; >> this.el.id = this.getId(); >> } >> if(!this.renderer || !this.renderer.supported()) { >> this.assignRenderer(); >> } >> this.renderer.map = { >> getResolution: (function() { >> return this.resolution; >> }).createDelegate(this) >> }; >> this.drawFeature(); >> GeoExt.FeatureRenderer.superclass.onRender.apply(this, >> arguments); >> } >> }); >> }, >> >> renderElements : function(n, a, targetNode, bulkRender){ >> // add some indent caching, this helps performance when >> rendering a large tree >> this.indentMarkup = n.parentNode ? >> n.parentNode.ui.getChildIndent() : ''; >> >> var cb = Ext.isBoolean(a.checked), >> nel, >> href = a.href ? a.href : Ext.isGecko ? "" : "#", >> buf = ['<li class="x-tree-node"><div >> ext:tree-node-id="',n.id,'" class="x-tree-node-el x-tree-node-leaf >> x-tree-node-legend x-unselectable ', a.cls,'" unselectable="on">', >> '<span class="x-tree-node-indent">',this.indentMarkup,"</span>", >> '<img src="', this.emptyIcon, '" class="x-tree-ec-icon >> x-tree-elbow" />', >> cb ? ('<input class="x-tree-node-cb" type="checkbox" ' + >> (a.checked ? 'checked="checked" />' : '/>')) : '', >> '<a hidefocus="on" class="x-tree-node-anchor" >> href="',href,'" tabIndex="1" ', >> a.hrefTarget ? ' target="'+a.hrefTarget+'"' : "", '><span >> unselectable="on">',n.text,"</span></a></div>", >> '<ul class="x-tree-node-ct" style="display:none;"></ul>', >> "</li>"].join(''); >> >> if(bulkRender !== true && n.nextSibling && (nel = >> n.nextSibling.ui.getEl())){ >> this.wrap = Ext.DomHelper.insertHtml("beforeBegin", nel, buf); >> }else{ >> this.wrap = Ext.DomHelper.insertHtml("beforeEnd", targetNode, >> buf); >> } >> >> this.elNode = this.wrap.childNodes[0]; >> this.ctNode = this.wrap.childNodes[1]; >> var cs = this.elNode.childNodes; >> this.indentNode = cs[0]; >> this.ecNode = cs[1]; >> var index = 2; >> if(cb){ >> this.checkbox = cs[2]; >> // fix for IE6 >> this.checkbox.defaultChecked = this.checkbox.checked; >> index++; >> } >> this.anchor = cs[index]; >> this.textNode = cs[index].firstChild; >> >> if(this.symbolType) { >> this.createRuleRenderer(this.rules[0]).render(this.elNode, 2); >> } >> } >> }); >> >> Cheers >> Adam >> >> Cheers >> Adam >> >> On Mon, Aug 2, 2010 at 7:44 PM, Andreas Hocevar <[email protected]> wrote: >>> Oops, sorry. I had missed the "TreePanel" part of your original mail >>> (thought you wanted a VectorLegend in your LegendPanel). At this point, you >>> cannot render a legend with a tree node. There are several tickets with >>> patches already, which may help you: >>> >>> http://trac.geoext.org/ticket/185 >>> http://trac.geoext.org/ticket/139 >>> >>> Regards, >>> Andreas. >>> >>> On Aug 2, 2010, at 09:27 , Adam Ratcliffe wrote: >>> >>>> That's great. >>>> >>>> Just one question, how do I configure my TreePanel to create the node >>>> with a vector legend instead of an icon, my current tree configuration >>>> looks like this: >>>> >>>> var config = { >>>> autoScroll: true, >>>> animate: true, >>>> border: false, >>>> region: 'center', >>>> stateful: true, >>>> root: new GeoExt.tree.LayerContainer({ >>>> text: 'Layers', >>>> loader: new GeoExt.tree.LayerLoader({ >>>> store: this.layerStore, >>>> createNode: function(attr) { >>>> var layer = attr.layer; >>>> attr.iconCls = layer.gsGeometryType ? 'icon_' >>>> + layer.gsGeometryType.toLowerCase() : 'icon_point'; >>>> return >>>> GeoExt.tree.LayerLoader.prototype.createNode.call(this, attr); >>>> } >>>> }), >>>> layerStore: this.layerStore, >>>> leaf: false, >>>> expanded: true >>>> }) >>>> } >>>> >>>> Cheers >>>> Adam >>>> >>>> On Mon, Aug 2, 2010 at 6:13 PM, Andreas Hocevar <[email protected]> >>>> wrote: >>>>> Hi, >>>>> >>>>> On Aug 2, 2010, at 05:41 , Adam Ratcliffe wrote: >>>>> >>>>>> I'd like to dynamically render symbols based upon the layer geometry >>>>>> type and styles in a TreePanel similar to the vector legend example >>>>>> here: http://dev.geoext.org/trunk/geoext/examples/vector-legend.html >>>>>> >>>>>> Is this possible? >>>>> >>>>> Yes! Just configure your vector layer with a StyleMap. The VectorLegend >>>>> will be built from the style and rules of the "default" render intent. >>>>> >>>>> Regards, >>>>> Andreas. >>>>> >>>>>> >>>>>> Cheers >>>>>> Adam >>>>>> _______________________________________________ >>>>>> Users mailing list >>>>>> [email protected] >>>>>> http://www.geoext.org/cgi-bin/mailman/listinfo/users >>>>> >>>>> >>>>> >>>>> -- >>>>> Andreas Hocevar >>>>> OpenGeo - http://opengeo.org/ >>>>> Expert service straight from the developers. >>>>> >>>>> >>> >>> -- >>> Andreas Hocevar >>> OpenGeo - http://opengeo.org/ >>> Expert service straight from the developers. >>> >>> >> _______________________________________________ >> Users mailing list >> [email protected] >> http://www.geoext.org/cgi-bin/mailman/listinfo/users > > -- > Andreas Hocevar > OpenGeo - http://opengeo.org/ > Expert service straight from the developers. > > _______________________________________________ Users mailing list [email protected] http://www.geoext.org/cgi-bin/mailman/listinfo/users
