|
@@ -1,23 +1,29 @@
|
|
<script setup lang="ts" >
|
|
<script setup lang="ts" >
|
|
|
|
+import { useStore } from '@/store';
|
|
import { UABaseNode } from '@/ua/UABaseNode';
|
|
import { UABaseNode } from '@/ua/UABaseNode';
|
|
-import { ref, computed } from 'vue'
|
|
|
|
|
|
+import { storeToRefs } from 'pinia';
|
|
|
|
+import { ref, computed, watch } from 'vue'
|
|
|
|
+
|
|
|
|
+
|
|
|
|
+const store = useStore()
|
|
|
|
+const { selectedNode } = storeToRefs(store)
|
|
|
|
+
|
|
|
|
|
|
const props = defineProps<{
|
|
const props = defineProps<{
|
|
model: UABaseNode,
|
|
model: UABaseNode,
|
|
filterFunc?: Function,
|
|
filterFunc?: Function,
|
|
- selectedNode: UABaseNode
|
|
|
|
|
|
+ markSelected: Boolean
|
|
}>();
|
|
}>();
|
|
|
|
|
|
|
|
+const emit = defineEmits(['selectNode']);
|
|
|
|
+
|
|
const isOpen = ref(false)
|
|
const isOpen = ref(false)
|
|
|
|
+const selected = ref(false)
|
|
const isFolder = computed(() => {
|
|
const isFolder = computed(() => {
|
|
const children=props.model?.getChildren();
|
|
const children=props.model?.getChildren();
|
|
return children && children.length;
|
|
return children && children.length;
|
|
})
|
|
})
|
|
|
|
|
|
-const isSelected = computed(() => {
|
|
|
|
- return (props.selectedNode?.nodeId.toString()===props.model?.nodeId.toString())
|
|
|
|
-})
|
|
|
|
-
|
|
|
|
const isFiltered = computed(() => {
|
|
const isFiltered = computed(() => {
|
|
if(!props.filterFunc)
|
|
if(!props.filterFunc)
|
|
return false;
|
|
return false;
|
|
@@ -31,14 +37,26 @@ const children = computed(() => {
|
|
function toggle() {
|
|
function toggle() {
|
|
isOpen.value = !isOpen.value
|
|
isOpen.value = !isOpen.value
|
|
}
|
|
}
|
|
|
|
+function selectNode(node:UABaseNode) {
|
|
|
|
+ emit('selectNode', node);
|
|
|
|
+ //this hack avoids updating props and re-evaluating the whole tree on select
|
|
|
|
+ //Needs ref to store unfortunately
|
|
|
|
+ if(props.markSelected) {
|
|
|
|
+ selected.value=true;
|
|
|
|
+ const unwatch = watch(selectedNode, () => {
|
|
|
|
+ selected.value=false;
|
|
|
|
+ unwatch();
|
|
|
|
+ });
|
|
|
|
+ }
|
|
|
|
+}
|
|
</script>
|
|
</script>
|
|
|
|
|
|
<template>
|
|
<template>
|
|
<li>
|
|
<li>
|
|
<div v-if="model" :class="{ bold: isFolder }">
|
|
<div v-if="model" :class="{ bold: isFolder }">
|
|
<span v-if="isFolder" @click="toggle">[{{ isOpen ? '-' : '+' }}]</span>
|
|
<span v-if="isFolder" @click="toggle">[{{ isOpen ? '-' : '+' }}]</span>
|
|
- <span @click.stop="$emit('selectNode', model)" class="itemtext" :class="[(isFiltered?'disabled':''),
|
|
|
|
- isSelected?'selected':'' ]">
|
|
|
|
|
|
+ <span @click.stop="selectNode(model)" class="itemtext" :class="[(isFiltered?'disabled':''),
|
|
|
|
+ selected?'selected':'' ]">
|
|
{{ model.displayName }}
|
|
{{ model.displayName }}
|
|
</span>
|
|
</span>
|
|
</div>
|
|
</div>
|
|
@@ -47,10 +65,10 @@ function toggle() {
|
|
class="item"
|
|
class="item"
|
|
:filter-func = "$props.filterFunc"
|
|
:filter-func = "$props.filterFunc"
|
|
@select-node="(node: UABaseNode) => $emit('selectNode', node)"
|
|
@select-node="(node: UABaseNode) => $emit('selectNode', node)"
|
|
|
|
+ :markSelected="markSelected"
|
|
v-for="child in children"
|
|
v-for="child in children"
|
|
v-bind:key="child.nodeId.toString()"
|
|
v-bind:key="child.nodeId.toString()"
|
|
- :model="child"
|
|
|
|
- :selectedNode="$props.selectedNode">
|
|
|
|
|
|
+ :model="child">
|
|
</TreeItem>
|
|
</TreeItem>
|
|
</ul>
|
|
</ul>
|
|
</li>
|
|
</li>
|