Add structured values support to <dougal-event-edit/>

This commit is contained in:
D. Berge
2023-10-28 20:02:13 +02:00
parent 83c3f9b401
commit a369f2dd7b

View File

@@ -123,29 +123,11 @@
<v-row dense> <v-row dense>
<v-col cols="12"> <v-col cols="12">
<v-combobox <dougal-event-select
ref="remarks" v-bind.sync="entryRemarks"
v-model="entryRemarks" :preset-remarks="presetRemarks"
:disabled="loading" @update:labels="(v) => this.entryLabels = v"
:search-input.sync="entryRemarksInput" ></dougal-event-select>
:items="remarksAvailable"
:filter="searchRemarks"
item-text="text"
return-object
label="Remarks"
hint="Placeholders: @DMS@, @DEG@, @EN@, @WD@, @BSP@, @CMG@, …"
prepend-icon="mdi-text-box-outline"
append-outer-icon="mdi-magnify"
@click:append-outer="(e) => remarksMenu = e"
></v-combobox>
<dougal-context-menu
:value="remarksMenu"
@input="handleRemarksMenu"
:items="presetRemarks"
absolute
></dougal-context-menu>
</v-col> </v-col>
</v-row> </v-row>
@@ -290,6 +272,7 @@
<script> <script>
import { mapActions } from 'vuex'; import { mapActions } from 'vuex';
import DougalContextMenu from '@/components/context-menu'; import DougalContextMenu from '@/components/context-menu';
import DougalEventSelect from '@/components/event-select';
function stringSort (a, b) { function stringSort (a, b) {
return a == b return a == b
@@ -308,6 +291,7 @@ function flattenRemarks(items, keywords=[], labels=[]) {
if (!item.items) { if (!item.items) {
result.push({ result.push({
text: item.text, text: item.text,
properties: item.properties,
labels: labels.concat(item.labels??[]), labels: labels.concat(item.labels??[]),
keywords keywords
}) })
@@ -342,7 +326,8 @@ export default {
name: 'DougalEventEdit', name: 'DougalEventEdit',
components: { components: {
DougalContextMenu DougalContextMenu,
DougalEventSelect
}, },
props: { props: {
@@ -354,6 +339,7 @@ export default {
sequence: { type: Number }, sequence: { type: Number },
point: { type: Number }, point: { type: Number },
remarks: { type: String }, remarks: { type: String },
meta: { type: Object },
labels: { type: Array, default: () => [] }, labels: { type: Array, default: () => [] },
latitude: { type: Number }, latitude: { type: Number },
longitude: { type: Number }, longitude: { type: Number },
@@ -371,18 +357,11 @@ export default {
entrySequence: null, entrySequence: null,
entryPoint: null, entryPoint: null,
entryRemarks: null, entryRemarks: null,
entryRemarksInput: null,
entryLatitude: null, entryLatitude: null,
entryLongitude: null entryLongitude: null
}), }),
computed: { computed: {
remarksAvailable () {
return this.entryRemarksInput == this.entryRemarks?.text ||
this.entryRemarksInput == this.entryRemarks
? []
: flattenRemarks(this.presetRemarks);
},
allSelected () { allSelected () {
return this.entryLabels.length === this.items.length return this.entryLabels.length === this.items.length
@@ -394,11 +373,6 @@ export default {
return true; return true;
} }
// The user is editing the remarks
if (this.entryRemarksText != this.entryRemarksInput) {
return true;
}
// Selected label set distinct from input labels // Selected label set distinct from input labels
if (distinctSets(this.selectedLabels, this.entryLabels, (i) => i.text)) { if (distinctSets(this.selectedLabels, this.entryLabels, (i) => i.text)) {
return true; return true;
@@ -502,11 +476,8 @@ export default {
this.entrySequence = this.sequence; this.entrySequence = this.sequence;
this.entryPoint = this.point; this.entryPoint = this.point;
this.entryRemarks = this.remarks;
this.entryLabels = [...(this.labels??[])]; this.entryLabels = [...(this.labels??[])];
this.makeEntryRemarks();
// Focus remarks field
this.$nextTick(() => this.$refs.remarks.focus());
} }
}, },
@@ -577,22 +548,13 @@ export default {
}; };
}, },
searchRemarks (item, queryText, itemText) { makeEntryRemarks () {
const needle = queryText.toLowerCase(); this.entryRemarks = {
const text = item.text.toLowerCase(); template: null,
const keywords = item.keywords.map(i => i.toLowerCase()); schema: {},
const labels = item.labels.map(i => i.toLowerCase()); values: [],
return text.includes(needle) || ...this.meta?.structured_values,
keywords.some(i => i.includes(needle)) || text: this.remarks
labels.some(i => i.includes(needle));
},
handleRemarksMenu (event) {
if (typeof event == 'boolean') {
this.remarksMenu = event;
} else {
this.entryRemarks = event;
this.remarksMenu = false;
} }
}, },
@@ -657,14 +619,24 @@ export default {
save () { save () {
// In case the focus goes directly from the remarks field // In case the focus goes directly from the remarks field
// to the Save button. // to the Save button.
if (this.entryRemarksInput != this.entryRemarksText) {
this.entryRemarks = this.entryRemarksInput; let meta;
if (this.entryRemarks.values?.length) {
meta = {
structured_values: {
template: this.entryRemarks.template,
schema: this.entryRemarks.schema,
values: this.entryRemarks.values
}
};
} }
const data = { const data = {
id: this.id, id: this.id,
remarks: this.entryRemarksText, remarks: this.entryRemarksText,
labels: this.entryLabels labels: this.entryLabels,
meta
}; };
/* NOTE This is the purist way. /* NOTE This is the purist way.