@arronqzy/vue-view 0.1.25 → 0.1.26

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@arronqzy/vue-view",
3
- "version": "0.1.25",
3
+ "version": "0.1.26",
4
4
  "description": "Vue 3 visual view editor for Abuilder (Ant Design Vue)",
5
5
  "license": "MIT",
6
6
  "type": "module",
@@ -23,13 +23,13 @@
23
23
  "selecto": "^1.26.3",
24
24
  "uuid": "^13.0.0",
25
25
  "vue": "^3.5.13",
26
+ "@arronqzy/rx-store": "1.0.8",
26
27
  "@arronqzy/blueprint-dsl": "1.0.17",
27
- "@arronqzy/i18n": "0.1.17",
28
28
  "@arronqzy/view-scene3d": "0.1.5",
29
- "@arronqzy/vue-rx-store": "0.1.6",
29
+ "@arronqzy/vue-blueprint": "0.1.20",
30
30
  "@arronqzy/view-table": "0.1.8",
31
- "@arronqzy/vue-blueprint": "0.1.19",
32
- "@arronqzy/rx-store": "1.0.8"
31
+ "@arronqzy/vue-rx-store": "0.1.6",
32
+ "@arronqzy/i18n": "0.1.17"
33
33
  },
34
34
  "peerDependencies": {
35
35
  "vue": "^3.4.0"
@@ -39,8 +39,8 @@
39
39
  "eslint": "^8.57.0",
40
40
  "typescript": "^5.5.4",
41
41
  "vue-tsc": "^2.2.0",
42
- "@arronqzy/typescript-config": "1.0.0",
43
- "@arronqzy/eslint-config": "0.0.0"
42
+ "@arronqzy/eslint-config": "0.0.0",
43
+ "@arronqzy/typescript-config": "1.0.0"
44
44
  },
