@liiift-studio/mac-os9-ui 0.2.24 → 0.2.26
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.cjs +106 -11
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.ts +26 -0
- package/dist/index.js +106 -11
- package/dist/index.js.map +1 -1
- package/dist/types/components/Window/Window.d.ts +26 -0
- package/package.json +1 -1
package/dist/index.cjs
CHANGED
|
@@ -818,14 +818,24 @@ var styles$6 = {"window":"Window-module_window","window--active":"Window-module_
|
|
|
818
818
|
* </Window>
|
|
819
819
|
* ```
|
|
820
820
|
*/
|
|
821
|
-
const Window = React.forwardRef(({ children, title, titleBar, active = true, width = 'auto', height = 'auto', className = '', contentClassName = '', classes, showControls = true, onClose, onMinimize, onMaximize, onMouseEnter, resizable = false, draggable = false, defaultPosition, position: controlledPosition, onPositionChange, }, ref) => {
|
|
821
|
+
const Window = React.forwardRef(({ children, title, titleBar, active = true, width = 'auto', height = 'auto', className = '', contentClassName = '', classes, showControls = true, onClose, onMinimize, onMaximize, onMouseEnter, resizable = false, minWidth = 200, minHeight = 100, maxWidth, maxHeight, onResize, draggable = false, defaultPosition, position: controlledPosition, onPositionChange, }, ref) => {
|
|
822
822
|
// Drag state management
|
|
823
823
|
const [internalPosition, setInternalPosition] = React.useState(defaultPosition || null);
|
|
824
824
|
const [isDragging, setIsDragging] = React.useState(false);
|
|
825
825
|
const [hasBeenDragged, setHasBeenDragged] = React.useState(!!(defaultPosition || controlledPosition));
|
|
826
826
|
const dragStartRef = React.useRef(null);
|
|
827
|
+
// Resize state management
|
|
828
|
+
const [internalSize, setInternalSize] = React.useState({
|
|
829
|
+
width,
|
|
830
|
+
height,
|
|
831
|
+
});
|
|
832
|
+
const [isResizing, setIsResizing] = React.useState(false);
|
|
833
|
+
const resizeStartRef = React.useRef(null);
|
|
827
834
|
// Use controlled position if provided, otherwise use internal state
|
|
828
835
|
const currentPosition = controlledPosition || internalPosition;
|
|
836
|
+
// Use internal size state for resize tracking
|
|
837
|
+
const currentWidth = isResizing ? internalSize.width : width;
|
|
838
|
+
const currentHeight = isResizing ? internalSize.height : height;
|
|
829
839
|
// Handle mouse down on title bar to start dragging
|
|
830
840
|
const handleTitleBarMouseDown = React.useCallback((event) => {
|
|
831
841
|
if (!draggable)
|
|
@@ -839,13 +849,80 @@ const Window = React.forwardRef(({ children, title, titleBar, active = true, wid
|
|
|
839
849
|
if (!windowElement)
|
|
840
850
|
return;
|
|
841
851
|
const rect = windowElement.getBoundingClientRect();
|
|
842
|
-
//
|
|
852
|
+
// Get the parent container to calculate position relative to it
|
|
853
|
+
const parent = windowElement.offsetParent;
|
|
854
|
+
const parentRect = parent ? parent.getBoundingClientRect() : { left: 0, top: 0 };
|
|
855
|
+
// Store drag start info - offset from mouse to window position within parent
|
|
856
|
+
// This accounts for the parent's coordinate system
|
|
843
857
|
dragStartRef.current = {
|
|
844
|
-
x: event.clientX - rect.left,
|
|
845
|
-
y: event.clientY - rect.top,
|
|
858
|
+
x: event.clientX - (rect.left - parentRect.left),
|
|
859
|
+
y: event.clientY - (rect.top - parentRect.top),
|
|
846
860
|
};
|
|
847
861
|
setIsDragging(true);
|
|
848
862
|
}, [draggable]);
|
|
863
|
+
// Handle mouse down on resize handle to start resizing
|
|
864
|
+
const handleResizeMouseDown = React.useCallback((event) => {
|
|
865
|
+
if (!resizable)
|
|
866
|
+
return;
|
|
867
|
+
event.preventDefault();
|
|
868
|
+
event.stopPropagation();
|
|
869
|
+
const windowElement = event.currentTarget.closest(`.${styles$6.window}`);
|
|
870
|
+
if (!windowElement)
|
|
871
|
+
return;
|
|
872
|
+
const rect = windowElement.getBoundingClientRect();
|
|
873
|
+
// Store resize start info
|
|
874
|
+
resizeStartRef.current = {
|
|
875
|
+
width: rect.width,
|
|
876
|
+
height: rect.height,
|
|
877
|
+
mouseX: event.clientX,
|
|
878
|
+
mouseY: event.clientY,
|
|
879
|
+
};
|
|
880
|
+
setIsResizing(true);
|
|
881
|
+
}, [resizable]);
|
|
882
|
+
// Handle mouse move during resize
|
|
883
|
+
React.useEffect(() => {
|
|
884
|
+
if (!isResizing || !resizeStartRef.current)
|
|
885
|
+
return;
|
|
886
|
+
const handleMouseMove = (event) => {
|
|
887
|
+
event.preventDefault();
|
|
888
|
+
if (!resizeStartRef.current)
|
|
889
|
+
return;
|
|
890
|
+
// Calculate delta
|
|
891
|
+
const deltaX = event.clientX - resizeStartRef.current.mouseX;
|
|
892
|
+
const deltaY = event.clientY - resizeStartRef.current.mouseY;
|
|
893
|
+
// Calculate new size
|
|
894
|
+
let newWidth = resizeStartRef.current.width + deltaX;
|
|
895
|
+
let newHeight = resizeStartRef.current.height + deltaY;
|
|
896
|
+
// Apply constraints
|
|
897
|
+
if (newWidth < minWidth)
|
|
898
|
+
newWidth = minWidth;
|
|
899
|
+
if (newHeight < minHeight)
|
|
900
|
+
newHeight = minHeight;
|
|
901
|
+
if (maxWidth && newWidth > maxWidth)
|
|
902
|
+
newWidth = maxWidth;
|
|
903
|
+
if (maxHeight && newHeight > maxHeight)
|
|
904
|
+
newHeight = maxHeight;
|
|
905
|
+
// Update size
|
|
906
|
+
setInternalSize({
|
|
907
|
+
width: newWidth,
|
|
908
|
+
height: newHeight,
|
|
909
|
+
});
|
|
910
|
+
// Call callback if provided
|
|
911
|
+
if (onResize) {
|
|
912
|
+
onResize({ width: newWidth, height: newHeight });
|
|
913
|
+
}
|
|
914
|
+
};
|
|
915
|
+
const handleMouseUp = () => {
|
|
916
|
+
setIsResizing(false);
|
|
917
|
+
resizeStartRef.current = null;
|
|
918
|
+
};
|
|
919
|
+
document.addEventListener('mousemove', handleMouseMove);
|
|
920
|
+
document.addEventListener('mouseup', handleMouseUp);
|
|
921
|
+
return () => {
|
|
922
|
+
document.removeEventListener('mousemove', handleMouseMove);
|
|
923
|
+
document.removeEventListener('mouseup', handleMouseUp);
|
|
924
|
+
};
|
|
925
|
+
}, [isResizing, minWidth, minHeight, maxWidth, maxHeight, onResize]);
|
|
849
926
|
// Handle mouse move during drag
|
|
850
927
|
React.useEffect(() => {
|
|
851
928
|
if (!isDragging || !dragStartRef.current)
|
|
@@ -854,9 +931,25 @@ const Window = React.forwardRef(({ children, title, titleBar, active = true, wid
|
|
|
854
931
|
event.preventDefault();
|
|
855
932
|
if (!dragStartRef.current)
|
|
856
933
|
return;
|
|
934
|
+
// Get the window element to find its parent
|
|
935
|
+
const windowElements = document.querySelectorAll(`.${styles$6.window}`);
|
|
936
|
+
let windowElement = null;
|
|
937
|
+
// Find the dragging window (the one with position absolute or the first one)
|
|
938
|
+
for (const el of Array.from(windowElements)) {
|
|
939
|
+
const htmlEl = el;
|
|
940
|
+
if (htmlEl.style.position === 'absolute' || windowElements.length === 1) {
|
|
941
|
+
windowElement = htmlEl;
|
|
942
|
+
break;
|
|
943
|
+
}
|
|
944
|
+
}
|
|
945
|
+
if (!windowElement)
|
|
946
|
+
return;
|
|
947
|
+
// Get parent container to calculate position relative to it
|
|
948
|
+
const parent = windowElement.offsetParent;
|
|
949
|
+
const parentRect = parent ? parent.getBoundingClientRect() : { left: 0, top: 0 };
|
|
857
950
|
const newPosition = {
|
|
858
|
-
x: event.clientX - dragStartRef.current.x,
|
|
859
|
-
y: event.clientY - dragStartRef.current.y,
|
|
951
|
+
x: event.clientX - parentRect.left - dragStartRef.current.x,
|
|
952
|
+
y: event.clientY - parentRect.top - dragStartRef.current.y,
|
|
860
953
|
};
|
|
861
954
|
// Update position
|
|
862
955
|
if (controlledPosition && onPositionChange) {
|
|
@@ -887,11 +980,13 @@ const Window = React.forwardRef(({ children, title, titleBar, active = true, wid
|
|
|
887
980
|
const titleBarClassNames = mergeClasses(styles$6.titleBar, draggable && styles$6['titleBar--draggable'], isDragging && styles$6['titleBar--dragging'], classes?.titleBar);
|
|
888
981
|
// Window style
|
|
889
982
|
const windowStyle = {};
|
|
890
|
-
|
|
891
|
-
|
|
983
|
+
// Apply width - use currentWidth during resize, otherwise use prop
|
|
984
|
+
if (currentWidth !== 'auto') {
|
|
985
|
+
windowStyle.width = typeof currentWidth === 'number' ? `${currentWidth}px` : currentWidth;
|
|
892
986
|
}
|
|
893
|
-
|
|
894
|
-
|
|
987
|
+
// Apply height - use currentHeight during resize, otherwise use prop
|
|
988
|
+
if (currentHeight !== 'auto') {
|
|
989
|
+
windowStyle.height = typeof currentHeight === 'number' ? `${currentHeight}px` : currentHeight;
|
|
895
990
|
}
|
|
896
991
|
// Apply position if draggable and has been dragged
|
|
897
992
|
if (draggable && hasBeenDragged && currentPosition) {
|
|
@@ -909,7 +1004,7 @@ const Window = React.forwardRef(({ children, title, titleBar, active = true, wid
|
|
|
909
1004
|
}
|
|
910
1005
|
return null;
|
|
911
1006
|
};
|
|
912
|
-
return (jsxRuntime.jsxs("div", { ref: ref, className: windowClassNames, style: windowStyle, onMouseEnter: onMouseEnter, children: [renderTitleBar(), jsxRuntime.jsx("div", { className: contentClassNames, children: children }), resizable && jsxRuntime.jsx("div", { className: styles$6.resizeHandle, "aria-hidden": "true" })] }));
|
|
1007
|
+
return (jsxRuntime.jsxs("div", { ref: ref, className: windowClassNames, style: windowStyle, onMouseEnter: onMouseEnter, children: [renderTitleBar(), jsxRuntime.jsx("div", { className: contentClassNames, children: children }), resizable && (jsxRuntime.jsx("div", { className: styles$6.resizeHandle, onMouseDown: handleResizeMouseDown, "aria-hidden": "true" }))] }));
|
|
913
1008
|
});
|
|
914
1009
|
Window.displayName = 'Window';
|
|
915
1010
|
|