Mercurial > gemma
view client/src/components/Bottlenecks.vue @ 2640:4bcb26542767
client: use new btn-xs class in tables
author | Markus Kottlaender <markus@intevation.de> |
---|---|
date | Thu, 14 Mar 2019 11:23:42 +0100 |
parents | 468c8dc796cf |
children | add2d47c2567 |
line wrap: on
line source
<template> <div> <UIBoxHeader icon="ship" title="Bottlenecks" :closeCallback="$parent.close" /> <UITableHeader :columns="[ { id: 'name', title: 'Name', class: 'col-4' }, { id: 'latestMeasurement', title: 'Latest Measurement', class: 'col-3' }, { id: 'chainage', title: 'Chainage', class: 'col-3' } ]" @sortingChanged="sortBy" /> <UITableBody :data="filteredAndSortedBottlenecks()" :maxHeight="(showSplitscreen ? 18 : 35) + 'rem'" :active="openBottleneck" v-slot="{ item: bottleneck }" > <div class="col-4 py-2 text-left"> <a href="#" @click="selectBottleneck(bottleneck)">{{ bottleneck.properties.name }}</a> </div> <div class="col-3 py-2"> {{ bottleneck.properties.current | surveyDate }} </div> <div class="col-3 py-2"> {{ displayCurrentChainage( bottleneck.properties.from, bottleneck.properties.to ) }} </div> <div class="col-2 pr-0 text-right d-flex flex-column"> <a class="text-info mt-auto mb-auto mr-2" @click="loadSurveys(bottleneck)" v-if="bottleneck.properties.current" > <font-awesome-icon class="pointer" icon="spinner" fixed-width spin v-if="loading === bottleneck" ></font-awesome-icon> <font-awesome-icon class="pointer" icon="angle-down" fixed-width v-if="loading !== bottleneck && openBottleneck !== bottleneck" ></font-awesome-icon> <font-awesome-icon class="pointer" icon="angle-up" fixed-width v-if="loading !== bottleneck && openBottleneck === bottleneck" ></font-awesome-icon> </a> </div> <div :class="[ 'col-12 p-0', 'surveys', { open: openBottleneck === bottleneck } ]" > <a href="#" class="d-inline-block px-3 py-2" v-for="(survey, index) in openBottleneckSurveys" :key="index" @click="selectSurvey(survey, bottleneck)" > {{ survey.date_info | surveyDate }} </a> </div> </UITableBody> </div> </template> <style lang="sass" scoped> .table-body .row > div:not(:last-child) transition: background-color 0.3s, color 0.3s &.active > div:not(:last-child) background-color: $color-info color: #fff a color: #fff !important .surveys border-bottom: solid 1px $color-info .surveys overflow: hidden max-height: 0 &.open overflow-y: auto max-height: 5rem </style> <script> /* This is Free Software under GNU Affero General Public License v >= 3.0 * without warranty, see README.md and license for details. * * SPDX-License-Identifier: AGPL-3.0-or-later * License-Filename: LICENSES/AGPL-3.0.txt * * Copyright (C) 2018 by via donau * – Österreichische Wasserstraßen-Gesellschaft mbH * Software engineering by Intevation GmbH * * Author(s): * Markus Kottländer <markus.kottlaender@intevation.de> */ import { mapState } from "vuex"; import { HTTP } from "@/lib/http"; import { displayError } from "@/lib/errors.js"; export default { name: "bottlenecks", data() { return { sortColumn: "name", sortDirection: "ASC", openBottleneck: null, openBottleneckSurveys: null, loading: null }; }, computed: { ...mapState("application", [ "searchQuery", "showSearchbarLastState", "showSplitscreen" ]), ...mapState("bottlenecks", ["bottlenecksList"]), sortIcon() { return this.sortDirection === "ASC" ? "sort-amount-down" : "sort-amount-up"; } }, methods: { filteredAndSortedBottlenecks() { return this.bottlenecksList .filter(bn => { return bn.properties.name .toLowerCase() .includes(this.searchQuery.toLowerCase()); }) .sort((bnA, bnB) => { switch (this.sortColumn) { case "name": if ( bnA.properties.name.toLowerCase() < bnB.properties.name.toLowerCase() ) return this.sortDirection === "ASC" ? -1 : 1; if ( bnA.properties.name.toLowerCase() > bnB.properties.name.toLowerCase() ) return this.sortDirection === "ASC" ? 1 : -1; return 0; case "latestMeasurement": { if ( (bnA.properties.current || "") < (bnB.properties.current || "") ) return this.sortDirection === "ASC" ? -1 : 1; if ( (bnA.properties.current || "") > (bnB.properties.current || "") ) return this.sortDirection === "ASC" ? 1 : -1; return 0; } case "chainage": if (bnA.properties.from < bnB.properties.from) return this.sortDirection === "ASC" ? -1 : 1; if (bnA.properties.from > bnB.properties.from) return this.sortDirection === "ASC" ? 1 : -1; return 0; default: return 0; } }); }, selectSurvey(survey, bottleneck) { this.$store .dispatch( "bottlenecks/setSelectedBottleneck", bottleneck.properties.name ) .then(() => { this.$store.commit("bottlenecks/selectedSurvey", survey); }) .then(() => { this.$store.commit("map/moveToExtent", { feature: bottleneck, zoom: 17, preventZoomOut: true }); }); }, selectBottleneck(bottleneck) { this.$store .dispatch( "bottlenecks/setSelectedBottleneck", bottleneck.properties.name ) .then(() => { this.$store.commit("bottlenecks/setFirstSurveySelected"); }) .then(() => { this.$store.commit("map/moveToExtent", { feature: bottleneck, zoom: 17, preventZoomOut: true }); }); }, sortBy(sorting) { this.sortColumn = sorting.sortColumn; this.sortDirection = sorting.sortDirection; }, loadSurveys(bottleneck) { if (bottleneck === this.openBottleneck) { this.openBottleneck = null; this.openBottleneckSurveys = null; } else { this.loading = bottleneck; HTTP.get("/surveys/" + bottleneck.properties.name, { headers: { "X-Gemma-Auth": localStorage.getItem("token"), "Content-type": "text/xml; charset=UTF-8" } }) .then(response => { this.openBottleneckSurveys = response.data.surveys.sort((a, b) => { return a.date_info < b.date_info ? 1 : -1; }); this.openBottleneck = bottleneck; }) .catch(error => { const { status, data } = error.response; displayError({ title: this.$gettext("Backend Error"), message: `${status}: ${data.message || data}` }); }) .finally(() => (this.loading = null)); } }, displayCurrentChainage(from, to) { return from / 10 + " - " + to / 10; } }, mounted() { this.$store.dispatch("bottlenecks/loadBottlenecksList"); } }; </script>