working dependency tree
parent
40a692ed6a
commit
3b49000e2b
|
@ -10,6 +10,7 @@
|
|||
"babel-loader": "^8.2.2",
|
||||
"css-loader": "^5.1.3",
|
||||
"gh-pages": "^3.1.0",
|
||||
"immutability-helper": "^3.1.1",
|
||||
"mini-css-extract-plugin": "^1.4.0",
|
||||
"postcss": "^8.2.9",
|
||||
"postcss-loader": "^5.2.0",
|
||||
|
@ -3633,6 +3634,12 @@
|
|||
"postcss": "^8.1.0"
|
||||
}
|
||||
},
|
||||
"node_modules/immutability-helper": {
|
||||
"version": "3.1.1",
|
||||
"resolved": "https://registry.npmjs.org/immutability-helper/-/immutability-helper-3.1.1.tgz",
|
||||
"integrity": "sha512-Q0QaXjPjwIju/28TsugCHNEASwoCcJSyJV3uO1sOIQGI0jKgm9f41Lvz0DZj3n46cNCyAZTsEYoY4C2bVRUzyQ==",
|
||||
"dev": true
|
||||
},
|
||||
"node_modules/import-fresh": {
|
||||
"version": "3.3.0",
|
||||
"resolved": "https://registry.npmjs.org/import-fresh/-/import-fresh-3.3.0.tgz",
|
||||
|
@ -11406,6 +11413,12 @@
|
|||
"dev": true,
|
||||
"requires": {}
|
||||
},
|
||||
"immutability-helper": {
|
||||
"version": "3.1.1",
|
||||
"resolved": "https://registry.npmjs.org/immutability-helper/-/immutability-helper-3.1.1.tgz",
|
||||
"integrity": "sha512-Q0QaXjPjwIju/28TsugCHNEASwoCcJSyJV3uO1sOIQGI0jKgm9f41Lvz0DZj3n46cNCyAZTsEYoY4C2bVRUzyQ==",
|
||||
"dev": true
|
||||
},
|
||||
"import-fresh": {
|
||||
"version": "3.3.0",
|
||||
"resolved": "https://registry.npmjs.org/import-fresh/-/import-fresh-3.3.0.tgz",
|
||||
|
|
|
@ -11,6 +11,7 @@
|
|||
"babel-loader": "^8.2.2",
|
||||
"css-loader": "^5.1.3",
|
||||
"gh-pages": "^3.1.0",
|
||||
"immutability-helper": "^3.1.1",
|
||||
"mini-css-extract-plugin": "^1.4.0",
|
||||
"postcss": "^8.2.9",
|
||||
"postcss-loader": "^5.2.0",
|
||||
|
|
70
src/app.jsx
70
src/app.jsx
|
@ -5,8 +5,7 @@ import './app.css'
|
|||
|
||||
import { Provider, useDispatch, useSelector } from 'react-redux'
|
||||
import { FaCube, FaEdit } from 'react-icons/fa'
|
||||
import { MdEdit, MdDone, MdVisibilityOff, MdVisibility } from 'react-icons/md'
|
||||
import { RiShape2Fill } from 'react-icons/ri'
|
||||
import { MdEdit, MdDone, MdVisibilityOff, MdVisibility, MdDelete } from 'react-icons/md'
|
||||
import * as Icon from "./icons";
|
||||
import { color } from './utils/shared'
|
||||
|
||||
|
@ -22,16 +21,11 @@ export const Root = ({ store }) => (
|
|||
const App = () => {
|
||||
const dispatch = useDispatch()
|
||||
const treeEntries = useSelector(state => state.treeEntries)
|
||||
const activeSketchNid = useSelector(state => state.activeSketchNid)
|
||||
|
||||
// const [state, setState] = useState('x')
|
||||
// useEffect(()=>{
|
||||
// console.log('hereeee')
|
||||
// },[state])
|
||||
const activeSketchId = useSelector(state => state.activeSketchId)
|
||||
|
||||
|
||||
useEffect(() => {
|
||||
if (!activeSketchNid) {
|
||||
if (!activeSketchId) {
|
||||
sc.canvas.addEventListener('pointermove', sc.onHover)
|
||||
sc.canvas.addEventListener('pointerdown', sc.onPick)
|
||||
return () => {
|
||||
|
@ -39,27 +33,38 @@ const App = () => {
|
|||
sc.canvas.removeEventListener('pointerdown', sc.onPick)
|
||||
}
|
||||
}
|
||||
}, [activeSketchNid])
|
||||
}, [activeSketchId])
|
||||
|
||||
|
||||
const btnz = [
|
||||
activeSketchNid ?
|
||||
activeSketchId ?
|
||||
[MdDone, () => {
|
||||
treeEntries.byNid[activeSketchNid].deactivate()
|
||||
treeEntries.byId[activeSketchId].deactivate()
|
||||
sc.activeSketch = null
|
||||
// sc.activeDim = this.activeSketch.obj3d.children[1].children
|
||||
}, 'Finish'] :
|
||||
[FaEdit, sc.addSketch, 'Sketch']
|
||||
,
|
||||
[FaCube, () => sc.extrude(treeEntries.byNid[activeSketchNid]), 'Extrude'],
|
||||
[Icon.Union, () => sc.extrude(treeEntries.byNid[activeSketchNid]), 'Union'],
|
||||
[Icon.Subtract, subtract, 'Subtract'],
|
||||
[Icon.Intersect, () => sc.extrude(treeEntries.byNid[activeSketchNid]), 'Intersect'],
|
||||
[Icon.Dimension, () => sc.extrude(treeEntries.byNid[activeSketchNid]), 'Dimension'],
|
||||
[Icon.Line, () => sc.extrude(treeEntries.byNid[activeSketchNid]), 'Line'],
|
||||
[Icon.Arc, () => sc.extrude(treeEntries.byNid[activeSketchNid]), 'Arc'],
|
||||
[FaCube, () => sc.extrude(treeEntries.byId[activeSketchId]), 'Extrude'],
|
||||
[Icon.Union, () => sc.extrude(treeEntries.byId[activeSketchId]), 'Union'],
|
||||
[Icon.Subtract, ()=> {
|
||||
if (sc.selected.length != 2 || !sc.selected.every(e => e.userData.type == 'mesh')) return
|
||||
// console.log('here')
|
||||
const [m1, m2] = sc.selected
|
||||
const mesh = subtract(m1,m2)
|
||||
|
||||
dispatch({ type: 'rx-extrusion', mesh, deps:[m1.name,m2.name] })
|
||||
sc.render()
|
||||
forceUpdate()
|
||||
}, 'Subtract'],
|
||||
[Icon.Intersect, () => sc.extrude(treeEntries.byId[activeSketchId]), 'Intersect'],
|
||||
[Icon.Dimension, () => sc.extrude(treeEntries.byId[activeSketchId]), 'Dimension'],
|
||||
[Icon.Line, () => sc.extrude(treeEntries.byId[activeSketchId]), 'Line'],
|
||||
[Icon.Arc, () => sc.extrude(treeEntries.byId[activeSketchId]), 'Arc'],
|
||||
]
|
||||
|
||||
const [_, forceUpdate] = useReducer(x => x + 1, 0);
|
||||
|
||||
return <div className='absolute left-0 w-40 flex flex-col'>
|
||||
{
|
||||
btnz.map(([Icon, fcn, txt], idx) => (
|
||||
|
@ -73,7 +78,7 @@ const App = () => {
|
|||
}
|
||||
|
||||
<div className=''>
|
||||
{treeEntries.allNids.map((entId, idx) => (
|
||||
{treeEntries.allIds.map((entId, idx) => (
|
||||
<TreeEntry key={idx} entId={entId} />
|
||||
))}
|
||||
</div>
|
||||
|
@ -84,9 +89,10 @@ const App = () => {
|
|||
|
||||
const TreeEntry = ({ entId }) => {
|
||||
|
||||
const treeEntries = useSelector(state => state.treeEntries.byNid)
|
||||
const treeEntries = useSelector(state => state.treeEntries.byId)
|
||||
const dispatch = useDispatch()
|
||||
|
||||
const activeSketchNid = useSelector(state => state.activeSketchNid)
|
||||
const activeSketchId = useSelector(state => state.activeSketchId)
|
||||
|
||||
let obj3d, entry;
|
||||
|
||||
|
@ -105,7 +111,7 @@ const TreeEntry = ({ entId }) => {
|
|||
return <div className='bg-gray-50 flex justify-between w-full'>
|
||||
<div className='btn'
|
||||
onClick={() => {
|
||||
activeSketchNid && treeEntries[activeSketchNid].deactivate()
|
||||
activeSketchId && treeEntries[activeSketchId].deactivate()
|
||||
entry.activate()
|
||||
sc.activeSketch = entry;
|
||||
}}
|
||||
|
@ -113,6 +119,13 @@ const TreeEntry = ({ entId }) => {
|
|||
<MdEdit />
|
||||
</div>
|
||||
|
||||
<div className='btn'
|
||||
onClick={() => {
|
||||
dispatch({type:'delete-node',id:entId})
|
||||
}}
|
||||
>
|
||||
<MdDelete/>
|
||||
</div>
|
||||
{
|
||||
vis ?
|
||||
<div className='btn'
|
||||
|
@ -165,12 +178,10 @@ const TreeEntry = ({ entId }) => {
|
|||
|
||||
}
|
||||
|
||||
const subtract = () => {
|
||||
const subtract = (m1,m2) => {
|
||||
// //Create a bsp tree from each of the meshes
|
||||
// console.log(sc.selected.length != 2 || !sc.selected.every(e => e.userData.type == 'mesh'), "wtf")
|
||||
if (sc.selected.length != 2 || !sc.selected.every(e => e.userData.type == 'mesh')) return
|
||||
// console.log('here')
|
||||
const [m1, m2] = sc.selected
|
||||
|
||||
|
||||
let bspA = BoolOp.fromMesh(m1)
|
||||
let bspB = BoolOp.fromMesh(m2)
|
||||
|
@ -184,9 +195,12 @@ const subtract = () => {
|
|||
// //Get the resulting mesh from the result bsp, and assign meshA.material to the resulting mesh
|
||||
|
||||
let meshResult = BoolOp.toMesh(bspResult, m1.matrix, m1.material)
|
||||
meshResult.userData.type = 'mesh'
|
||||
meshResult.userData.name = `${m1.name}-${m2.name}`
|
||||
|
||||
sc.obj3d.add(meshResult)
|
||||
sc.render()
|
||||
|
||||
return meshResult
|
||||
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,102 @@
|
|||
class DepTree {
|
||||
constructor() {
|
||||
this.tree = {}
|
||||
this.order = {}
|
||||
this.arr = []
|
||||
}
|
||||
|
||||
addParent(id) {
|
||||
if (this.tree[id]) return
|
||||
this.tree[id] = new Set()
|
||||
this.order[id] = this.arr.length
|
||||
this.arr.push(id)
|
||||
}
|
||||
|
||||
addChild(childId, ...parentIds) {
|
||||
for (let parentId of parentIds) {
|
||||
this.tree[parentId].add(childId)
|
||||
}
|
||||
|
||||
this.addParent(childId)
|
||||
}
|
||||
|
||||
|
||||
deleteNode(id) {
|
||||
this.visited = new Set()
|
||||
|
||||
this.nodesToDel = []
|
||||
this.dfs(id)
|
||||
|
||||
const idx = []
|
||||
this.nodesToDel.sort((a, b) => this.order[b] - this.order[a])
|
||||
|
||||
for (let id of this.nodesToDel) {
|
||||
idx.push(this.order[id])
|
||||
this.arr.splice(this.order[id], 1)
|
||||
delete this.tree[id]
|
||||
delete this.order[id]
|
||||
}
|
||||
|
||||
for (let i = idx[idx.length - 1]; i < this.arr.length; i++) {
|
||||
this.order[this.arr[i]] = i
|
||||
}
|
||||
|
||||
const nodeToDelSet = new Set(this.nodesToDel)
|
||||
|
||||
for (let k in this.tree) {
|
||||
for (let ent of this.tree[k]) {
|
||||
if (nodeToDelSet.has(ent)) {
|
||||
this.tree[k].delete(ent)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return idx
|
||||
}
|
||||
|
||||
|
||||
dfs(id) {
|
||||
this.visited.add(id)
|
||||
this.nodesToDel.push(id)
|
||||
for (let x of this.tree[id]) {
|
||||
if (!this.visited.has(x)) {
|
||||
this.dfs(x)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
const dt = new DepTree()
|
||||
|
||||
|
||||
dt.addParent('r1')
|
||||
dt.addParent('r2')
|
||||
|
||||
|
||||
dt.addChild('r3', 'r1', 'r2')
|
||||
|
||||
dt.addParent('r4')
|
||||
|
||||
dt.addChild('r5', 'r4', 'r3')
|
||||
|
||||
dt.addChild('r6', 'r1', 'r5')
|
||||
|
||||
dt.addChild('r7', 'r3', 'r5')
|
||||
|
||||
|
||||
// const x = dt.deleteNode('r3')
|
||||
|
||||
// console.log(x)
|
||||
// console.log(dt.arr, dt.order)
|
||||
|
||||
// expectd output
|
||||
// [ 6, 5, 4, 2 ]
|
||||
// [ 'r1', 'r2', 'r4' ] { r1: 0, r2: 1, r4: 2 }
|
||||
|
||||
|
||||
const x = dt.deleteNode('r5')
|
||||
|
||||
console.log(x)
|
||||
console.log(dt.tree)
|
|
@ -0,0 +1,120 @@
|
|||
export class DepTree {
|
||||
constructor(obj) {
|
||||
if (obj) {
|
||||
console.log('load', obj)
|
||||
this.order = { ...obj.order }
|
||||
this.byId = { ...obj.byId }
|
||||
this.allIds = [...obj.allIds]
|
||||
|
||||
this.tree = {}
|
||||
for (let k in obj.tree) {
|
||||
this.tree[k] = { ...obj.tree[k] }
|
||||
}
|
||||
|
||||
} else {
|
||||
this.tree = {}
|
||||
this.order = {}
|
||||
this.allIds = []
|
||||
}
|
||||
}
|
||||
|
||||
addParent(id) {
|
||||
if (this.tree[id]) return
|
||||
this.tree[id] = {}
|
||||
this.order[id] = this.allIds.length
|
||||
this.allIds.push(id)
|
||||
}
|
||||
|
||||
addChild(childId, ...parentIds) {
|
||||
for (let parentId of parentIds) {
|
||||
this.tree[parentId][childId] = true;
|
||||
}
|
||||
|
||||
this.addParent(childId)
|
||||
}
|
||||
|
||||
|
||||
deleteNode(id) {
|
||||
const dfs = (id) => {
|
||||
visited.add(id)
|
||||
nodesToDel.push(id)
|
||||
for (let k in this.tree[id]) {
|
||||
if (!visited.has(k)) {
|
||||
dfs(k)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
const visited = new Set()
|
||||
|
||||
const nodesToDel = []
|
||||
dfs(id)
|
||||
|
||||
nodesToDel.sort((a, b) => this.order[b] - this.order[a])
|
||||
|
||||
|
||||
let spliceIdx;
|
||||
for (let id of nodesToDel) {
|
||||
spliceIdx = this.order[id]
|
||||
|
||||
this.allIds.splice(spliceIdx, 1)
|
||||
|
||||
const deletedObj = sc.obj3d.children.splice(spliceIdx + 4, 1)[0]
|
||||
|
||||
deletedObj.traverse((obj)=>{
|
||||
if (obj.geometry) obj.geometry.dispose()
|
||||
if (obj.material) obj.material.dispose()
|
||||
})
|
||||
|
||||
delete this.tree[id]
|
||||
delete this.byId[id]
|
||||
delete this.order[id]
|
||||
}
|
||||
|
||||
for (let i = spliceIdx; i < this.allIds.length; i++) {
|
||||
this.order[this.allIds[i]] = i
|
||||
}
|
||||
|
||||
const nodeToDelSet = new Set(nodesToDel)
|
||||
for (let k in this.tree) {
|
||||
for (let m in this.tree[k]) {
|
||||
if (nodeToDelSet.has(m)) {
|
||||
delete this.tree[k][m]
|
||||
}
|
||||
}
|
||||
}
|
||||
return this
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
// const dt = new DepTree()
|
||||
// dt.addParent('r1')
|
||||
// dt.addParent('r2')
|
||||
// dt.addChild('r3', 'r1', 'r2')
|
||||
// dt.addParent('r4')
|
||||
// dt.addChild('r5', 'r4', 'r3')
|
||||
// dt.addChild('r6', 'r1', 'r5')
|
||||
// dt.addChild('r7', 'r3', 'r5')
|
||||
|
||||
// dt.addParent('r8')
|
||||
|
||||
// // console.log(dt)
|
||||
|
||||
// // const x = dt.deleteNode('r3')
|
||||
// // console.log(x)
|
||||
// // console.log(dt.allIds, dt.order)
|
||||
// // [ 6, 5, 4, 2 ]
|
||||
// // [ 'r1', 'r2', 'r4' ] { r1: 0, r2: 1, r4: 2 }
|
||||
|
||||
|
||||
// const x = dt.deleteNode('r5')
|
||||
// console.log(dt)
|
||||
// DepTree {
|
||||
// tree: { r1: { r3: true }, r2: { r3: true }, r3: {}, r4: {}, r8: {} },
|
||||
// order: { r1: 0, r2: 1, r3: 2, r4: 3, r8: 4 },
|
||||
// allIds: [ 'r1', 'r2', 'r3', 'r4', 'r8' ]
|
||||
// }
|
||||
|
|
@ -98,7 +98,7 @@ export function extrude(sketch) {
|
|||
this.render()
|
||||
|
||||
// sketch.visible = false
|
||||
this.store.dispatch({ type: 'rx-extrusion', mesh, sketch })
|
||||
this.store.dispatch({ type: 'rx-extrusion', mesh, sketchId: sketch.obj3d.name })
|
||||
}
|
||||
|
||||
|
||||
|
|
72
src/index.js
72
src/index.js
|
@ -2,43 +2,64 @@
|
|||
import ReactDOM from 'react-dom'
|
||||
import React from 'react'
|
||||
import { Root } from './app.jsx'
|
||||
|
||||
import update from 'immutability-helper';
|
||||
|
||||
import { createStore, applyMiddleware } from 'redux'
|
||||
import logger from 'redux-logger'
|
||||
|
||||
let _entId = 0
|
||||
import { DepTree } from './depTree.mjs'
|
||||
|
||||
|
||||
|
||||
|
||||
function reducer(state = {}, action) {
|
||||
switch (action.type) {
|
||||
case 'rx-sketch':
|
||||
return {
|
||||
...state,
|
||||
return update(state, {
|
||||
treeEntries: {
|
||||
byNid: { ...state.treeEntries.byNid, [action.obj.obj3d.name]: action.obj },
|
||||
allNids: [...state.treeEntries.allNids, action.obj.obj3d.name]
|
||||
}
|
||||
}
|
||||
byId: { [action.obj.obj3d.name]: { $set: action.obj } },
|
||||
allIds: { $push: [action.obj.obj3d.name] },
|
||||
tree: { [action.obj.obj3d.name]: { $set: {} } },
|
||||
order: { [action.obj.obj3d.name]: { $set: state.treeEntries.allIds.length } }
|
||||
},
|
||||
})
|
||||
|
||||
case 'set-active-sketch':
|
||||
return {
|
||||
...state, activeSketchNid: action.sketch
|
||||
}
|
||||
return update(state, {
|
||||
activeSketchId: { $set: action.sketch },
|
||||
})
|
||||
case 'exit-sketch':
|
||||
return {
|
||||
...state, activeSketchNid: ''
|
||||
...state, activeSketchId: ''
|
||||
}
|
||||
case 'rx-extrusion':
|
||||
return {
|
||||
...state,
|
||||
|
||||
return update(state, {
|
||||
treeEntries: {
|
||||
byNid: { ...state.treeEntries.byNid, [action.mesh.name]: action.mesh },
|
||||
allNids: [...state.treeEntries.allNids, action.mesh.name]
|
||||
},
|
||||
mesh2sketch: {
|
||||
...state.mesh2sketch,
|
||||
[action.sketch.obj3d.name]: action.mesh.name
|
||||
byId: {
|
||||
[action.mesh.name]: { $set: action.mesh }
|
||||
},
|
||||
allIds: { $push: [action.mesh.name] },
|
||||
tree: {
|
||||
[action.sketchId]: { [action.mesh.name]: { $set: true } },
|
||||
},
|
||||
order: { [action.mesh.name]: { $set: state.treeEntries.allIds.length } }
|
||||
}
|
||||
}
|
||||
})
|
||||
|
||||
case 'delete-node':
|
||||
|
||||
const depTree = new DepTree(state.treeEntries)
|
||||
|
||||
const obj = depTree.deleteNode(action.id)
|
||||
|
||||
|
||||
return update(state, {
|
||||
treeEntries: {$set: obj}
|
||||
})
|
||||
|
||||
|
||||
|
||||
case 'restore-state':
|
||||
return action.state
|
||||
default:
|
||||
|
@ -48,12 +69,13 @@ function reducer(state = {}, action) {
|
|||
|
||||
|
||||
|
||||
|
||||
const preloadedState = {
|
||||
treeEntries: {
|
||||
byNid: {},
|
||||
allNids: []
|
||||
}
|
||||
byId: {},
|
||||
allIds: [],
|
||||
tree: {},
|
||||
order: {},
|
||||
},
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -9,7 +9,7 @@ import { get3PtArc } from './drawArc'
|
|||
import { _vec2, _vec3, raycaster, awaitPts } from '../utils/shared'
|
||||
import { replacer, reviver } from '../utils/mapJSONReplacer'
|
||||
import { AxesHelper } from '../utils/axes'
|
||||
import { drawDimension, _onMoveDimension, setDimLines } from './drawDimension';
|
||||
import { drawDimension, _onMoveDimension, setDimLines, updateDim } from './drawDimension';
|
||||
|
||||
|
||||
|
||||
|
@ -114,6 +114,7 @@ class Sketch {
|
|||
this.drawDimension = drawDimension.bind(this)
|
||||
this._onMoveDimension = _onMoveDimension.bind(this)
|
||||
this.setDimLines = setDimLines.bind(this)
|
||||
this.updateDim = updateDim.bind(this)
|
||||
|
||||
this.awaitPts = awaitPts.bind(this);
|
||||
|
||||
|
|
|
@ -87,29 +87,9 @@ export async function drawDimension() {
|
|||
point.name = this.c_id
|
||||
point.userData.type = 'dimension'
|
||||
|
||||
const updateDim = (c_id) => (ev_focus) => {
|
||||
const value = ev_focus.target.textContent
|
||||
console.log(value)
|
||||
document.addEventListener('keydown', (e) => {
|
||||
if (e.key == 'Enter') {
|
||||
e.preventDefault()
|
||||
const ent = this.constraints.get(c_id)
|
||||
ent[1] = parseFloat(ev_focus.target.textContent)
|
||||
this.constraints.set(c_id, ent)
|
||||
this.updateOtherBuffers()
|
||||
this.solve()
|
||||
sc.render()
|
||||
ev_focus.target.blur()
|
||||
this.updateBoundingSpheres()
|
||||
} else if (e.key == 'Escape') {
|
||||
ev_focus.target.textContent = value
|
||||
getSelection().empty()
|
||||
ev_focus.target.blur()
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
point.label.addEventListener('focus', updateDim(this.c_id))
|
||||
|
||||
point.label.addEventListener('focus', this.updateDim(this.c_id))
|
||||
|
||||
|
||||
|
||||
|
@ -133,12 +113,39 @@ const p2 = new THREE.Vector2()
|
|||
const p3 = new THREE.Vector2()
|
||||
let dir, hyp, proj, perp, p1e, p2e, nids, _p1, _p2;
|
||||
|
||||
|
||||
|
||||
export function updateDim(c_id) {
|
||||
return (ev_focus) => {
|
||||
const value = ev_focus.target.textContent
|
||||
document.addEventListener('keydown', (e) => {
|
||||
if (e.key == 'Enter') {
|
||||
e.preventDefault()
|
||||
const ent = this.constraints.get(c_id)
|
||||
ent[1] = parseFloat(ev_focus.target.textContent)
|
||||
this.constraints.set(c_id, ent)
|
||||
this.updateOtherBuffers()
|
||||
this.solve()
|
||||
sc.render()
|
||||
ev_focus.target.blur()
|
||||
this.updateBoundingSpheres()
|
||||
} else if (e.key == 'Escape') {
|
||||
ev_focus.target.textContent = value
|
||||
getSelection().empty()
|
||||
ev_focus.target.blur()
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
export function _onMoveDimension(point, line) {
|
||||
|
||||
nids = line.userData.nids
|
||||
|
||||
_p1 = this.obj3d.children[sketcher.objIdx.get(nids[0])].geometry.attributes.position.array
|
||||
_p2 = this.obj3d.children[sketcher.objIdx.get(nids[1])].geometry.attributes.position.array
|
||||
_p1 = this.obj3d.children[this.objIdx.get(nids[0])].geometry.attributes.position.array
|
||||
_p2 = this.obj3d.children[this.objIdx.get(nids[1])].geometry.attributes.position.array
|
||||
|
||||
p1.set(_p1[0], _p1[1])
|
||||
p2.set(_p2[0], _p2[1])
|
||||
|
@ -163,27 +170,6 @@ export function _onMoveDimension(point, line) {
|
|||
|
||||
|
||||
export function setDimLines() {
|
||||
const updateDim = (c_id) => (ev_focus) => {
|
||||
const value = ev_focus.target.textContent
|
||||
console.log(value)
|
||||
document.addEventListener('keydown', (e) => {
|
||||
if (e.key == 'Enter') {
|
||||
e.preventDefault()
|
||||
const ent = this.constraints.get(c_id)
|
||||
ent[1] = parseFloat(ev_focus.target.textContent)
|
||||
this.constraints.set(c_id, ent)
|
||||
this.updateOtherBuffers()
|
||||
this.solve()
|
||||
sc.render()
|
||||
ev_focus.target.blur()
|
||||
this.updateBoundingSpheres()
|
||||
} else if (e.key == 'Escape') {
|
||||
ev_focus.target.textContent = value
|
||||
getSelection().empty()
|
||||
ev_focus.target.blur()
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
const restoreLabels = this.labelContainer.childElementCount == 0;
|
||||
|
||||
|
@ -200,18 +186,15 @@ export function setDimLines() {
|
|||
point.label.textContent = dist.toFixed(3);
|
||||
point.label.contentEditable = true;
|
||||
this.labelContainer.append(point.label)
|
||||
|
||||
|
||||
|
||||
point.label.addEventListener('focus', updateDim(this.c_id))
|
||||
|
||||
point.label.addEventListener('focus', this.updateDim(this.c_id))
|
||||
}
|
||||
|
||||
|
||||
nids = dims[i].userData.nids
|
||||
|
||||
_p1 = this.obj3d.children[sketcher.objIdx.get(nids[0])].geometry.attributes.position.array
|
||||
_p2 = this.obj3d.children[sketcher.objIdx.get(nids[1])].geometry.attributes.position.array
|
||||
_p1 = this.obj3d.children[this.objIdx.get(nids[0])].geometry.attributes.position.array
|
||||
_p2 = this.obj3d.children[this.objIdx.get(nids[1])].geometry.attributes.position.array
|
||||
|
||||
const offset = dims[i + 1].userData.offset
|
||||
|
||||
|
|
|
@ -13,35 +13,51 @@ export function onHover(e) {
|
|||
);
|
||||
|
||||
let hoverPts;
|
||||
let idx = []
|
||||
|
||||
if (this.obj3d.userData.type == 'sketch') {
|
||||
hoverPts = raycaster.intersectObjects([...this.obj3d.children[1].children, ...this.obj3d.children])
|
||||
|
||||
// if (!hoverPts.length) {
|
||||
// hoverPts = raycaster.intersectObjects(this.obj3d.children)
|
||||
// }
|
||||
} else {
|
||||
hoverPts = raycaster.intersectObjects(this.obj3d.children, true)
|
||||
}
|
||||
|
||||
// if (hoverDim.length) {
|
||||
// }
|
||||
|
||||
let idx = []
|
||||
if (hoverPts.length) {
|
||||
let minDist = Infinity;
|
||||
for (let i = 0; i < hoverPts.length; i++) {
|
||||
if (!hoverPts[i].distanceToRay) continue;
|
||||
if (hoverPts[i].distanceToRay < minDist - 0.0001) {
|
||||
minDist = hoverPts[i].distanceToRay
|
||||
idx = [i]
|
||||
} else if (Math.abs(hoverPts[i].distanceToRay - minDist) < 0.0001) {
|
||||
idx.push(i)
|
||||
if (hoverPts.length) {
|
||||
let minDist = Infinity;
|
||||
for (let i = 0; i < hoverPts.length; i++) {
|
||||
if (!hoverPts[i].distanceToRay) continue;
|
||||
if (hoverPts[i].distanceToRay < minDist - 0.0001) {
|
||||
minDist = hoverPts[i].distanceToRay
|
||||
idx = [i]
|
||||
} else if (Math.abs(hoverPts[i].distanceToRay - minDist) < 0.0001) {
|
||||
idx.push(i)
|
||||
}
|
||||
}
|
||||
// console.log(hoverPts, idx)
|
||||
if (!idx.length) idx.push(0)
|
||||
}
|
||||
// console.log(hoverPts, idx)
|
||||
if (!idx.length) idx.push(0)
|
||||
|
||||
|
||||
} else {
|
||||
// hoverPts = raycaster.intersectObjects(this.obj3d.children)
|
||||
hoverPts = raycaster.intersectObjects(this.obj3d.children,true)
|
||||
|
||||
|
||||
// for (let i = 0; i < hoverPts.length; i++) {
|
||||
// const obj = hoverPts[i].object
|
||||
// if (obj.userData.type == "mesh" && obj.visible || obj.userData.type == "plane") {
|
||||
// idx.push(i)
|
||||
// }
|
||||
// }
|
||||
if (hoverPts.length) {
|
||||
// console.log(hoverPts)
|
||||
if (!idx.length) idx.push(0)
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
if (idx.length) { // after filtering, hovered objs still exists
|
||||
if (hoverPts[idx[0]].object != this.hovered[0]) { // if the previous hovered obj is not the same as current
|
||||
|
||||
|
|
28
todo.txt
28
todo.txt
|
@ -1,11 +1,31 @@
|
|||
fix css on design tree (a lot of work) \
|
||||
clear dim on exit exit sketch / rehydrate when back or after loading
|
||||
boolean flesh out refresh / replace mesh
|
||||
dimension to origin
|
||||
clear dim on exit exit sketch / rehydrate when back or after loading \\\ done
|
||||
|
||||
boolean flesh out refresh / replace mesh / delete mesh
|
||||
- need to auto hide ( consume) when new boolean created
|
||||
- create derived part using relationship as name
|
||||
- sensible default names, like extrude 1, sketch 1, leverage react for this
|
||||
- hidden bodies messes up hover highlight
|
||||
|
||||
extrude edit dialog. directio and magnitude
|
||||
|
||||
fix extrusion loop find
|
||||
|
||||
dimension to origin
|
||||
|
||||
reattaching sketch
|
||||
file save
|
||||
stl export
|
||||
|
||||
angle
|
||||
other constraints / sprite
|
||||
other constraints / sprite
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
finish mode messed up after restore
|
Loading…
Reference in New Issue