Skip to content

Commit

Permalink
feat: color picker for pie chart
Browse files Browse the repository at this point in the history
  • Loading branch information
nextchamp-saqib committed Oct 10, 2022
1 parent b31468e commit b91deae
Show file tree
Hide file tree
Showing 4 changed files with 112 additions and 25 deletions.
115 changes: 94 additions & 21 deletions frontend/src/components/Controls/Color.vue
Original file line number Diff line number Diff line change
Expand Up @@ -10,16 +10,27 @@
:class="inputClass"
class="flex h-8 w-full items-center rounded-md bg-gray-100 px-3 placeholder-gray-500 focus:outline-none"
@click="togglePopover()"
readonly
>
<div class="flex items-center">
<div
v-if="value"
class="mr-1 h-3 w-3 rounded"
:style="{ backgroundColor: value }"
></div>
<span v-if="value">
{{ selectedColorLabel }}
</span>
class="flex items-center space-x-2"
v-if="(!multiple && value) || (multiple && value.length > 0)"
>
<div class="flex -space-x-2 overflow-hidden">
<div
v-for="(color, idx) in multiple && value.length > 0
? value
: [value]"
:key="idx"
class="h-5 w-5 rounded-full"
:style="{ backgroundColor: color }"
></div>
</div>
<span>
{{ selectedColorLabel }}
</span>
</div>
<span class="text-gray-400" v-else>
{{ placeholder || label }}
</span>
Expand All @@ -30,21 +41,41 @@
<div class="mt-1 w-fit rounded-md border bg-white p-3 pt-2 text-center shadow-md">
<div>
<div class="inline-grid grid-cols-5 gap-3 border-b border-none">
<div class="col-span-5 text-left text-base">Pick a color</div>
<div
class="col-span-5 text-left text-sm uppercase tracking-wide text-gray-500"
>
Select Color
</div>
<div
v-for="color in colors"
:key="color"
class="h-5 w-5 cursor-pointer rounded"
:style="{ backgroundColor: color }"
@click="setColorValue(color)"
></div>
class="flex h-5 w-5 cursor-pointer items-center justify-center rounded bg-opacity-50"
:class="[
isSelected(color) ? 'bg-opacity-50 shadow' : 'bg-opacity-100',
]"
:style="{
backgroundColor: color,
}"
@click="toggleColor(color)"
>
<FeatherIcon
v-if="isSelected(color)"
class="h-4 w-4 text-white"
name="check"
@click.prevent.stop="toggleColor(color)"
></FeatherIcon>
</div>
<div
class="col-span-5 text-left text-sm uppercase tracking-wide text-gray-500"
>
Hex
</div>
<input
ref="input"
type="text"
:value="value"
placeholder="Custom Hex"
:class="inputClass"
class="col-span-5 flex h-8 items-center rounded-md border-0 bg-gray-100 px-3 text-base placeholder-gray-500 focus:outline-none"
class="col-span-5 -mt-1 flex h-8 items-center rounded-md border-0 bg-gray-100 px-3 text-base placeholder-gray-500 focus:outline-none"
@change="(e) => setColorValue(e.target.value)"
/>
</div>
Expand All @@ -56,14 +87,19 @@
</template>

