162 lines
No EOL
6.4 KiB
JavaScript
162 lines
No EOL
6.4 KiB
JavaScript
import ActiveObjectContext from '@/components/Context/activeObject/ObjectContext';
|
|
import CanvasContext from '@/components/Context/canvasContext/CanvasContext';
|
|
import { Card, CardContent } from '@/components/ui/card';
|
|
import { Input } from '@/components/ui/input';
|
|
import { Label } from '@/components/ui/label';
|
|
import { Slider } from '@/components/ui/slider';
|
|
import { useContext, useEffect, useState } from 'react';
|
|
import { ArrowUp, ArrowDown, ArrowLeft, ArrowRight, ChevronUp, ChevronDown } from 'lucide-react';
|
|
import { Button } from '@/components/ui/button';
|
|
import { Collapsible, CollapsibleContent, CollapsibleTrigger } from '@/components/ui/collapsible';
|
|
import CollapsibleComponent from './CollapsibleComponent';
|
|
|
|
const PositionCustomization = () => {
|
|
const { canvas } = useContext(CanvasContext)
|
|
const { activeObject } = useContext(ActiveObjectContext)
|
|
|
|
const [objectPosition, setObjectPosition] = useState({ left: 50, top: 50 })
|
|
|
|
const [isOpen, setIsOpen] = useState(true);
|
|
|
|
useEffect(() => {
|
|
if (activeObject) {
|
|
setObjectPosition({
|
|
left: Math.round(activeObject.left || 0),
|
|
top: Math.round(activeObject.top || 0),
|
|
})
|
|
}
|
|
}, [activeObject])
|
|
|
|
const updateObjectPosition = (key, value) => {
|
|
const updatedPosition = { ...objectPosition, [key]: value }
|
|
setObjectPosition(updatedPosition)
|
|
|
|
if (canvas && activeObject) {
|
|
activeObject.set(updatedPosition)
|
|
canvas.renderAll()
|
|
}
|
|
}
|
|
|
|
const handleInputChange = (key, value) => {
|
|
const numValue = parseInt(value, 10)
|
|
if (!isNaN(numValue)) {
|
|
updateObjectPosition(key, numValue)
|
|
}
|
|
}
|
|
|
|
const handleSliderChange = (key, value) => {
|
|
updateObjectPosition(key, value[0])
|
|
}
|
|
|
|
const adjustPosition = (key, delta) => {
|
|
const newValue = objectPosition[key] + delta
|
|
updateObjectPosition(key, newValue)
|
|
}
|
|
|
|
const content = () => {
|
|
return (
|
|
<CardContent className="space-y-6 p-0">
|
|
<div className="space-y-4">
|
|
<div className="space-y-1">
|
|
<Label htmlFor="position-left">Left</Label>
|
|
<div className="flex items-center space-x-2">
|
|
<Input
|
|
id="position-left"
|
|
type="number"
|
|
value={objectPosition.left}
|
|
onChange={(e) => handleInputChange('left', e.target.value)}
|
|
className="w-20"
|
|
/>
|
|
<Slider
|
|
min={0}
|
|
max={canvas ? canvas.width : 1000}
|
|
step={1}
|
|
value={[objectPosition.left]}
|
|
onValueChange={(value) => handleSliderChange('left', value)}
|
|
className="flex-grow"
|
|
/>
|
|
</div>
|
|
</div>
|
|
<div className="space-y-1">
|
|
<Label htmlFor="position-top">Top</Label>
|
|
<div className="flex items-center space-x-2">
|
|
<Input
|
|
id="position-top"
|
|
type="number"
|
|
value={objectPosition.top}
|
|
onChange={(e) => handleInputChange('top', e.target.value)}
|
|
className="w-20"
|
|
/>
|
|
<Slider
|
|
min={0}
|
|
max={canvas ? canvas.height : 1000}
|
|
step={1}
|
|
value={[objectPosition.top]}
|
|
onValueChange={(value) => handleSliderChange('top', value)}
|
|
className="flex-grow"
|
|
/>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<div className="w-32 h-32 grid grid-cols-3 gap-1 p-2 mx-auto">
|
|
<div className="col-start-2">
|
|
<Button
|
|
onClick={() => adjustPosition('top', -1)}
|
|
aria-label="Move up"
|
|
variant="outline"
|
|
size="icon"
|
|
className="w-full h-full"
|
|
>
|
|
<ArrowUp className="w-4 h-4" />
|
|
</Button>
|
|
</div>
|
|
<div className="col-start-1 row-start-2">
|
|
<Button
|
|
onClick={() => adjustPosition('left', -1)}
|
|
aria-label="Move left"
|
|
variant="outline"
|
|
size="icon"
|
|
className="w-full h-full"
|
|
>
|
|
<ArrowLeft className="w-4 h-4" />
|
|
</Button>
|
|
</div>
|
|
<div className="col-start-3 row-start-2">
|
|
<Button
|
|
onClick={() => adjustPosition('left', 1)}
|
|
aria-label="Move right"
|
|
variant="outline"
|
|
size="icon"
|
|
className="w-full h-full"
|
|
>
|
|
<ArrowRight className="w-4 h-4" />
|
|
</Button>
|
|
</div>
|
|
<div className="col-start-2 row-start-3">
|
|
<Button
|
|
onClick={() => adjustPosition('top', 1)}
|
|
aria-label="Move down"
|
|
variant="outline"
|
|
size="icon"
|
|
className="w-full h-full"
|
|
>
|
|
<ArrowDown className="w-4 h-4" />
|
|
</Button>
|
|
</div>
|
|
</div>
|
|
|
|
</CardContent>
|
|
)
|
|
}
|
|
|
|
return (
|
|
<Card className="p-2">
|
|
<CollapsibleComponent text={"Position Control"}>
|
|
{content()}
|
|
</CollapsibleComponent>
|
|
</Card>
|
|
)
|
|
}
|
|
|
|
export default PositionCustomization |