Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Custom 3D-views #60

Merged
merged 7 commits into from
Jun 18, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 1 addition & 5 deletions src/components/Graphs/SelectablePieChart.vue
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,6 @@
<script lang="ts">
import * as d3 from 'd3'
import { ref, reactive, onMounted, watch, type PropType } from 'vue'
import chroma from 'chroma-js'

import { getValueColorFromGradient } from '@/utils/colors'
import { truncateText } from '@/utils/projectUtils'
Expand Down Expand Up @@ -42,7 +41,6 @@ export default {
const svg = ref<SVGSVGElement | null>(null)
const tooltip = ref<HTMLDivElement | null>(null)
const container = ref<HTMLDivElement | null>(null)
const options: ChartOptions = props.options

//Clear so we dont get overlaps
const clearSVG = () => {
Expand Down Expand Up @@ -107,7 +105,6 @@ function SelectablePieChart(data: ChartData[], options: ChartOptions = {}) {
const margin = reactive(options.margin || { top: 20, right: 20, bottom: 20, left: 20 })

const total = ref(d3.sum(data, d => d.value))
const totalAbs = ref(d3.sum(data, d => Math.abs(d.value)))
const groupData = ref(groupDataFunc(data, total))

const w = width.value - margin.left - margin.right
Expand Down Expand Up @@ -173,7 +170,7 @@ function SelectablePieChart(data: ChartData[], options: ChartOptions = {}) {
}

tooltipDiv
.html(data.data.label + ": " + roundNumber(data.value, 3) + " " + unit)
.html(data.data.label + ": " + roundNumber(data.data.value, 3) + " " + unit)
.style("left", left + "px")
.style("top", top + "px")
}
Expand All @@ -182,7 +179,6 @@ function SelectablePieChart(data: ChartData[], options: ChartOptions = {}) {

//Need to get this beforehand so that we can select the fill and darken it on mouseleave
const element = d3.select(event.currentTarget as Element)
const fillColor = element.style("fill")

if(element.node().tagName === 'text'){
element
Expand Down
6 changes: 5 additions & 1 deletion src/components/Mapping/MaterialMappingCard.vue
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,8 @@ import { useMaterialStore } from '@/stores/material'

import type { NestedGroup } from '@/models/filters'
import { useProjectStore } from '@/stores/main'
import { getMappedMaterial } from '@/utils/projectUtils'
import { useSpeckleStore } from '@/stores/speckle'
import { getMappedMaterial, setMappingColorGroup } from '@/utils/projectUtils'

export default defineComponent({
name: 'MappingCard',
Expand All @@ -51,6 +52,7 @@ export default defineComponent({
setup(props) {
const materialStore = useMaterialStore()
const projStore = useProjectStore()
const speckleStore = useSpeckleStore()

const inGroup = ref(props.group)

Expand All @@ -66,6 +68,8 @@ export default defineComponent({
obj.material = materialStore.currentMapping
}
})
const mappingColors = setMappingColorGroup()
speckleStore.setColorGroups(mappingColors)
}

// Open sub group if there are any
Expand Down
117 changes: 117 additions & 0 deletions src/components/Misc/RenderToggle.vue
Original file line number Diff line number Diff line change
@@ -0,0 +1,117 @@
<template>
<Switch
v-model="renderMode"
:class="[
!renderMode ? 'bg-indigo-600' : 'bg-gray-200',
'relative inline-flex mt-4 mb-2 mr-4 h-6 w-11 flex-shrink-0 cursor-pointer rounded-full border-2 border-transparent transition-colors duration-200 ease-in-out focus:outline-none focus:ring-2 focus:ring-indigo-600 focus:ring-offset-2'
]"
@click="toggleRenderMode"
>
<span class="sr-only">Toggle Render Mode</span>
<span
:class="[
!renderMode ? 'translate-x-5' : 'translate-x-0',
'pointer-events-none relative inline-block h-5 w-5 transform rounded-full bg-white shadow ring-0 transition duration-200 ease-in-out'
]"
>
<span
:class="[
!renderMode ? 'opacity-0 duration-100 ease-out' : 'opacity-100 duration-200 ease-in',
'absolute inset-0 flex h-full w-full items-center justify-center transition-opacity'
]"
aria-hidden="true"
>
<HomeOutline class="h-3 w-3 text-gray-400" />
</span>
<span
:class="[
!renderMode ? 'opacity-100 duration-200 ease-in' : 'opacity-0 duration-100 ease-out',
'absolute inset-0 flex h-full w-full items-center justify-center transition-opacity'
]"
aria-hidden="true"
>
<HomeIcon class="h-3 w-3 text-indigo-600" />
</span>
</span>
</Switch>

<Switch
v-model="showHiddenObjects"
:class="[
showHiddenObjects ? 'bg-indigo-600' : 'bg-gray-200',
'relative inline-flex mt-4 mb-2 h-6 w-11 flex-shrink-0 cursor-pointer rounded-full border-2 border-transparent transition-colors duration-200 ease-in-out focus:outline-none focus:ring-2 focus:ring-indigo-600 focus:ring-offset-2'
]"
@click="toggleHidden"
>
<span class="sr-only">Toggle Hidden</span>
<span
:class="[
showHiddenObjects ? 'translate-x-5' : 'translate-x-0',
'pointer-events-none relative inline-block h-5 w-5 transform rounded-full bg-white shadow ring-0 transition duration-200 ease-in-out'
]"
>
<span
:class="[
showHiddenObjects ? 'opacity-0 duration-100 ease-out' : 'opacity-100 duration-200 ease-in',
'absolute inset-0 flex h-full w-full items-center justify-center transition-opacity'
]"
aria-hidden="true"
>
<EyeSlashIcon class="h-3 w-3 text-gray-400" />
</span>
<span
:class="[
showHiddenObjects ? 'opacity-100 duration-200 ease-in' : 'opacity-0 duration-100 ease-out',
'absolute inset-0 flex h-full w-full items-center justify-center transition-opacity'
]"
aria-hidden="true"
>
<EyeIcon class="h-3 w-3 text-indigo-600" />
</span>
</span>
</Switch>
</template>

