mirror of
https://github.com/invoke-ai/InvokeAI
synced 2024-08-30 20:32:17 +00:00
feat(ui): store all stage attrs in nanostores
This commit is contained in:
parent
2c3ac972e5
commit
154e3e6f64
@ -1,18 +1,20 @@
|
||||
import { Box, Flex, Text } from '@invoke-ai/ui-library';
|
||||
import { useStore } from '@nanostores/react';
|
||||
import { useAppSelector } from 'app/store/storeHooks';
|
||||
import { $stageScale } from 'features/controlLayers/store/controlLayersSlice';
|
||||
import { $stageAttrs } from 'features/controlLayers/store/controlLayersSlice';
|
||||
import { round } from 'lodash-es';
|
||||
import { memo } from 'react';
|
||||
|
||||
export const HeadsUpDisplay = memo(() => {
|
||||
const stageScale = useStore($stageScale);
|
||||
const stageAttrs = useStore($stageAttrs);
|
||||
const layerCount = useAppSelector((s) => s.controlLayers.present.layers.length);
|
||||
const bbox = useAppSelector((s) => s.controlLayers.present.bbox);
|
||||
|
||||
return (
|
||||
<Flex flexDir="column" bg="blackAlpha.400" borderBottomEndRadius="base" p={2} minW={64} gap={2}>
|
||||
<HUDItem label="Scale" value={round(stageScale, 3)} />
|
||||
<HUDItem label="Scale" value={round(stageAttrs.scale, 3)} />
|
||||
<HUDItem label="Stage Pos" value={`${round(stageAttrs.x, 3)}, ${round(stageAttrs.y, 3)}`} />
|
||||
<HUDItem label="Stage Size" value={`${round(stageAttrs.width, 3)}, ${round(stageAttrs.height, 3)}`} />
|
||||
<HUDItem label="Layer Count" value={layerCount} />
|
||||
<HUDItem label="BBox Size" value={`${bbox.width}×${bbox.height}`} />
|
||||
<HUDItem label="BBox Position" value={`${bbox.x}, ${bbox.y}`} />
|
||||
|
@ -26,8 +26,7 @@ import {
|
||||
$lastMouseDownPos,
|
||||
$selectedLayer,
|
||||
$shouldInvertBrushSizeScrollDirection,
|
||||
$stagePos,
|
||||
$stageScale,
|
||||
$stageAttrs,
|
||||
$tool,
|
||||
$toolBuffer,
|
||||
bboxChanged,
|
||||
@ -89,7 +88,6 @@ const useStageRenderer = (stage: Konva.Stage, container: HTMLDivElement | null,
|
||||
const lastCursorPos = useStore($lastCursorPos);
|
||||
const lastMouseDownPos = useStore($lastMouseDownPos);
|
||||
const isMouseDown = useStore($isMouseDown);
|
||||
const stageScale = useStore($stageScale);
|
||||
const isDrawing = useStore($isDrawing);
|
||||
const brushColor = useAppSelector(selectBrushColor);
|
||||
const selectedLayer = useAppSelector(selectSelectedLayer);
|
||||
@ -197,8 +195,7 @@ const useStageRenderer = (stage: Konva.Stage, container: HTMLDivElement | null,
|
||||
$lastMouseDownPos,
|
||||
$lastCursorPos,
|
||||
$lastAddedPoint,
|
||||
$stageScale,
|
||||
$stagePos,
|
||||
$stageAttrs,
|
||||
$brushSize,
|
||||
$brushColor,
|
||||
$brushSpacingPx,
|
||||
@ -236,6 +233,13 @@ const useStageRenderer = (stage: Konva.Stage, container: HTMLDivElement | null,
|
||||
const fitStageToContainer = () => {
|
||||
stage.width(container.offsetWidth);
|
||||
stage.height(container.offsetHeight);
|
||||
$stageAttrs.set({
|
||||
x: stage.x(),
|
||||
y: stage.y(),
|
||||
width: stage.width(),
|
||||
height: stage.height(),
|
||||
scale: stage.scaleX(),
|
||||
});
|
||||
};
|
||||
|
||||
const resizeObserver = new ResizeObserver(fitStageToContainer);
|
||||
|
@ -1,15 +1,16 @@
|
||||
import { calculateNewBrushSize } from 'features/canvas/hooks/useCanvasZoom';
|
||||
import { CANVAS_SCALE_BY, MAX_CANVAS_SCALE, MIN_CANVAS_SCALE } from 'features/canvas/util/constants';
|
||||
import { getIsMouseDown, getScaledFlooredCursorPosition, snapPosToStage } from 'features/controlLayers/konva/util';
|
||||
import {
|
||||
type AddBrushLineArg,
|
||||
type AddEraserLineArg,
|
||||
type AddPointToLineArg,
|
||||
type AddRectShapeArg,
|
||||
DEFAULT_RGBA_COLOR,
|
||||
type Layer,
|
||||
type Tool,
|
||||
import type {
|
||||
AddBrushLineArg,
|
||||
AddEraserLineArg,
|
||||
AddPointToLineArg,
|
||||
AddRectShapeArg,
|
||||
Layer,
|
||||
StageAttrs,
|
||||
Tool,
|
||||
} from 'features/controlLayers/store/types';
|
||||
import { DEFAULT_RGBA_COLOR } from 'features/controlLayers/store/types';
|
||||
import type Konva from 'konva';
|
||||
import type { Vector2d } from 'konva/lib/types';
|
||||
import { clamp } from 'lodash-es';
|
||||
@ -27,8 +28,7 @@ type SetStageEventHandlersArg = {
|
||||
$lastMouseDownPos: WritableAtom<Vector2d | null>;
|
||||
$lastCursorPos: WritableAtom<Vector2d | null>;
|
||||
$lastAddedPoint: WritableAtom<Vector2d | null>;
|
||||
$stageScale: WritableAtom<number>;
|
||||
$stagePos: WritableAtom<Vector2d>;
|
||||
$stageAttrs: WritableAtom<StageAttrs>;
|
||||
$brushColor: WritableAtom<RgbaColor>;
|
||||
$brushSize: WritableAtom<number>;
|
||||
$brushSpacingPx: WritableAtom<number>;
|
||||
@ -93,8 +93,7 @@ export const setStageEventHandlers = ({
|
||||
$lastMouseDownPos,
|
||||
$lastCursorPos,
|
||||
$lastAddedPoint,
|
||||
$stagePos,
|
||||
$stageScale,
|
||||
$stageAttrs,
|
||||
$brushColor,
|
||||
$brushSize,
|
||||
$brushSpacingPx,
|
||||
@ -333,15 +332,31 @@ export const setStageEventHandlers = ({
|
||||
stage.scaleX(newScale);
|
||||
stage.scaleY(newScale);
|
||||
stage.position(newPos);
|
||||
$stageScale.set(newScale);
|
||||
$stagePos.set(newPos);
|
||||
$stageAttrs.set({ ...newPos, width: stage.width(), height: stage.height(), scale: newScale });
|
||||
}
|
||||
});
|
||||
|
||||
stage.on('dragmove', () => {
|
||||
$stageAttrs.set({
|
||||
x: stage.x(),
|
||||
y: stage.y(),
|
||||
width: stage.width(),
|
||||
height: stage.height(),
|
||||
scale: stage.scaleX(),
|
||||
});
|
||||
});
|
||||
|
||||
stage.on('dragend', () => {
|
||||
// Stage position should always be an integer, else we get fractional pixels which are blurry
|
||||
stage.x(Math.floor(stage.x()));
|
||||
stage.y(Math.floor(stage.y()));
|
||||
$stageAttrs.set({
|
||||
x: stage.x(),
|
||||
y: stage.y(),
|
||||
width: stage.width(),
|
||||
height: stage.height(),
|
||||
scale: stage.scaleX(),
|
||||
});
|
||||
});
|
||||
|
||||
const onKeyDown = (e: KeyboardEvent) => {
|
||||
|
@ -13,6 +13,9 @@ export const PREVIEW_RECT_ID = 'preview_layer.rect';
|
||||
export const PREVIEW_GENERATION_BBOX_GROUP = 'preview_layer.gen_bbox_group';
|
||||
export const PREVIEW_GENERATION_BBOX_TRANSFORMER = 'preview_layer.gen_bbox_transformer';
|
||||
export const PREVIEW_GENERATION_BBOX_DUMMY_RECT = 'preview_layer.gen_bbox_dummy_rect';
|
||||
export const PREVIEW_DOCUMENT_SIZE_GROUP = 'preview_layer.doc_size_group';
|
||||
export const PREVIEW_DOCUMENT_SIZE_STAGE_RECT = 'preview_layer.doc_size_stage_rect';
|
||||
export const PREVIEW_DOCUMENT_SIZE_DOCUMENT_RECT = 'preview_layer.doc_size_doc_rect';
|
||||
|
||||
// Names for Konva layers and objects (comparable to CSS classes)
|
||||
export const LAYER_BBOX_NAME = 'layer.bbox';
|
||||
|
@ -60,6 +60,7 @@ import type {
|
||||
RasterLayer,
|
||||
RegionalGuidanceLayer,
|
||||
RgbaColor,
|
||||
StageAttrs,
|
||||
Tool,
|
||||
} from './types';
|
||||
import {
|
||||
@ -997,8 +998,13 @@ export const $lastCursorPos = atom<Vector2d | null>(null);
|
||||
export const $isPreviewVisible = atom(true);
|
||||
export const $lastAddedPoint = atom<Vector2d | null>(null);
|
||||
export const $isSpaceDown = atom(false);
|
||||
export const $stageScale = atom<number>(1);
|
||||
export const $stagePos = atom<Vector2d>({ x: 0, y: 0 });
|
||||
export const $stageAttrs = atom<StageAttrs>({
|
||||
x: 0,
|
||||
y: 0,
|
||||
width: 0,
|
||||
height: 0,
|
||||
scale: 0,
|
||||
});
|
||||
|
||||
// Some nanostores that are manually synced to redux state to provide imperative access
|
||||
// TODO(psyche): This is a hack, figure out another way to handle this...
|
||||
|
@ -272,6 +272,7 @@ export type ControlLayersState = {
|
||||
bbox: IRect;
|
||||
};
|
||||
|
||||
export type StageAttrs = { x: number; y: number; width: number; height: number; scale: number };
|
||||
export type AddEraserLineArg = { layerId: string; points: [number, number, number, number] };
|
||||
export type AddBrushLineArg = AddEraserLineArg & { color: RgbaColor };
|
||||
export type AddPointToLineArg = { layerId: string; point: [number, number] };
|
||||
|
Loading…
Reference in New Issue
Block a user