From 06de1cb8e40b1cdcb1d8a4db37f612a9a9e1571c Mon Sep 17 00:00:00 2001 From: tankchintan Date: Tue, 19 Jul 2011 19:19:12 +0000 Subject: [PATCH] 1. Fix for http://issues.library.cornell.edu/browse/NIHVIVO-2851 Improved function calling & added reasonable circle-smoothness defaults for map of science vis. Code reviewed by Chin Hua --- .../mapofscience/MarkerManager.js | 3 +- .../js/visualization/mapofscience/Polygon.js | 301 ++++++++-------- .../mapofscience/ScimapWidget.js | 338 ++++++++++-------- 3 files changed, 333 insertions(+), 309 deletions(-) diff --git a/productMods/js/visualization/mapofscience/MarkerManager.js b/productMods/js/visualization/mapofscience/MarkerManager.js index 266f8004..5f6ceff3 100644 --- a/productMods/js/visualization/mapofscience/MarkerManager.js +++ b/productMods/js/visualization/mapofscience/MarkerManager.js @@ -168,9 +168,8 @@ var DisciplineMarkerManager = ScimapMarkerManager.extend({ this._super(map, colorStrategy, sizeCoder); this.layer = DISCIPLINES; }, - createMarker: function(subdisciplineKey, density) { + createMarker: function(key, density) { var me = this; - var key = SUBDISCIPLINES[subdisciplineKey].discipline; var marker = this._super(key, density); var poly = marker.polygon; diff --git a/productMods/js/visualization/mapofscience/Polygon.js b/productMods/js/visualization/mapofscience/Polygon.js index fa799f70..c49ea2f0 100644 --- a/productMods/js/visualization/mapofscience/Polygon.js +++ b/productMods/js/visualization/mapofscience/Polygon.js @@ -1,150 +1,151 @@ -/* $This file is distributed under the terms of the license in /doc/license.txt$ */ -var INFO_WINDOW = createInfoWindow("", "300"); - -var Polygon = Class.extend({ - init : function(options) { - this.options = $.extend({}, this.options, options); - if (options.polygon) { - this.polygon = options.polygon; - } else { - this.polygon = createGooglePolygon(options); - } - this.registerEvents(); - }, - options : { - map : null, - icon : null, - position : null, - content : null - }, - addToMap : function() { - this.polygon.setMap(this.options.map); - this.registerEvents(); - }, - removeFromMap : function() { - this.unregisterEvents(); - this.polygon.setMap(null); - }, - show : function() { - this.polygon.setMap(this.options.map); - }, - hide : function() { - this.polygon.setMap(null); - }, - setIcon : function(icon) { - }, - setZIndex: function(zIndex){ - this.polygon.zIndex = zIndex; - }, - setTitle : function(title) { - this.polygon.title = title; - }, - setOptions: function(options) { - this.polygon.setOptions(options); - }, - registerEvent : function(handler) { - var me = this; - if (me.handlers == null) { - me.handlers = new Array(); - } - me.handlers.push(handler); - }, - unregisterEvent : function(handler) { - if (this.handlers[handler]) { - removeListener(handler); - delete(this.handlers[handler]); - } - }, - registerEvents : function() { - }, - unregisterEvents : function() { - $.each(this.handlers, function(){ - removeListener(this); - }); - this.handlers = null; - } -}); - -var RADIAN_PER_DEGREE = Math.PI / 180; - -function degreeToRadians(degree) { - return degree * RADIAN_PER_DEGREE; -} - -var TOOLTIP = new Tooltip({ attachedToMouse: true }); - -var CirclePolygon = Polygon.extend({ - init : function(options) { - this.options = $.extend({}, this.options, options); - this._super(this.options); - }, - options : { - radius: 0.0, - center: null - }, - addToMap: function() { - if (!this.isPointsCreated()) { - this.initCirclePoints(); - } - this._super(); - }, - show: function() { - if (!this.isPointsCreated()) { - this.initCirclePoints(); - } - - this._super(); - }, - isPointsCreated: function() { - return (this.polygon.getPath().getLength() > 1); - }, - initCirclePoints: function() { - this.clearCirclePoints(); - this.createCirclePoints(); - }, - createCirclePoints: function() { - var me = this; - var map = me.options.map; - var latLngArray = new google.maps.MVCArray(); // Circle's LatLngs - if (map && map.getProjection()) { - var projection = map.getProjection(); - var centerPoint = projection.fromLatLngToPoint(me.options.center); - var radius = me.options.radius; - - // Create polygon points (extra point to close polygon) - for (var degree = 0; degree < 360; degree++) { - var radian = degreeToRadians(degree); - var x = centerPoint.x + (radius * Math.sin(radian)); - var y = centerPoint.y + (radius * Math.cos(radian)); - var point = new google.maps.Point(parseFloat(x), parseFloat(y)); - latLngArray.push(projection.fromPointToLatLng(point)); - } - } - me.polygon.setPath(latLngArray); - }, - clearCirclePoints: function() { - this.polygon.getPath().clear(); - }, - setRadius: function(radius) { - this.polygon.radius = radius; - this.options.radius = radius; - this.initCirclePoints(); - }, - registerEvents: function() { - var me = this; - var polygon = me.polygon; - this.registerEvent(addMapProjectionChangedListener(me.options.map, function() { - me.initCirclePoints(); - })); - - this.registerEvent(addMouseOverListener(polygon, function() { - TOOLTIP.setHtml("" + this.label + ""); - TOOLTIP.show(); - })); - - this.registerEvent(addMouseOutListener(polygon, function() { - TOOLTIP.hide(); - })); - } -}); - +/* $This file is distributed under the terms of the license in /doc/license.txt$ */ +var INFO_WINDOW = createInfoWindow("", "300"); + +var Polygon = Class.extend({ + init : function(options) { + this.options = $.extend({}, this.options, options); + if (options.polygon) { + this.polygon = options.polygon; + } else { + this.polygon = createGooglePolygon(options); + } + this.registerEvents(); + }, + options : { + map : null, + icon : null, + position : null, + content : null + }, + addToMap : function() { + this.polygon.setMap(this.options.map); + this.registerEvents(); + }, + removeFromMap : function() { + this.unregisterEvents(); + this.polygon.setMap(null); + }, + show : function() { + this.polygon.setMap(this.options.map); + }, + hide : function() { + this.polygon.setMap(null); + }, + setIcon : function(icon) { + }, + setZIndex: function(zIndex){ + this.polygon.zIndex = zIndex; + }, + setTitle : function(title) { + this.polygon.title = title; + }, + setOptions: function(options) { + this.polygon.setOptions(options); + }, + registerEvent : function(handler) { + var me = this; + if (me.handlers == null) { + me.handlers = new Array(); + } + me.handlers.push(handler); + }, + unregisterEvent : function(handler) { + if (this.handlers[handler]) { + removeListener(handler); + delete(this.handlers[handler]); + } + }, + registerEvents : function() { + }, + unregisterEvents : function() { + $.each(this.handlers, function(){ + removeListener(this); + }); + this.handlers = null; + } +}); + +var RADIAN_PER_DEGREE = Math.PI / 180; + +function degreeToRadians(degree) { + return degree * RADIAN_PER_DEGREE; +} + +var TOOLTIP = new Tooltip({ attachedToMouse: true }); + +var CirclePolygon = Polygon.extend({ + init : function(options) { + this.options = $.extend({}, this.options, options); + this._super(this.options); + }, + options : { + radius: 0.0, + center: null + }, + addToMap: function() { + if (!this.isPointsCreated()) { + this.initCirclePoints(); + } + this._super(); + }, + show: function() { + if (!this.isPointsCreated()) { + this.initCirclePoints(); + } + + this._super(); + }, + isPointsCreated: function() { + return (this.polygon.getPath().getLength() > 1); + }, + initCirclePoints: function() { + this.clearCirclePoints(); + this.createCirclePoints(); + }, + createCirclePoints: function() { + var me = this; + var map = me.options.map; + var latLngArray = new google.maps.MVCArray(); // Circle's LatLngs + if (map && map.getProjection()) { + var projection = map.getProjection(); + var centerPoint = projection.fromLatLngToPoint(me.options.center); + var radius = me.options.radius; + + var incrementDegreeBy = (radius > 2) ? 1 : 10; + + // Create polygon points (extra point to close polygon) + for (var degree = 0; degree < 360; degree+=incrementDegreeBy) { + var radian = degreeToRadians(degree); + var x = centerPoint.x + (radius * Math.sin(radian)); + var y = centerPoint.y + (radius * Math.cos(radian)); + var point = new google.maps.Point(parseFloat(x), parseFloat(y)); + latLngArray.push(projection.fromPointToLatLng(point)); + } + } + me.polygon.setPath(latLngArray); + }, + clearCirclePoints: function() { + this.polygon.getPath().clear(); + }, + setRadius: function(radius) { + this.polygon.radius = radius; + this.options.radius = radius; + this.initCirclePoints(); + }, + registerEvents: function() { + var me = this; + var polygon = me.polygon; + this.registerEvent(addMapProjectionChangedListener(me.options.map, function() { + me.initCirclePoints(); + })); + + this.registerEvent(addMouseOverListener(polygon, function() { + TOOLTIP.setHtml("" + this.label + ""); + TOOLTIP.show(); + })); + + this.registerEvent(addMouseOutListener(polygon, function() { + TOOLTIP.hide(); + })); + } +}); \ No newline at end of file diff --git a/productMods/js/visualization/mapofscience/ScimapWidget.js b/productMods/js/visualization/mapofscience/ScimapWidget.js index 119e6f02..1bf7dadf 100644 --- a/productMods/js/visualization/mapofscience/ScimapWidget.js +++ b/productMods/js/visualization/mapofscience/ScimapWidget.js @@ -1,158 +1,182 @@ -/* $This file is distributed under the terms of the license in /doc/license.txt$ */ - -var ScimapWidget = Class.extend({ - init: function(map, sliderControl) { - var me = this; - me.activeManager = null; - me.isUnloaded = true; - me.map = map; - me.sliderControl = sliderControl; - me.labelsMarkerManager = new DisciplineLabelsMarkerManager(map); - me.disciplineLabelsControl = new CheckBoxPanel({ - map: map, - checked: true, - text: "Show discipline labels", - click: function() { - if($(this).attr('checked')) { - me.labelsMarkerManager.showMarkers(); - } else { - me.labelsMarkerManager.hideMarkers(); - } - } - }); - me.initView(); - }, - initView: function(){ - var me = this; - /* Display labels if checked */ - if (me.disciplineLabelsControl.isChecked()) { - me.labelsMarkerManager.showMarkers(); - } - me.initMarkerManagers(); - me.sliderControl.setChangeEventHandler(function(event, ui) { - me.updateDisplayedMarkers(ui.value); - }); - me.show(SCIMAP_TYPE.SUBDISCIPLINE); - }, - initMarkerManagers: function() { - if (this.keyToMarkerManagers == null) { - var managers = {}; - - // Create discipline Marker Manager - managers[SCIMAP_TYPE.DISCIPLINE] = new DisciplineMarkerManager( - this.map, - new DisciplineColorStrategy(), - null - ); - - // Create subdiscipline Marker Manager - managers[SCIMAP_TYPE.SUBDISCIPLINE] = new SubdisciplineMarkerManager( - this.map, - new SubdisciplineColorStrategy(), - null - ); - this.keyToMarkerManagers = managers; - } - }, - needLoaded: function(){ - return this.isUnloaded; - }, - loadJsonData: function(data) { - var me = this; - me.uri = data.uri; - me.label = data.label; - me.pubsWithNoJournals = data.pubsWithNoJournals; - me.pubsWithInvalidJournals = data.pubsWithInvalidJournals; - me.pubsMapped = data.pubsMapped; - - this.isUnloaded = false; - $.each(this.keyToMarkerManagers, function(key, manager) { - // Need to create the AreaSizeCoding function - manager.setSizeCoder(new CircleSizeCoder({ - scaler: new Scaler({ maxValue: me.pubsMapped }) - })); - //markerManager.setSiseCodingFunction(new AreaSizeCoding(0, data.pubsMapped)); - $.each(data.subdisciplineActivity, function(subdiscipline, density) { - - // Create marker and add it to manager - var marker = manager.createMarker(subdiscipline, density); - - }); // end each subdisciplineActivity - - manager.sort(); - }); // end each markerManagers - me.updateMap(); - }, - mouseIn: function(key, childKey) { - var manager = this.getMarkerManager(key); - // Focus if only it is an active manager - if (manager == this.activeManager) { - // Focus all if no childKey is given - if (childKey) { - manager.mouseIn(childKey); - } else { - manager.mouseInAll(); - } - } - }, - mouseOut: function(key, childKey) { - var manager = this.getMarkerManager(key); - // Focus if only it is an active manager - if (manager == this.activeManager) { - // Unfocus all if no childKey is given - if (childKey) { - manager.mouseOut(childKey); - } else { - manager.mouseOutAll(); - } - } - }, - getMarkerManager: function(key) { - return this.keyToMarkerManagers[key]; - }, - hasKey: function(key) { - return (this.keyToMarkerManagers.hasOwnProperty(key)); - }, - show: function(key) { - var manager = this.getMarkerManager(key); - if (manager) { - this._switchActiveManager(manager); - } - }, - hide: function(key) { - var manager = this.getMarkerManager(key); - if (this.activeManager == manager) { - this.cleanup(); - } - }, - _switchActiveManager: function(manager) { - if (this.activeManager != manager) { - this.cleanUp(); - manager.addMarkersToMap(); - this.activeManager = manager; - this.updateMap(); - } - }, - cleanUp: function() { - if (this.activeManager) { - this.activeManager.removeMarkersFromMap(); - INFO_WINDOW.close(); - } - }, - updateDisplayedMarkers: function(numberOfMarkers) { - this.activeManager.display(numberOfMarkers); - }, - updateMap: function() { - var manager = this.activeManager; - if (manager) { - var length = manager.length(); - var slider = this.sliderControl; - slider.setMin(Math.min(1, length)); - slider.setMax(length); - slider.setValue(length); - } - }, - changeFilter: function(filterType) { - this.show(filterType); - } +/* $This file is distributed under the terms of the license in /doc/license.txt$ */ + +var ScimapWidget = Class.extend({ + init: function(map, sliderControl) { + var me = this; + me.activeManager = null; + me.isUnloaded = true; + me.map = map; + + me.sliderControl = sliderControl; + me.labelsMarkerManager = new DisciplineLabelsMarkerManager(map); + me.disciplineLabelsControl = new CheckBoxPanel({ + map: map, + checked: true, + text: "Show discipline labels", + click: function() { + if($(this).attr('checked')) { + me.labelsMarkerManager.showMarkers(); + } else { + me.labelsMarkerManager.hideMarkers(); + } + } + }); + me.initView(); + }, + initView: function(){ + var me = this; + /* Display labels if checked */ + if (me.disciplineLabelsControl.isChecked()) { + me.labelsMarkerManager.showMarkers(); + } + me.initMarkerManagers(); + me.sliderControl.setChangeEventHandler(function(event, ui) { + me.updateDisplayedMarkers(ui.value); + }); + me.show(SCIMAP_TYPE.SUBDISCIPLINE); + }, + initMarkerManagers: function() { + if (this.keyToMarkerManagers == null) { + var managers = {}; + + // Create discipline Marker Manager + managers[SCIMAP_TYPE.DISCIPLINE] = new DisciplineMarkerManager( + this.map, + new DisciplineColorStrategy(), + null + ); + + // Create subdiscipline Marker Manager + managers[SCIMAP_TYPE.SUBDISCIPLINE] = new SubdisciplineMarkerManager( + this.map, + new SubdisciplineColorStrategy(), + null + ); + this.keyToMarkerManagers = managers; + } + }, + needLoaded: function(){ + return this.isUnloaded; + }, + loadJsonData: function(data) { + var me = this; + me.uri = data.uri; + me.label = data.label; + me.pubsWithNoJournals = data.pubsWithNoJournals; + me.pubsWithInvalidJournals = data.pubsWithInvalidJournals; + me.pubsMapped = data.pubsMapped; + + var scienceActivities = {}; + scienceActivities[SCIMAP_TYPE.DISCIPLINE] = me._collateDisciplineActivity(data.subdisciplineActivity); + scienceActivities[SCIMAP_TYPE.SUBDISCIPLINE] = data.subdisciplineActivity; + + this.isUnloaded = false; + + $.each(this.keyToMarkerManagers, function(key, manager) { + + // Need to create the AreaSizeCoding function + manager.setSizeCoder(new CircleSizeCoder({ + scaler: new Scaler({ maxValue: me.pubsMapped }) + })); + + $.each(scienceActivities[key], function(science, density) { + + // Create marker and add it to manager + var marker = manager.createMarker(science, density); + + }); // end each scienceActivity + + manager.sort(); + }); // end each markerManagers + me.updateMap(); + }, + + _collateDisciplineActivity: function(subdiscipline) { + + var disciplineToActivity = {}; + + $.each(DISCIPLINES, function(id, discipline) { + disciplineToActivity[id] = 0.0; + }); + + $.each(subdiscipline, function(key, activity) { + var currentSubdisciplinesDiscipline = SUBDISCIPLINES[key].discipline; + disciplineToActivity[currentSubdisciplinesDiscipline] += activity; + }); + + return disciplineToActivity; + }, + + mouseIn: function(key, childKey) { + var manager = this.getMarkerManager(key); + // Focus if only it is an active manager + if (manager == this.activeManager) { + // Focus all if no childKey is given + if (childKey) { + manager.mouseIn(childKey); + } else { + manager.mouseInAll(); + } + } + }, + mouseOut: function(key, childKey) { + var manager = this.getMarkerManager(key); + // Focus if only it is an active manager + if (manager == this.activeManager) { + // Unfocus all if no childKey is given + if (childKey) { + manager.mouseOut(childKey); + } else { + manager.mouseOutAll(); + } + } + }, + getMarkerManager: function(key) { + return this.keyToMarkerManagers[key]; + }, + hasKey: function(key) { + return (this.keyToMarkerManagers.hasOwnProperty(key)); + }, + show: function(key) { + var manager = this.getMarkerManager(key); + if (manager) { + this._switchActiveManager(manager); + } + }, + hide: function(key) { + var manager = this.getMarkerManager(key); + if (this.activeManager == manager) { + this.cleanup(); + } + }, + _switchActiveManager: function(manager) { + if (this.activeManager != manager) { + this.cleanUp(); + manager.addMarkersToMap(); + this.activeManager = manager; + this.updateMap(); + } + }, + cleanUp: function() { + if (this.activeManager) { + this.activeManager.removeMarkersFromMap(); + INFO_WINDOW.close(); + } + }, + updateDisplayedMarkers: function(numberOfMarkers) { + this.activeManager.display(numberOfMarkers); + }, + updateMap: function() { + var manager = this.activeManager; + if (manager) { + var length = manager.length(); + var slider = this.sliderControl; + slider.setMin(Math.min(1, length)); + slider.setMax(length); + slider.setValue(length); + } + }, + changeFilter: function(filterType) { + this.show(filterType); + } }); \ No newline at end of file