<script lang="ts">
import { storeToRefs } from 'pinia'
import { Switch } from '@headlessui/vue'
import { HomeIcon, EyeIcon } from '@heroicons/vue/20/solid'
import { HomeIcon as HomeOutline, EyeSlashIcon } from '@heroicons/vue/24/outline'

import { useSpeckleStore } from '@/stores/speckle'

/**
* Dashboard view.
* This component represents the main dashboard view of the application.
*/
export default {
name: 'DashboardView',
components: {
// eslint-disable-next-line vue/no-reserved-component-names
Switch,
HomeIcon,
HomeOutline,
EyeIcon,
EyeSlashIcon
},
setup() {
const speckleStore = useSpeckleStore()
const { renderMode, showHiddenObjects } = storeToRefs(speckleStore)

const toggleRenderMode = () => {
speckleStore.toggleRenderMode()
}

const toggleHidden = () => {
speckleStore.toggleHiddenObjects()
}

return {
toggleRenderMode,
toggleHidden,
showHiddenObjects,
renderMode
}
}
}
</script>
33 changes: 20 additions & 13 deletions src/components/ModelViewer/SpeckleViewer.vue
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@
id="renderParent"
>
<div class="absolute text-sm select-none left-4">
<RenderToggle />
<h3 class="font-semibold leading-5 text-gray-400 border-b border-gray-300 pb-2">
Controls
</h3>
Expand Down Expand Up @@ -78,6 +79,7 @@
// Component imports
import ViewerControls from '@/components/ModelViewer/ViewerControls.vue'
import DetailBar from '@/components/DetailBar/DetailBar.vue'
import RenderToggle from '@/components/Misc/RenderToggle.vue'
import SelectablePieChart from '@/components/Graphs/SelectablePieChart.vue'

// Type imports
Expand All @@ -91,11 +93,15 @@
const projectStore = useProjectStore()
const { selectedObjects } = storeToRefs(projectStore)
const navStore = useNavigationStore()
const speckleStore = useSpeckleStore()
const serverUrl = import.meta.env.VITE_APP_SERVER_URL
const token = import.meta.env.VITE_SPECKLE_TOKEN
const resizeObserver = ref<ResizeObserver | null>(null)
const fadeOut = ref(false)

