From e2a77274dcde43cdfb0232941d13a7027668b481 Mon Sep 17 00:00:00 2001 From: Young Hahn Date: Fri, 29 Jul 2011 17:03:06 -0400 Subject: [PATCH] Add mbtiles preview for exports. --- assets/css/style.css | 20 ++++++++++++++++++++ assets/images/sprite.png | Bin 19227 -> 19575 bytes assets/images/sprite.svg | 15 ++++++++++++--- index.js | 5 ++--- models/Preview.bones | 3 +++ models/Preview.server.bones | 17 +++++++++++++++++ servers/Tile.bones | 25 +++++++++++++++++++++++-- templates/Exports._ | 5 +++++ templates/Preview._ | 11 +++++++++++ views/Exports.bones | 18 ++++++++++++++++-- views/Preview.bones | 27 +++++++++++++++++++++++++++ views/Project.bones | 6 +----- 12 files changed, 137 insertions(+), 15 deletions(-) create mode 100644 models/Preview.bones create mode 100644 models/Preview.server.bones create mode 100644 templates/Preview._ create mode 100644 views/Preview.bones diff --git a/assets/css/style.css b/assets/css/style.css index dad0988e1..fb8b499a1 100644 --- a/assets/css/style.css +++ b/assets/css/style.css @@ -836,6 +836,7 @@ li:hover .icon { display:block; } .icon.tooltip { background-position:-580px -180px; } .icon.star { background-position:-600px -180px; } .icon.cloud { background-position:-620px -180px; } +.icon.eye { background-position:-640px -180px; } .reverse.edit { background-position:0px -200px; } .reverse.inspect { background-position:-20px -200px; } @@ -863,6 +864,7 @@ li:hover .icon { display:block; } .reverse.tooltip { background-position:-580px -200px; } .reverse.star { background-position:-600px -200px; } .reverse.cloud { background-position:-620px -200px; } +.reverse.eye { background-position:-640px -200px; } /* Dock-icon specific reverse styles */ .dock .active > .icon.legend { background-position:-280px -200px; } @@ -1356,6 +1358,24 @@ div.fonts { padding-top:30px; } width:120px; } +/* Exports preview */ +#preview { + background-position:50% 50%; + background-repeat:no-repeat; + background-color:#eee; + border:1px solid #ccc; + position:absolute !important; + left:20px !important; + right:20px !important; + top:80px !important; + bottom:20px !important; + width:auto !important; + height:auto !important; + box-shadow:inset #ddd 0px 0px 5px; + -moz-box-shadow:inset #ddd 0px 0px 5px; + -webkit-box-shadow:inset #ddd 0px 0px 5px; + } + /* Error page */ .empty { text-align:center; diff --git a/assets/images/sprite.png b/assets/images/sprite.png index 233a9cd3f3c65f45d7d1ac4265b873b3a2f9394b..92db69fb420b1b0390e9a62f833be2a280bdc48f 100644 GIT binary patch literal 19575 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 pB + + diff --git a/index.js b/index.js index c19074475..ed2644936 100755 --- a/index.js +++ b/index.js @@ -1,9 +1,8 @@ #!/usr/bin/env node process.title = 'tilemill'; - -var tilelive_mapnik = require('tilelive-mapnik'); -tilelive_mapnik.registerProtocols(require('tilelive')); +require('tilelive-mapnik').registerProtocols(require('tilelive')); +require('mbtiles').registerProtocols(require('tilelive')); require('bones').load(__dirname); !module.parent && require('bones').start(); diff --git a/models/Preview.bones b/models/Preview.bones new file mode 100644 index 000000000..d9e6aa97a --- /dev/null +++ b/models/Preview.bones @@ -0,0 +1,3 @@ +// Preview of an mbtiles export. +model = Backbone.Model.extend({}); +model.prototype.url = function() { return '/api/Preview/' + this.id; }; diff --git a/models/Preview.server.bones b/models/Preview.server.bones new file mode 100644 index 000000000..a8148eb61 --- /dev/null +++ b/models/Preview.server.bones @@ -0,0 +1,17 @@ +var path = require('path'); +var tilelive = require('tilelive'); +var settings = Bones.plugin.config; + +models.Preview.prototype.sync = function(method, model, success, error) { + if (method !== 'read') return error(new Error('Method not supported.')); + var filepath = path.join(settings.files, 'export', model.id); + tilelive.load('mbtiles://' + filepath, function(err, source) { + if (err) return error(err); + source.getInfo(function(err, info) { + if (err) return error(err); + info.tiles = ['/1.0.0/' + model.id + '/{z}/{x}/{y}.png']; + success(_(info).extend({id: model.id })); + }); + }); +}; + diff --git a/servers/Tile.bones b/servers/Tile.bones index 98964b4ad..f56590136 100644 --- a/servers/Tile.bones +++ b/servers/Tile.bones @@ -5,7 +5,9 @@ var path = require('path'), server = Bones.Server.extend({}); server.prototype.initialize = function() { - _.bindAll(this, 'load', 'grid', 'getArtifact'); + _.bindAll(this, 'load', 'grid', 'getArtifact', 'mbtiles'); + this.get('/1.0.0/:id.mbtiles/:z/:x/:y.:format(png8|png|jpeg[\\d]+|jpeg)', this.mbtiles); + this.get('/1.0.0/:id.mbtiles/:z/:x/:y.:format(grid.json)', this.mbtiles); this.get('/1.0.0/:id/:z/:x/:y.:format(png8|png|jpeg[\\d]+|jpeg)', this.load, this.getArtifact); this.get('/1.0.0/:id/:z/:x/:y.:format(grid.json)', this.load, this.grid, this.getArtifact); }; @@ -50,7 +52,7 @@ server.prototype.getArtifact = function(req, res, next) { var fn = req.params.format === 'grid.json' ? 'getGrid' : 'getTile'; source[fn](z, x, y, function(err, tile, headers) { if (err) return next(err); - headers['max-age'] = 3600; + if (headers) headers['max-age'] = 3600; res.send(tile, headers); }); }); @@ -70,3 +72,22 @@ server.prototype.grid = function(req, res, next) { next(); }; +server.prototype.mbtiles = function(req, res, next) { + var uri = 'mbtiles://' + path.join(settings.files, 'export', req.param('id') + '.mbtiles'); + tilelive.load(uri, function(err, source) { + if (err) return next(err); + + var z = req.params.z, x = +req.params.x, y = +req.params.y; + + // The interface is still TMS. + y = (1 << z) - 1 - y; + + var fn = req.params.format === 'grid.json' ? 'getGrid' : 'getTile'; + source[fn](z, x, y, function(err, tile, headers) { + if (err) return next(err); + if (headers) headers['max-age'] = 3600; + res.send(tile, headers); + }); + }); +}; + diff --git a/templates/Exports._ b/templates/Exports._ index cbe95d30c..89a91aa97 100644 --- a/templates/Exports._ +++ b/templates/Exports._ @@ -22,7 +22,12 @@ <%= obj.time(m.get('remaining')) %> remaining <% } %> <% if (m.get('status') === 'complete') { %> +
+ <% if (m.get('format') === 'mbtiles') { %> + '> Preview + <% } %> '> Download +
<% } %> <% if (m.get('status') === 'error') { %> <%=m.get('error')%> diff --git a/templates/Preview._ b/templates/Preview._ new file mode 100644 index 000000000..c577ff92d --- /dev/null +++ b/templates/Preview._ @@ -0,0 +1,11 @@ + + +
+ diff --git a/views/Exports.bones b/views/Exports.bones index 652513568..29c880d39 100644 --- a/views/Exports.bones +++ b/views/Exports.bones @@ -1,11 +1,12 @@ view = Backbone.View.extend(); view.prototype.events = { - 'click a.delete': 'exportDelete' + 'click a.delete': 'exportDelete', + 'click a.preview': 'exportPreview' }; view.prototype.initialize = function(options) { - _(this).bindAll('render', 'exportDelete', 'poll'); + _(this).bindAll('render', 'exportDelete', 'exportPreview', 'poll'); this.collection.bind('all', this.render); this.collection.bind('all', this.poll); this.render(true).poll(); @@ -47,6 +48,19 @@ view.prototype.exportDelete = function(ev) { return false; }; +view.prototype.exportPreview = function(ev) { + var id = $(ev.currentTarget).attr('href').split('#').pop(); + (new models.Preview({id:id})).fetch({ + success: function(model, resp) { + new views.Preview({ + el: $('#popup'), + model:model + }); + }, + error: function(m, e) { new views.Modal(e) } + }); +}; + // Poll controller. // - Starts polling if exports are active and drawer shows this view. // - Stops polling under all other conditions. diff --git a/views/Preview.bones b/views/Preview.bones new file mode 100644 index 000000000..2f8aedf33 --- /dev/null +++ b/views/Preview.bones @@ -0,0 +1,27 @@ +view = Backbone.View.extend(); + +view.prototype.initialize = function(options) { + _(this).bindAll('render'); + this.render(); +}; + +view.prototype.render = function() { + this.$('.content').html(templates.Preview(this.model)); + + if (!com.modestmaps) throw new Error('ModestMaps not found.'); + this.map = new com.modestmaps.Map('preview', + new wax.mm.connector(this.model.attributes)); + wax.mm.interaction(this.map, this.model.attributes); + wax.mm.legend(this.map, this.model.attributes); + wax.mm.zoombox(this.map); + wax.mm.zoomer(this.map).appendTo(this.map.parent); + + var center = this.model.get('center'); + this.map.setCenterZoom(new com.modestmaps.Location( + center[1], + center[0]), + center[2]); + + return this; +}; + diff --git a/views/Project.bones b/views/Project.bones index a92a42342..1067744bf 100644 --- a/views/Project.bones +++ b/views/Project.bones @@ -80,12 +80,8 @@ view.prototype.render = function(init) { new wax.mm.connector(this.model.attributes)); // Add references to all controls onto the map object. - // Allows controls to be removed later on. @TODO need - // wax 3.x and updates to controls to return references - // to themselves. + // Allows controls to be removed later on. this.map.controls = { - // @TODO wax 3.x. - // interaction, legend require TileJSON attributes from the model. interaction: wax.mm.interaction(this.map, this.model.attributes), legend: wax.mm.legend(this.map, this.model.attributes), zoombox: wax.mm.zoombox(this.map),