diff --git a/TODO.md b/TODO.md
index 8794b5da6..c99806be5 100644
--- a/TODO.md
+++ b/TODO.md
@@ -100,12 +100,12 @@ A step-by-step checklist for porting MatterControl's design features to a Vue +
- [x] Distinguish single vs multi-selection visually
### Context Menu
-- [ ] Create right-click context menu component
-- [ ] Show context menu on object right-click
-- [ ] Add "Delete" option to context menu
-- [ ] Add "Duplicate" option to context menu
-- [ ] Add "Group" option to context menu
-- [ ] Close menu on click outside
+- [x] Create right-click context menu component
+- [x] Show context menu on object right-click
+- [x] Add "Delete" option to context menu
+- [x] Add "Duplicate" option to context menu
+- [x] Add "Group" option to context menu
+- [x] Close menu on click outside
---
diff --git a/src/App.vue b/src/App.vue
index a55fe55e5..9a0445119 100644
--- a/src/App.vue
+++ b/src/App.vue
@@ -1,12 +1,37 @@
+
+
+
+
+
+
diff --git a/src/components/Viewport.vue b/src/components/Viewport.vue
index 0e85f612a..a358ea62f 100644
--- a/src/components/Viewport.vue
+++ b/src/components/Viewport.vue
@@ -29,6 +29,7 @@ const props = withDefaults(
const emit = defineEmits<{
pick: [object: SceneObject | null, event: MouseEvent]
+ contextmenu: [object: SceneObject | null, event: MouseEvent]
}>()
const sceneStore = useSceneStore()
@@ -205,6 +206,7 @@ function setupMouseHandlers() {
renderer.domElement.addEventListener('click', onCanvasClick)
renderer.domElement.addEventListener('mousemove', onCanvasMouseMove)
+ renderer.domElement.addEventListener('contextmenu', onCanvasContextMenu)
}
function cleanupMouseHandlers() {
@@ -212,6 +214,7 @@ function cleanupMouseHandlers() {
renderer.domElement.removeEventListener('click', onCanvasClick)
renderer.domElement.removeEventListener('mousemove', onCanvasMouseMove)
+ renderer.domElement.removeEventListener('contextmenu', onCanvasContextMenu)
}
function updateMouseCoordinates(event: MouseEvent) {
@@ -258,6 +261,12 @@ function onCanvasMouseMove(event: MouseEvent) {
}
}
+function onCanvasContextMenu(event: MouseEvent) {
+ event.preventDefault()
+ const pickedObject = pickObject(event)
+ emit('contextmenu', pickedObject, event)
+}
+
function setupResizeObserver() {
if (!containerRef.value) return