speckleStore.setServerUrl(serverUrl)
speckleStore.setToken(token)

// Computed property for dynamic component
const leftModule = computed(() => {
switch (navStore.activePage) {
Expand Down Expand Up @@ -132,9 +138,7 @@
// Event handler for Escape key
const handleEscKey = (e: KeyboardEvent) => {
if (e.key.toLowerCase() === 'escape') {
console.log('Pressed Esc')
projectStore.clearSelectedGroup()
viewer?.resetFilters()
}
}

Expand Down Expand Up @@ -183,33 +187,37 @@
resizeObserver.value = new ResizeObserver(handleResize)
resizeObserver.value.observe(renderParent)

const speckleStore = useSpeckleStore()
speckleStore.setViewerInstance(viewer)


if (!speckleStore.selectedProject || !speckleStore.selectedVersion) {
throw new Error('No project or version selected!')
}
const url = `${serverUrl}/streams/${speckleStore.selectedProject.id}/objects/${speckleStore.selectedVersion.referencedObject}`
await viewer.loadObject(url, token, true, true)

let selection: string[] = []
viewer.on(ViewerEvent.ObjectClicked, (selectionInfo: SelectionEvent) => {
if (selectionInfo) {
// Object was clicked. Highlight it.
const id = selectionInfo.hits[0].object.id
// Object was clicked. Check if its in hidden objects then highlight it
let id
const hiddenIds = new Set(speckleStore.hiddenObjects.map(obj => obj.id))
for(let hit of selectionInfo.hits) {
if (!hiddenIds.has(hit.object.id)) {
id = hit.object.id
break
}
}

if (selectionInfo.event.shiftKey) selection.push(id)
else selection = [id]

projectStore.setObjectsByURI(selection)
viewer.highlightObjects(projectStore.getSelectedObjectsURI(), true)
// Zoom in on the hit and focus the camera target.
// viewer.zoom()
} else {
// No object clicked. Restore selection from group.
projectStore.setObjectsFromGroup()

if (projectStore.selectedObjects.length === 0) viewer.resetHighlight()
else viewer.highlightObjects(projectStore.getSelectedObjectsURI(), true)

viewer.zoom()
}
})

Expand All @@ -234,8 +242,7 @@
watch(
() => selectedObjects.value,
() => {
viewer?.resetFilters()
viewer?.isolateObjects(projectStore.getSelectedObjectsURI())
speckleStore.isolateObjects(projectStore.getSelectedObjectsURI())
}
)
// function setObjectColorsByVolume() {}
Expand Down
9 changes: 6 additions & 3 deletions src/components/Sidebar/GroupCard.vue
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@
'rounded-2xl bg-gray-200 p-4 ring-1 ring-gray-400' : selectedBool,
'rounded-2xl bg-gray-200 p-4' : selectedBool == false,
}"
:style="groupColorMode ? { 'background-color': inGroups.color } : {}"
:style="activePage == 'Overview' && !renderMode ? { 'background-color': inGroups.color } : {}"
@click="selectSubGroup(inGroups, $event)"
>
<div class="flex pb-2 justify-between items-center">
Expand Down Expand Up @@ -88,6 +88,7 @@ import ResultsGroupCard from '@/components/Sidebar/Results/ResultsGroupCard.vue'

import type { NestedGroup } from '@/models/filters'
import { useNavigationStore, useProjectStore } from '@/stores/main'
import { useSpeckleStore } from '@/stores/speckle'
import { storeToRefs } from 'pinia'

export default defineComponent({
Expand Down Expand Up @@ -115,7 +116,8 @@ export default defineComponent({

const inGroups = ref(props.groups)
const expand = ref(false)
const { editName, groupColorMode } = storeToRefs(navStore)
const { editName, activePage } = storeToRefs(navStore)
const { renderMode } = storeToRefs(useSpeckleStore())
const { selectedGroup } = storeToRefs(projectStore)

watch(
Expand Down Expand Up @@ -208,7 +210,8 @@ export default defineComponent({
currGroupTotal,
currIconAction,
selectedBool,
groupColorMode
activePage,
renderMode
}
},
})
Expand Down
Loading
Loading