Add selection guard and clean up
This commit is contained in:
@ -776,7 +776,6 @@ const shellPointAndClickCapCases = [
|
|||||||
shellPointAndClickCapCases.forEach(({ shouldPreselect }) => {
|
shellPointAndClickCapCases.forEach(({ shouldPreselect }) => {
|
||||||
test(`Shell point-and-click cap (preselected sketches: ${shouldPreselect})`, async ({
|
test(`Shell point-and-click cap (preselected sketches: ${shouldPreselect})`, async ({
|
||||||
app,
|
app,
|
||||||
page,
|
|
||||||
scene,
|
scene,
|
||||||
editor,
|
editor,
|
||||||
toolbar,
|
toolbar,
|
||||||
@ -877,7 +876,7 @@ extrude001 = extrude(40, sketch001)
|
|||||||
|
|
||||||
// One dumb hardcoded screen pixel value
|
// One dumb hardcoded screen pixel value
|
||||||
const testPoint = { x: 580, y: 250 }
|
const testPoint = { x: 580, y: 250 }
|
||||||
const [clickOnCap] = scene.makeMouseHelpers(testPoint.x, testPoint.y)
|
const [clickOnWall] = scene.makeMouseHelpers(testPoint.x, testPoint.y)
|
||||||
const mutatedCode = 'xLine(-40, %, $seg01)'
|
const mutatedCode = 'xLine(-40, %, $seg01)'
|
||||||
const shellDeclaration =
|
const shellDeclaration =
|
||||||
'shell001 = shell({ faces = [seg01], thickness = 5 }, extrude001)'
|
'shell001 = shell({ faces = [seg01], thickness = 5 }, extrude001)'
|
||||||
@ -899,7 +898,7 @@ extrude001 = extrude(40, sketch001)
|
|||||||
highlightedHeaderArg: 'selection',
|
highlightedHeaderArg: 'selection',
|
||||||
commandName: 'Shell',
|
commandName: 'Shell',
|
||||||
})
|
})
|
||||||
await clickOnCap()
|
await clickOnWall()
|
||||||
await cmdBar.progressCmdBar()
|
await cmdBar.progressCmdBar()
|
||||||
await cmdBar.expectState({
|
await cmdBar.expectState({
|
||||||
stage: 'review',
|
stage: 'review',
|
||||||
|
@ -70,6 +70,7 @@ import {
|
|||||||
} from 'lang/modifyAst'
|
} from 'lang/modifyAst'
|
||||||
import { Program, parse, recast } from 'lang/wasm'
|
import { Program, parse, recast } from 'lang/wasm'
|
||||||
import {
|
import {
|
||||||
|
doesSceneHaveExtrudedSketch,
|
||||||
doesSceneHaveSweepableSketch,
|
doesSceneHaveSweepableSketch,
|
||||||
getNodePathFromSourceRange,
|
getNodePathFromSourceRange,
|
||||||
isSingleCursorInPipe,
|
isSingleCursorInPipe,
|
||||||
@ -586,18 +587,21 @@ export const ModelingMachineProvider = ({
|
|||||||
if (err(canLoft)) return false
|
if (err(canLoft)) return false
|
||||||
return canLoft
|
return canLoft
|
||||||
},
|
},
|
||||||
'has valid shell selection': ({ context: { selectionRanges } }) => {
|
'has valid shell selection': ({
|
||||||
|
context: { selectionRanges },
|
||||||
|
event,
|
||||||
|
}) => {
|
||||||
const hasNoSelection =
|
const hasNoSelection =
|
||||||
selectionRanges.graphSelections.length === 0 ||
|
selectionRanges.graphSelections.length === 0 ||
|
||||||
isRangeBetweenCharacters(selectionRanges) ||
|
isRangeBetweenCharacters(selectionRanges) ||
|
||||||
isSelectionLastLine(selectionRanges, codeManager.code)
|
isSelectionLastLine(selectionRanges, codeManager.code)
|
||||||
|
|
||||||
if (hasNoSelection) {
|
if (hasNoSelection) {
|
||||||
// TODO: find extrude in ast
|
return doesSceneHaveExtrudedSketch(kclManager.ast)
|
||||||
// return doesSceneHaveSweepableSketch(kclManager.ast, count)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
const canShell = canShellSelection(selectionRanges)
|
const canShell = canShellSelection(selectionRanges)
|
||||||
|
console.log('canShellSelection', canShellSelection(selectionRanges))
|
||||||
if (err(canShell)) return false
|
if (err(canShell)) return false
|
||||||
return canShell
|
return canShell
|
||||||
},
|
},
|
||||||
|
@ -1042,6 +1042,35 @@ export function doesSceneHaveSweepableSketch(ast: Node<Program>, count = 1) {
|
|||||||
return Object.keys(theMap).length >= count
|
return Object.keys(theMap).length >= count
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export function doesSceneHaveExtrudedSketch(ast: Node<Program>) {
|
||||||
|
const theMap: any = {}
|
||||||
|
traverse(ast as any, {
|
||||||
|
enter(node) {
|
||||||
|
if (
|
||||||
|
node.type === 'VariableDeclarator' &&
|
||||||
|
node.init?.type === 'PipeExpression'
|
||||||
|
) {
|
||||||
|
for (const pipe of node.init.body) {
|
||||||
|
if (
|
||||||
|
pipe.type === 'CallExpression' &&
|
||||||
|
pipe.callee.name === 'extrude'
|
||||||
|
) {
|
||||||
|
theMap[node.id.name] = true
|
||||||
|
break
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else if (
|
||||||
|
node.type === 'CallExpression' &&
|
||||||
|
node.callee.name === 'extrude' &&
|
||||||
|
node.arguments[1]?.type === 'Identifier'
|
||||||
|
) {
|
||||||
|
theMap[node.moduleId] = true
|
||||||
|
}
|
||||||
|
},
|
||||||
|
})
|
||||||
|
return Object.keys(theMap).length > 0
|
||||||
|
}
|
||||||
|
|
||||||
export function getObjExprProperty(
|
export function getObjExprProperty(
|
||||||
node: ObjectExpression,
|
node: ObjectExpression,
|
||||||
propName: string
|
propName: string
|
||||||
|
@ -289,7 +289,7 @@ export const modelingMachineCommandConfig: StateMachineCommandSetConfig<
|
|||||||
selection: {
|
selection: {
|
||||||
inputType: 'selection',
|
inputType: 'selection',
|
||||||
selectionTypes: ['cap', 'wall'],
|
selectionTypes: ['cap', 'wall'],
|
||||||
// TODO: check if we can have multiple here
|
// TODO: allow multiple faces to be selected here
|
||||||
multiple: false,
|
multiple: false,
|
||||||
required: true,
|
required: true,
|
||||||
skip: true,
|
skip: true,
|
||||||
|
@ -583,15 +583,10 @@ export function canShellSelection(selection: Selections) {
|
|||||||
const commonNodes = selection.graphSelections.map((_, i) =>
|
const commonNodes = selection.graphSelections.map((_, i) =>
|
||||||
buildCommonNodeFromSelection(selection, i)
|
buildCommonNodeFromSelection(selection, i)
|
||||||
)
|
)
|
||||||
return (
|
return commonNodes.every(
|
||||||
// TODO: check what's needed here
|
(n) =>
|
||||||
// !!isCursorInSketchCommandRange(
|
n.selection.artifact?.type == 'cap' ||
|
||||||
// engineCommandManager.artifactGraph,
|
n.selection.artifact?.type == 'wall'
|
||||||
// selection
|
|
||||||
// ) &&
|
|
||||||
commonNodes.every((n) => !hasSketchPipeBeenExtruded(n.selection, n.ast)) &&
|
|
||||||
commonNodes.every((n) => nodeHasClose(n) || nodeHasCircle(n)) &&
|
|
||||||
commonNodes.every((n) => !nodeHasExtrude(n))
|
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1682,11 +1682,13 @@ export const modelingMachine = setup({
|
|||||||
|
|
||||||
Loft: {
|
Loft: {
|
||||||
target: 'Applying loft',
|
target: 'Applying loft',
|
||||||
|
guard: 'has valid loft selection',
|
||||||
reenter: true,
|
reenter: true,
|
||||||
},
|
},
|
||||||
|
|
||||||
Shell: {
|
Shell: {
|
||||||
target: 'Applying shell',
|
target: 'Applying shell',
|
||||||
|
guard: 'has valid shell selection',
|
||||||
reenter: true,
|
reenter: true,
|
||||||
},
|
},
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user