is the first planet from the Sun and is also the smallest and densest planet of the Solar System. Mercury has yet to be entirely mapped, making it the least known planet in our system.
+
+
+
+
Mercury Observation Progress
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ Venus
+
+
is the second planet from the Sun and is often called Earth's sister due to its many similarities with the Blue Planet. However, a strong greenhouse effect gives Venus the hottest climate in the Solar System.
+
+
+
+
65 KM
+ -100°C
+ Sulfuric Acid Cloud Layers
+
+
50 KM
+ 0°C
+ Sulfuric Acid Haze
+
+
38 KM
+ 25°C
+ Troposphere
+
+
0 KM
+ 467°C
+ Surface Level
+
+
+
+
+
+
+
+
+ Earth
+
+
is the third planet from the Sun, and the densest and fifth-largest of the eight planets in the Solar System. Sometimes referred to as the Blue Planet, Earth is the only known planet to harbor life.
+
+
+
+
+
+
+
+
+ 5.9736 x 1024 kg
+ That's 80 times the mass of the moon
+
+
+
+ 40,075,16 km
+ Equatorial circumference
+
+
+
+ 365 days
+ Complete Orbital Period
+
+
+
+ -89.2°C to 57.8°C
+ Temperature range
+
+
+
+
+
+
+
+
+ Mars
+
+
is the fourth planet from the Sun. Named after the Roman god of war, Mars is often described as the "Red Planet" and is the site of Olympus Mons, the highest known mountain in the Solar System.
+
+
+
+
Olympus Mons27,000 KM
+
Mount Everest8,848 KM
+
Mount Fuji3,776 KM
+
+
+
+
+
+
+
+ Jupiter
+
+
is the fifth planet from the Sun and is the largest planet of the Solar System. Jupiter has 63 known satellites, the biggest of which are called the four Galilean Moons : Io, Europa, Ganymede and Callisto.
+
+
+
+
+ IO
+ Land of Volcanoes
+
+
+ EUROPA
+ Ice Ice Baby
+
+
+ GANYMEDE
+ Larger than Mercury
+
+
+ CALLISTO
+ The Habitable Moon ?
+
+
+
+
+
+
+
+
+
+ Saturn
+
+
is the sixth planet from the Sun and is the second largest planet in our system. Despite its size (9.4 Earths), Saturn's density is so low that it would float on water if there was a large enough ocean.
+
+
+
+
The origin of Saturn's rings
+
Almost entirely composed of water ice, Saturn's rings are believed to be the remains of a former moon.
+
+
1
+
+
+
+
2
+
+
+
+
3
+
+
+
+
+
+
+
+
+
+
+
+ Uranus
+
+
is the seventh planet from the Sun and is the coldest in the Solar System. Altough the first pictures taken by Voyager 2 showed a featureless, pale-blue planet, astronomers later discovered the complex atmosphere of Uranus.
+
+
+
+
Axial Tilt
+
+ 98°
+
+
+
The atmosphere of uranus
+
+
+
+
+ 85.3%
+ Hydrogen
+
+
+
+
+
+
+ 15.3%
+ Helium
+
+
+
+
+
+
+ 2.3%
+ Methane
+
+
+
+
+
+
+ 0.01%
+ Hydrogen Deuteride
+
+
+
+
+
+
+
+
+
+ Neptune
+
+
is the eighth and farthest planet from the sun. Neptune has been approached only once by a man-made object, Voyager 2 space probe, in 1989. Most of our knowledge of Neptune comes from this first and only flyby.
+
+
+
+
+ 2100 km/h
+
+ max wind speed
+
+
+ 13 known satellites
+
+ and counting
+
+
+ 164 earth years
+
+ per neptunian year
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/planetarium/fonts/BEBAS___-webfont.ttf b/planetarium/fonts/BEBAS___-webfont.ttf
new file mode 100755
index 0000000..800b51e
Binary files /dev/null and b/planetarium/fonts/BEBAS___-webfont.ttf differ
diff --git a/planetarium/fonts/CartoGothicStd-Book-webfont.ttf b/planetarium/fonts/CartoGothicStd-Book-webfont.ttf
new file mode 100644
index 0000000..097a7cd
Binary files /dev/null and b/planetarium/fonts/CartoGothicStd-Book-webfont.ttf differ
diff --git a/planetarium/fonts/CartoGothicStd-Book-webfont.woff b/planetarium/fonts/CartoGothicStd-Book-webfont.woff
new file mode 100644
index 0000000..96e780b
Binary files /dev/null and b/planetarium/fonts/CartoGothicStd-Book-webfont.woff differ
diff --git a/planetarium/fonts/Franchise-Bold.ttf b/planetarium/fonts/Franchise-Bold.ttf
new file mode 100755
index 0000000..75d0b33
Binary files /dev/null and b/planetarium/fonts/Franchise-Bold.ttf differ
diff --git a/planetarium/fonts/MarketingScript.ttf b/planetarium/fonts/MarketingScript.ttf
new file mode 100644
index 0000000..23ac028
Binary files /dev/null and b/planetarium/fonts/MarketingScript.ttf differ
diff --git a/planetarium/img/246min.png b/planetarium/img/246min.png
new file mode 100644
index 0000000..98dfe29
Binary files /dev/null and b/planetarium/img/246min.png differ
diff --git a/planetarium/img/30years.png b/planetarium/img/30years.png
new file mode 100644
index 0000000..dadba8a
Binary files /dev/null and b/planetarium/img/30years.png differ
diff --git a/planetarium/img/astronauts.png b/planetarium/img/astronauts.png
new file mode 100644
index 0000000..d5d1643
Binary files /dev/null and b/planetarium/img/astronauts.png differ
diff --git a/planetarium/img/bg.jpg b/planetarium/img/bg.jpg
new file mode 100644
index 0000000..61cb12f
Binary files /dev/null and b/planetarium/img/bg.jpg differ
diff --git a/planetarium/img/callistopicto.png b/planetarium/img/callistopicto.png
new file mode 100644
index 0000000..a3472ac
Binary files /dev/null and b/planetarium/img/callistopicto.png differ
diff --git a/planetarium/img/distance.png b/planetarium/img/distance.png
new file mode 100644
index 0000000..72f2b87
Binary files /dev/null and b/planetarium/img/distance.png differ
diff --git a/planetarium/img/doorlight.png b/planetarium/img/doorlight.png
new file mode 100644
index 0000000..44bcc12
Binary files /dev/null and b/planetarium/img/doorlight.png differ
diff --git a/planetarium/img/earth.jpg b/planetarium/img/earth.jpg
new file mode 100644
index 0000000..ae483a4
Binary files /dev/null and b/planetarium/img/earth.jpg differ
diff --git a/planetarium/img/earthicon.png b/planetarium/img/earthicon.png
new file mode 100644
index 0000000..ebaa1f9
Binary files /dev/null and b/planetarium/img/earthicon.png differ
diff --git a/planetarium/img/europapicto.png b/planetarium/img/europapicto.png
new file mode 100644
index 0000000..8db2963
Binary files /dev/null and b/planetarium/img/europapicto.png differ
diff --git a/planetarium/img/everest.png b/planetarium/img/everest.png
new file mode 100644
index 0000000..ea25f99
Binary files /dev/null and b/planetarium/img/everest.png differ
diff --git a/planetarium/img/fuji.png b/planetarium/img/fuji.png
new file mode 100644
index 0000000..2e494ac
Binary files /dev/null and b/planetarium/img/fuji.png differ
diff --git a/planetarium/img/ganymedepicto.png b/planetarium/img/ganymedepicto.png
new file mode 100644
index 0000000..b66cc60
Binary files /dev/null and b/planetarium/img/ganymedepicto.png differ
diff --git a/planetarium/img/glow.png b/planetarium/img/glow.png
new file mode 100644
index 0000000..84d8453
Binary files /dev/null and b/planetarium/img/glow.png differ
diff --git a/planetarium/img/grid.png b/planetarium/img/grid.png
new file mode 100644
index 0000000..6ec9206
Binary files /dev/null and b/planetarium/img/grid.png differ
diff --git a/planetarium/img/iopicto.png b/planetarium/img/iopicto.png
new file mode 100644
index 0000000..a5164fb
Binary files /dev/null and b/planetarium/img/iopicto.png differ
diff --git a/planetarium/img/jupiter.jpg b/planetarium/img/jupiter.jpg
new file mode 100644
index 0000000..3f9a7bc
Binary files /dev/null and b/planetarium/img/jupiter.jpg differ
diff --git a/planetarium/img/mariner10.png b/planetarium/img/mariner10.png
new file mode 100644
index 0000000..9de8907
Binary files /dev/null and b/planetarium/img/mariner10.png differ
diff --git a/planetarium/img/mars.jpg b/planetarium/img/mars.jpg
new file mode 100644
index 0000000..475f424
Binary files /dev/null and b/planetarium/img/mars.jpg differ
diff --git a/planetarium/img/mass.svg b/planetarium/img/mass.svg
new file mode 100644
index 0000000..da31e4c
--- /dev/null
+++ b/planetarium/img/mass.svg
@@ -0,0 +1,15 @@
+
+
+
+
diff --git a/planetarium/img/mercury.jpg b/planetarium/img/mercury.jpg
new file mode 100644
index 0000000..028c287
Binary files /dev/null and b/planetarium/img/mercury.jpg differ
diff --git a/planetarium/img/mercuryobs1.png b/planetarium/img/mercuryobs1.png
new file mode 100644
index 0000000..4bd3c59
Binary files /dev/null and b/planetarium/img/mercuryobs1.png differ
diff --git a/planetarium/img/mercuryobs2.png b/planetarium/img/mercuryobs2.png
new file mode 100644
index 0000000..5a57e4a
Binary files /dev/null and b/planetarium/img/mercuryobs2.png differ
diff --git a/planetarium/img/mercuryobs3.png b/planetarium/img/mercuryobs3.png
new file mode 100644
index 0000000..b6f2aeb
Binary files /dev/null and b/planetarium/img/mercuryobs3.png differ
diff --git a/planetarium/img/messenger.png b/planetarium/img/messenger.png
new file mode 100644
index 0000000..dcfbd42
Binary files /dev/null and b/planetarium/img/messenger.png differ
diff --git a/planetarium/img/neptune.jpg b/planetarium/img/neptune.jpg
new file mode 100644
index 0000000..786d8fc
Binary files /dev/null and b/planetarium/img/neptune.jpg differ
diff --git a/planetarium/img/olympus.png b/planetarium/img/olympus.png
new file mode 100644
index 0000000..8343a92
Binary files /dev/null and b/planetarium/img/olympus.png differ
diff --git a/planetarium/img/perimeter.svg b/planetarium/img/perimeter.svg
new file mode 100644
index 0000000..dc2b158
--- /dev/null
+++ b/planetarium/img/perimeter.svg
@@ -0,0 +1,12 @@
+
+
+
+
diff --git a/planetarium/img/previous.svg b/planetarium/img/previous.svg
new file mode 100644
index 0000000..55fc17b
--- /dev/null
+++ b/planetarium/img/previous.svg
@@ -0,0 +1,8 @@
+
+
+
+
diff --git a/planetarium/img/reflect.png b/planetarium/img/reflect.png
new file mode 100644
index 0000000..196807a
Binary files /dev/null and b/planetarium/img/reflect.png differ
diff --git a/planetarium/img/revolution.svg b/planetarium/img/revolution.svg
new file mode 100644
index 0000000..e396acb
--- /dev/null
+++ b/planetarium/img/revolution.svg
@@ -0,0 +1,16 @@
+
+
+
+
diff --git a/planetarium/img/rings1.png b/planetarium/img/rings1.png
new file mode 100644
index 0000000..f4cf65c
Binary files /dev/null and b/planetarium/img/rings1.png differ
diff --git a/planetarium/img/rings2.png b/planetarium/img/rings2.png
new file mode 100644
index 0000000..4291e79
Binary files /dev/null and b/planetarium/img/rings2.png differ
diff --git a/planetarium/img/rings3.png b/planetarium/img/rings3.png
new file mode 100644
index 0000000..6c928bf
Binary files /dev/null and b/planetarium/img/rings3.png differ
diff --git a/planetarium/img/ruler.png b/planetarium/img/ruler.png
new file mode 100644
index 0000000..0468d06
Binary files /dev/null and b/planetarium/img/ruler.png differ
diff --git a/planetarium/img/satellite.png b/planetarium/img/satellite.png
new file mode 100644
index 0000000..eb92add
Binary files /dev/null and b/planetarium/img/satellite.png differ
diff --git a/planetarium/img/saturn-arrow1.png b/planetarium/img/saturn-arrow1.png
new file mode 100644
index 0000000..821afc3
Binary files /dev/null and b/planetarium/img/saturn-arrow1.png differ
diff --git a/planetarium/img/saturn-arrow2.png b/planetarium/img/saturn-arrow2.png
new file mode 100644
index 0000000..5b1cde1
Binary files /dev/null and b/planetarium/img/saturn-arrow2.png differ
diff --git a/planetarium/img/saturn-arrow3.png b/planetarium/img/saturn-arrow3.png
new file mode 100644
index 0000000..3eee8a9
Binary files /dev/null and b/planetarium/img/saturn-arrow3.png differ
diff --git a/planetarium/img/saturn.png b/planetarium/img/saturn.png
new file mode 100644
index 0000000..9dff926
Binary files /dev/null and b/planetarium/img/saturn.png differ
diff --git a/planetarium/img/spinner.gif b/planetarium/img/spinner.gif
new file mode 100644
index 0000000..c95d05a
Binary files /dev/null and b/planetarium/img/spinner.gif differ
diff --git a/planetarium/img/temperature.svg b/planetarium/img/temperature.svg
new file mode 100644
index 0000000..8ad9a41
--- /dev/null
+++ b/planetarium/img/temperature.svg
@@ -0,0 +1,19 @@
+
+
+
+
diff --git a/planetarium/img/tilt.png b/planetarium/img/tilt.png
new file mode 100644
index 0000000..8731d56
Binary files /dev/null and b/planetarium/img/tilt.png differ
diff --git a/planetarium/img/time.png b/planetarium/img/time.png
new file mode 100644
index 0000000..8ac701e
Binary files /dev/null and b/planetarium/img/time.png differ
diff --git a/planetarium/img/uranus.png b/planetarium/img/uranus.png
new file mode 100644
index 0000000..db61a8a
Binary files /dev/null and b/planetarium/img/uranus.png differ
diff --git a/planetarium/img/venus.jpg b/planetarium/img/venus.jpg
new file mode 100644
index 0000000..8ad1abe
Binary files /dev/null and b/planetarium/img/venus.jpg differ
diff --git a/planetarium/img/venussurface.png b/planetarium/img/venussurface.png
new file mode 100644
index 0000000..f0c571b
Binary files /dev/null and b/planetarium/img/venussurface.png differ
diff --git a/planetarium/img/voyager2.png b/planetarium/img/voyager2.png
new file mode 100644
index 0000000..bb6c10b
Binary files /dev/null and b/planetarium/img/voyager2.png differ
diff --git a/planetarium/img/wind.png b/planetarium/img/wind.png
new file mode 100644
index 0000000..c9528d6
Binary files /dev/null and b/planetarium/img/wind.png differ
diff --git a/planetarium/js/build.js b/planetarium/js/build.js
new file mode 100644
index 0000000..4868ae3
--- /dev/null
+++ b/planetarium/js/build.js
@@ -0,0 +1,18 @@
+({
+ appDir: "../",
+ baseUrl: "js/",
+ dir: "../../planetarium-build",
+ optimize: "closure",
+ optimizeCss: "none",
+
+ paths: {
+ "jquery": "require-jquery-1.4.4.min"
+ },
+
+ modules: [
+ {
+ name: "main",
+ exclude: ["jquery"]
+ }
+ ]
+})
\ No newline at end of file
diff --git a/planetarium/js/camera.js b/planetarium/js/camera.js
new file mode 100644
index 0000000..b539cf3
--- /dev/null
+++ b/planetarium/js/camera.js
@@ -0,0 +1,105 @@
+
+define(["constants"], function(Constants) {
+
+ var Camera = Class.extend({
+
+ init: function(system) {
+ this.w = 0;
+ this.h = 0;
+ this.system = system;
+ this._focusedPlanet = this.system.getPlanet("mars");
+ this._focusPlanetIndex = 0;
+ this.currentView = Constants.VIEW.SYSTEM;
+
+ this.resize();
+ },
+
+ update: function() {
+ this.resize();
+
+ if (this.currentView === Constants.VIEW.PLANET) {
+ this.changeToPlanetView();
+ }
+ if (this.currentView === Constants.VIEW.SYSTEM) {
+ this.changeToSystemView();
+ }
+ },
+
+ resize: function() {
+ this.w = $(window).width();
+ this.h = $(window).height();
+ },
+
+ /**
+ * Centers and zooms on a specific planet.
+ * By scaling and moving the whole solar system we simulate a zooming effect and a camera movement.
+ */
+ focusPlanet: function(planetName) {
+ var planet = this.system.getPlanet(planetName),
+ s = 1;
+
+ this._focusedPlanet = planet;
+ this._focusedPlanetIndex = this.system.getPlanetIndex(planetName);
+
+ if(this.w < 1100) {
+ s = 0.6;
+ } else if(this.w < 1300) {
+ s = 0.8;
+ } else if(this.w < 1500) {
+ s = 0.9;
+ }
+
+ var m = (1 / planet.m) * s; // System scale factor when the focused planet is at scale 1
+ this.system.scale(m);
+
+ this.system.distance = this.w;
+ var distanceFromLeftToPlanet = this.system.getDistanceTo(planetName);
+
+ var x = -distanceFromLeftToPlanet - Constants.IMG_SIZE * s;
+ var y = (this.h / 2) - (Constants.IMG_SIZE / 2); // The focused planet must be in the center of the Y axis
+ this.system.move(x, y);
+
+ this.currentView = Constants.VIEW.PLANET;
+ },
+
+ focusPlanetIndex: function(index) {
+ var planet = this.system.getPlanetAt(index);
+ this.focusPlanet(planet.getName());
+ },
+
+ focusNextPlanet: function() {
+ var newIndex = this._focusedPlanetIndex + 1;
+ var lastPlanetIndex = this.system.getNbPlanets() - 1;
+ this.focusPlanetIndex(newIndex > lastPlanetIndex ? lastPlanetIndex : newIndex);
+ },
+
+ focusPreviousPlanet: function() {
+ var newIndex = this._focusedPlanetIndex - 1;
+ this.focusPlanetIndex(newIndex < 0 ? 0 : newIndex);
+ },
+
+ getFocusedPlanet: function() {
+ return this._focusedPlanet;
+ },
+
+ setFocusedPlanet: function(name) {
+ this._focusedPlanet = this.system.getPlanet(name);
+ },
+
+ changeToSystemView: function() {
+ this.currentView = Constants.VIEW.SYSTEM;
+ this.system.fit(this.w, this.h);
+ },
+
+ changeToPlanetView: function() {
+ this.currentView = Constants.VIEW.PLANET;
+ this.focusPlanet(this._focusedPlanet.getName());
+ },
+
+ getCurrentView: function() {
+ return this.currentView;
+ }
+ });
+
+ return Camera;
+});
diff --git a/planetarium/js/class.js b/planetarium/js/class.js
new file mode 100644
index 0000000..8894389
--- /dev/null
+++ b/planetarium/js/class.js
@@ -0,0 +1,64 @@
+/* Simple JavaScript Inheritance
+ * By John Resig http://ejohn.org/
+ * MIT Licensed.
+ */
+// Inspired by base2 and Prototype
+(function(){
+ var initializing = false, fnTest = /xyz/.test(function(){xyz;}) ? /\b_super\b/ : /.*/;
+
+ // The base Class implementation (does nothing)
+ this.Class = function(){};
+
+ // Create a new Class that inherits from this class
+ Class.extend = function(prop) {
+ var _super = this.prototype;
+
+ // Instantiate a base class (but only create the instance,
+ // don't run the init constructor)
+ initializing = true;
+ var prototype = new this();
+ initializing = false;
+
+ // Copy the properties over onto the new prototype
+ for (var name in prop) {
+ // Check if we're overwriting an existing function
+ prototype[name] = typeof prop[name] == "function" &&
+ typeof _super[name] == "function" && fnTest.test(prop[name]) ?
+ (function(name, fn){
+ return function() {
+ var tmp = this._super;
+
+ // Add a new ._super() method that is the same method
+ // but on the super-class
+ this._super = _super[name];
+
+ // The method only need to be bound temporarily, so we
+ // remove it when we're done executing
+ var ret = fn.apply(this, arguments);
+ this._super = tmp;
+
+ return ret;
+ };
+ })(name, prop[name]) :
+ prop[name];
+ }
+
+ // The dummy class constructor
+ function Class() {
+ // All construction is actually done in the init method
+ if ( !initializing && this.init )
+ this.init.apply(this, arguments);
+ }
+
+ // Populate our constructed prototype object
+ Class.prototype = prototype;
+
+ // Enforce the constructor to be what we expect
+ Class.constructor = Class;
+
+ // And make this class extendable
+ Class.extend = arguments.callee;
+
+ return Class;
+ };
+})();
diff --git a/planetarium/js/constants.js b/planetarium/js/constants.js
new file mode 100644
index 0000000..3141d89
--- /dev/null
+++ b/planetarium/js/constants.js
@@ -0,0 +1,17 @@
+
+define({
+ // Camera view
+ VIEW: {
+ PLANET: 0,
+ SYSTEM: 1
+ },
+
+ /**
+ * Planet JPEG file size in pixels
+ * @type {number}
+ */
+ IMG_SIZE: 600,
+
+ // Miscellaneous
+ TRANSITION_END: "transitionend webkitTransitionEnd oTransitionEnd"
+});
\ No newline at end of file
diff --git a/planetarium/js/counter.js b/planetarium/js/counter.js
new file mode 100644
index 0000000..74845a3
--- /dev/null
+++ b/planetarium/js/counter.js
@@ -0,0 +1,72 @@
+
+define(["jquery"], function($) {
+
+ var Counter = Class.extend({
+ UPDATE_FREQ: 40,
+
+ init: function(container, start, end, zeroes) {
+ this.start = start;
+ this.end = end;
+ this.zeroes = zeroes || 0;
+
+ if(container) {
+ this.el = document.createElement("div");
+ container.appendChild(this.el);
+ $(this.el).css("opacity", start < end ? start/end : 1);
+ }
+ },
+
+ onStep: function(callback) {
+ this.stepCallback = callback;
+ },
+
+ onStop: function(callback) {
+ this.stopCallback = callback;
+ },
+
+ zeroFill: function(number, width) {
+ width -= number.toString().length;
+ if (width > 0) {
+ return new Array( width + (/\./.test( number ) ? 2 : 1) ).join( '0' ) + number;
+ }
+ return number;
+ },
+
+ run: function() {
+ var self = this,
+ start = this.start,
+ end = this.end;
+
+ setTimeout(function() {
+ $(self.el).css("opacity", start < end ? 1 : end/start);
+ }, 50);
+
+ var updater = setInterval(function() {
+ var value = Math.round($(self.el).css("opacity") * (start < end ? end : start));
+ value = self.zeroes > 0 ? self.zeroFill(value, self.zeroes) : value;
+ if(self.stepCallback) {
+ self.stepCallback(value);
+ }
+ if(self.finished) {
+ clearInterval(updater);
+ }
+ }, this.UPDATE_FREQ);
+
+ var stop = function() {
+ self.finished = true;
+ if(self.stopCallback) {
+ self.stopCallback();
+ }
+ };
+ this.el.addEventListener("transitionend", stop, true);
+ this.el.addEventListener("webkitTransitionEnd", stop, true);
+ this.el.addEventListener("oTransitionEnd", stop, true);
+ },
+
+ stop: function() {
+ this.finished = true;
+ }
+ });
+
+ return Counter;
+});
diff --git a/planetarium/js/init.js b/planetarium/js/init.js
new file mode 100644
index 0000000..676327d
--- /dev/null
+++ b/planetarium/js/init.js
@@ -0,0 +1,242 @@
+
+define(["jquery", "constants", "planetarium"], function($, Constants, Planetarium) {
+
+ $(document).ready(function() {
+ var demo = null,
+ readyToFadeIn = false,
+
+ messageHandlers = {
+ start_demo: function() {
+ var waiting = setInterval(function() {
+ if(readyToFadeIn) {
+ playFadeInIntro();
+ clearInterval(waiting);
+ } else {
+ log.debug("Loading assets...");
+ }
+ }, 100);
+ },
+ stop_demo: function() {
+ postToParent("finished_exit");
+ }
+ },
+
+ postToParent = function(message) {
+ window.parent.postMessage(message, '*');
+ log.debug("Sent : "+message);
+ },
+
+ initDemo = function() {
+ window.addEventListener("message", function(event) {
+ var message = event.data;
+ if(message in messageHandlers) {
+ log.debug("Received : " + message);
+ messageHandlers[message]();
+ }
+ }, false);
+
+ $(document).bind("keydown", function() { return false; }); // Prevent any keyboard interaction while the demo is loading
+
+ postToParent("loaded"); // Tell the demo gallery we're ready to go
+ loadImages(onImagesLoaded);
+
+ if(window === window.top) {
+ // If we're not in a iframe, fake an incoming message from the demo gallery
+ window.postMessage("start_demo", '*');
+ }
+ },
+
+ loadImages = function(onload_callback) {
+ var images = ["mercury.jpg", "venus.jpg", "earth.jpg", "mars.jpg", "jupiter.jpg", "saturn.png", "uranus.png", "neptune.jpg"],
+ loadedCount = 0;
+
+ for(var i=0, nb=images.length; i < nb; i += 1) {
+ var filename = images[i],
+ name = filename.split('.')[0],
+ filetype = filename.split('.')[1],
+ $li = $("#"+ name),
+ $div = $(""),
+ $img = $("");
+
+ if(filetype === "png") { // PNGs don't need a clipmask
+ $li.append($img);
+ } else {
+ $div.append($img);
+ $li.append($div);
+ }
+
+ $img.bind("load", function () {
+ loadedCount += 1;
+ if(loadedCount === nb) {
+ setTimeout(function() {
+ onload_callback();
+ }, 1000); // Fake loading time
+ }
+ });
+ }
+ },
+
+ startDemo = function(ready_callback) {
+ demo = new Planetarium();
+ demo.onChangeView(function(view) {
+ if(view === Constants.VIEW.SYSTEM) {
+ postToParent("show_exit_ui");
+ } else {
+ postToParent("hide_exit_ui");
+ }
+ });
+ demo.run();
+
+ $("#previous").click(function() {
+ demo.previousPlanet();
+ });
+
+ $("#next").click(function() {
+ demo.nextPlanet();
+ });
+
+ $("#back").click(function() {
+ if(demo.getCurrentView() === Constants.VIEW.PLANET) {
+ demo.showSystemView();
+ }
+ });
+
+ $("li.planet").click(function() {
+ if(demo.getCurrentView() === Constants.VIEW.SYSTEM) {
+ demo.zoomOnPlanet(this.id);
+ }
+ });
+
+ $("#moveleft").mousemove(function(e){
+ var y = e.pageY;
+ $("#previous").css("top" , y + "px");
+ });
+
+ $("#moveleft").mouseleave(function() {
+ $("#previous").css("top" , "50%");
+ });
+
+ $("#moveright").mousemove(function(e){
+ var y = e.pageY;
+ $("#next").css("top" , y + "px");
+ });
+
+ $("#moveright").mouseleave(function() {
+ $("#next").css("top" , "50%");
+ });
+
+ var toggleCredits = function() {
+ var $togglespan = $("#toggle-credits span");
+
+ if($("body").hasClass("showcredits")) {
+ $togglespan.html("back to demo");
+ } else {
+ $togglespan.html("view credits");
+ }
+ };
+
+ $("#toggle-credits").click(function() {
+ var $body = $("body");
+
+ if($body.hasClass("showcredits")) {
+ $("ul#planets").addClass("delayed");
+ $("#instructions").addClass("delayed");
+ $("#credits").removeClass("alwaysontop");
+ $body.removeClass("showcredits");
+
+ setTimeout(function() {
+ $("ul#planets").removeClass("delayed");
+ $("#instructions").removeClass("delayed");
+ }, 1000);
+
+ } else {
+ $body.addClass("showcredits");
+
+ setTimeout(function() {
+ $("#credits").addClass("alwaysontop");
+ }, 1000);
+ }
+
+ toggleCredits();
+ });
+
+ $("#title").click(function() {
+ var $body = $("body");
+
+ if($body.hasClass("showcredits")) {
+ $("ul#planets").addClass("delayed");
+ $("#instructions").addClass("delayed");
+ $("#credits").removeClass("alwaysontop");
+ $body.removeClass("showcredits");
+
+ setTimeout(function() {
+ $("#instructions").removeClass("delayed");
+ $("ul#planets").removeClass("delayed");
+ }, 1000);
+ }
+
+ toggleCredits();
+ });
+
+ $(window).resize(function() {
+ demo.refresh();
+ });
+
+ $(document).unbind("keydown").bind("keydown", function(e) {
+ var key = e.which;
+ var keys = [32, 37, 38, 39, 40];
+
+ if(keys.indexOf(key) !== -1) {
+ switch(key) {
+ case 32: // Spacebar
+ break;
+ case 37: // Left
+ demo.previousPlanet();
+ break;
+ case 39: // Right
+ demo.nextPlanet();
+ break;
+ case 38: // Up
+ if(demo.getCurrentView() === Constants.VIEW.SYSTEM) {
+ demo.showPlanetView();
+ }
+ break;
+ case 40: // Down
+ if(demo.getCurrentView() === Constants.VIEW.PLANET) {
+ demo.showSystemView();
+ }
+ break;
+ }
+ return false;
+ }
+ });
+
+ ready_callback();
+ },
+
+ onImagesLoaded = function() {
+ startDemo(function() {
+ readyToFadeIn = true;
+ });
+ },
+
+ playFadeInIntro = function() {
+ $("#spinner").remove();
+ $("#planets").removeClass("loading");
+ setTimeout(function() {
+ $("#instructions").removeClass("loading");
+ setTimeout(function() {
+ $("#toggle-credits").removeClass("loading");
+ }, 800);
+ }, 1000);
+ };
+
+ initDemo();
+ });
+
+ $(window).mousedown(function(e) {
+ if(e.which === 2) {
+ e.preventDefault();
+ }
+ });
+});
diff --git a/planetarium/js/log.js b/planetarium/js/log.js
new file mode 100644
index 0000000..d20fd5d
--- /dev/null
+++ b/planetarium/js/log.js
@@ -0,0 +1,26 @@
+
+var log = {
+ level: "info",
+
+ info: function(message) {
+ if(this.level === "info" || this.level === "debug") {
+ if(window.console) {
+ console.info(message);
+ }
+ }
+ },
+
+ debug: function(message) {
+ if(this.level === "debug") {
+ if(window.console) {
+ console.log(message);
+ }
+ }
+ },
+
+ error: function(message) {
+ if(window.console) {
+ console.error(message);
+ }
+ }
+};
\ No newline at end of file
diff --git a/planetarium/js/main.js b/planetarium/js/main.js
new file mode 100644
index 0000000..c6cfaf1
--- /dev/null
+++ b/planetarium/js/main.js
@@ -0,0 +1,5 @@
+
+define(["class", "log"], function() {
+ log.level = "info";
+ require(["init"]);
+});
\ No newline at end of file
diff --git a/planetarium/js/planet.js b/planetarium/js/planet.js
new file mode 100644
index 0000000..ad8df49
--- /dev/null
+++ b/planetarium/js/planet.js
@@ -0,0 +1,19 @@
+
+define(["transformable", "constants"], function(Transformable, Constants) {
+
+ var Planet = Transformable.extend({
+ getName: function() {
+ return this.id;
+ },
+
+ getDiameter: function(scale) {
+ if (scale === undefined) {
+ scale = 1;
+ }
+ var diameter = Constants.IMG_SIZE * this.m * scale;
+ return diameter;
+ }
+ });
+
+ return Planet;
+});
\ No newline at end of file
diff --git a/planetarium/js/planetarium.js b/planetarium/js/planetarium.js
new file mode 100644
index 0000000..1e3d0fa
--- /dev/null
+++ b/planetarium/js/planetarium.js
@@ -0,0 +1,419 @@
+
+define(["raphael", "constants", "solarsystem", "camera", "satellites", "counter"],
+ function(R, Constants, SolarSystem, Camera, SatelliteSystem, Counter) {
+
+ var Planetarium = Class.extend({
+
+ init: function() {
+ this.started = false;
+ this.moving = false;
+
+ this.currentKm = 0;
+
+ var self = this;
+ var callback = function() {
+ self.moving = false;
+ };
+
+ $("li.planet").bind(Constants.TRANSITION_END, callback);
+ },
+
+ run: function() {
+ this.started = true;
+ this.disableTransitions(); // Disable CSS3 transitions for initial solar system setup
+
+ this.system = new SolarSystem();
+ this.camera = new Camera(this.system);
+
+ this.earthGraph = new EarthSystem("earth-moon", 130, 130, 1.06);
+ this.jupiterGraph = new JupiterSystem("galilean-moons", 500, 330, 0.7);
+
+ this.distanceCounter = null;
+
+ this.earthGraph.draw();
+ this.jupiterGraph.draw();
+
+ this.showSystemView();
+ this.removeHiddenContentForAllPlanets();
+
+ this.enableTransitions();
+
+ this.moving = false;
+ this.userHasZoomedOnce = false;
+ },
+
+ refresh: function() {
+ if(this.started) {
+ this.camera.update();
+ }
+ },
+
+ toggleBodyClass: function() {
+ var view = this.camera.getCurrentView(),
+ planetName = this.camera.getFocusedPlanet().getName();
+
+ if(view === Constants.VIEW.SYSTEM) {
+ $("body").removeClass(planetName).addClass("system");
+ }
+ else { // PLANET_VIEW
+ $("body").addClass(planetName).removeClass("system");
+ }
+ },
+
+ getCurrentView: function() {
+ return this.camera.getCurrentView();
+ },
+
+ onCurrentPlanetTransitionOver: function(callback) {
+ var name = this.camera.getFocusedPlanet().getName(),
+ currentInfo = $("#"+name+"-info"),
+ transitionEndWrapper = function() {
+ callback();
+ currentInfo.unbind(Constants.TRANSITION_END, transitionEndWrapper);
+ };
+
+ currentInfo.bind(Constants.TRANSITION_END, transitionEndWrapper);
+ },
+
+ showSystemView: function() {
+ var self = this;
+
+ if(!this.moving) {
+ this.camera.changeToSystemView();
+ this.toggleBodyClass();
+ this.hidePlanetInfo();
+ this.resetAllOtherPlanets();
+
+ this.onCurrentPlanetTransitionOver(function() {
+ self.removeHiddenContentForAllPlanets();
+ });
+
+ this.moving = true;
+
+ this.updateGalleryUI();
+ }
+ },
+
+ showPlanetView: function() {
+ var self = this;
+
+ if(!this.moving) {
+ this.camera.changeToPlanetView();
+ this.toggleBodyClass();
+ this.hidePlanetsContentOnLeft();
+ this.hidePlanetsContentOnRight();
+
+ this.showPlanetInfo();
+
+ this.onCurrentPlanetTransitionOver(function() {
+ self.removeHiddenContentForAllPlanets();
+ });
+
+ this.moving = true;
+
+ this.updateGalleryUI();
+ if(!this.userHasZoomedOnce) {
+ this.userHasZoomedOnce = true;
+ }
+ }
+ },
+
+ onChangeView: function(callback) {
+ this.changeview_callback = callback;
+ },
+
+ updateGalleryUI: function() {
+ if(this.userHasZoomedOnce) {
+ this.changeview_callback(this.getCurrentView());
+ }
+ },
+
+ isPreviousPlanet: function() {
+ var current = this.camera.getFocusedPlanet().getName(),
+ index = this.system.getPlanetIndex(current);
+
+ return index > 0;
+ },
+
+ isNextPlanet: function() {
+ var current = this.camera.getFocusedPlanet().getName(),
+ index = this.system.getPlanetIndex(current);
+
+ return index < 7;
+ },
+
+ getPreviousPlanetName: function() {
+ var current = this.camera.getFocusedPlanet().getName(),
+ index = this.system.getPlanetIndex(current);
+
+ return this.system.getPlanetNameAt(index - 1);
+ },
+
+ getNextPlanetName: function() {
+ var current = this.camera.getFocusedPlanet().getName(),
+ index = this.system.getPlanetIndex(current);
+
+ return this.system.getPlanetNameAt(index + 1);
+ },
+
+ nextPlanet: function() {
+ var name = "",
+ self = this,
+ $body = $("body");
+
+ if(!this.moving && this.camera.getCurrentView() === Constants.VIEW.PLANET && this.isNextPlanet()) {
+ name = this.camera.getFocusedPlanet().getName();
+ $("#"+name+"-info").addClass("left");
+ $body.removeClass(name);
+
+ this.camera.focusNextPlanet();
+
+ name = this.camera.getFocusedPlanet().getName();
+ $("#"+name+"-info").removeClass("right");
+ $body.addClass(name);
+
+ this.showPlanetInfo();
+
+ this.moving = true;
+ }
+ },
+
+ previousPlanet: function() {
+ var name = "",
+ self = this,
+ $body = $("body");
+
+ if(!this.moving && this.camera.getCurrentView() === Constants.VIEW.PLANET && this.isPreviousPlanet()) {
+ name = this.camera.getFocusedPlanet().getName();
+ $("#"+name+"-info").addClass("right");
+ $body.removeClass(name);
+
+ this.camera.focusPreviousPlanet();
+
+ name = this.camera.getFocusedPlanet().getName();
+ $("#"+name+"-info").removeClass("left");
+ $body.addClass(name);
+
+ this.showPlanetInfo();
+
+ this.moving = true;
+ }
+ },
+
+ zoomOnPlanet: function(planetName) {
+ this.camera.setFocusedPlanet(planetName);
+ this.showPlanetView();
+ },
+
+ disableTransitions: function() {
+ function doDisable(prefix) {
+ $("li.planet").css(prefix + "transition-duration", "0s");
+ }
+ doDisable("-moz-");
+ doDisable("-webkit-");
+ doDisable("-o-");
+ },
+
+ enableTransitions: function() {
+ setTimeout(function() {
+ function doEnable(prefix) {
+ $("li.planet").css(prefix + "transition-duration", "0.5s").css("-moz-transition-timing-function", "ease");
+ }
+ doEnable("-moz-");
+ doEnable("-webkit-");
+ doEnable("-o-");
+ }, 100);
+ },
+
+ createCounter: function(start, end) {
+ var self = this;
+
+ if(this.distanceCounter) {
+ this.distanceCounter.stop();
+ this.distanceCounter = null;
+ }
+ this.distanceCounter = new Counter($("#counters").get(0), start, end);
+
+ this.distanceCounter.onStep(function(value) {
+ $("#kilometers").text(addCommas(value)+" KM");
+ });
+ this.distanceCounter.onStop(function() {
+ self.distanceCounter = null;
+ });
+
+ this.distanceCounter.run();
+ },
+
+ showPlanetInfo: function() {
+ var name = this.camera.getFocusedPlanet().getName(),
+ index = this.system.getPlanetIndex(name),
+ start = this.currentKm,
+ end = this.system.getPlanetDistanceToSun(index),
+ $gui = $("#gui");
+
+ $gui.addClass("visible");
+ $gui.removeClass("shrink");
+
+ this.createCounter(start, end);
+ this.currentKm = end;
+
+ this.updateGraphs();
+
+ // Navigation buttons visiblity
+ if(name === "neptune") {
+ $("#moveright").hide();
+ } else if(name === "mercury") {
+ $("#moveleft").hide();
+ } else {
+ $("#moveleft").show();
+ $("#moveright").show();
+ }
+ },
+
+ hidePlanetInfo: function() {
+ var $gui = $("#gui"),
+ $starfield = $("#starfield");
+
+ $gui.addClass("shrink");
+ $gui.removeClass("visible");
+ $starfield.removeClass("reset");
+ $starfield.removeClass("zoom");
+
+ this.currentKm = 0;
+ this.updateGraphs();
+ },
+
+ updateGraphs: function() {
+ var planetName = this.camera.getFocusedPlanet().getName(),
+ view = this.camera.getCurrentView(),
+ pause = false;
+
+ if(view === Constants.VIEW.PLANET) {
+ if(planetName === "jupiter") {
+ this.jupiterGraph.play();
+ } else if(planetName === "earth") {
+ this.earthGraph.play();
+ } else {
+ pause = true;
+ }
+ } else {
+ pause = true;
+ }
+
+ if(pause) {
+ this.earthGraph.pause();
+ this.jupiterGraph.pause();
+ }
+ },
+
+ resetAllOtherPlanets: function() {
+ var current = this.camera.getFocusedPlanet().getName();
+
+ this.system.forEachPlanet(function(planet) {
+ var $info = $("#"+planet.id+"-info");
+
+ $info.removeClass("left").removeClass("right");
+
+ if(planet.id !== current) {
+ $info.addClass("hidden");
+ }
+ });
+ },
+
+ removeHiddenContentForAllPlanets: function() {
+ this.system.forEachPlanet(function(planet) {
+ $("#"+planet.id+"-info").removeClass("hidden");
+ });
+ },
+
+ forPlanetsOnLeft: function(callback) {
+ var self = this,
+ current = this.camera.getFocusedPlanet().getName(),
+ index = this.system.getPlanetIndex(current);
+
+ for(var i=index-1; i >= 0; i -= 1) {
+ (function(j) {
+ var name = self.system.getPlanetNameAt(j);
+ callback(name);
+ })(i);
+ }
+ },
+
+ forPlanetsOnRight: function(callback) {
+ var self = this,
+ current = this.camera.getFocusedPlanet().getName(),
+ index = this.system.getPlanetIndex(current);
+
+ for(var i=index+1; i < 8; i += 1) {
+ (function(j) {
+ var name = self.system.getPlanetNameAt(j);
+ callback(name);
+ })(i);
+ }
+ },
+
+ hidePlanetsContentOnLeft: function() {
+ this.forPlanetsOnLeft(function(name) {
+ $("#"+name+"-info").addClass("left").addClass("hidden");
+ });
+ },
+
+ hidePlanetsContentOnRight: function() {
+ this.forPlanetsOnRight(function(name) {
+ $("#"+name+"-info").addClass("right").addClass("hidden");
+ });
+ },
+
+ hidePlanetsImageOnLeft: function() {
+ this.forPlanetsOnLeft(function(name) {
+ $("#"+name).addClass("hidden");
+ });
+ },
+
+ hidePlanetsImageOnRight: function() {
+ this.forPlanetsOnRight(function(name) {
+ $("#"+name).addClass("hidden");
+ });
+ },
+
+ changeName: function(name) {
+ $(".content h1").html(name);
+ }
+ });
+
+ var JupiterSystem = SatelliteSystem.extend({
+ init: function(divId, width, height, scale) {
+ this._super(divId, width, height, scale);
+ this.planetRadius = 10;
+ this.satellites = {"io":{o: 40, r: 5, a: 25, s: 0.8, c: "#fff075"},
+ "europa":{o: 60, r: 5, a: 60, s: 0.4, c: "#75d0ff"},
+ "ganymede":{o: 90, r: 5, a: 140, s: 0.2, c: "#4bfe86"},
+ "callisto":{o: 150, r: 5, a: 250, s: 0.1, c: "#ff7575"}};
+ }
+ });
+
+ var EarthSystem = SatelliteSystem.extend({
+ init: function(divId, width, height, scale) {
+ this._super(divId, width, height, scale);
+
+ this.satellites = {"moon":{o: 47, r: 4.5, a: -45, s: 0.5, c: "white"}};
+ }
+ });
+
+ /**
+ * @author http://www.mredkj.com/javascript/numberFormat.html#addcommas
+ */
+ var addCommas = function addCommas(str) {
+ str += '';
+ x = str.split('.');
+ x1 = x[0];
+ x2 = x.length > 1 ? '.' + x[1] : '';
+ var rgx = /(\d+)(\d{3})/;
+ while (rgx.test(x1)) {
+ x1 = x1.replace(rgx, '$1' + ',' + '$2');
+ }
+ return x1 + x2;
+ };
+
+ return Planetarium;
+});
diff --git a/planetarium/js/raphael-min.js b/planetarium/js/raphael-min.js
new file mode 100644
index 0000000..e5e7126
--- /dev/null
+++ b/planetarium/js/raphael-min.js
@@ -0,0 +1,7 @@
+/*
+ * Raphael 1.5.2 - JavaScript Vector Library
+ *
+ * Copyright (c) 2010 Dmitry Baranovskiy (http://raphaeljs.com)
+ * Licensed under the MIT (http://raphaeljs.com/license.html) license.
+ */
+(function(){function a(){if(a.is(arguments[0],G)){var b=arguments[0],d=bV[m](a,b.splice(0,3+a.is(b[0],E))),e=d.set();for(var g=0,h=b[w];g";bg=bf.firstChild;bg.style.behavior="url(#default#VML)";if(!(bg&&typeof bg.adj=="object"))return a.type=null;bf=null}a.svg=!(a.vml=a.type=="VML");j[e]=a[e];k=j[e];a._id=0;a._oid=0;a.fn={};a.is=function(a,b){b=x.call(b);if(b=="finite")return!O[f](+a);return b=="null"&&a===null||b==typeof a||b=="object"&&a===Object(a)||b=="array"&&Array.isArray&&Array.isArray(a)||J.call(a).slice(8,-1).toLowerCase()==b};a.angle=function(b,c,d,e,f,g){{if(f==null){var h=b-d,i=c-e;if(!h&&!i)return 0;return((h<0)*180+y.atan(-i/-h)*180/D+360)%360}return a.angle(b,c,f,g)-a.angle(d,e,f,g)}};a.rad=function(a){return a%360*D/180};a.deg=function(a){return a*180/D%360};a.snapTo=function(b,c,d){d=a.is(d,"finite")?d:10;if(a.is(b,G)){var e=b.length;while(e--)if(B(b[e]-c)<=d)return b[e]}else{b=+b;var f=c%b;if(fb-d)return c-f+b}return c};function bh(){var a=[],b=0;for(;b<32;b++)a[b]=(~(~(y.random()*16)))[H](16);a[12]=4;a[16]=(a[16]&3|8)[H](16);return"r-"+a[v]("")}a.setWindow=function(a){h=a;g=h.document};var bi=function(b){if(a.vml){var c=/^\s+|\s+$/g,d;try{var e=new ActiveXObject("htmlfile");e.write("");e.close();d=e.body}catch(a){d=createPopup().document.body}var f=d.createTextRange();bi=bm(function(a){try{d.style.color=r(a)[Y](c,p);var b=f.queryCommandValue("ForeColor");b=(b&255)<<16|b&65280|(b&16711680)>>>16;return"#"+("000000"+b[H](16)).slice(-6)}catch(a){return"none"}})}else{var h=g.createElement("i");h.title="Raphaël Colour Picker";h.style.display="none";g.body[l](h);bi=bm(function(a){h.style.color=a;return g.defaultView.getComputedStyle(h,p).getPropertyValue("color")})}return bi(b)},bj=function(){return"hsb("+[this.h,this.s,this.b]+")"},bk=function(){return"hsl("+[this.h,this.s,this.l]+")"},bl=function(){return this.hex};a.hsb2rgb=function(b,c,d,e){if(a.is(b,"object")&&"h"in b&&"s"in b&&"b"in b){d=b.b;c=b.s;b=b.h;e=b.o}return a.hsl2rgb(b,c,d/2,e)};a.hsl2rgb=function(b,c,d,e){if(a.is(b,"object")&&"h"in b&&"s"in b&&"l"in b){d=b.l;c=b.s;b=b.h}if(b>1||c>1||d>1){b/=360;c/=100;d/=100}var f={},g=["r","g","b"],h,i,j,k,l,m;if(c){d<0.5?h=d*(1+c):h=d+c-d*c;i=2*d-h;for(var n=0;n<3;n++){j=b+1/3*-(n-1);j<0&&j++;j>1&&j--;j*6<1?f[g[n]]=i+(h-i)*6*j:j*2<1?f[g[n]]=h:j*3<2?f[g[n]]=i+(h-i)*(2/3-j)*6:f[g[n]]=i}}else f={r:d,g:d,b:d};f.r*=255;f.g*=255;f.b*=255;f.hex="#"+(16777216|f.b|f.g<<8|f.r<<16).toString(16).slice(1);a.is(e,"finite")&&(f.opacity=e);f.toString=bl;return f};a.rgb2hsb=function(b,c,d){if(c==null&&a.is(b,"object")&&"r"in b&&"g"in b&&"b"in b){d=b.b;c=b.g;b=b.r}if(c==null&&a.is(b,F)){var e=a.getRGB(b);b=e.r;c=e.g;d=e.b}if(b>1||c>1||d>1){b/=255;c/=255;d/=255}var f=z(b,c,d),g=A(b,c,d),h,i,j=f;{if(g==f)return{h:0,s:0,b:f,toString:bj};var k=f-g;i=k/f;b==f?h=(c-d)/k:c==f?h=2+(d-b)/k:h=4+(b-c)/k;h/=6;h<0&&h++;h>1&&h--}return{h:h,s:i,b:j,toString:bj}};a.rgb2hsl=function(b,c,d){if(c==null&&a.is(b,"object")&&"r"in b&&"g"in b&&"b"in b){d=b.b;c=b.g;b=b.r}if(c==null&&a.is(b,F)){var e=a.getRGB(b);b=e.r;c=e.g;d=e.b}if(b>1||c>1||d>1){b/=255;c/=255;d/=255}var f=z(b,c,d),g=A(b,c,d),h,i,j=(f+g)/2,k;if(g==f)k={h:0,s:0,l:j};else{var l=f-g;i=j<0.5?l/(f+g):l/(2-f-g);b==f?h=(c-d)/l:c==f?h=2+(d-b)/l:h=4+(b-c)/l;h/=6;h<0&&h++;h>1&&h--;k={h:h,s:i,l:j}}k.toString=bk;return k};a._path2string=function(){return this.join(",")[Y](ba,"$1")};function bm(a,b,c){function d(){var g=Array[e].slice.call(arguments,0),h=g[v]("►"),i=d.cache=d.cache||{},j=d.count=d.count||[];if(i[f](h))return c?c(i[h]):i[h];j[w]>=1000&&delete i[j.shift()];j[L](h);i[h]=a[m](b,g);return c?c(i[h]):i[h]}return d}a.getRGB=bm(function(b){if(!b||!(!((b=r(b)).indexOf("-")+1)))return{r:-1,g:-1,b:-1,hex:"none",error:1};if(b=="none")return{r:-1,g:-1,b:-1,hex:"none"};!(_[f](b.toLowerCase().substring(0,2))||b.charAt()=="#")&&(b=bi(b));var c,d,e,g,h,i,j,k=b.match(N);if(k){if(k[2]){g=T(k[2].substring(5),16);e=T(k[2].substring(3,5),16);d=T(k[2].substring(1,3),16)}if(k[3]){g=T((i=k[3].charAt(3))+i,16);e=T((i=k[3].charAt(2))+i,16);d=T((i=k[3].charAt(1))+i,16)}if(k[4]){j=k[4][s]($);d=S(j[0]);j[0].slice(-1)=="%"&&(d*=2.55);e=S(j[1]);j[1].slice(-1)=="%"&&(e*=2.55);g=S(j[2]);j[2].slice(-1)=="%"&&(g*=2.55);k[1].toLowerCase().slice(0,4)=="rgba"&&(h=S(j[3]));j[3]&&j[3].slice(-1)=="%"&&(h/=100)}if(k[5]){j=k[5][s]($);d=S(j[0]);j[0].slice(-1)=="%"&&(d*=2.55);e=S(j[1]);j[1].slice(-1)=="%"&&(e*=2.55);g=S(j[2]);j[2].slice(-1)=="%"&&(g*=2.55);(j[0].slice(-3)=="deg"||j[0].slice(-1)=="°")&&(d/=360);k[1].toLowerCase().slice(0,4)=="hsba"&&(h=S(j[3]));j[3]&&j[3].slice(-1)=="%"&&(h/=100);return a.hsb2rgb(d,e,g,h)}if(k[6]){j=k[6][s]($);d=S(j[0]);j[0].slice(-1)=="%"&&(d*=2.55);e=S(j[1]);j[1].slice(-1)=="%"&&(e*=2.55);g=S(j[2]);j[2].slice(-1)=="%"&&(g*=2.55);(j[0].slice(-3)=="deg"||j[0].slice(-1)=="°")&&(d/=360);k[1].toLowerCase().slice(0,4)=="hsla"&&(h=S(j[3]));j[3]&&j[3].slice(-1)=="%"&&(h/=100);return a.hsl2rgb(d,e,g,h)}k={r:d,g:e,b:g};k.hex="#"+(16777216|g|e<<8|d<<16).toString(16).slice(1);a.is(h,"finite")&&(k.opacity=h);return k}return{r:-1,g:-1,b:-1,hex:"none",error:1}},a);a.getColor=function(a){var b=this.getColor.start=this.getColor.start||{h:0,s:1,b:a||0.75},c=this.hsb2rgb(b.h,b.s,b.b);b.h+=0.075;if(b.h>1){b.h=0;b.s-=0.2;b.s<=0&&(this.getColor.start={h:0,s:1,b:b.b})}return c.hex};a.getColor.reset=function(){delete this.start};a.parsePathString=bm(function(b){if(!b)return null;var c={a:7,c:6,h:1,l:2,m:2,q:4,s:4,t:2,v:1,z:0},d=[];a.is(b,G)&&a.is(b[0],G)&&(d=bo(b));d[w]||r(b)[Y](bb,function(a,b,e){var f=[],g=x.call(b);e[Y](bc,function(a,b){b&&f[L](+b)});if(g=="m"&&f[w]>2){d[L]([b][n](f.splice(0,2)));g="l";b=b=="m"?"l":"L"}while(f[w]>=c[g]){d[L]([b][n](f.splice(0,c[g])));if(!c[g])break}});d[H]=a._path2string;return d});a.findDotsAtSegment=function(a,b,c,d,e,f,g,h,i){var j=1-i,k=C(j,3)*a+C(j,2)*3*i*c+j*3*i*i*e+C(i,3)*g,l=C(j,3)*b+C(j,2)*3*i*d+j*3*i*i*f+C(i,3)*h,m=a+2*i*(c-a)+i*i*(e-2*c+a),n=b+2*i*(d-b)+i*i*(f-2*d+b),o=c+2*i*(e-c)+i*i*(g-2*e+c),p=d+2*i*(f-d)+i*i*(h-2*f+d),q=(1-i)*a+i*c,r=(1-i)*b+i*d,s=(1-i)*e+i*g,t=(1-i)*f+i*h,u=90-y.atan((m-o)/(n-p))*180/D;(m>o||n