45
45
  "publishConfig": {
46
46
  "access": "public"
@@ -50,9 +50,9 @@ import {
50
50
  Modal,
51
51
  Slider,
52
52
  Space,
53
- Switch,
54
53
  Tabs,
55
54
  Tag,
55
+ Tooltip,
56
56
  message,
57
57
  } from "ant-design-vue";
58
58
  import { usePanelElements } from "./hooks/usePanelElements";
@@ -188,8 +188,8 @@ const editingLayerId = ref<string | null>(null);
188
188
  const editingLayerName = ref("");
189
189
  const isMergingLayers = ref(false);
190
190
  const mergeLayerName = ref("");
191
- const leftWidth = ref(240);
192
- const rightWidth = ref(300);
191
+ const leftWidth = ref(220);
192
+ const rightWidth = ref(280);
193
193
  const importInputRef = ref<HTMLInputElement | null>(null);
194
194
  const blueprintImportInputRef = ref<HTMLInputElement | null>(null);
195
195
  const apiCollectionManagerOpen = ref(false);
@@ -858,9 +858,9 @@ onUnmounted(() => window.removeEventListener("keydown", onKeyDown));
858
858
 
859
859
  <template>
860
860
  <Layout class="vue-view-panel h-screen overflow-hidden" :class="props.class" :key="locale">
861
- <Layout.Header class="flex h-auto flex-wrap items-center gap-2 bg-[#001529] px-3 py-2">
861
+ <Layout.Header class="flex h-10 flex-wrap items-center gap-2 border-b border-border/70 !bg-background/80 px-3 py-0 leading-none backdrop-blur-md">
862
862
  <Dropdown :trigger="['click']">
863
- <Button type="text" class="!text-white">{{ t("panel.menubar.file") }}</Button>
863
+ <Button type="text" class="!text-foreground">{{ t("panel.menubar.file") }}</Button>
864
864
  <template #overlay>
865
865
  <Menu>
866
866
  <Menu.Item @click="handleExport">{{ t("panel.menubar.exportPanelJson") }}</Menu.Item>
@@ -869,7 +869,7 @@ onUnmounted(() => window.removeEventListener("keydown", onKeyDown));
869
869
  </template>
870
870
  </Dropdown>
871
871
  <Dropdown :trigger="['click']">
872
- <Button type="text" class="!text-white">{{ t("panel.menubar.edit") }}</Button>
872
+ <Button type="text" class="!text-foreground">{{ t("panel.menubar.edit") }}</Button>
873
873
  <template #overlay>
874
874
  <Menu>
875
875
  <Menu.Item :disabled="!canUndo" @click="undo">{{ t("panel.menubar.undo") }}</Menu.Item>
@@ -885,7 +885,7 @@ onUnmounted(() => window.removeEventListener("keydown", onKeyDown));
885
885
  </template>
886
886
  </Dropdown>
887
887
  <Dropdown :trigger="['click']">
888
- <Button type="text" class="!text-white">{{ t("panel.menubar.blueprint") }}</Button>
888
+ <Button type="text" class="!text-foreground">{{ t("panel.menubar.blueprint") }}</Button>
889
889
  <template #overlay>
890
890
  <Menu>
891
891
  <Menu.Item @click="openBlueprintExport">{{ t("panel.menubar.exportBlueprint") }}</Menu.Item>
@@ -908,7 +908,7 @@ onUnmounted(() => window.removeEventListener("keydown", onKeyDown));
908
908
  @preview-project="openOnlinePreviewForProject"
909
909
  />
910
910
  <Dropdown :trigger="['click']">
911
- <Button type="text" class="!text-white">{{ t("panel.menubar.settings") }}</Button>
911
+ <Button type="text" class="!text-foreground">{{ t("panel.menubar.settings") }}</Button>
912
912
  <template #overlay>
913
913
  <Menu>
914
914
  <Menu.ItemGroup :title="t('panel.theme.language')">
@@ -930,7 +930,7 @@ onUnmounted(() => window.removeEventListener("keydown", onKeyDown));
930
930
  </template>
931
931
  </Dropdown>
932
932
  <Dropdown :trigger="['click']">
933
- <Button type="text" class="!text-white">{{ t("panel.theme.language") }}</Button>
933
+ <Button type="text" class="!text-foreground">{{ t("panel.theme.language") }}</Button>
934
934
  <template #overlay>
935
935
  <Menu>
936
936
  <Menu.Item :class="{ 'ant-menu-item-selected': locale === 'zh-CN' }" @click="setLocale('zh-CN')">{{ t("panel.theme.zhCN") }}</Menu.Item>
@@ -965,12 +965,12 @@ onUnmounted(() => window.removeEventListener("keydown", onKeyDown));
965
965
 
966
966
  <Layout.Content class="relative min-h-0 min-w-0">
967
967
  <div class="flex h-full min-h-0 flex-col">
968
- <div class="flex flex-wrap items-center gap-2 border-b bg-white px-3 py-2">
968
+ <div class="flex flex-wrap items-center gap-2 border-b border-border/60 bg-muted/15 px-3 py-1.5">
969
969
  <Input
970
970
  :value="displayProductName"
971
971
  size="small"
972
972
  @update:value="(value: string) => (productName = value)"
973
- class="w-[200px]"
973
+ class="w-[180px]"
974
974
  :placeholder="t('panel.menubar.productName')"
975
975
  />
976
976
  <span class="text-xs text-gray-500">{{ t("panel.menubar.zoom") }}</span>
@@ -984,10 +984,35 @@ onUnmounted(() => window.removeEventListener("keydown", onKeyDown));
984
984
  />
985
985
  <Tag v-if="activeLayer">{{ activeLayer.name }}</Tag>
986
986
  <Tag color="blue">{{ t("panel.menubar.selectedCount", { count: selectedIds.length }) }}</Tag>
987
- <div data-blueprint-toggle class="ml-auto flex items-center gap-2">
988
- <span class="text-xs text-gray-500">{{ t("panel.menubar.blueprint") }}</span>
989
- <Switch v-model:checked="blueprintOpen" size="small" />
990
- </div>
987
+ <Tooltip :title="t('panel.menubar.showBlueprintPanel')">
988
+ <button
989
+ type="button"
990
+ data-blueprint-toggle
991
+ class="ml-auto inline-flex h-7 w-7 items-center justify-center rounded-md border transition-colors"
992
+ :class="
993
+ blueprintOpen
994
+ ? 'border-primary/50 bg-primary/15 text-primary'
995
+ : 'border-border/70 bg-background/80 text-muted-foreground hover:bg-accent hover:text-accent-foreground'
996
+ "
997
+ :aria-pressed="blueprintOpen"
998
+ :aria-label="t('panel.menubar.showBlueprintPanel')"
999
+ @click="blueprintOpen = !blueprintOpen"
1000
+ >
1001
+ <svg
1002
+ viewBox="0 0 24 24"
1003
+ class="h-3.5 w-3.5"
1004
+ fill="none"
1005
+ stroke="currentColor"
1006
+ :stroke-width="blueprintOpen ? 2.2 : 2"
1007
+ >
1008
+ <rect x="3" y="4" width="18" height="16" rx="2" />
1009
+ <circle cx="8" cy="10" r="1.5" :fill="blueprintOpen ? 'currentColor' : 'none'" />
1010
+ <circle cx="16" cy="10" r="1.5" :fill="blueprintOpen ? 'currentColor' : 'none'" />
1011
+ <circle cx="12" cy="16" r="1.5" :fill="blueprintOpen ? 'currentColor' : 'none'" />
1012
+ <path d="M9.2 10.8 10.8 14.2M14.8 10.8 13.2 14.2" />
1013
+ </svg>
1014
+ </button>
1015
+ </Tooltip>
991
1016
  </div>
992
1017
 
993
1018
  <WorkspaceStageSplit
@@ -1056,63 +1081,112 @@ onUnmounted(() => window.removeEventListener("keydown", onKeyDown));
1056
1081
  </PanelCanvas>
1057
1082
  </WorkspaceStageSplit>
1058
1083
 
1059
- <div class="border-t bg-white px-2 py-2">
1060
- <div class="mb-2 flex flex-wrap items-center gap-2">
1061
- <span class="text-xs font-semibold text-gray-500">{{ t("panel.layers.title") }}</span>
1062
- <Button size="small" @click="addLayer()">{{ t("panel.layers.addShort") }}</Button>
1063
- <Button size="small" :disabled="!canMergeLayers" @click="isMergingLayers = true">{{ t("panel.layers.mergeShort") }}</Button>
1084
+ <div class="border-t border-border/50 bg-muted/5 px-1.5 py-0.5">
1085
+ <div class="flex min-w-0 flex-wrap items-center gap-1">
1086
+ <Tooltip :title="t('panel.layers.title')">
1087
+ <span class="inline-flex h-6 items-center px-1 text-[11px] font-semibold text-muted-foreground">
1088
+ {{ t("panel.layers.title") }}
1089
+ </span>
1090
+ </Tooltip>
1091
+ <Tooltip :title="t('panel.layers.add')">
1092
+ <Button size="small" class="!h-6 !px-2 !text-[11px]" @click="addLayer()">
1093
+ {{ t("panel.layers.addShort") }}
1094
+ </Button>
1095
+ </Tooltip>
1096
+ <Tooltip :title="canMergeLayers ? t('panel.layers.merge') : t('panel.layers.mergeNeedTwo')">
1097
+ <Button
1098
+ size="small"
1099
+ class="!h-6 !px-2 !text-[11px]"
1100
+ :disabled="!canMergeLayers"
1101
+ @click="isMergingLayers = true"
1102
+ >
1103
+ {{ t("panel.layers.mergeShort") }}
1104
+ </Button>
1105
+ </Tooltip>
1106
+ <Tabs
1107
+ size="small"
1108
+ class="min-w-0 flex-1"
1109
+ :active-key="activeLayerId"
1110
+ type="card"
1111
+ @update:active-key="(k: string | number) => setActiveLayer(String(k))"
1112
+ >
1113
+ <Tabs.TabPane v-for="layer in layers" :key="layer.id">
1114
+ <template #tab>
1115
+ <span class="inline-flex max-w-[110px] items-center gap-1 text-[11px] font-medium">
1116
+ <span class="truncate">{{ layer.name }}</span>
1117
+ <Tag v-if="layer.isPrimary" color="green" class="!m-0 !px-1 !text-[10px]">
1118
+ {{ t("panel.layers.primary") }}
1119
+ </Tag>
1120
+ </span>
1121
+ </template>
1122
+ </Tabs.TabPane>
1123
+ </Tabs>
1064
1124
  </div>
1065
- <Tabs
1066
- size="small"
1067
- :active-key="activeLayerId"
1068
- type="card"
1069
- @update:active-key="(k: string | number) => setActiveLayer(String(k))"
1125
+
1126
+ <div
1127
+ v-if="activeLayer"
1128
+ class="mt-1 flex flex-wrap items-center gap-1 rounded-md border border-border/50 bg-card/80 px-1.5 py-0.5 text-[11px]"
1070
1129
  >
1071
- <Tabs.TabPane v-for="layer in layers" :key="layer.id">
1072
- <template #tab>
1073
- <span class="inline-flex items-center gap-1">
1074
- {{ layer.name }}
1075
- <Tag v-if="layer.isMapping" color="blue" class="!m-0">{{ t("panel.layers.mapping") }}</Tag>
1076
- <Tag v-if="layer.isPrimary" color="green" class="!m-0">{{ t("panel.layers.primary") }}</Tag>
1077
- </span>
1078
- </template>
1079
- </Tabs.TabPane>
1080
- </Tabs>
1081
-
1082
- <div v-if="activeLayer" class="mt-2 flex flex-wrap items-center gap-2 rounded border px-2 py-1.5 text-xs">
1083
1130
  <template v-if="editingLayerId === activeLayer.id">
1084
1131
  <Input
1085
1132
  v-model:value="editingLayerName"
1086
1133
  size="small"
1087
- class="w-40"
1134
+ class="!h-6 w-28"
1088
1135
  @press-enter="commitRenameLayer"
1089
1136
  />
1090
- <Button size="small" type="primary" @click="commitRenameLayer">{{ t("common.ok") }}</Button>
1137
+ <Tooltip :title="t('common.ok')">
1138
+ <Button size="small" type="primary" class="!h-6 !px-2" @click="commitRenameLayer">
1139
+ {{ t("common.ok") }}
1140
+ </Button>
1141
+ </Tooltip>
1091
1142
  </template>
1092
1143
  <template v-else>
1093
- <span class="font-medium">{{ activeLayer.name }}</span>
1094
- <Button size="small" type="link" @click="startRenameLayer(activeLayer.id, activeLayer.name)">{{ t("panel.layers.renameShort") }}</Button>
1144
+ <span class="max-w-[100px] truncate font-semibold">{{ activeLayer.name }}</span>
1145
+ <Tooltip :title="t('panel.layers.rename')">
1146
+ <Button
1147
+ size="small"
1148
+ type="link"
1149
+ class="!h-6 !px-1 !text-[11px]"
1150
+ @click="startRenameLayer(activeLayer.id, activeLayer.name)"
1151
+ >
1152
+ {{ t("panel.layers.renameShort") }}
1153
+ </Button>
1154
+ </Tooltip>
1095
1155
  </template>
1096
- <Button size="small" @click="toggleLayerLock(activeLayer.id)">
1097
- {{ activeLayer.locked ? t("panel.layers.unlockShort") : t("panel.layers.lockShort") }}
1098
- </Button>
1099
- <Checkbox
1100
- :checked="Boolean(activeLayer.mergeSelected)"
1101
- @change="() => toggleLayerMergeSelected(activeLayer!.id)"
1102
- >
1103
- {{ t("panel.layers.joinMerge") }}
1104
- </Checkbox>
1105
- <Button size="small" :disabled="activeLayer.isPrimary" @click="setPrimaryLayer(activeLayer.id)">
1106
- {{ t("panel.layers.setPrimary") }}
1107
- </Button>
1108
- <Button
1109
- size="small"
1110
- danger
1111
- :disabled="!activeLayer.editable"
1112
- @click="deleteLayer(activeLayer.id)"
1113
- >
1114
- {{ t("panel.layers.delete") }}
1115
- </Button>
1156
+ <Tooltip :title="activeLayer.locked ? t('panel.layers.unlock') : t('panel.layers.lock')">
1157
+ <Button size="small" class="!h-6 !px-2 !text-[11px]" @click="toggleLayerLock(activeLayer.id)">
1158
+ {{ activeLayer.locked ? t("panel.layers.unlockShort") : t("panel.layers.lockShort") }}
1159
+ </Button>
1160
+ </Tooltip>
1161
+ <Tooltip :title="t('panel.layers.joinMerge')">
1162
+ <Checkbox
1163
+ :checked="Boolean(activeLayer.mergeSelected)"
1164
+ @change="() => toggleLayerMergeSelected(activeLayer!.id)"
1165
+ >
1166
+ <span class="text-[11px]">{{ t("panel.layers.joinMerge") }}</span>
1167
+ </Checkbox>
1168
+ </Tooltip>
1169
+ <Tooltip :title="t('panel.layers.setPrimaryHint')">
1170
+ <Button
1171
+ size="small"
1172
+ class="!h-6 !px-2 !text-[11px]"
1173
+ :disabled="activeLayer.isPrimary"
1174
+ @click="setPrimaryLayer(activeLayer.id)"
1175
+ >
1176
+ {{ t("panel.layers.setPrimary") }}
1177
+ </Button>
1178
+ </Tooltip>
1179
+ <Tooltip :title="t('panel.layers.delete')">
1180
+ <Button
1181
+ size="small"
1182
+ danger
1183
+ class="!h-6 !px-2 !text-[11px]"
1184
+ :disabled="!activeLayer.editable"
1185
+ @click="deleteLayer(activeLayer.id)"
1186
+ >
1187
+ {{ t("panel.layers.delete") }}
1188
+ </Button>
1189
+ </Tooltip>
1116
1190
  </div>
1117
1191
  </div>
1118
1192
  </div>
@@ -189,7 +189,7 @@ function hasViewEvent(el: PanelElement) {
189
189
  :class="[
190
190
  'absolute select-none',
191
191
  previewMode ? '' : 'rv-selectable',
192
- !previewMode && selectedIds.includes(el.id) ? 'ring-2 ring-blue-500/90 ring-offset-0' : '',
192
+ !previewMode && selectedIds.includes(el.id) ? 'rv-node-selected' : '',
193
193
  hasViewEvent(el) ? 'cursor-pointer' : '',
194
194
  ]"
195
195
  :data-element-id="el.id"
@@ -4,20 +4,21 @@ const { t, locale } = useI18n();
4
4
  defineProps<{ id: string }>();
5
5
 
6
6
  const common =
7
- "relative aspect-[4/3] w-full shrink-0 overflow-hidden rounded-md border border-border bg-gradient-to-br from-card to-muted/40";
7
+ "relative mx-auto aspect-[4/3] w-full shrink-0 overflow-hidden rounded-md border border-border/60 bg-gradient-to-br from-card to-muted/35";
8
+ const previewStyle = "max-width: 88px; max-height: 64px";
8
9
  </script>
9
10
 
10
11
  <template>
11
- <div v-if="id === 'bar'" :class="common">
12
- <div class="absolute inset-0 grid grid-cols-5 items-end gap-1 px-2 pb-2 pt-1.5">
13
- <div class="h-2 rounded-sm bg-primary/55" />
14
- <div class="h-4 rounded-sm bg-primary/65" />
15
- <div class="h-7 rounded-sm bg-primary/80" />
16
- <div class="h-5 rounded-sm bg-primary/70" />
17
- <div class="h-3 rounded-sm bg-primary/60" />
18
- </div>
12
+ <div v-if="id === 'bar'" :class="common" :style="previewStyle">
13
+ <svg viewBox="0 0 80 60" class="h-full w-full" aria-hidden="true">
14
+ <rect x="8" y="40" width="8" height="12" rx="1.5" class="fill-primary/55" />
15
+ <rect x="22" y="30" width="8" height="22" rx="1.5" class="fill-primary/65" />
16
+ <rect x="36" y="16" width="8" height="36" rx="1.5" class="fill-primary/80" />
17
+ <rect x="50" y="24" width="8" height="28" rx="1.5" class="fill-primary/70" />
18
+ <rect x="64" y="34" width="8" height="18" rx="1.5" class="fill-primary/60" />
19
+ </svg>
19
20
  </div>
20
- <div v-else-if="id === 'line' || id === 'area'" :class="common">
21
+ <div v-else-if="id === 'line' || id === 'area'" :class="common" :style="previewStyle">
21
22
  <svg viewBox="0 0 80 60" class="h-full w-full">
22
23
  <polygon
23
24
  v-if="id === 'area'"
@@ -34,14 +35,14 @@ const common =
34
35
  />
35
36
  </svg>
36
37
  </div>
37
- <div v-else-if="id === 'pie'" :class="common">
38
+ <div v-else-if="id === 'pie'" :class="common" :style="previewStyle">
38
39
  <svg viewBox="0 0 80 60" class="h-full w-full">
39
40
  <circle cx="40" cy="30" r="16" class="fill-primary/20" />
40
41
  <path d="M40 30 L40 14 A16 16 0 0 1 55 39 Z" class="fill-primary/75" />
41
42
  <path d="M40 30 L55 39 A16 16 0 0 1 27 43 Z" class="fill-primary/45" />
42
43
  </svg>
43
44
  </div>
44
- <div v-else-if="id === 'scatter'" :class="common">
45
+ <div v-else-if="id === 'scatter'" :class="common" :style="previewStyle">
45
46
  <svg viewBox="0 0 80 60" class="h-full w-full">
46
47
  <circle cx="14" cy="42" r="2.5" class="fill-primary/80" />
47
48
  <circle cx="24" cy="34" r="2.5" class="fill-primary/70" />
@@ -50,27 +51,27 @@ const common =
50
51
  <circle cx="62" cy="14" r="2.5" class="fill-primary/85" />
51
52
  </svg>
52
53
  </div>
53
- <div v-else-if="id === 'radar'" :class="common">
54
+ <div v-else-if="id === 'radar'" :class="common" :style="previewStyle">
54
55
  <svg viewBox="0 0 80 60" class="h-full w-full">
55
56
  <polygon points="40,10 58,20 54,40 26,40 22,20" class="fill-primary/20 stroke-primary/60" />
56
57
  <polygon points="40,16 52,23 49,36 31,36 28,24" class="fill-primary/45 stroke-primary/80" />
57
58
  </svg>
58
59
  </div>
59
- <div v-else-if="id === 'gauge'" :class="common">
60
+ <div v-else-if="id === 'gauge'" :class="common" :style="previewStyle">
60
61
  <svg viewBox="0 0 80 60" class="h-full w-full">
61
62
  <path d="M12 44a28 28 0 0 1 56 0" class="fill-none stroke-primary/35" stroke-width="6" />
62
63
  <path d="M12 44a28 28 0 0 1 40-24" class="fill-none stroke-primary/80" stroke-width="6" />
63
64
  <line x1="40" y1="44" x2="54" y2="28" class="stroke-primary" stroke-width="2" />
64
65
  </svg>
65
66
  </div>
66
- <div v-else-if="id === 'funnel'" :class="common">
67
+ <div v-else-if="id === 'funnel'" :class="common" :style="previewStyle">
67
68
  <svg viewBox="0 0 80 60" class="h-full w-full">
68
69
  <polygon points="10,10 70,10 58,22 22,22" class="fill-primary/80" />
69
70
  <polygon points="22,24 58,24 50,34 30,34" class="fill-primary/65" />
70
71
  <polygon points="30,36 50,36 44,44 36,44" class="fill-primary/50" />
71
72
  </svg>
72
73
  </div>
73
- <div v-else-if="id === 'text'" :class="common">
74
+ <div v-else-if="id === 'text'" :class="common" :style="previewStyle">
74
75
  <div class="space-y-1.5 px-2 py-2">
75
76
  <div class="h-2 w-10 rounded bg-primary/70" />
76
77
  <div class="h-1.5 w-full rounded bg-muted-foreground/45" />
@@ -78,7 +79,7 @@ const common =
78
79
  <div class="h-1.5 w-8/12 rounded bg-muted-foreground/45" />
79
80
  </div>
80
81
  </div>
81
- <div v-else-if="id === 'table'" :class="common">
82
+ <div v-else-if="id === 'table'" :class="common" :style="previewStyle">
82
83
  <div class="absolute inset-0 flex flex-col gap-1 p-2">
83
84
  <div class="grid h-3 flex-none grid-cols-3 gap-1">
84
85
  <div class="rounded-sm bg-primary/75" />
@@ -94,10 +95,10 @@ const common =
94
95
  </div>
95
96
  </div>
96
97
  </div>
97
- <div v-else-if="id === 'rect'" :class="common">
98
+ <div v-else-if="id === 'rect'" :class="common" :style="previewStyle">
98
99
  <div class="absolute inset-2 rounded-md border-2 border-primary/80 bg-primary/15" />
99
100
  </div>
100
- <div v-else-if="id === 'geometry'" :class="common">
101
+ <div v-else-if="id === 'geometry'" :class="common" :style="previewStyle">
101
102
  <svg viewBox="0 0 80 60" class="h-full w-full">
102
103
  <circle cx="22" cy="18" r="8" class="fill-primary/75" />
103
104
  <rect x="36" y="10" width="16" height="16" rx="3" class="fill-primary/55" />
@@ -106,7 +107,7 @@ const common =
106
107
  <polygon points="50,36 54,42 50,48 42,48 38,42 42,36" class="fill-primary/70" />
107
108
  </svg>
108
109
  </div>
109
- <div v-else-if="id === 'scene3d'" :class="common">
110
+ <div v-else-if="id === 'scene3d'" :class="common" :style="previewStyle">
110
111
  <svg viewBox="0 0 80 60" class="h-full w-full">
111
112
  <polygon points="40,8 62,22 62,44 40,56 18,44 18,22" class="fill-primary/20 stroke-primary/80" stroke-width="1.5" />
112
113
  <polygon points="40,8 62,22 40,32 18,22" class="fill-primary/45" />
@@ -114,13 +115,13 @@ const common =
114
115
  <polygon points="40,32 18,22 18,44 40,56" class="fill-primary/55" />
115
116
  </svg>
116
117
  </div>
117
- <div v-else-if="id === 'reference'" :class="common">
118
+ <div v-else-if="id === 'reference'" :class="common" :style="previewStyle">
118
119
  <div class="absolute inset-2 rounded-md border border-dashed border-primary/70 bg-primary/10" />
119
120
  <div class="absolute inset-0 flex items-center justify-center text-[10px] text-primary/80">
120
121
  {{ t("panel.material.reference") }}
121
122
  </div>
122
123
  </div>
123
- <div v-else-if="id === 'image'" :class="common">
124
+ <div v-else-if="id === 'image'" :class="common" :style="previewStyle">
124
125
  <div class="absolute inset-0 bg-gradient-to-br from-primary/25 via-muted/60 to-card" />
125
126
  <svg viewBox="0 0 80 60" class="absolute inset-0 h-full w-full">
126
127
  <circle cx="16" cy="14" r="5" class="fill-primary/70" />
@@ -128,7 +129,7 @@ const common =
128
129
  <polygon points="0,60 18,42 30,54 44,36 62,60" class="fill-primary/55" />
129
130
  </svg>
130
131
  </div>
131
- <div v-else-if="id === 'video'" :class="common">
132
+ <div v-else-if="id === 'video'" :class="common" :style="previewStyle">
132
133
  <div class="absolute inset-0 bg-primary/12" />
133
134
  <div class="absolute left-2 right-2 top-2 h-1.5 rounded bg-primary/35" />
134
135
  <div class="absolute inset-0 flex items-center justify-center">
@@ -139,7 +140,7 @@ const common =
139
140
  </div>
140
141
  </div>
141
142
  </div>
142
- <div v-else-if="id === 'audio'" :class="common">
143
+ <div v-else-if="id === 'audio'" :class="common" :style="previewStyle">
143
144
  <div class="absolute inset-0 flex items-center justify-center gap-1">
144
145
  <div class="h-3 w-1.5 rounded bg-primary/50" />
145
146
  <div class="h-6 w-1.5 rounded bg-primary/75" />
@@ -148,7 +149,7 @@ const common =
148
149
  <div class="h-4 w-1.5 rounded bg-primary/55" />
149
150
  </div>
150
151
  </div>
151
- <div v-else-if="id === 'grid'" :class="common">
152
+ <div v-else-if="id === 'grid'" :class="common" :style="previewStyle">
152
153
  <div class="absolute inset-0 grid grid-cols-3 grid-rows-2 gap-1.5 p-2">
153
154
  <div
154
155
  v-for="idx in 6"
@@ -157,7 +158,7 @@ const common =
157
158
  />
158
159
  </div>
159
160
  </div>
160
- <div v-else-if="id === 'viewport'" :class="common">
161
+ <div v-else-if="id === 'viewport'" :class="common" :style="previewStyle">
161
162
  <div class="absolute inset-1.5 overflow-hidden rounded-sm border border-primary/70 bg-primary/10">
162
163
  <div class="absolute left-1 top-1 h-6 w-8 rounded-[2px] bg-primary/45" />
163
164
  <div class="absolute left-6 top-4 h-7 w-10 rounded-[2px] bg-primary/30" />
@@ -165,5 +166,5 @@ const common =
165
166
  <div class="absolute bottom-0 right-0 top-2 w-1.5 rounded-l bg-primary/40" />
166
167
  </div>
167
168
  </div>
168
- <div v-else :class="common" />
169
+ <div v-else :class="common" :style="previewStyle" />
169
170
  </template>