Compare commits

...

30 Commits

Author SHA1 Message Date
Michelle Tilley
838bf92265
Bump to 1.1.13 2018-10-30 11:52:33 -07:00
Michelle Tilley
24ad38a824
Merge pull request #23 from christiannaths/master
Fixes incorrect dependency notation
2018-10-30 11:45:49 -07:00
Christian Naths
1a388e7c4a
Fixes incorrect dependency notation
Locks dependencies down to:
  - topojson version 1
  - d3 version 3

As described in the docs
2018-08-25 15:14:22 -06:00
BinaryMuse
801ccb28e5 v1.1.2 2015-11-22 02:14:02 -08:00
BinaryMuse
52716cba5b Name update 2015-11-22 02:04:36 -08:00
Brandon Tilley
80ef60d6cf Update planet#draw docs 2014-12-13 12:04:48 -08:00
Brandon Tilley
f4d9536f17 v1.1.1 2014-05-18 10:37:03 -07:00
Rolf Sommerhalder
9344299298 Set planetaryjs global when using AMD
While using RequireJS to AMD load ng-planetaryjs, planetaryjs, and their
dependencies, ng-planetaryjs still looks for global object planetaryjs
(such as in `var globe = planetaryjs.planet();`). Thus use the UMD
pattern "AMD with global, Node, or global" instead of "AMD, Node, or
browser global" from https://sublime.wbond.net/packages/UMD%20snippets
2014-05-18 10:32:26 -07:00
Brandon Tilley
3d6ca445f8 Update devDependencies 2014-05-18 10:25:51 -07:00
Brandon Tilley
c86479db1f Update changelog retroactively to match release notes on GitHub 2014-02-03 00:25:33 -08:00
Brandon Tilley
5e807f52e0 v1.1.0 2014-02-03 00:16:47 -08:00
Brandon Tilley
cfb059369e Update CHANGELOG 2014-02-03 00:14:39 -08:00
Brandon Tilley
4edb647564 (core) Add stop method 2014-02-03 00:13:37 -08:00
Brandon Tilley
74013bde29 v1.0.3 2014-01-22 20:45:13 -08:00
Brandon Tilley
62e8d08bd9 (core) Don't disable adaptive resampling on the projection 2014-01-22 20:43:26 -08:00
Brandon Tilley
f5bf0743fb (site) Fix broken markup around 'download source' link 2014-01-15 21:39:35 -08:00
Brandon Tilley
53b7a3b2b7 v1.0.2 2014-01-15 21:33:16 -08:00
Brandon Tilley
2aa72ca45e (site) Update CommonJS installation instructions 2014-01-15 21:31:48 -08:00
Brandon Tilley
d873121c08 (core) Update dependencies on D3 and TopoJSON 2014-01-15 14:17:50 -08:00
Brandon Tilley
1eae3fb7c9 Merge pull request #5 from darul75/master
(site) Fix ID of globe in rotating example
2014-01-11 15:18:50 -08:00
Julien Valéry
c8c4bfa4bd fix id globe name
great job, thanks
2014-01-11 17:11:14 +01:00
Brandon Tilley
6350c397b2 (site) Fix broken DOM 2014-01-06 18:37:17 -08:00
Brandon Tilley
bbe2e15283 (site) Count clicks to GH as non-bounce visitors 2014-01-03 15:11:16 -08:00
Brandon Tilley
b9a070ab76 Don't forget important things like creating releases 2014-01-03 07:32:03 -08:00
Brandon Tilley
964dfbc366 v1.0.1 2014-01-02 09:06:06 -08:00
Brandon Tilley
05313d79f8 (core) Depend on D3 and TopoJSON 2014-01-02 09:04:40 -08:00
Brandon Tilley
461561340b (site) Note TopoJSON PR in CommonJS installation instructions 2014-01-02 09:04:20 -08:00
Brandon Tilley
fe1de35576 (site) Add installation section; move AMD and CommonJS info there 2014-01-01 18:18:51 -08:00
Brandon Tilley
1764ee07f7 (site) Fix incorrect plugins in quake example 2014-01-01 11:49:02 -08:00
Brandon Tilley
19ed44d67b (site) Add FB meta tags 2013-12-31 12:41:49 -08:00
28 changed files with 4535 additions and 140 deletions

View File

@ -1,3 +1,36 @@
v1.1.2 (2015/11/22)
-------------------
* Update LICENSE and copyright notices
v1.1.1 (2014/05/18)
-------------------
* Set `planetaryjs` on root when using AMD
v1.1.0 (2014/02/03)
-------------------
**Core**
* Add `stop` method
* Add `onStop` hooks
v1.0.3 (2014/01/23)
-------------------
* Don't disable adaptive resampling on the projection
v1.0.2 (2014/01/16)
-------------------
* Update version dependencies for D3 and TopoJSON
v1.0.1 (2013/01/02)
-------------------
* Add D3 and TopoJSON as dependencies in `package.json`
v1.0.0 (2013/12/31)
-------------------

View File

@ -1,4 +1,4 @@
Copyright (c) 2013 Brandon Tilley
Copyright (c) 2013 Michelle Tilley
Permission is hereby granted, free of charge, to any person
obtaining a copy of this software and associated documentation

View File

