selection filter

This commit is contained in:
Val Erastov 2022-12-16 20:10:19 -08:00
parent baa06f564d
commit 5720a980f4
5 changed files with 76 additions and 17 deletions

View file

@ -22,6 +22,7 @@ import {SketchStorageBundleContext} from "cad/sketch/sketchStorageBundle";
import {StorageBundleContext} from "cad/storage/storageBundle"; import {StorageBundleContext} from "cad/storage/storageBundle";
import {WorkbenchBundleContext} from "cad/workbench/workbenchBundle"; import {WorkbenchBundleContext} from "cad/workbench/workbenchBundle";
import {LegacyStructureBundleContext} from "cad/context/LegacyStructureBundle"; import {LegacyStructureBundleContext} from "cad/context/LegacyStructureBundle";
import {PickControlBundleContext} from "cad/scene/controls/pickControlBundle";
export interface ApplicationContext extends export interface ApplicationContext extends
LegacyStructureBundleContext, LegacyStructureBundleContext,
@ -47,7 +48,8 @@ export interface ApplicationContext extends
SketcherBundleContext, SketcherBundleContext,
SketchStorageBundleContext, SketchStorageBundleContext,
StorageBundleContext, StorageBundleContext,
WorkbenchBundleContext WorkbenchBundleContext,
PickControlBundleContext
{} {}
export default {} as ApplicationContext; export default {} as ApplicationContext;

View file

@ -1,7 +1,7 @@
import {FACE} from 'cad/model/entities'; import {FACE} from 'cad/model/entities';
import {OperationRequest} from "cad/craft/craftBundle"; import {OperationRequest} from "cad/craft/craftBundle";
import {ParamsPath, WizardService} from "cad/craft/wizard/wizardTypes"; import {ParamsPath, WizardService, WizardState, WorkingRequest} from "cad/craft/wizard/wizardTypes";
import {OperationParamPrimitive} from "cad/craft/schema/schema"; import {OperationParamPrimitive, OperationParams, OperationParamValue} from "cad/craft/schema/schema";
import {EntityReference} from "cad/craft/operationBundle"; import {EntityReference} from "cad/craft/operationBundle";
import {Bundle} from "bundler/bundleSystem"; import {Bundle} from "bundler/bundleSystem";
import {MarkerBundleContext} from "cad/scene/selectionMarker/markerBundle"; import {MarkerBundleContext} from "cad/scene/selectionMarker/markerBundle";
@ -9,6 +9,7 @@ import {WizardBundleContext} from "cad/craft/wizard/wizardBundle";
import {PickControlBundleContext} from "cad/scene/controls/pickControlBundle"; import {PickControlBundleContext} from "cad/scene/controls/pickControlBundle";
import _ from "lodash"; import _ from "lodash";
import {MObject} from "cad/model/mobject"; import {MObject} from "cad/model/mobject";
import {combine} from "lstream";
type WizardSelectionBundleActivationContext = MarkerBundleContext & WizardBundleContext & PickControlBundleContext; type WizardSelectionBundleActivationContext = MarkerBundleContext & WizardBundleContext & PickControlBundleContext;
@ -63,6 +64,27 @@ export const WizardSelectionBundle: Bundle<WizardSelectionBundleWorkingContext>
syncMarkers(); syncMarkers();
} }
}); });
combine(wizardService.state$, wizardService.workingRequest$).attach(([state, req]: [WizardState, WorkingRequest]) => {
if (req && state?.activeParam && ctx.wizardService.operation) {
const entity = ctx.wizardService.operation.schemaIndex.entitiesByFlattenedPaths[state.activeParam];
if (entity) {
ctx.pickControlService.setSelectionFilter(entity.metadata.entityCapture);
} else {
ctx.pickControlService.setSelectionFilter(() => false);
}
} else {
ctx.pickControlService.setSelectionFilter(null);
}
});
wizardService.state$.attach(state => {
if (state?.activeParam) {
}
})
}, },
BundleName: "@WizardSelection", BundleName: "@WizardSelection",

