UNPKG

@playcanvas/react

Version:

A React renderer for PlayCanvas – build interactive 3D applications using React's declarative paradigm.

49 lines 2.24 kB
"use client"; import { jsx as _jsx } from "react/jsx-runtime"; import { BoundingBox, Vec3, Mat4 } from "playcanvas"; import { Children, useLayoutEffect, useRef, useState } from "react"; import { Entity } from "../Entity.js"; import { useApp, useParent } from "../hooks/index.js"; export const Align = (props) => { const { left, right, top, bottom, front, back, children } = props; const containerRef = useRef(null); const boundsRef = useRef(new BoundingBox(new Vec3(), new Vec3())); const [, setBounds] = useState(null); const app = useApp(); const parent = useParent(); // all children should be part of the scene hierarchy now useLayoutEffect(() => { if (!app) return; const entity = containerRef.current; const bounds = boundsRef.current; if (!entity) return; bounds.center.set(0, 0, 0); bounds.halfExtents.set(0.0, 0.0, 0.0); const tmpAABB = new BoundingBox(); const invWorldTransform = new Mat4(); const renderComponents = entity.findComponents("render"); // Compute the bounds of all render components const updatedBounds = renderComponents.reduce((bounds, component) => { const meshInstances = component.meshInstances; meshInstances.forEach((mi) => { invWorldTransform.copy(mi.node.getWorldTransform()).invert(); tmpAABB.setFromTransformedAabb(mi.aabb, invWorldTransform); bounds.add(mi.aabb); }); return bounds; }, bounds); boundsRef.current = updatedBounds; setBounds(updatedBounds); }, [app, parent, Children.count(children)]); const { center, halfExtents } = boundsRef.current; // Align based on bounds and alignment flags const position = [ left ? -center.x + halfExtents.x : right ? -center.x - halfExtents.x : -center.x, bottom ? -center.y + halfExtents.y : top ? -center.y - halfExtents.y : -center.y, front ? -center.z + halfExtents.z : back ? -center.z - halfExtents.z : -center.z, ]; return (_jsx(Entity, { ref: containerRef, position: position, children: children })); }; //# sourceMappingURL=Align.js.map