<script>
import { COLOR_MAP } from '@/utils/charts/colors'
export default {
name: 'Color',
props: {
label: String,
modelValue: String,
modelValue: [String, Array],
options: Array,
inputClass: String,
placeholder: String,
autofocus: Boolean,
multiple: Boolean,
max: Number,
},
emits: ['focus', 'update:modelValue'],
mounted() {
Expand All @@ -78,35 +114,72 @@ export default {
}
},
setColorValue(value) {
if (this.multiple && this.max) {
if (this.value.length >= this.max) {
return
}
}
if (this.isValidColor(value)) {
this.triggerChange(value)
}
},
isValidColor(value) {
if (!value.startsWith('#')) {
value = '#' + value
}
if (/^#[0-9A-F]{6}$/i.test(value)) {
this.triggerChange(value)
return true
}
return false
},
triggerChange(value) {
if (value === '') {
value = null
}
this.$emit('update:modelValue', value)
if (this.multiple) {
this.$emit('update:modelValue', [...this.modelValue, value])
} else {
this.$emit('update:modelValue', value)
}
},
isSelected(color) {
if (this.multiple) {
return this.value.includes(color)
}
return this.value === color
},
toggleColor(color) {
if (this.isSelected(color)) {
this.removeColor(color)
} else {
this.setColorValue(color)
}
},
removeColor(color) {
if (this.multiple) {
const value = this.modelValue.filter((c) => c !== color)
this.$emit('update:modelValue', value)
}
},
},
computed: {
value: {
get() {
return this.modelValue
if (this.multiple) {
!this.modelValue && this.$emit('update:modelValue', [])
return this.modelValue || []
}
return Array.isArray(this.modelValue) ? this.modelValue[0] : this.modelValue
},
set(value) {
this.setColorValue(value)
},
},
colors() {
return ['#23546B', '#2F7A8B', '#3B9FAA', '#47C5C9', '#53ECE9']
return this.options || Object.values(COLOR_MAP)
},
selectedColorLabel() {
const color = this.colors.find((c) => this.value === c.value)
return color ? color.label : this.value
return this.multiple ? this.modelValue.length + ' colors selected' : this.modelValue
},
},
}
Expand Down
2 changes: 1 addition & 1 deletion frontend/src/components/Query/Visualize/PieChart.vue
Original file line number Diff line number Diff line change
Expand Up @@ -92,7 +92,7 @@ function updateLegendOptions(position) {
</script>
<template>
<Chart :title="props.title" :subtitle="props.subtitle">
<Chart :title="props.title" :subtitle="props.subtitle" :color="props.options.colors">
<ChartSeries
type="pie"
:name="dataset.label"
Expand Down
7 changes: 5 additions & 2 deletions frontend/src/components/Query/Visualize/PieChartOptions.vue
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
<script setup>
import { inject } from 'vue'
import { inject, computed } from 'vue'
import Autocomplete from '@/components/Controls/Autocomplete.vue'
import Color from '@/components/Controls/Color.vue'
const query = inject('query')
const chart = inject('chart')
Expand All @@ -19,7 +20,7 @@ const chart = inject('chart')

<div class="space-y-2 text-gray-600">
<div class="text-base font-light text-gray-500">Maximum Slices</div>
<Input class="h-8" v-model="chart.options.maxSlices" type="number" value="10" />
<Input class="h-8" v-model="chart.options.maxSlices" type="number" />
</div>

<div class="space-y-2 text-gray-600">
Expand All @@ -30,5 +31,7 @@ const chart = inject('chart')
/>
</div>

<Color label="Colors" v-model="chart.options.colors" :max="chart.options.maxSlices" multiple />

<Checkbox class="text-gray-600" v-model="chart.options.scrollLabels" label="Paginate Labels" />
</template>
13 changes: 12 additions & 1 deletion frontend/src/utils/charts/colors.js
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
const COLOR_MAP = {
export const COLOR_MAP = {
pink: '#F683AE',
blue: '#318AD8',
green: '#48BB74',
Expand All @@ -9,6 +9,17 @@ const COLOR_MAP = {
cyan: '#15CCEF',
orange: '#F8814F',
grey: '#A6B1B9',
'#449CF0': '#449CF0',
'#ECAD4B': '#ECAD4B',
'#761ACB': '#761ACB',
'#CB2929': '#CB2929',
'#ED6396': '#ED6396',
'#29CD42': '#29CD42',
'#4463F0': '#4463F0',
'#EC864B': '#EC864B',
'#4F9DD9': '#4F9DD9',
'#39E4A5': '#39E4A5',
'#B4CD29': '#B4CD29',
}

const LIGHT_COLOR_MAP = {
Expand Down

0 comments on commit b91deae

Please sign in to comment.