Sto usando d3.js per eseguire il rendering di una mappa del mondo in svg (utilizzando https://github.com/johan/world.geo.json/blob/master/countries.geo.json per le funzionalità). Sto incapsulando la logica di rendering in una vista backbone. Quando eseguo il rendering della vista e la allego al DOM, non viene visualizzato nulla nel mio browser, sebbene il markup SVG sia generato correttamente quando si guarda l'HTML generato. Questo rende bene quando non incapsula all'interno di un Backbone.View. Ecco il mio codice utilizzando Backbone.view:SVG non visualizzato correttamente come vista backbone
/**
* SVG Map view
*/
var MapView = Backbone.View.extend({
tagName: 'svg',
translationOffset: [480, 500],
zoomLevel: 1000,
/**
* Sets up the map projector and svg path generator
*/
initialize: function() {
this.projector = d3.geo.mercator();
this.path = d3.geo.path().projection(this.projector);
this.projector.translate(this.translationOffset);
this.projector.scale(this.zoomLevel);
},
/**
* Renders the map using the supplied features collection
*/
render: function() {
d3.select(this.el)
.selectAll('path')
.data(this.options.featureCollection.features)
.enter().append('path')
.attr('d', this.path);
},
/**
* Updates the zoom level
*/
zoom: function(level) {
this.projector.scale(this.zoomLevel = level);
},
/**
* Updates the translation offset
*/
pan: function(x, y) {
this.projector.translate([
this.translationOffset[0] += x,
this.translationOffset[1] += y
]);
},
/**
* Refreshes the map
*/
refresh: function() {
d3.select(this.el)
.selectAll('path')
.attr('d', this.path);
}
});
var map = new MapView({featureCollection: countryFeatureCollection});
map.$el.appendTo('body');
map.render();
Ecco il codice che funziona, senza l'utilizzo di Backbone.View
var projector = d3.geo.mercator(),
path = d3.geo.path().projection(projector),
countries = d3.select('body').append('svg'),
zoomLevel = 1000;
coords = [480, 500];
projector.translate(coords);
projector.scale(zoomLevel);
countries.selectAll('path')
.data(countryFeatureCollection.features)
.enter().append('path')
.attr('d', path);
ho anche allegato uno screenshot del markup generato SVG. Qualche idea di cosa potrebbe andare storto qui?
Edit - Ecco il metodo make override che ha finito per la soluzione di questo, per richiesta:
/**
* Custom make method needed as backbone does not support creation of
* namespaced HTML elements.
*/
make: function(tagName, attributes, content) {
var el = document.createElementNS('http://www.w3.org/2000/svg', tagName);
if (attributes) $(el).attr(attributes);
if (content) $(el).html(content);
return el;
}
Grazie! Ho scavalcato 'make' a mio avviso e ho usato createElementNS con 'http://www.w3.org/2000/svg' invece di createElement e sembra che faccia il trucco. Apprezzo la guida. –
@rr: potresti pubblicare il tuo metodo make da qualche parte? –
@PierreSpring: Fatto, non sono sicuro di quanto sia rilevante con le versioni più recenti di Backbone, non ho tenuto il passo. –