@ -1,11 +1,11 @@
{
"name": "planetary.js",
"version": "1.0.0",
"version": "1.1.2",
"main": "dist/planetaryjs.min.js",
"description": "Awesome interactive globes for the web",
"homepage": "http://planetaryjs.com",
"authors": [
"Brandon Tilley <brandon@brandontilley.com>"
"Michelle Tilley <michelle@michelletilley.net>"
],
"license": "MIT",
"ignore": [

View File

@ -1,12 +1,14 @@
/*! Planetary.js v1.0.0
* Copyright (c) 2013 Brandon Tilley
/*! Planetary.js v1.1.3
* Copyright (c) 2013 Michelle Tilley
*
* Released under the MIT license
* Date: 2013-12-31T18:52:59.372Z
* Date: 2018-10-30T18:49:58.804Z
*/
(function (root, factory) {
if (typeof define === 'function' && define.amd) {
define(['d3', 'topojson'], factory);
define(['d3', 'topojson'], function(d3, topojson) {
return (root.planetaryjs = factory(d3, topojson, root));
});
} else if (typeof exports === 'object') {
module.exports = factory(require('d3'), require('topojson'));
} else {
@ -21,6 +23,10 @@
var doDrawLoop = function(planet, canvas, hooks) {
d3.timer(function() {
if (planet.stopped) {
return true;
}
planet.context.clearRect(0, 0, canvas.width, canvas.height);
for (var i = 0; i < hooks.onDraw.length; i++) {
hooks.onDraw[i]();
@ -76,11 +82,14 @@
};
var startDraw = function(planet, canvas, localPlugins, hooks) {
initPlugins(planet, localPlugins);
planet.canvas = canvas;
planet.context = canvas.getContext('2d');
if (planet.stopped !== true) {
initPlugins(planet, localPlugins);
}
planet.stopped = false;
runOnInitHooks(planet, canvas, hooks);
};
@ -100,7 +109,8 @@
var localPlugins = [];
var hooks = {
onInit: [],
onDraw: []
onDraw: [],
onStop: []
};
var planet = {
@ -118,10 +128,21 @@
hooks.onDraw.push(fn);
},
onStop: function(fn) {
hooks.onStop.push(fn);
},
loadPlugin: function(plugin) {
localPlugins.push(plugin);
},
stop: function() {
planet.stopped = true;
for (var i = 0; i < hooks.onStop.length; i++) {
hooks.onStop[i](planet);
}
},
withSavedContext: function(fn) {
if (!this.context) {
throw new Error("No canvas to fetch context for");
@ -134,8 +155,7 @@
};
planet.projection = d3.geo.orthographic()
.clipAngle(90)
.precision(0);
.clipAngle(90);
planet.path = d3.geo.path().projection(planet.projection);
return planet;

View File

@ -1,2 +1,2 @@
/*! Planetary.js 1.0.0 | (c) 2013 Brandon Tilley | Released under MIT License */
!function(n,t){"function"==typeof define&&define.amd?define(["d3","topojson"],t):"object"==typeof exports?module.exports=t(require("d3"),require("topojson")):n.planetaryjs=t(n.d3,n.topojson,n)}(this,function(n,t,o){"use strict";var e=null;o&&(e=o.planetaryjs);var i=[],r=function(t,o,e){n.timer(function(){t.context.clearRect(0,0,o.width,o.height);for(var n=0;n<e.onDraw.length;n++)e.onDraw[n]()})},u=function(n,t){for(var o=i.length-1;o>=0;o--)t.unshift(i[o]);for(0===t.length&&(s.plugins.earth&&n.loadPlugin(s.plugins.earth()),s.plugins.pings&&n.loadPlugin(s.plugins.pings())),o=0;o<t.length;o++)t[o](n)},c=function(n,t,o){if(o.onInit.length){var e=0,i=function(n){var t=o.onInit[e];t.length?t(function(){e++,n()}):(t(),e++,setTimeout(n,0))},u=function(){e>=o.onInit.length?r(n,t,o):i(u)};i(u)}else r(n,t,o)},a=function(n,t,o,e){u(n,o),n.canvas=t,n.context=t.getContext("2d"),c(n,t,e)},s={plugins:{},noConflict:function(){return o.planetaryjs=e,s},loadPlugin:function(n){i.push(n)},planet:function(){var t=[],o={onInit:[],onDraw:[]},e={plugins:{},draw:function(n){a(e,n,t,o)},onInit:function(n){o.onInit.push(n)},onDraw:function(n){o.onDraw.push(n)},loadPlugin:function(n){t.push(n)},withSavedContext:function(n){if(!this.context)throw new Error("No canvas to fetch context for");this.context.save(),n(this.context),this.context.restore()}};return e.projection=n.geo.orthographic().clipAngle(90).precision(0),e.path=n.geo.path().projection(e.projection),e}};return s});
/*! Planetary.js 1.1.3 | (c) 2013 Michelle Tilley | Released under MIT License */
!function(n,t){"function"==typeof define&&define.amd?define(["d3","topojson"],function(o,e){return n.planetaryjs=t(o,e,n)}):"object"==typeof exports?module.exports=t(require("d3"),require("topojson")):n.planetaryjs=t(n.d3,n.topojson,n)}(this,function(n,t,o){"use strict";var e=null;o&&(e=o.planetaryjs);var i=[],r=function(t,o,e){n.timer(function(){if(t.stopped)return!0;t.context.clearRect(0,0,o.width,o.height);for(var n=0;n<e.onDraw.length;n++)e.onDraw[n]()})},u=function(n,t){for(var o=i.length-1;o>=0;o--)t.unshift(i[o]);for(0===t.length&&(s.plugins.earth&&n.loadPlugin(s.plugins.earth()),s.plugins.pings&&n.loadPlugin(s.plugins.pings())),o=0;o<t.length;o++)t[o](n)},p=function(n,t,o){if(o.onInit.length){var e=0,i=function(n){var t=o.onInit[e];t.length?t(function(){e++,n()}):(t(),e++,setTimeout(n,0))},u=function(){e>=o.onInit.length?r(n,t,o):i(u)};i(u)}else r(n,t,o)},c=function(n,t,o,e){n.canvas=t,n.context=t.getContext("2d"),n.stopped!==!0&&u(n,o),n.stopped=!1,p(n,t,e)},s={plugins:{},noConflict:function(){return o.planetaryjs=e,s},loadPlugin:function(n){i.push(n)},planet:function(){var t=[],o={onInit:[],onDraw:[],onStop:[]},e={plugins:{},draw:function(n){c(e,n,t,o)},onInit:function(n){o.onInit.push(n)},onDraw:function(n){o.onDraw.push(n)},onStop:function(n){o.onStop.push(n)},loadPlugin:function(n){t.push(n)},stop:function(){e.stopped=!0;for(var n=0;n<o.onStop.length;n++)o.onStop[n](e)},withSavedContext:function(n){if(!this.context)throw new Error("No canvas to fetch context for");this.context.save(),n(this.context),this.context.restore()}};return e.projection=n.geo.orthographic().clipAngle(90),e.path=n.geo.path().projection(e.projection),e}};return s});

38
dist/planetaryjs.js vendored
View File

@ -1,12 +1,14 @@
/*! Planetary.js v1.0.0
* Copyright (c) 2013 Brandon Tilley
/*! Planetary.js v1.1.3
* Copyright (c) 2013 Michelle Tilley
*
* Released under the MIT license
* Date: 2013-12-31T18:52:59.214Z
* Date: 2018-10-30T18:49:58.667Z
*/
(function (root, factory) {
if (typeof define === 'function' && define.amd) {
define(['d3', 'topojson'], factory);
define(['d3', 'topojson'], function(d3, topojson) {
return (root.planetaryjs = factory(d3, topojson, root));
});
} else if (typeof exports === 'object') {
module.exports = factory(require('d3'), require('topojson'));
} else {
@ -21,6 +23,10 @@
var doDrawLoop = function(planet, canvas, hooks) {
d3.timer(function() {
if (planet.stopped) {
return true;
}
planet.context.clearRect(0, 0, canvas.width, canvas.height);
for (var i = 0; i < hooks.onDraw.length; i++) {
hooks.onDraw[i]();
@ -76,11 +82,14 @@
};
var startDraw = function(planet, canvas, localPlugins, hooks) {
initPlugins(planet, localPlugins);
planet.canvas = canvas;
planet.context = canvas.getContext('2d');
if (planet.stopped !== true) {
initPlugins(planet, localPlugins);
}
planet.stopped = false;
runOnInitHooks(planet, canvas, hooks);
};
@ -100,7 +109,8 @@
var localPlugins = [];
var hooks = {
onInit: [],
onDraw: []
onDraw: [],
onStop: []
};
var planet = {
@ -118,10 +128,21 @@
hooks.onDraw.push(fn);
},
onStop: function(fn) {
hooks.onStop.push(fn);
},
loadPlugin: function(plugin) {
localPlugins.push(plugin);
},
stop: function() {
planet.stopped = true;
for (var i = 0; i < hooks.onStop.length; i++) {
hooks.onStop[i](planet);
}
},
withSavedContext: function(fn) {
if (!this.context) {
throw new Error("No canvas to fetch context for");
@ -134,8 +155,7 @@
};
planet.projection = d3.geo.orthographic()
.clipAngle(90)
.precision(0);
.clipAngle(90);
planet.path = d3.geo.path().projection(planet.projection);
return planet;

View File

@ -1,2 +1,2 @@
/*! Planetary.js 1.0.0 | (c) 2013 Brandon Tilley | Released under MIT License */
!function(n,t){"function"==typeof define&&define.amd?define(["d3","topojson"],t):"object"==typeof exports?module.exports=t(require("d3"),require("topojson")):n.planetaryjs=t(n.d3,n.topojson,n)}(this,function(n,t,o){"use strict";var i=null;o&&(i=o.planetaryjs);var e=[],r=function(t,o,i){n.timer(function(){t.context.clearRect(0,0,o.width,o.height);for(var n=0;n<i.onDraw.length;n++)i.onDraw[n]()})},l=function(n,t){for(var o=e.length-1;o>=0;o--)t.unshift(e[o]);for(0===t.length&&(u.plugins.earth&&n.loadPlugin(u.plugins.earth()),u.plugins.pings&&n.loadPlugin(u.plugins.pings())),o=0;o<t.length;o++)t[o](n)},a=function(n,t,o){if(o.onInit.length){var i=0,e=function(n){var t=o.onInit[i];t.length?t(function(){i++,n()}):(t(),i++,setTimeout(n,0))},l=function(){i>=o.onInit.length?r(n,t,o):e(l)};e(l)}else r(n,t,o)},c=function(n,t,o,i){l(n,o),n.canvas=t,n.context=t.getContext("2d"),a(n,t,i)},u={plugins:{},noConflict:function(){return o.planetaryjs=i,u},loadPlugin:function(n){e.push(n)},planet:function(){var t=[],o={onInit:[],onDraw:[]},i={plugins:{},draw:function(n){c(i,n,t,o)},onInit:function(n){o.onInit.push(n)},onDraw:function(n){o.onDraw.push(n)},loadPlugin:function(n){t.push(n)},withSavedContext:function(n){if(!this.context)throw new Error("No canvas to fetch context for");this.context.save(),n(this.context),this.context.restore()}};return i.projection=n.geo.orthographic().clipAngle(90).precision(0),i.path=n.geo.path().projection(i.projection),i}};return u.plugins.topojson=function(t){return function(o){o.plugins.topojson={},o.onInit(function(i){if(t.world)o.plugins.topojson.world=t.world,setTimeout(i,0);else{var e=t.file||"world-110m.json";n.json(e,function(n,t){if(n)throw new Error("Could not load JSON "+e);o.plugins.topojson.world=t,i()})}})}},u.plugins.oceans=function(n){return function(t){t.onDraw(function(){t.withSavedContext(function(o){o.beginPath(),t.path.context(o)({type:"Sphere"}),o.fillStyle=n.fill||"black",o.fill()})})}},u.plugins.land=function(n){return function(o){var i=null;o.onInit(function(){var n=o.plugins.topojson.world;i=t.feature(n,n.objects.land)}),o.onDraw(function(){o.withSavedContext(function(t){t.beginPath(),o.path.context(t)(i),n.fill!==!1&&(t.fillStyle=n.fill||"white",t.fill()),n.stroke&&(n.lineWidth&&(t.lineWidth=n.lineWidth),t.strokeStyle=n.stroke,t.stroke())})})}},u.plugins.borders=function(n){return function(o){var i=null,e={internal:function(n,t){return n.id!==t.id},external:function(n,t){return n.id===t.id},both:function(){return!0}};o.onInit(function(){var r=o.plugins.topojson.world,l=r.objects.countries,a=n.type||"internal";i=t.mesh(r,l,e[a])}),o.onDraw(function(){o.withSavedContext(function(t){t.beginPath(),o.path.context(t)(i),t.strokeStyle=n.stroke||"gray",n.lineWidth&&(t.lineWidth=n.lineWidth),t.stroke()})})}},u.plugins.earth=function(n){n=n||{};var t=n.topojson||{},o=n.oceans||{},i=n.land||{},e=n.borders||{};return function(n){u.plugins.topojson(t)(n),u.plugins.oceans(o)(n),u.plugins.land(i)(n),u.plugins.borders(e)(n)}},u.plugins.pings=function(t){var o=[];t=t||{};var i=function(n,i,e){e=e||{},e.color=e.color||t.color||"white",e.angle=e.angle||t.angle||5,e.ttl=e.ttl||t.ttl||2e3;var r={time:new Date,options:e};t.latitudeFirst?(r.lat=n,r.lng=i):(r.lng=n,r.lat=i),o.push(r)},e=function(n,t,i){for(var e=[],l=0;l<o.length;l++){var a=o[l],c=i-a.time;c<a.options.ttl&&(e.push(a),r(n,t,i,c,a))}o=e},r=function(t,o,i,e,r){var l=1-e/r.options.ttl,a=n.rgb(r.options.color);a="rgba("+a.r+","+a.g+","+a.b+","+l+")",o.strokeStyle=a;var c=n.geo.circle().origin([r.lng,r.lat]).angle(e/r.options.ttl*r.options.angle)();o.beginPath(),t.path.context(o)(c),o.stroke()};return function(n){n.plugins.pings={add:i},n.onDraw(function(){var t=new Date;n.withSavedContext(function(o){e(n,o,t)})})}},u.plugins.zoom=function(t){t=t||{};var o=function(){},i=t.onZoomStart||o,e=t.onZoomEnd||o,r=t.onZoom||o,l=t.afterZoom||o,a=t.initialScale,c=t.scaleExtent||[50,2e3];return function(t){t.onInit(function(){var o=n.behavior.zoom().scaleExtent(c);null!==a&&void 0!==a?o.scale(a):o.scale(t.projection.scale()),o.on("zoomstart",i.bind(t)).on("zoomend",e.bind(t)).on("zoom",function(){r.call(t),t.projection.scale(n.event.scale),l.call(t)}),n.select(t.canvas).call(o)})}},u.plugins.drag=function(t){t=t||{};var o=function(){},i=t.onDragStart||o,e=t.onDragEnd||o,r=t.onDrag||o,l=t.afterDrag||o;return function(t){t.onInit(function(){var o=n.behavior.drag().on("dragstart",i.bind(t)).on("dragend",e.bind(t)).on("drag",function(){r.call(t);var o=n.event.dx,i=n.event.dy,e=t.projection.rotate(),a=t.projection.scale(),c=n.scale.linear().domain([-1*a,a]).range([-90,90]),u=c(o),s=c(i);e[0]+=u,e[1]-=s,e[1]>90&&(e[1]=90),e[1]<-90&&(e[1]=-90),e[0]>=180&&(e[0]-=360),t.projection.rotate(e),l.call(t)});n.select(t.canvas).call(o)})}},u});
/*! Planetary.js 1.1.3 | (c) 2013 Michelle Tilley | Released under MIT License */
!function(n,t){"function"==typeof define&&define.amd?define(["d3","topojson"],function(o,e){return n.planetaryjs=t(o,e,n)}):"object"==typeof exports?module.exports=t(require("d3"),require("topojson")):n.planetaryjs=t(n.d3,n.topojson,n)}(this,function(n,t,o){"use strict";var e=null;o&&(e=o.planetaryjs);var i=[],r=function(t,o,e){n.timer(function(){if(t.stopped)return!0;t.context.clearRect(0,0,o.width,o.height);for(var n=0;n<e.onDraw.length;n++)e.onDraw[n]()})},l=function(n,t){for(var o=i.length-1;o>=0;o--)t.unshift(i[o]);for(0===t.length&&(c.plugins.earth&&n.loadPlugin(c.plugins.earth()),c.plugins.pings&&n.loadPlugin(c.plugins.pings())),o=0;o<t.length;o++)t[o](n)},a=function(n,t,o){if(o.onInit.length){var e=0,i=function(n){var t=o.onInit[e];t.length?t(function(){e++,n()}):(t(),e++,setTimeout(n,0))},l=function(){e>=o.onInit.length?r(n,t,o):i(l)};i(l)}else r(n,t,o)},u=function(n,t,o,e){n.canvas=t,n.context=t.getContext("2d"),n.stopped!==!0&&l(n,o),n.stopped=!1,a(n,t,e)},c={plugins:{},noConflict:function(){return o.planetaryjs=e,c},loadPlugin:function(n){i.push(n)},planet:function(){var t=[],o={onInit:[],onDraw:[],onStop:[]},e={plugins:{},draw:function(n){u(e,n,t,o)},onInit:function(n){o.onInit.push(n)},onDraw:function(n){o.onDraw.push(n)},onStop:function(n){o.onStop.push(n)},loadPlugin:function(n){t.push(n)},stop:function(){e.stopped=!0;for(var n=0;n<o.onStop.length;n++)o.onStop[n](e)},withSavedContext:function(n){if(!this.context)throw new Error("No canvas to fetch context for");this.context.save(),n(this.context),this.context.restore()}};return e.projection=n.geo.orthographic().clipAngle(90),e.path=n.geo.path().projection(e.projection),e}};return c.plugins.topojson=function(t){return function(o){o.plugins.topojson={},o.onInit(function(e){if(t.world)o.plugins.topojson.world=t.world,setTimeout(e,0);else{var i=t.file||"world-110m.json";n.json(i,function(n,t){if(n)throw new Error("Could not load JSON "+i);o.plugins.topojson.world=t,e()})}})}},c.plugins.oceans=function(n){return function(t){t.onDraw(function(){t.withSavedContext(function(o){o.beginPath(),t.path.context(o)({type:"Sphere"}),o.fillStyle=n.fill||"black",o.fill()})})}},c.plugins.land=function(n){return function(o){var e=null;o.onInit(function(){var n=o.plugins.topojson.world;e=t.feature(n,n.objects.land)}),o.onDraw(function(){o.withSavedContext(function(t){t.beginPath(),o.path.context(t)(e),n.fill!==!1&&(t.fillStyle=n.fill||"white",t.fill()),n.stroke&&(n.lineWidth&&(t.lineWidth=n.lineWidth),t.strokeStyle=n.stroke,t.stroke())})})}},c.plugins.borders=function(n){return function(o){var e=null,i={internal:function(n,t){return n.id!==t.id},external:function(n,t){return n.id===t.id},both:function(){return!0}};o.onInit(function(){var r=o.plugins.topojson.world,l=r.objects.countries,a=n.type||"internal";e=t.mesh(r,l,i[a])}),o.onDraw(function(){o.withSavedContext(function(t){t.beginPath(),o.path.context(t)(e),t.strokeStyle=n.stroke||"gray",n.lineWidth&&(t.lineWidth=n.lineWidth),t.stroke()})})}},c.plugins.earth=function(n){n=n||{};var t=n.topojson||{},o=n.oceans||{},e=n.land||{},i=n.borders||{};return function(n){c.plugins.topojson(t)(n),c.plugins.oceans(o)(n),c.plugins.land(e)(n),c.plugins.borders(i)(n)}},c.plugins.pings=function(t){var o=[];t=t||{};var e=function(n,e,i){i=i||{},i.color=i.color||t.color||"white",i.angle=i.angle||t.angle||5,i.ttl=i.ttl||t.ttl||2e3;var r={time:new Date,options:i};t.latitudeFirst?(r.lat=n,r.lng=e):(r.lng=n,r.lat=e),o.push(r)},i=function(n,t,e){for(var i=[],l=0;l<o.length;l++){var a=o[l],u=e-a.time;u<a.options.ttl&&(i.push(a),r(n,t,e,u,a))}o=i},r=function(t,o,e,i,r){var l=1-i/r.options.ttl,a=n.rgb(r.options.color);a="rgba("+a.r+","+a.g+","+a.b+","+l+")",o.strokeStyle=a;var u=n.geo.circle().origin([r.lng,r.lat]).angle(i/r.options.ttl*r.options.angle)();o.beginPath(),t.path.context(o)(u),o.stroke()};return function(n){n.plugins.pings={add:e},n.onDraw(function(){var t=new Date;n.withSavedContext(function(o){i(n,o,t)})})}},c.plugins.zoom=function(t){t=t||{};var o=function(){},e=t.onZoomStart||o,i=t.onZoomEnd||o,r=t.onZoom||o,l=t.afterZoom||o,a=t.initialScale,u=t.scaleExtent||[50,2e3];return function(t){t.onInit(function(){var o=n.behavior.zoom().scaleExtent(u);null!==a&&void 0!==a?o.scale(a):o.scale(t.projection.scale()),o.on("zoomstart",e.bind(t)).on("zoomend",i.bind(t)).on("zoom",function(){r.call(t),t.projection.scale(n.event.scale),l.call(t)}),n.select(t.canvas).call(o)})}},c.plugins.drag=function(t){t=t||{};var o=function(){},e=t.onDragStart||o,i=t.onDragEnd||o,r=t.onDrag||o,l=t.afterDrag||o;return function(t){t.onInit(function(){var o=n.behavior.drag().on("dragstart",e.bind(t)).on("dragend",i.bind(t)).on("drag",function(){r.call(t);var o=n.event.dx,e=n.event.dy,i=t.projection.rotate(),a=t.projection.scale(),u=n.scale.linear().domain([-1*a,a]).range([-90,90]),c=u(o),s=u(e);i[0]+=c,i[1]-=s,i[1]>90&&(i[1]=90),i[1]<-90&&(i[1]=-90),i[0]>=180&&(i[0]-=360),t.projection.rotate(i),l.call(t)});n.select(t.canvas).call(o)})}},c});

View File

@ -7,14 +7,15 @@ var jshint = require('gulp-jshint');
var replace = require('gulp-replace');
var metadata = require('./package.json');
var shortHeader = "/*! Planetary.js {{version}} | (c) 2013 Brandon Tilley | Released under MIT License */"
var shortHeader = "/*! Planetary.js <%= version %> | (c) 2013 Michelle Tilley | Released under MIT License */\n"
var fullHeader = [
"/*! Planetary.js v{{version}}",
" * Copyright (c) 2013 Brandon Tilley",
"/*! Planetary.js v<%= version %>",
" * Copyright (c) 2013 Michelle Tilley",
" *",
" * Released under the MIT license",
" * Date: {{now}}",
" */"
" * Date: <%= new Date().toISOString() %>",
" */",
""
].join("\n");
var fullSource = gulp.src(['./src/_umd_header.js', './src/body.js', './src/plugins.js', './src/_umd_footer.js']);
@ -42,7 +43,4 @@ gulp.task('build', function() {
gulp.src('./src/world-110m.json').pipe(gulp.dest('./dist'));
});
gulp.task('default', function() {
gulp.run('jshint');
gulp.run('build');
});
gulp.task('default', ['jshint', 'build']);

4222
package-lock.json generated Normal file

File diff suppressed because it is too large Load Diff

View File

@ -1,6 +1,6 @@
{
"name": "planetary.js",
"version": "1.0.0",
"version": "1.1.3",
"description": "Awesome interactive globes for the web",
"main": "dist/planetaryjs",
"scripts": {
@ -12,20 +12,24 @@
"type": "git",
"url": "git://github.com/BinaryMuse/planetary.js.git"
},
"author": "Brandon Tilley <brandon@brandontilley.com>",
"author": "Michelle Tilley <michelle@michelletilley.net>",
"license": "MIT",
"bugs": {
"url": "https://github.com/BinaryMuse/planetary.js/issues"
},
"homepage": "http://planetaryjs.com",
"devDependencies": {
"gulp": "~3.2.0",
"gulp": "~3.6.2",
"gulp-concat": "BinaryMuse/gulp-concat",
"gulp-header": "~0.4.0",
"gulp-uglify": "~0.1.0",
"gulp-rename": "~0.2.1",
"gulp-header": "~1.0.2",
"gulp-uglify": "~0.3.0",
"gulp-rename": "~1.2.0",
"bower": "~1.2.8",
"gulp-jshint": "~1.3.1",
"gulp-replace": "~0.2.0"
"gulp-jshint": "~1.6.1",
"gulp-replace": "~0.3.0"
},
"dependencies": {
"topojson": "^1.4.6",
"d3": "^3.3.13"
}
}

View File

@ -36,4 +36,4 @@ fs.writeFileSync('site/public/download/_data.json', JSON.stringify(site, null, '
spawn('npm', ['run', 'build']);
console.log("Tasks:\n\n - Update CHANGELOG.md\n - Regenerate site");
console.log("Tasks:\n\n - Update CHANGELOG.md\n - Regenerate site\n - Create release on GH");

View File

@ -9,7 +9,7 @@
"start": "harp server",
"compile": "harp compile"
},
"author": "Brandon Tilley <brandon@brandontilley.com>",
"author": "Michelle Tilley <michelle@michelletilley.net>",
"license": "MIT",
"private": true,
"dependencies": {

View File

@ -3,6 +3,8 @@
<link type="text/css" rel="stylesheet" href="/semantic/css/semantic.min.css">
<link type="text/css" rel="stylesheet" href="/css/planetaryjs.css">
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta content="IE=edge,chrome=1" http-equiv="X-UA-Compatible">
<meta property="og:image" content="http://planetaryjs.com/images/ex-rotating.png">
<meta property="og:site_name" content="Planetary.js">

View File

@ -13,7 +13,8 @@
<a class='item minor <%- current.path[0] == 'documentation' ? 'active' : '' %>' href='/documentation/'>
<i class='book icon'></i><span class='hide-on-mobile'>Documentation</span>
</a>
<a class='item minor' href='https://github.com/BinaryMuse/planetary.js'>
<a class='item minor' href='https://github.com/BinaryMuse/planetary.js'
onclick="_gaq.push(['_trackPageview', '/redirect-to-github-project-page']);">
<i class='github alternate icon'></i><span class='hide-on-mobile'>Fork on GitHub</span>
</a>
</div>

View File

@ -15,6 +15,10 @@
Introduction
<i class='icon home'></i>
</a>
<a class='purple item <%- current.source == 'installation' ? 'active' : '' %>' href='/documentation/installation.html'>
Installation
<i class='icon download'></i>
</a>
<a class='blue item <%- current.source == 'core' ? 'active' : '' %>' href='/documentation/core.html'>
Core API
<i class='icon setting'></i>

View File

@ -1,28 +1,6 @@
Core API
========
Installation
------------
Once you've [downloaded Planetary.js](/download/), you can include it via a `script` tag on your page *after* the inclusion of D3 and TopoJSON. This example uses the CDN URLs for those libraries:
<div class='ui raised segment'>
<div class='ui blue ribbon label'>HTML</div>
```html
<html>
<head>
<script type='text/javascript' src='http://d3js.org/d3.v3.min.js'></script>
<script type='text/javascript' src='http://d3js.org/topojson.v1.min.js'></script>
<script type='text/javascript' src='path/to/planetaryjs.min.js'></script>
</head>
<body>
...
```
</div>
If you use the default `topojson` plugin (most people will), you'll also need to make sure `world-110m.json` (or some other TopoJSON data file) is available on your server. This file is also available from [the download page](/download/). See the [TopoJSON Plugin documentation](/documentation/builtin_topojson.html) for more information.
Core API
--------

View File

@ -45,53 +45,3 @@ planet's `draw` method.
**Q:** I'm getting "Cannot read property 'geo' of undefined" or "Cannot call method 'feature' of undefined."
**A:** Ensure you're requiring the [D3](http://d3js.org/) and [TopoJSON](https://github.com/mbostock/topojson) libraries before Planetary.js.
<div class="ui horizontal icon divider">
<i class="globe icon"></i>
</div>
**Q:** Can I use Planetary.js with AMD or CommonJS?
**A:** Yes and no. Planetary.js uses a universal module definition, and so is compatible with AMD and CommonJS. However, neither D3 nor TopoJSON support AMD, and TopoJSON's CommonJS package (as installed with [npm](https://npmjs.org/)) uses Node-specific functionality, so you can't, for instance, [browserify](http://browserify.org/) it directly.
## AMD
This example uses [RequireJS](http://requirejs.org/). Since neither D3 nor TopoJSON support AMD, we will use RequireJS's [shim configuration](http://requirejs.org/docs/api.html#config-shim).
<div class='ui raised segment'>
<div class='ui blue ribbon label'>HTML</div>
```html
<body>
<canvas id='globe' width='500' height='500'></canavs>
<script src='//cdnjs.cloudflare.com/ajax/libs/require.js/2.1.9/require.min.js'
data-main='/app.js'></script>
</body>
```
<div class='ui red ribbon label'>JavaScript</div>
```javascript
requirejs.config({
// Tell RequireJS to use `window.d3` and `window.topojson`
// for those libraries, respectively
shim: {
d3: { exports: 'd3' },
topojson: { exports: 'topojson' }
},
paths: {
'd3': 'path/to/d3.v3.min',
'topojson': 'path/to/topojson.v1.min'
}
});
requirejs(['planetaryjs'], function(planetaryjs) {
// Use Planetary.js here
});
```
</div>
## CommonJS
To use Planetary.js with a tool like Browserify, you will need to create a shim for TopoJSON (D3 includes a Browserify-compatible script). Take a look at [browserify-shim](https://github.com/thlorenz/browserify-shim) for more information.

View File

@ -15,7 +15,7 @@ The documentation is split up into several sections:
Quick Start
-----------
If you want to get up-and-running quickly, or like to experiment and figure things out, you can use this HTML and JavaScript to get a very simple globe up and running.
If you want to get up-and-running quickly, or like to experiment and figure things out, you can use this HTML and JavaScript to get a very simple globe up and running (once you've [installed Planetary.js](/documentation/installation.html)).
Note that you'll need to run this page from a web server of some kind so that Planetary.js can load the TopoJSON data via Ajax (Ajax requests don't work when viewing a page directly from the filesystem).

View File

@ -0,0 +1,97 @@
Installation
============
Once you've [downloaded Planetary.js](/download/), you can include it via a `script` tag on your page *after* the inclusion of D3 and TopoJSON. This example uses the CDN URLs for those libraries:
<div class='ui raised segment'>
<div class='ui blue ribbon label'>HTML</div>
```html
<html>
<head>
<script type='text/javascript' src='http://d3js.org/d3.v3.min.js'></script>
<script type='text/javascript' src='http://d3js.org/topojson.v1.min.js'></script>
<script type='text/javascript' src='path/to/planetaryjs.min.js'></script>
</head>
<body>
...
```
</div>
If you use the default `topojson` plugin (most people will), you'll also need to make sure `world-110m.json` (or some other TopoJSON data file) is available on your server. This file is also available from [the download page](/download/). See the [TopoJSON Plugin documentation](/documentation/builtin_topojson.html) for more information.
Planetary.js also supports installation via AMD and CommonJS loaders.
AMD
---
This example uses [RequireJS](http://requirejs.org/). Since neither D3 nor TopoJSON support AMD, we will use RequireJS's [shim configuration](http://requirejs.org/docs/api.html#config-shim).
<div class='ui raised segment'>
<div class='ui blue ribbon label'>HTML</div>
```html
<body>
<canvas id='globe' width='500' height='500'></canavs>
<script src='//cdnjs.cloudflare.com/ajax/libs/require.js/2.1.9/require.min.js'
data-main='/app.js'></script>
</body>
```
<div class='ui red ribbon label'>JavaScript</div>
```javascript
requirejs.config({
// Tell RequireJS to use `window.d3` and `window.topojson`
// for those libraries, respectively
shim: {
d3: { exports: 'd3' },
topojson: { exports: 'topojson' }
},
paths: {
'd3': 'path/to/d3.v3.min',
'topojson': 'path/to/topojson.v1.min'
}
});
requirejs(['planetaryjs'], function(planetaryjs) {
// Use Planetary.js here
});
```
</div>
CommonJS
--------
First, install `browserify` from npm (as well as `planetary.js` v1.0.2+, if you haven't already). Then, create your application (here referred to as `app.js`) and bundle it with browserify.
<div class='ui raised segment'>
<div class='ui red ribbon label'>JavaScript</div>
```javascript
var planetaryjs = require('planetary.js');
var planet = planetaryjs.planet();
var canvas = document.getElementById('canvas');
planet.draw(canvas);
```
<div class='ui purple ribbon label'>Shell</div>
```shell
$ npm install browserify
$ ./node_modules/.bin/browserify app.js > bundle.js
```
</div>
`bundle.js` is now ready to use! You may need to set the `charset` option on your script tag:
<div class='ui raised segment'>
<div class='ui blue ribbon label'>HTML</div>
```html
<script type='text/javascript' src='bundle.js' charset='utf-8'></script>
```
</div>

View File

@ -94,6 +94,24 @@ planet.onDraw(function() {
```
</div>
**`planet.onStop( function(){} )`**
Registers a function to be called when the planet is stopped with the `stop` method. This can be used to clean up timers and remove references to internal planet properties and plugins, if necessary, so that it can be property garbage collected.
<div class='ui raised segment'>
<div class='ui red ribbon label'>JavaScript</div>
```javascript
var interval = setInterval(function() {
addRandomPing(planet); // uses `planet.plugins.pings`
}, 150);
planet.onStop(function() {
clearInterval(interval);
});
```
</div>
**`planet.withSavedContext( function(context){} )`**
Calls the function with the current canvas context as a parameter, wrapping the function call in `context.save()` and `context.restore()`. Use this function any time you're going to modify the context to ensure it gets put back to the way it was.
@ -119,7 +137,7 @@ Begins drawing the globe onto the given canvas. `canvas` should be a raw DOM ele
Calling `draw` will perform the following operations:
1. Initialize each loaded plugin by calling the plugin function.
1. Initialize each loaded plugin by calling the plugin function (note: this only happens the first time you call `draw`).
2. Set `planet.canvas` and `planet.context` to the canvas and the canvas' context, respectively.
3. Run each registered `onInit` hook in the order it was registered (note that `onInit` calls made by plugins will not be made until step 1, after `draw` has been called).
4. Start the animation loop, each tick clearing the canvas and calling any registered `onDraw` hooks in order.
@ -138,3 +156,21 @@ var canvas = document.getElementById('myCanvas');
planet.draw(canvas);
```
</div>
Once you've called `draw()` on a planet, you should not call it again unless you first call `stop()`.
**`planet.stop()`**
Stop drawing the planet to the canvas. This disables the internal draw loop. You can register functions to call when the planet is stopped using the `onStop` method; if you don't plan on reusing the planet, be sure to clean up timers and references to internal properties, if necessary, so that it can be garbage collected.
You can draw the planet to a new (or the same) canvas using the `draw` method as normal. All your plugins' `onInit` functions will fire, although the plugin function itself will not be called again.
Keep in mind that, since the internal draw loop is stopped, your plugins' `onDraw` functions are not being called. If you have timers or other mechanisms that continually push data into a data structure that an `onDraw` method cleans up, you should disable or pause it.
<div class='ui raised segment'>
<div class='ui red ribbon label'>JavaScript</div>
```javascript
planet.stop();
```
</div>

View File

@ -1,7 +1,7 @@
{
"stable": {
"latest": {
"version": "v1.0.0"
"version": "v1.1.2"
}
},
"unstable": {

View File

@ -191,16 +191,20 @@
// Plugin to resize the canvas to fill the window and to
// automatically center the planet when the window size changes
function autocenter(options) {
options = options || {};
var needsCentering = false;
var globe = null;
var resize = function() {
var width = window.innerWidth + (options.extraWidth || 0);
var height = window.innerHeight + (options.extraHeight || 0);
planet.canvas.width = width;
planet.canvas.height = height;
planet.projection.translate([width / 2, height / 2]);
globe.canvas.width = width;
globe.canvas.height = height;
globe.projection.translate([width / 2, height / 2]);
};
return function(planet) {
globe = planet;
planet.onInit(function() {
needsCentering = true;
d3.select(window).on('resize', function() {
@ -217,6 +221,7 @@
// Plugin to automatically scale the planet's projection based
// on the window size when the planet is initialized
function autoscale(options) {
options = options || {};
return function(planet) {
planet.onInit(function() {
var width = window.innerWidth + (options.extraWidth || 0);

View File

@ -161,16 +161,20 @@
// Plugin to resize the canvas to fill the window and to
// automatically center the planet when the window size changes
function autocenter(options) {
options = options || {};
var needsCentering = false;
var globe = null;
var resize = function() {
var width = window.innerWidth + (options.extraWidth || 0);
var height = window.innerHeight + (options.extraHeight || 0);
planet.canvas.width = width;
planet.canvas.height = height;
planet.projection.translate([width / 2, height / 2]);
globe.canvas.width = width;
globe.canvas.height = height;
globe.projection.translate([width / 2, height / 2]);
};
return function(planet) {
globe = planet;
planet.onInit(function() {
needsCentering = true;
d3.select(window).on('resize', function() {
@ -187,6 +191,7 @@
// Plugin to automatically scale the planet's projection based
// on the window size when the planet is initialized
function autoscale(options) {
options = options || {};
return function(planet) {
planet.onInit(function() {
var width = window.innerWidth + (options.extraWidth || 0);

View File

@ -19,7 +19,7 @@
<div class='ui raised segment'>
<div class='ui blue ribbon label'>HTML</div>
<pre class='line-numbers'><code class='language-html'>&lt;canvas id='basicGlobe' width='400' height='400'
<pre class='line-numbers'><code class='language-html'>&lt;canvas id='rotatingGlobe' width='400' height='400'
style='width: 400px; height: 400px; cursor: move;'&gt;&lt;/canvas&gt;</code></pre>
<div class='ui red ribbon label'>JavaScript</div>

View File

@ -33,7 +33,7 @@
<div class='ui buttons'>
<a class='ui green labeled icon button' href='/download/'><i class='icon download'></i>Download</a>
<div class='or'></div>
<a class='ui labeled button' href='https://github.com/BinaryMuse/planetary.js'>View Source</a>
<a class='ui labeled button' href='https://github.com/BinaryMuse/planetary.js' onclick="_gaq.push(['_trackPageview', '/redirect-to-github-project-page']);">View Source</a>
</div>
<div style='padding-top: 10px;'>
@ -87,12 +87,12 @@
<p><a class='ui orange button' href='/documentation/'>Peruse the Documentation</a></p>
</div>
<div class='column'>
<a class='ui icon header' href='https://github.com/BinaryMuse/planetary.js'>
<a class='ui icon header' href='https://github.com/BinaryMuse/planetary.js' onclick="_gaq.push(['_trackPageview', '/redirect-to-github-project-page']);">
<i class='ui huge icon github alternate'></i>
Source Code
</a>
<p class='section-description'>Take a look at the source on GitHub and contribute to the project</p>
<p><a class='ui purple button' href='https://github.com/BinaryMuse/planetary.js'>Examine the Source</a></p>
<p><a class='ui purple button' href='https://github.com/BinaryMuse/planetary.js' onclick="_gaq.push(['_trackPageview', '/redirect-to-github-project-page']);">Examine the Source</a></p>
</div>
</div>

View File

@ -1,2 +1,2 @@
/*! Planetary.js 1.0.0 | (c) 2013 Brandon Tilley | Released under MIT License */
!function(n,t){"function"==typeof define&&define.amd?define(["d3","topojson"],t):"object"==typeof exports?module.exports=t(require("d3"),require("topojson")):n.planetaryjs=t(n.d3,n.topojson,n)}(this,function(n,t,o){"use strict";var i=null;o&&(i=o.planetaryjs);var e=[],r=function(t,o,i){n.timer(function(){t.context.clearRect(0,0,o.width,o.height);for(var n=0;n<i.onDraw.length;n++)i.onDraw[n]()})},l=function(n,t){for(var o=e.length-1;o>=0;o--)t.unshift(e[o]);for(0===t.length&&(u.plugins.earth&&n.loadPlugin(u.plugins.earth()),u.plugins.pings&&n.loadPlugin(u.plugins.pings())),o=0;o<t.length;o++)t[o](n)},a=function(n,t,o){if(o.onInit.length){var i=0,e=function(n){var t=o.onInit[i];t.length?t(function(){i++,n()}):(t(),i++,setTimeout(n,0))},l=function(){i>=o.onInit.length?r(n,t,o):e(l)};e(l)}else r(n,t,o)},c=function(n,t,o,i){l(n,o),n.canvas=t,n.context=t.getContext("2d"),a(n,t,i)},u={plugins:{},noConflict:function(){return o.planetaryjs=i,u},loadPlugin:function(n){e.push(n)},planet:function(){var t=[],o={onInit:[],onDraw:[]},i={plugins:{},draw:function(n){c(i,n,t,o)},onInit:function(n){o.onInit.push(n)},onDraw:function(n){o.onDraw.push(n)},loadPlugin:function(n){t.push(n)},withSavedContext:function(n){if(!this.context)throw new Error("No canvas to fetch context for");this.context.save(),n(this.context),this.context.restore()}};return i.projection=n.geo.orthographic().clipAngle(90).precision(0),i.path=n.geo.path().projection(i.projection),i}};return u.plugins.topojson=function(t){return function(o){o.plugins.topojson={},o.onInit(function(i){if(t.world)o.plugins.topojson.world=t.world,setTimeout(i,0);else{var e=t.file||"world-110m.json";n.json(e,function(n,t){if(n)throw new Error("Could not load JSON "+e);o.plugins.topojson.world=t,i()})}})}},u.plugins.oceans=function(n){return function(t){t.onDraw(function(){t.withSavedContext(function(o){o.beginPath(),t.path.context(o)({type:"Sphere"}),o.fillStyle=n.fill||"black",o.fill()})})}},u.plugins.land=function(n){return function(o){var i=null;o.onInit(function(){var n=o.plugins.topojson.world;i=t.feature(n,n.objects.land)}),o.onDraw(function(){o.withSavedContext(function(t){t.beginPath(),o.path.context(t)(i),n.fill!==!1&&(t.fillStyle=n.fill||"white",t.fill()),n.stroke&&(n.lineWidth&&(t.lineWidth=n.lineWidth),t.strokeStyle=n.stroke,t.stroke())})})}},u.plugins.borders=function(n){return function(o){var i=null,e={internal:function(n,t){return n.id!==t.id},external:function(n,t){return n.id===t.id},both:function(){return!0}};o.onInit(function(){var r=o.plugins.topojson.world,l=r.objects.countries,a=n.type||"internal";i=t.mesh(r,l,e[a])}),o.onDraw(function(){o.withSavedContext(function(t){t.beginPath(),o.path.context(t)(i),t.strokeStyle=n.stroke||"gray",n.lineWidth&&(t.lineWidth=n.lineWidth),t.stroke()})})}},u.plugins.earth=function(n){n=n||{};var t=n.topojson||{},o=n.oceans||{},i=n.land||{},e=n.borders||{};return function(n){u.plugins.topojson(t)(n),u.plugins.oceans(o)(n),u.plugins.land(i)(n),u.plugins.borders(e)(n)}},u.plugins.pings=function(t){var o=[];t=t||{};var i=function(n,i,e){e=e||{},e.color=e.color||t.color||"white",e.angle=e.angle||t.angle||5,e.ttl=e.ttl||t.ttl||2e3;var r={time:new Date,options:e};t.latitudeFirst?(r.lat=n,r.lng=i):(r.lng=n,r.lat=i),o.push(r)},e=function(n,t,i){for(var e=[],l=0;l<o.length;l++){var a=o[l],c=i-a.time;c<a.options.ttl&&(e.push(a),r(n,t,i,c,a))}o=e},r=function(t,o,i,e,r){var l=1-e/r.options.ttl,a=n.rgb(r.options.color);a="rgba("+a.r+","+a.g+","+a.b+","+l+")",o.strokeStyle=a;var c=n.geo.circle().origin([r.lng,r.lat]).angle(e/r.options.ttl*r.options.angle)();o.beginPath(),t.path.context(o)(c),o.stroke()};return function(n){n.plugins.pings={add:i},n.onDraw(function(){var t=new Date;n.withSavedContext(function(o){e(n,o,t)})})}},u.plugins.zoom=function(t){t=t||{};var o=function(){},i=t.onZoomStart||o,e=t.onZoomEnd||o,r=t.onZoom||o,l=t.afterZoom||o,a=t.initialScale,c=t.scaleExtent||[50,2e3];return function(t){t.onInit(function(){var o=n.behavior.zoom().scaleExtent(c);null!==a&&void 0!==a?o.scale(a):o.scale(t.projection.scale()),o.on("zoomstart",i.bind(t)).on("zoomend",e.bind(t)).on("zoom",function(){r.call(t),t.projection.scale(n.event.scale),l.call(t)}),n.select(t.canvas).call(o)})}},u.plugins.drag=function(t){t=t||{};var o=function(){},i=t.onDragStart||o,e=t.onDragEnd||o,r=t.onDrag||o,l=t.afterDrag||o;return function(t){t.onInit(function(){var o=n.behavior.drag().on("dragstart",i.bind(t)).on("dragend",e.bind(t)).on("drag",function(){r.call(t);var o=n.event.dx,i=n.event.dy,e=t.projection.rotate(),a=t.projection.scale(),c=n.scale.linear().domain([-1*a,a]).range([-90,90]),u=c(o),s=c(i);e[0]+=u,e[1]-=s,e[1]>90&&(e[1]=90),e[1]<-90&&(e[1]=-90),e[0]>=180&&(e[0]-=360),t.projection.rotate(e),l.call(t)});n.select(t.canvas).call(o)})}},u});
/*! Planetary.js 1.1.2 | (c) 2013 Michelle Tilley | Released under MIT License */
!function(n,t){"function"==typeof define&&define.amd?define(["d3","topojson"],function(o,i){return n.planetaryjs=t(o,i,n)}):"object"==typeof exports?module.exports=t(require("d3"),require("topojson")):n.planetaryjs=t(n.d3,n.topojson,n)}(this,function(n,t,o){"use strict";var i=null;o&&(i=o.planetaryjs);var e=[],r=function(t,o,i){n.timer(function(){if(t.stopped)return!0;t.context.clearRect(0,0,o.width,o.height);for(var n=0;n<i.onDraw.length;n++)i.onDraw[n]()})},l=function(n,t){for(var o=e.length-1;o>=0;o--)t.unshift(e[o]);for(0===t.length&&(c.plugins.earth&&n.loadPlugin(c.plugins.earth()),c.plugins.pings&&n.loadPlugin(c.plugins.pings())),o=0;o<t.length;o++)t[o](n)},a=function(n,t,o){if(o.onInit.length){var i=0,e=function(n){var t=o.onInit[i];t.length?t(function(){i++,n()}):(t(),i++,setTimeout(n,0))},l=function(){i>=o.onInit.length?r(n,t,o):e(l)};e(l)}else r(n,t,o)},u=function(n,t,o,i){n.canvas=t,n.context=t.getContext("2d"),n.stopped!==!0&&l(n,o),n.stopped=!1,a(n,t,i)},c={plugins:{},noConflict:function(){return o.planetaryjs=i,c},loadPlugin:function(n){e.push(n)},planet:function(){var t=[],o={onInit:[],onDraw:[],onStop:[]},i={plugins:{},draw:function(n){u(i,n,t,o)},onInit:function(n){o.onInit.push(n)},onDraw:function(n){o.onDraw.push(n)},onStop:function(n){o.onStop.push(n)},loadPlugin:function(n){t.push(n)},stop:function(){i.stopped=!0;for(var n=0;n<o.onStop.length;n++)o.onStop[n](i)},withSavedContext:function(n){if(!this.context)throw new Error("No canvas to fetch context for");this.context.save(),n(this.context),this.context.restore()}};return i.projection=n.geo.orthographic().clipAngle(90),i.path=n.geo.path().projection(i.projection),i}};return c.plugins.topojson=function(t){return function(o){o.plugins.topojson={},o.onInit(function(i){if(t.world)o.plugins.topojson.world=t.world,setTimeout(i,0);else{var e=t.file||"world-110m.json";n.json(e,function(n,t){if(n)throw new Error("Could not load JSON "+e);o.plugins.topojson.world=t,i()})}})}},c.plugins.oceans=function(n){return function(t){t.onDraw(function(){t.withSavedContext(function(o){o.beginPath(),t.path.context(o)({type:"Sphere"}),o.fillStyle=n.fill||"black",o.fill()})})}},c.plugins.land=function(n){return function(o){var i=null;o.onInit(function(){var n=o.plugins.topojson.world;i=t.feature(n,n.objects.land)}),o.onDraw(function(){o.withSavedContext(function(t){t.beginPath(),o.path.context(t)(i),n.fill!==!1&&(t.fillStyle=n.fill||"white",t.fill()),n.stroke&&(n.lineWidth&&(t.lineWidth=n.lineWidth),t.strokeStyle=n.stroke,t.stroke())})})}},c.plugins.borders=function(n){return function(o){var i=null,e={internal:function(n,t){return n.id!==t.id},external:function(n,t){return n.id===t.id},both:function(){return!0}};o.onInit(function(){var r=o.plugins.topojson.world,l=r.objects.countries,a=n.type||"internal";i=t.mesh(r,l,e[a])}),o.onDraw(function(){o.withSavedContext(function(t){t.beginPath(),o.path.context(t)(i),t.strokeStyle=n.stroke||"gray",n.lineWidth&&(t.lineWidth=n.lineWidth),t.stroke()})})}},c.plugins.earth=function(n){n=n||{};var t=n.topojson||{},o=n.oceans||{},i=n.land||{},e=n.borders||{};return function(n){c.plugins.topojson(t)(n),c.plugins.oceans(o)(n),c.plugins.land(i)(n),c.plugins.borders(e)(n)}},c.plugins.pings=function(t){var o=[];t=t||{};var i=function(n,i,e){e=e||{},e.color=e.color||t.color||"white",e.angle=e.angle||t.angle||5,e.ttl=e.ttl||t.ttl||2e3;var r={time:new Date,options:e};t.latitudeFirst?(r.lat=n,r.lng=i):(r.lng=n,r.lat=i),o.push(r)},e=function(n,t,i){for(var e=[],l=0;l<o.length;l++){var a=o[l],u=i-a.time;u<a.options.ttl&&(e.push(a),r(n,t,i,u,a))}o=e},r=function(t,o,i,e,r){var l=1-e/r.options.ttl,a=n.rgb(r.options.color);a="rgba("+a.r+","+a.g+","+a.b+","+l+")",o.strokeStyle=a;var u=n.geo.circle().origin([r.lng,r.lat]).angle(e/r.options.ttl*r.options.angle)();o.beginPath(),t.path.context(o)(u),o.stroke()};return function(n){n.plugins.pings={add:i},n.onDraw(function(){var t=new Date;n.withSavedContext(function(o){e(n,o,t)})})}},c.plugins.zoom=function(t){t=t||{};var o=function(){},i=t.onZoomStart||o,e=t.onZoomEnd||o,r=t.onZoom||o,l=t.afterZoom||o,a=t.initialScale,u=t.scaleExtent||[50,2e3];return function(t){t.onInit(function(){var o=n.behavior.zoom().scaleExtent(u);o.scale(null!==a&&void 0!==a?a:t.projection.scale()),o.on("zoomstart",i.bind(t)).on("zoomend",e.bind(t)).on("zoom",function(){r.call(t),t.projection.scale(n.event.scale),l.call(t)}),n.select(t.canvas).call(o)})}},c.plugins.drag=function(t){t=t||{};var o=function(){},i=t.onDragStart||o,e=t.onDragEnd||o,r=t.onDrag||o,l=t.afterDrag||o;return function(t){t.onInit(function(){var o=n.behavior.drag().on("dragstart",i.bind(t)).on("dragend",e.bind(t)).on("drag",function(){r.call(t);var o=n.event.dx,i=n.event.dy,e=t.projection.rotate(),a=t.projection.scale(),u=n.scale.linear().domain([-1*a,a]).range([-90,90]),c=u(o),s=u(i);e[0]+=c,e[1]-=s,e[1]>90&&(e[1]=90),e[1]<-90&&(e[1]=-90),e[0]>=180&&(e[0]-=360),t.projection.rotate(e),l.call(t)});n.select(t.canvas).call(o)})}},c});

View File

@ -1,6 +1,8 @@
(function (root, factory) {
if (typeof define === 'function' && define.amd) {
define(['d3', 'topojson'], factory);
define(['d3', 'topojson'], function(d3, topojson) {
return (root.planetaryjs = factory(d3, topojson, root));
});
} else if (typeof exports === 'object') {
module.exports = factory(require('d3'), require('topojson'));
} else {

View File

@ -4,6 +4,10 @@
var doDrawLoop = function(planet, canvas, hooks) {
d3.timer(function() {
if (planet.stopped) {
return true;
}
planet.context.clearRect(0, 0, canvas.width, canvas.height);
for (var i = 0; i < hooks.onDraw.length; i++) {
hooks.onDraw[i]();
@ -59,11 +63,14 @@
};
var startDraw = function(planet, canvas, localPlugins, hooks) {
initPlugins(planet, localPlugins);
planet.canvas = canvas;
planet.context = canvas.getContext('2d');
if (planet.stopped !== true) {
initPlugins(planet, localPlugins);
}
planet.stopped = false;
runOnInitHooks(planet, canvas, hooks);
};
@ -83,7 +90,8 @@
var localPlugins = [];
var hooks = {
onInit: [],
onDraw: []
onDraw: [],
onStop: []
};
var planet = {
@ -101,10 +109,21 @@
hooks.onDraw.push(fn);
},
onStop: function(fn) {
hooks.onStop.push(fn);
},
loadPlugin: function(plugin) {
localPlugins.push(plugin);
},
stop: function() {
planet.stopped = true;
for (var i = 0; i < hooks.onStop.length; i++) {
hooks.onStop[i](planet);
}
},
withSavedContext: function(fn) {
if (!this.context) {
throw new Error("No canvas to fetch context for");
@ -117,8 +136,7 @@
};
planet.projection = d3.geo.orthographic()
.clipAngle(90)
.precision(0);
.clipAngle(90);
planet.path = d3.geo.path().projection(planet.projection);
return planet;