View file

@ -1,11 +1,11 @@
import React from "react"; import React, {useContext} from "react";
import {state} from "lstream"; import {state} from "lstream";
import {useStreamWithUpdater} from "ui/effects"; import {useStreamWithUpdater} from "ui/effects";
import Window from "ui/components/Window"; import Window from "ui/components/Window";
import {MObject} from "cad/model/mobject"; import {MObject} from "cad/model/mobject";
import Stack from "ui/components/Stack"; import Stack from "ui/components/Stack";
import {ModelSection} from "cad/craft/ui/SceneInlineObjectExplorer";
import {ModelButton} from "cad/craft/ui/ModelButton"; import {ModelButton} from "cad/craft/ui/ModelButton";
import {ReactApplicationContext} from "cad/dom/ReactApplicationContext";
export interface PickListDialogRequest { export interface PickListDialogRequest {
@ -21,6 +21,8 @@ export function PickListDialog() {
const [req, setReq] = useStreamWithUpdater(() => PickListDialogRequest$); const [req, setReq] = useStreamWithUpdater(() => PickListDialogRequest$);
const ctx = useContext(ReactApplicationContext);
const close = () => setReq(null); const close = () => setReq(null);
if (!req) { if (!req) {
@ -35,12 +37,14 @@ export function PickListDialog() {
className='small-typography' className='small-typography'
onClose={close}> onClose={close}>
<Stack> <Stack>
{req.capture.map(model => { {req.capture
return <ModelButton .filter(model => ctx.pickControlService.isSelectionEnabledFor(model))
key={model.id} .map(model => {
model={model} return <ModelButton
/> key={model.id}
})} model={model}
/>
})}
</Stack> </Stack>
</Window> </Window>

View file

@ -1,6 +1,6 @@
import * as mask from 'gems/mask' import * as mask from 'gems/mask'
import {getAttribute} from 'scene/objectData'; import {getAttribute} from 'scene/objectData';
import {DATUM, DATUM_AXIS, EDGE, FACE, LOOP, SHELL, SKETCH_OBJECT} from 'cad/model/entities'; import {DATUM, DATUM_AXIS, EDGE, EntityKind, FACE, LOOP, SHELL, SKETCH_OBJECT} from 'cad/model/entities';
import {LOG_FLAGS} from 'cad/logFlags'; import {LOG_FLAGS} from 'cad/logFlags';
import {initRayCastDebug, printRaycastDebugInfo, RayCastDebugInfo} from "./rayCastDebug"; import {initRayCastDebug, printRaycastDebugInfo, RayCastDebugInfo} from "./rayCastDebug";
import {PickListDialog, PickListDialogRequest$} from "cad/scene/controls/PickListDialog"; import {PickListDialog, PickListDialogRequest$} from "cad/scene/controls/PickListDialog";
@ -20,6 +20,10 @@ export interface PickControlService {
releasePickControl(controlToken: PickControlToken); releasePickControl(controlToken: PickControlToken);
setSelectionFilter(selectionFilter: (entity: MObject) => boolean);
isSelectionEnabledFor(entity: MObject): boolean;
deselectAll() deselectAll()
pick() pick()
@ -61,6 +65,9 @@ interface PickContext {
export const ALL_EXCLUDING_SOLID_KINDS = PICK_KIND.FACE | PICK_KIND.SKETCH | PICK_KIND.EDGE | PICK_KIND.DATUM_AXIS | PICK_KIND.LOOP; export const ALL_EXCLUDING_SOLID_KINDS = PICK_KIND.FACE | PICK_KIND.SKETCH | PICK_KIND.EDGE | PICK_KIND.DATUM_AXIS | PICK_KIND.LOOP;
export const ALL_POSSIBLE_KIND = Number.MAX_SAFE_INTEGER; export const ALL_POSSIBLE_KIND = Number.MAX_SAFE_INTEGER;
const ALLOW_ALL = (kind) => true;
export function activate(context) { export function activate(context) {
const {services} = context; const {services} = context;
@ -113,6 +120,8 @@ export function activate(context) {
let pickContext: PickContext = defaultPickContext; let pickContext: PickContext = defaultPickContext;
let contextStack = []; let contextStack = [];
let selectionFilter: (kind: EntityKind) => boolean = ALLOW_ALL;
const domElement = services.viewer.sceneSetup.domElement(); const domElement = services.viewer.sceneSetup.domElement();
domElement.addEventListener('mousedown', mousedown, false); domElement.addEventListener('mousedown', mousedown, false);
@ -187,6 +196,12 @@ export function activate(context) {
pickContext.syncMarkers(); pickContext.syncMarkers();
} }
function setSelectionFilter(_selectionFilter: (kind: EntityKind) => boolean) {
selectionFilter = _selectionFilter || ALLOW_ALL;
}
const isSelectionEnabledFor = (kind: EntityKind) => selectionFilter(kind);
const deselectAll = () => { const deselectAll = () => {
if (pickContext !== defaultPickContext) { if (pickContext !== defaultPickContext) {
console.info("deselect all cannot be used in current context"); console.info("deselect all cannot be used in current context");
@ -259,7 +274,8 @@ export function activate(context) {
} }
services.pickControl = { services.pickControl = {
takePickControl, releasePickControl, deselectAll, pick, pickFromRay, simulatePickFromRay takePickControl, releasePickControl, setSelectionFilter, isSelectionEnabledFor,
deselectAll, pick, pickFromRay, simulatePickFromRay
}; };
context.pickControlService = services.pickControl; context.pickControlService = services.pickControl;

View file

@ -9,6 +9,7 @@ import DatumView from './views/datumView';
import {View} from './views/view'; import {View} from './views/view';
import {HighlightBundle} from "cad/scene/highlightBundle"; import {HighlightBundle} from "cad/scene/highlightBundle";
import {AttributesBundle} from "cad/attributes/attributesBundle"; import {AttributesBundle} from "cad/attributes/attributesBundle";
import {EntityKind} from "cad/model/entities";
export const ViewSyncBundle = { export const ViewSyncBundle = {
@ -16,18 +17,32 @@ export const ViewSyncBundle = {
activationDependencies: [ activationDependencies: [
HighlightBundle.BundleName, HighlightBundle.BundleName,
AttributesBundle.BundleName AttributesBundle.BundleName,
"@PickControl"
], ],
activate(ctx) { activate(ctx) {
const {streams} = ctx; const {streams} = ctx;
ctx.highlightService.highlightEvents.attach(id => { ctx.highlightService.highlightEvents.attach(id => {
const model = ctx.cadRegistry.find(id); const model = ctx.cadRegistry.find(id);
model?.ext?.view?.mark('highlight'); if (model) {
if (ctx.pickControlService.isSelectionEnabledFor(model)) {
model.ext?.view?.mark('highlight');
} else if (model.TYPE === EntityKind.FACE && model.parent) {
if (ctx.pickControlService.isSelectionEnabledFor(model.parent)) {
model.parent?.ext?.view?.mark('highlight');
}
}
}
}); });
ctx.highlightService.unHighlightEvents.attach(id => { ctx.highlightService.unHighlightEvents.attach(id => {
const model = ctx.cadRegistry.find(id); const model = ctx.cadRegistry.find(id);
model?.ext?.view?.withdraw('highlight'); if (model) {
model.ext?.view?.withdraw('highlight');
if (model.TYPE === EntityKind.FACE && model.parent) {
model.parent.ext?.view?.withdraw('highlight');
}
}
}); });
streams.cadRegistry.update.attach(sceneSynchronizer(ctx)); streams.cadRegistry.update.attach(sceneSynchronizer(ctx));