diff options
| author | syuilo <Syuilotan@yahoo.co.jp> | 2023-01-03 14:08:52 +0900 |
|---|---|---|
| committer | syuilo <Syuilotan@yahoo.co.jp> | 2023-01-03 14:08:52 +0900 |
| commit | fb05e86db72740933292f105da3fce43b8fafb1f (patch) | |
| tree | 350c5e7f18444a9fbcc46088d3ffaee3a09e43a6 /packages/frontend/src/components | |
| parent | perf(client): use shallowRef instead of ref for template reference (diff) | |
| download | misskey-fb05e86db72740933292f105da3fce43b8fafb1f.tar.gz misskey-fb05e86db72740933292f105da3fce43b8fafb1f.tar.bz2 misskey-fb05e86db72740933292f105da3fce43b8fafb1f.zip | |
:art:
Diffstat (limited to 'packages/frontend/src/components')
| -rw-r--r-- | packages/frontend/src/components/MkChart.vue | 13 | ||||
| -rw-r--r-- | packages/frontend/src/components/MkChartLegend.vue | 75 |
2 files changed, 82 insertions, 6 deletions
diff --git a/packages/frontend/src/components/MkChart.vue b/packages/frontend/src/components/MkChart.vue index c0562f02e3..ea28cfa794 100644 --- a/packages/frontend/src/components/MkChart.vue +++ b/packages/frontend/src/components/MkChart.vue @@ -1,6 +1,7 @@ <template> <div class="cbbedffa"> <canvas ref="chartEl"></canvas> + <MkChartLegend ref="legendEl" style="margin-top: 8px;"/> <div v-if="fetching" class="fetching"> <MkLoading/> </div> @@ -24,6 +25,8 @@ import { chartVLine } from '@/scripts/chart-vline'; import { alpha } from '@/scripts/color'; import date from '@/filters/date'; import { initChart } from '@/scripts/init-chart'; +import { chartLegend } from '@/scripts/chart-legend'; +import MkChartLegend from '@/components/MkChartLegend.vue'; initChart(); @@ -67,6 +70,8 @@ const props = defineProps({ }, }); +let legendEl = $shallowRef<InstanceType<typeof MkChartLegend>>(); + const sum = (...arr) => arr.reduce((r, a) => r.map((b, i) => a[i] + b)); const negate = arr => arr.map(x => -x); @@ -220,11 +225,7 @@ const render = () => { }, plugins: { legend: { - display: props.detailed, - position: 'bottom', - labels: { - boxWidth: 16, - }, + display: false, }, tooltip: { enabled: false, @@ -264,7 +265,7 @@ const render = () => { gradient, }, }, - plugins: [chartVLine(vLineColor)], + plugins: [chartVLine(vLineColor), ...(props.detailed ? [chartLegend(legendEl)] : [])], }); }; diff --git a/packages/frontend/src/components/MkChartLegend.vue b/packages/frontend/src/components/MkChartLegend.vue new file mode 100644 index 0000000000..f33f753723 --- /dev/null +++ b/packages/frontend/src/components/MkChartLegend.vue @@ -0,0 +1,75 @@ +<template> +<div :class="$style.root"> + <button v-for="item in items" class="_button item" :class="{ disabled: item.hidden }" @click="onClick(item)"> + <span class="box" :style="{ background: chart.config.type === 'line' ? item.strokeStyle?.toString() : item.fillStyle?.toString() }"></span> + {{ item.text }} + </button> +</div> +</template> + +<script lang="ts" setup> +import { onMounted, ref, shallowRef, watch, PropType, onUnmounted } from 'vue'; +import { Chart, LegendItem } from 'chart.js'; + +const props = defineProps({ +}); + +let chart = $shallowRef<Chart>(); +let items = $shallowRef<LegendItem[]>([]); + +function update(_chart: Chart, _items: LegendItem[]) { + chart = _chart, + items = _items; +} + +function onClick(item: LegendItem) { + if (chart == null) return; + const { type } = chart.config; + if (type === 'pie' || type === 'doughnut') { + // Pie and doughnut charts only have a single dataset and visibility is per item + chart.toggleDataVisibility(item.index); + } else { + chart.setDatasetVisibility(item.datasetIndex, !chart.isDatasetVisible(item.datasetIndex)); + } + chart.update(); +} + +defineExpose({ + update, +}); +</script> + +<style lang="scss" module> +.root { + display: flex; + flex-wrap: wrap; + justify-content: center; + gap: 8px; + + &:global { + > .item { + font-size: 85%; + padding: 4px 12px 4px 8px; + border: solid 1px var(--divider); + border-radius: 999px; + + &:hover { + border-color: var(--inputBorderHover); + } + + &.disabled { + text-decoration: line-through; + opacity: 0.6; + } + + > .box { + display: inline-block; + width: 12px; + height: 12px; + border-radius: 100%; + vertical-align: -10%; + } + } + } +} +</style> |