enso/app/gui2/stories/UserDefinedVisualization.story.vue
Kaz Wesley 277dfb1991
Ast edits (#8576)
- The module is edited by changing the AST, not the text representation.
- `IdMap`s no longer need to be maintained in parallel with the module content; they are snapshots produced as needed from the ASTs.
- Simplistic synchronization is in place until #8237: Edits are never merged; if two edits are started from the same state, one will be overwritten.
2023-12-19 17:58:11 +00:00

107 lines
3.1 KiB
Vue

<script setup lang="ts">
import GraphVisualization from '@/components/GraphEditor/GraphVisualization.vue'
import { Vec2 } from '@/util/data/vec2'
import type { VisualizationIdentifier } from 'shared/yjsModel'
import { computed, ref } from 'vue'
import MockFSWrapper from './MockFSWrapper.vue'
import HstCode from './histoire/HstCode.vue'
import HstDirectory from './histoire/HstDirectory.vue'
// The `.slice()` is required to make this array mutable.
const fsSources = (
[
{ label: 'Code Editor', value: 'editor' },
{ label: 'File System (Chromium only)', value: 'fs' },
] as const
).slice()
const fsSource = ref<'editor' | 'fs'>('editor')
const directory = ref<FileSystemDirectoryHandle>()
const type = ref('Example Visualization')
const isCircularMenuVisible = ref(false)
// Opening angle brackets for top-level elements escaped to avoid breaking Vue.
const code = ref(`\
\x3cscript lang="ts">
export const name = 'Example Visualization'
export const inputType = 'Any'
\x3c/script>
\x3cscript setup lang="ts">
import { VisualizationContainer } from 'builtins'
const props = defineProps<{ data: unknown }>()
\x3c/script>
\x3ctemplate>
<VisualizationContainer :belowToolbar="true">
<pre><code class="green-text" v-text="props.data"></code></pre>
</VisualizationContainer>
\x3c/template>
\x3cstyle scoped>
.green-text {
color: green;
}
\x3c/style>`)
const data = ref<any>({
axis: {
x: { label: 'x-axis label', scale: 'linear' },
y: { label: 'y-axis label', scale: 'logarithmic' },
},
points: { labels: 'visible' },
data: [
{ x: 0.1, y: 0.7, label: 'foo', color: '#FF0000', shape: 'circle', size: 0.2 },
{ x: 0.4, y: 0.2, label: 'baz', color: '#0000FF', shape: 'square', size: 0.3 },
],
})
const nodePosition = ref(new Vec2(0, 0))
const nodeSize = ref(new Vec2(400, 32))
const currentType = computed<VisualizationIdentifier>(() => ({
module: { kind: 'CurrentProject' },
name: type.value,
}))
const mockFsWrapperProps = computed(() => ({
prefix: ['visualizations'],
files: fsSource.value === 'editor' ? { 'ExampleVisualization.vue': code.value } : undefined,
directory: directory.value,
}))
</script>
<template>
<Story
title="User Defined"
group="visualizations"
:layout="{ type: 'grid', width: 450 }"
autoPropsDisabled
>
<div style="height: 322px">
<MockFSWrapper v-bind="mockFsWrapperProps">
<GraphVisualization
:currentType="currentType"
:data="data"
:scale="1"
:nodePosition="nodePosition"
:nodeSize="nodeSize"
:isCircularMenuVisible="isCircularMenuVisible"
@setVisualizationId="$event.module.kind === 'CurrentProject' && (type = $event.name)"
/>
</MockFSWrapper>
</div>
<template #controls>
<HstText v-model="type" title="type" />
<HstJson v-model="data" title="data" />
<HstRadio v-model="fsSource" title="viz source" :options="fsSources" />
<HstCode v-if="fsSource === 'editor'" v-model="code" title="viz code" />
<HstDirectory
v-if="fsSource === 'fs'"
title="viz folder"
@update:directory="directory = $event"
/>
</template>
</Story>
</template>