diff --git a/frontend/app-dashboard/css/side-panel.css b/frontend/app-dashboard/css/side-panel.css index 745c255..26b7b9e 100644 --- a/frontend/app-dashboard/css/side-panel.css +++ b/frontend/app-dashboard/css/side-panel.css @@ -284,13 +284,18 @@ form label { } .box-count-left { - padding: 0 5px 5px 15px; - width: 180px; + padding: 0 2px 5px 5px; + width: 33%; } .box-count-right { - padding: 0 15px 5px 5px; - width: 170px; + padding: 0 5px 5px 2px; + width: 33%; +} + +.box-count-middle { + padding: 0 2px 5px 2px; + width: 33%; } #building-count, #vulnerability-score, .score, #road-count, #vulnerability-score-road{ diff --git a/frontend/app-dashboard/dashboard.html b/frontend/app-dashboard/dashboard.html index 401dfca..bd291d8 100644 --- a/frontend/app-dashboard/dashboard.html +++ b/frontend/app-dashboard/dashboard.html @@ -446,10 +446,13 @@
- Buildings + Buildings
-
- Roads +
+ +
+
+
@@ -488,6 +491,24 @@
+
@@ -501,7 +522,7 @@ diff --git a/frontend/app-dashboard/js/model/population_district_summary.js b/frontend/app-dashboard/js/model/population_district_summary.js new file mode 100644 index 0000000..6b9af91 --- /dev/null +++ b/frontend/app-dashboard/js/model/population_district_summary.js @@ -0,0 +1,20 @@ +define([ + 'backbone', + 'moment' +], function (Backbone) { + + const PopulationDistrictSummary = Backbone.Model.extend({ + urlRoot: postgresUrl + 'mv_flood_event_population_district_summary', + url: function () { + return `${this.urlRoot}?id=eq.${this.id}` + } + }); + + return Backbone.Collection.extend({ + model: PopulationDistrictSummary, + urlRoot: postgresUrl + 'mv_flood_event_population_district_summary', + url: function () { + return this.urlRoot; + } + }); +}); diff --git a/frontend/app-dashboard/js/model/population_sub_district_summary.js b/frontend/app-dashboard/js/model/population_sub_district_summary.js new file mode 100644 index 0000000..3e20ffa --- /dev/null +++ b/frontend/app-dashboard/js/model/population_sub_district_summary.js @@ -0,0 +1,20 @@ +define([ + 'backbone', + 'moment' +], function (Backbone) { + + const PopulationSubDistrictSummary = Backbone.Model.extend({ + urlRoot: postgresUrl + 'mv_flood_event_population_sub_district_summary', + url: function () { + return `${this.urlRoot}?id=eq.${this.id}` + } + }); + + return Backbone.Collection.extend({ + model: PopulationSubDistrictSummary, + urlRoot: postgresUrl + 'mv_flood_event_population_sub_district_summary', + url: function () { + return this.urlRoot; + } + }); +}); diff --git a/frontend/app-dashboard/js/model/population_village_summary.js b/frontend/app-dashboard/js/model/population_village_summary.js new file mode 100644 index 0000000..ad37579 --- /dev/null +++ b/frontend/app-dashboard/js/model/population_village_summary.js @@ -0,0 +1,20 @@ +define([ + 'backbone', + 'moment' +], function (Backbone) { + + const PopulationVillageSummary = Backbone.Model.extend({ + urlRoot: postgresUrl + 'mv_flood_event_population_village_summary', + url: function () { + return `${this.urlRoot}?id=eq.${this.id}` + } + }); + + return Backbone.Collection.extend({ + model: PopulationVillageSummary, + urlRoot: postgresUrl + 'mv_flood_event_population_village_summary', + url: function () { + return this.urlRoot; + } + }); +}); diff --git a/frontend/app-dashboard/js/view/flood-collection.js b/frontend/app-dashboard/js/view/flood-collection.js index 5dbb913..8c880e8 100644 --- a/frontend/app-dashboard/js/view/flood-collection.js +++ b/frontend/app-dashboard/js/view/flood-collection.js @@ -12,8 +12,14 @@ define([ 'js/model/village_summary.js', 'js/model/road_district_summary.js', 'js/model/road_sub_district_summary.js', - 'js/model/road_village_summary.js' -], function (Backbone, _, moment, L, Wellknown, utils, ForecastEvent, TriggerStatusCollection, DistrictSummaryCollection, SubDistrictSummaryCollection, VillageSummaryCollection, RoadDistrictSummaryCollection, RoadSubDistrictSummaryCollection, RoadVillageSummaryCollection) { + 'js/model/road_village_summary.js', + 'js/model/population_district_summary.js', + 'js/model/population_sub_district_summary.js', + 'js/model/population_village_summary.js' +], function (Backbone, _, moment, L, Wellknown, utils, ForecastEvent, TriggerStatusCollection, + DistrictSummaryCollection, SubDistrictSummaryCollection, VillageSummaryCollection, + RoadDistrictSummaryCollection, RoadSubDistrictSummaryCollection, RoadVillageSummaryCollection, + PopulationDistrictSummaryCollection, PopulationSubDistrictSummaryCollection, PopulationVillageSummaryCollection) { return Backbone.View.extend({ el: '.panel-browse-flood', forecasts_list: [], @@ -31,6 +37,9 @@ define([ roadVillageStats: null, roadSubDistrictStats: null, roadDistrictStats: null, + populationVillageStats: null, + populationSubDistrictStats: null, + populationDistrictStats: null, areaLookup: null, fetchedDate: {}, events: { @@ -40,6 +49,11 @@ define([ 'blur': 'onFocusOut' }, legend: [], + keyStats: { + 'district': 'district_id', + 'sub_district': 'sub_district_id', + 'village': 'village_id' + }, initialize: function () { // jquery element this.$flood_info = this.$el.find('.flood-info'); @@ -61,6 +75,10 @@ define([ this.road_village_summaries = new RoadVillageSummaryCollection(); this.road_district_summaries = new RoadDistrictSummaryCollection(); this.road_subdistrict_summaries = new RoadSubDistrictSummaryCollection(); + // Uncomment this when population table is ready + // this.population_village_summaries = new PopulationVillageSummaryCollection(); + // this.population_district_summaries = new PopulationDistrictSummaryCollection(); + // this.population_subdistrict_summaries = new PopulationSubDistrictSummaryCollection(); // dispatcher registration dispatcher.on('flood:fetch-forecast-collection', this.fetchForecastCollection, this); @@ -306,6 +324,10 @@ define([ that.fetchRoadVillageData(that.selected_forecast.id); that.fetchRoadSubDistrictData(that.selected_forecast.id); that.fetchRoadDistrictData(that.selected_forecast.id); + // uncomment this when population table is ready. + // that.fetchPopulationVillageData(that.selected_forecast.id); + // that.fetchPopulationSubDistrictData(that.selected_forecast.id); + // that.fetchPopulationDistrictData(that.selected_forecast.id); }); // dispatch event to draw flood @@ -395,12 +417,6 @@ define([ 'sub_district': that.subDistrictStats }; - let key = { - 'district': 'district_id', - 'sub_district': 'sub_district_id', - 'village': 'village_id' - }; - let buildings = []; let overall = []; let region_render; @@ -440,7 +456,7 @@ define([ let statData = []; let subRegionList = that.getListSubRegion(sub_region, region_id); $.each(data[sub_region], function (index, value) { - if (subRegionList.indexOf(value[key[sub_region]]) >= 0) { + if (subRegionList.indexOf(value[that.keyStats[sub_region]]) >= 0) { statData.push(value) } }); @@ -458,7 +474,7 @@ define([ } for (let index = 0; index < data[region].length; index++) { - if (data[region][index][key[region]] === parseInt(region_id)) { + if (data[region][index][that.keyStats[region]] === parseInt(region_id)) { overall = data[region][index]; if (overall.hasOwnProperty('police_flooded_building_count')) { overall['police_station_flooded_building_count'] = overall['police_flooded_building_count']; @@ -469,10 +485,10 @@ define([ } overall['region'] = region; } - dispatcher.trigger('dashboard:render-chart-2', overall, main_panel); + dispatcher.trigger('dashboard:render-chart-building', overall, main_panel); if (region !== 'village') { - dispatcher.trigger('dashboard:render-region-summary', buildings, region_render, key[region_render]); + dispatcher.trigger('dashboard:render-region-summary', buildings, region_render, that.keyStats[region_render]); } }, fetchVillageData: function (flood_event_id) { @@ -577,12 +593,6 @@ define([ 'sub_district': that.roadSubDistrictStats }; - let key = { - 'district': 'district_id', - 'sub_district': 'sub_district_id', - 'village': 'village_id' - }; - let roads = []; let overall = []; let region_render; @@ -616,7 +626,7 @@ define([ let statData = []; let subRegionList = that.getListSubRegion(sub_region, region_id); $.each(data[sub_region], function (index, value) { - if (subRegionList.indexOf(value[key[sub_region]]) >= 0) { + if (subRegionList.indexOf(value[that.keyStats[sub_region]]) >= 0) { statData.push(value) } }); @@ -631,16 +641,16 @@ define([ } for (let index = 0; index < data[region].length; index++) { - if (data[region][index][key[region]] === parseInt(region_id)) { + if (data[region][index][that.keyStats[region]] === parseInt(region_id)) { overall = data[region][index]; break } } overall['region'] = region; } - dispatcher.trigger('dashboard:render-chart-road', overall); + dispatcher.trigger('dashboard:render-chart-element', overall, 'road'); if (region !== 'village') { - dispatcher.trigger('dashboard:inject-road-region-summary', roads, region_render, key[region_render]); + dispatcher.trigger('dashboard:inject-road-region-summary', roads, region_render, that.keyStats[region_render]); } }, fetchRoadDistrictData: function (flood_event_id) { @@ -694,5 +704,128 @@ define([ console.log(data) }); }, + fetchPopulationStatisticData: function (region, region_id, renderRegionDetail) { + if (!region) { + return [] + } + + let that = this; + let data = { + 'village': that.populationVillageStats, + 'district': that.populationDistrictStats, + 'sub_district': that.populationSubDistrictStats + }; + + let roads = []; + let overall = []; + let region_render; + if (renderRegionDetail) { + region_render = region; + $.each(data[region], function (idx, value) { + roads[idx] = []; + $.each(value, function (key, value) { + roads[idx][key] = value; + if (!overall[key]) { + overall[key] = value + } else { + overall[key] += value + } + }) + }); + delete overall['region_id']; + delete overall[region + '_id']; + delete overall['name']; + delete overall['village_id']; + delete overall['sub_district_id']; + delete overall['district_id']; + delete overall['trigger_status']; + } else { + let sub_region = 'sub_district'; + if (region === 'sub_district') { + sub_region = 'village' + } + region_render = sub_region; + + let statData = []; + let subRegionList = that.getListSubRegion(sub_region, region_id); + $.each(data[sub_region], function (index, value) { + if (subRegionList.indexOf(value[that.keyStats[sub_region]]) >= 0) { + statData.push(value) + } + }); + + if (region !== 'village') { + $.each(statData, function (idx, value) { + roads[idx] = []; + $.each(value, function (key, value) { + roads[idx][key] = value; + }) + }); + } + + for (let index = 0; index < data[region].length; index++) { + if (data[region][index][that.keyStats[region]] === parseInt(region_id)) { + overall = data[region][index]; + break + } + } + overall['region'] = region; + } + dispatcher.trigger('dashboard:render-chart-element', overall, 'population'); + if (region !== 'village') { + dispatcher.trigger('dashboard:inject-population-region-summary', roads, region_render, that.keyStats[region_render]); + } + }, + fetchPopulationDistrictData: function (flood_event_id) { + let that = this; + this.population_district_summaries.fetch({ + data: { + flood_event_id: `eq.${flood_event_id}`, + order: 'trigger_status.desc,total_vulnerability_score.desc' + } + }).then(function (data) { + that.roadDistrictStats = data; + if (that.roadVillageStats !== null && that.roadDistrictStats !== null && that.roadSubDistrictStats !== null) { + that.fetchRoadStatisticData('district', that.selected_forecast.id, true); + } + }).catch(function (data) { + console.log('District stats request failed'); + console.log(data); + }); + }, + fetchPopulationSubDistrictData: function (flood_event_id) { + let that = this; + this.population_subdistrict_summaries.fetch({ + data: { + flood_event_id: `eq.${flood_event_id}`, + order: 'trigger_status.desc,total_vulnerability_score.desc' + } + }).then(function (data) { + that.roadSubDistrictStats = data; + if (that.roadVillageStats !== null && that.roadDistrictStats !== null && that.roadSubDistrictStats !== null) { + that.fetchRoadStatisticData('district', that.selected_forecast.id, true); + } + }).catch(function (data) { + console.log('Sub district stats request failed'); + console.log(data); + }) + }, + fetchPopulationVillageData: function (flood_event_id) { + let that = this; + this.population_village_summaries.fetch({ + data: { + flood_event_id: `eq.${flood_event_id}`, + order: 'trigger_status.desc,total_vulnerability_score.desc' + } + }).then(function (data) { + that.roadVillageStats = data; + if (that.roadVillageStats !== null && that.roadDistrictStats !== null && that.roadSubDistrictStats !== null) { + that.fetchRoadStatisticData('district', that.selected_forecast.id, true); + } + }).catch(function (data) { + console.log('Village stats request failed'); + console.log(data) + }); + }, }) }); diff --git a/frontend/app-dashboard/js/view/panel-dashboard.js b/frontend/app-dashboard/js/view/panel-dashboard.js index 2c1c21c..09a5aba 100644 --- a/frontend/app-dashboard/js/view/panel-dashboard.js +++ b/frontend/app-dashboard/js/view/panel-dashboard.js @@ -31,8 +31,8 @@ define([ }, initialize: function () { this.referer_region = []; - dispatcher.on('dashboard:render-chart-2', this.renderChart2, this); - dispatcher.on('dashboard:render-chart-road', this.renderChartRoad, this); + dispatcher.on('dashboard:render-chart-building', this.renderChartBuilding, this); + dispatcher.on('dashboard:render-chart-element', this.renderChartElement, this); dispatcher.on('dashboard:reset', this.resetDashboard, this); dispatcher.on('dashboard:hide', this.hideDashboard, this); dispatcher.on('dashboard:render-region-summary', this.renderRegionSummary, this); @@ -73,12 +73,12 @@ define([ $('#road-count').html(that.loading_template); this.changeStatus(floodCollectionView.selected_forecast.attributes.trigger_status); }, - renderChartRoad: function (data) { + renderChartElement: function (data, element) { let $parentWrapper = $('#chart-score-panel'); - $parentWrapper.find('#summary-chart-road').remove(); - $parentWrapper.find('.panel-chart-road').html(''); - $parentWrapper.find('#summary-chart-road-residential').remove(); - $parentWrapper.find('.panel-chart-road-residential').html(''); + $parentWrapper.find('#summary-chart-' + element).remove(); + $parentWrapper.find('.panel-chart-' + element).html(''); + $parentWrapper.find('#summary-chart-' + element + '-residential').remove(); + $parentWrapper.find('.panel-chart-' + element + '-residential').html(''); let total_road_array = []; let graph_data = []; @@ -175,11 +175,11 @@ define([ }; let total_vulnerability_score = data['total_vulnerability_score'] ? data['total_vulnerability_score'].toFixed(2): 0; - $('#vulnerability-score-road').html(total_vulnerability_score); - $('#road-count').html(data['flooded_flooded_road_count']); - this.renderChartData(datasets, ctx, 'Residential Roads', datasetsResidential, ctxResidential, 'Other Roads'); + $('#vulnerability-score-' + element).html(total_vulnerability_score); + $('#'+ element +'-count').html(data['flooded_flooded_road_count']); + this.renderChartData(datasets, ctx, 'Residential ' + toTitleCase(element) + 's', datasetsResidential, ctxResidential, 'Other ' + toTitleCase(element) + 's'); }, - renderChart2: function (data, main_panel) { + renderChartBuilding: function (data, main_panel) { let that = this; let id_key = { 'district': 'district_id', @@ -392,6 +392,7 @@ define([ name: item['name'], flooded_road_count: that.loading_template, flooded_building_count: building_total_score, + flooded_population_count: '-', trigger_status: trigger_status })); } @@ -578,8 +579,16 @@ define([ let $div = $(e.target).closest('.tab-title'); if(!$div.hasClass('tab-active')) { $('.tab-wrapper').hide(); - $('.tab-title').removeClass('tab-active'); - $div.addClass('tab-active'); + $('.tab-title').removeClass('tab-active').removeClass('col-lg-6'); + $('.tab-title').each(function () { + let that = this; + if(!$(that).hasClass('col-lg-3')){ + $(that).addClass('col-lg-3') + } + }); + $div.addClass('tab-active').removeClass('col-lg-3').addClass('col-lg-6'); + $('.tab-name').hide(); + $div.find('.tab-name').show(); let target = $div.attr('tab-target'); $('.tab-' + target).show(); }