diff --git a/app/components/buttonPanel/buttonPanel.tpl.html b/app/components/buttonPanel/buttonPanel.tpl.html index 0d522cb..dd532e7 100644 --- a/app/components/buttonPanel/buttonPanel.tpl.html +++ b/app/components/buttonPanel/buttonPanel.tpl.html @@ -2,5 +2,6 @@ + diff --git a/app/components/heatmap/heatmapDirective.js b/app/components/heatmap/heatmapDirective.js index 1a66129..6ecea67 100644 --- a/app/components/heatmap/heatmapDirective.js +++ b/app/components/heatmap/heatmapDirective.js @@ -7,14 +7,35 @@ (function() { angular .module('search_heatmap_component', []) - .directive('heatmap', heatmap); - - function heatmap() { + .directive('heatmap', [function() { return { restrict: 'EA', templateUrl: 'components/heatmap/heatmap.tpl.html', scope: {} }; - } + }]) + .directive('heatmapButton', ['searchFilter', 'HeatMapSourceGenerator', + function(searchFilter, HeatMapSourceGenerator) { + return { + link: link, + template: '', + scope: {} + }; + function link(scope) { + var vm = scope; + vm.buttonName = 'SENTIMENT HEATMAP'; + vm.toggleHeatmap = function() { + var heatmapSentiment = !searchFilter.posSent; + vm.buttonName = heatmapSentiment ? 'TWEETS HEATMAP' : 'SENTIMENT HEATMAP'; + searchFilter.setFilter({ + posSent: heatmapSentiment + }); + HeatMapSourceGenerator.search(); + }; + } + }]); + + })(); diff --git a/app/components/tweetlist/tweet.less b/app/components/tweetlist/tweet.less index 3659b4c..a4578e8 100644 --- a/app/components/tweetlist/tweet.less +++ b/app/components/tweetlist/tweet.less @@ -16,6 +16,11 @@ margin:-10px 0 0 0; } +.tweet-emoji { + font-size: 20px !important; + margin-top: -4px; +} + .height-tweet { height: 260px; overflow-y: auto; diff --git a/app/components/tweetlist/tweetPanel.tpl.html b/app/components/tweetlist/tweetPanel.tpl.html index a5ad759..668ec8f 100644 --- a/app/components/tweetlist/tweetPanel.tpl.html +++ b/app/components/tweetlist/tweetPanel.tpl.html @@ -15,4 +15,12 @@
User Name
{{selectedTweet.user_name}}
+
+
Geo position
+
{{selectedTweet.geoadmin_admin2_txt}}
+
+
+
Sentiment
+
{{selectedTweet.sentiment_pos ? "😀" : "☚ī¸"}}
+
diff --git a/app/service/HeatMapSourceGenerator.js b/app/service/HeatMapSourceGenerator.js index d768c29..94fbdfc 100644 --- a/app/service/HeatMapSourceGenerator.js +++ b/app/service/HeatMapSourceGenerator.js @@ -43,12 +43,14 @@ 'q.time': timeTextFormat(sF.time, sF.minDate, sF.maxDate), 'q.geo': sF.geo, 'a.hm.filter': sF.hm, + 'a.hm.posSent': sF.posSent, 'a.time.limit': '1', 'a.time.gap': sF.gap, 'd.docs.limit': sF.numOfDocs, 'a.text.limit': sF.textLimit, 'a.user.limit': sF.userLimit, - 'd.docs.sort': 'distance' + 'd.docs.sort': 'distance', + 'a.hm.limit': solrHeatmapApp.bopwsConfig.heatmapFacetLimit }; } @@ -70,8 +72,6 @@ if (params) { canceler.resolve(); canceler = $q.defer(); - - params['a.hm.limit'] = solrHeatmapApp.bopwsConfig.heatmapFacetLimit; config = { url: solrHeatmapApp.appConfig.tweetsSearchBaseUrl, method: 'GET', @@ -102,17 +102,19 @@ function broadcastData(data) { data['a.text'] = data['a.text'] || []; + var heatmapData = {}; if (data && data['a.hm']) { - MapService.createOrUpdateHeatMapLayer(data['a.hm']); - + if (data['a.hm.posSent']) { + heatmapData = data['a.hm.posSent']; + heatmapData.posSent = true; + }else { + heatmapData = data['a.hm']; + } + MapService.createOrUpdateHeatMapLayer(heatmapData); $rootScope.$broadcast('setCounter', data['a.matchDocs']); - $rootScope.$broadcast('setHistogram', data['a.time']); - $rootScope.$broadcast('setTweetList', data['d.docs']); - $rootScope.$broadcast('setSuggestWords', data['a.text']); - $rootScope.$broadcast('setUserSuggestWords', data['a.user']); } } diff --git a/app/service/Map.js b/app/service/Map.js index c9e74c7..cd4f46b 100644 --- a/app/service/Map.js +++ b/app/service/Map.js @@ -213,7 +213,8 @@ flattenCount.push.apply(flattenCount, row); }); var series = new geostats(flattenCount); - var numberOfClassifications = hmParams.gradientArray.length - 5; + var gradientLength = hmParams.gradientArray.length; + var numberOfClassifications = gradientLength - Math.ceil(gradientLength*0.4); return series.getClassJenks(numberOfClassifications); } @@ -337,12 +338,13 @@ service.createOrUpdateHeatMapLayer = function(hmData) { var existingHeatMapLayers, transformInteractionLayer, olVecSrc, newHeatMapLayer; - + var sentimetGradient = ['#ff0000', '#ff0000', '#ff0000','#ff0088', '#ff0088', + '#ff00ff', '#8800ff', '#0000ff', '#0000ff', '#0077ff', '#00aaff', '#00ddff']; + var normalCountGradient = ['#000000', '#0000df', '#0000df', '#00effe', '#00effe', + '#00ff42', ' #00ff42', '#00ff42', '#feec30', '#ff5f00', '#ff0000']; hmData.heatmapRadius = 20; - hmData.blur = 6; - hmData.gradientArray = ['#000000', '#0000df', '#0000df', '#00effe', - '#00effe', '#00ff42',' #00ff42', '#00ff42', - '#feec30', '#ff5f00', '#ff0000']; + hmData.blur = 10; + hmData.gradientArray = hmData.posSent ? sentimetGradient : normalCountGradient; existingHeatMapLayers = service.getLayersBy('name', 'HeatMapLayer'); transformInteractionLayer = service.getLayersBy('name', @@ -357,7 +359,7 @@ layerSrc.clear(); } currHeatmapLayer.setSource(olVecSrc); - // currHeatmapLayer.setRadius(hmData.heatmapRadius); + currHeatmapLayer.setGradient(hmData.gradientArray); } else { newHeatMapLayer = new ol.layer.Heatmap({ name: 'HeatMapLayer', diff --git a/app/service/searchFilter.js b/app/service/searchFilter.js index ff9cfec..87ae93b 100644 --- a/app/service/searchFilter.js +++ b/app/service/searchFilter.js @@ -16,6 +16,7 @@ userLimit: null, numOfDocs: 50, gap: 'P1W', + posSent: false, minDate: new Date(moment().subtract(3, 'months').format('YYYY-MM-DD')), maxDate: new Date(moment().format('YYYY-MM-DD')) }; @@ -40,6 +41,9 @@ if (filter.hm) { service.hm = filter.hm; } + if (angular.isDefined(filter.posSent)) { + service.posSent = filter.posSent; + } }; service.resetFilter = function() { diff --git a/tests/service/HeatMapSourceGenerator.spec.js b/tests/service/HeatMapSourceGenerator.spec.js index 26880bf..f7f0025 100644 --- a/tests/service/HeatMapSourceGenerator.spec.js +++ b/tests/service/HeatMapSourceGenerator.spec.js @@ -22,7 +22,7 @@ describe( 'HeatMapSourceGenerator', function() { geospatialFilter = {queryGeo: { minX: 1, maxX: 1, minY: 1, maxY: 1}}; searchFilter.minDate = new Date('2016-12-10'); searchFilter.maxDate = new Date('2016-12-21'); - exportRequest = $httpBackend.when('GET', '/search?a.hm.filter=%5B-90,-180+TO+90,180%5D&a.time.gap=P1W&a.time.limit=1&d.docs.limit=50&d.docs.sort=distance&q.geo=%5B-90,-180+TO+90,180%5D&q.time=%5B2016-12-10T00:00:00+TO+2016-12-21T00:00:00%5D').respond(''); + exportRequest = $httpBackend.when('GET', '/search?a.hm.filter=%5B-90,-180+TO+90,180%5D&a.hm.posSent=false&a.time.gap=P1W&a.time.limit=1&d.docs.limit=50&d.docs.sort=distance&q.geo=%5B-90,-180+TO+90,180%5D&q.time=%5B2016-12-10T00:00:00+TO+2016-12-21T00:00:00%5D').respond(''); }); afterEach(function() { $httpBackend.resetExpectations(); @@ -30,7 +30,7 @@ describe( 'HeatMapSourceGenerator', function() { $httpBackend.verifyNoOutstandingRequest(); }); it('sends the search request', function() { - $httpBackend.expectGET('/search?a.hm.filter=%5B-90,-180+TO+90,180%5D&a.time.gap=P1W&a.time.limit=1&d.docs.limit=50&d.docs.sort=distance&q.geo=%5B-90,-180+TO+90,180%5D&q.time=%5B2016-12-10T00:00:00+TO+2016-12-21T00:00:00%5D').respond(''); + $httpBackend.expectGET('/search?a.hm.filter=%5B-90,-180+TO+90,180%5D&a.hm.posSent=false&a.time.gap=P1W&a.time.limit=1&d.docs.limit=50&d.docs.sort=distance&q.geo=%5B-90,-180+TO+90,180%5D&q.time=%5B2016-12-10T00:00:00+TO+2016-12-21T00:00:00%5D').respond(''); subject.search(); $httpBackend.flush(); }); diff --git a/tests/service/Map.spec.js b/tests/service/Map.spec.js index db5790d..4d2338d 100644 --- a/tests/service/Map.spec.js +++ b/tests/service/Map.spec.js @@ -237,10 +237,10 @@ describe( 'HeatMapSourceGenerator', function() { describe('#createOrUpdateHeatMapLayer', function() { var data, layerSpy, setSourceSpy, setRadiusSpy; beforeEach(function() { - var clearSourceSpy = jasmine.createSpyObj('getSource', ['clear']); - layer = { getFilters: function() { return [{ setActive: function() {}}]; }, setSource: function() {}, setRadius: function() {}, getSource: function() { return { clear: function() {}, getFeatures: function() { return [{getGeometry: function() { return { getExtent: function() { return [0,0,0,0];}};}}];}}; }}; + var clearSourceSpy = jasmine.createSpyObj('getSource', ['clear']);layer = { getFilters: function() {return [{ setActive: function() {}}];}, setSource: function() {}, setRadius: function() {}, setGradient: function() {}, getSource: function() { return { clear: function() {}, getFeatures: function() { return [{getGeometry: function() { return { getExtent: function() { return [0,0,0,0];}};}}];}}; }}; setSourceSpy = spyOn(layer, 'setSource'); - setRadiusSpy = spyOn(layer, 'setRadius'); + spyOn(layer, 'setRadius'); + spyOn(layer, 'setGradient'); data = { columns: 4, rows: 4, gridLevel: 2, maxX: 1, maxY: 1, minY: 0, minX: 0, projection: 'EPSG:4326', counts_ints2D: [[0,0,0,0],[0,0,0,0],[0,0,0,0],[0,0,0,0]]}; });