QLine 그룹화
This commit is contained in:
parent
ee88a3e47e
commit
864e892a7d
@ -2,7 +2,6 @@ import { useCanvas } from '@/hooks/useCanvas'
|
|||||||
import { useEffect, useState } from 'react'
|
import { useEffect, useState } from 'react'
|
||||||
import { Mode, useMode } from '@/hooks/useMode'
|
import { Mode, useMode } from '@/hooks/useMode'
|
||||||
import QRect from '@/components/fabric/QRect'
|
import QRect from '@/components/fabric/QRect'
|
||||||
import QLine from '@/components/fabric/QLine'
|
|
||||||
import QPolygon from '@/components/fabric/QPolygon'
|
import QPolygon from '@/components/fabric/QPolygon'
|
||||||
|
|
||||||
import RangeSlider from './ui/RangeSlider'
|
import RangeSlider from './ui/RangeSlider'
|
||||||
@ -12,6 +11,7 @@ import {
|
|||||||
fontSizeState,
|
fontSizeState,
|
||||||
sortedPolygonArray,
|
sortedPolygonArray,
|
||||||
} from '@/store/canvasAtom'
|
} from '@/store/canvasAtom'
|
||||||
|
import { QLine } from '@/components/fabric/QLine'
|
||||||
|
|
||||||
export default function Roof2() {
|
export default function Roof2() {
|
||||||
const {
|
const {
|
||||||
@ -165,6 +165,18 @@ export default function Roof2() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const makeQLine = () => {
|
||||||
|
if (canvas) {
|
||||||
|
const line = new QLine([50, 50, 200, 50], {
|
||||||
|
stroke: 'black',
|
||||||
|
strokeWidth: 2,
|
||||||
|
fontSize: fontSize,
|
||||||
|
})
|
||||||
|
|
||||||
|
canvas?.add(line)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
{canvas && (
|
{canvas && (
|
||||||
@ -303,6 +315,12 @@ export default function Roof2() {
|
|||||||
>
|
>
|
||||||
회전
|
회전
|
||||||
</button>
|
</button>
|
||||||
|
<button
|
||||||
|
className="w-30 m-2 p-2 rounded bg-gray-500 text-white"
|
||||||
|
onClick={makeQLine}
|
||||||
|
>
|
||||||
|
QLine
|
||||||
|
</button>
|
||||||
</div>
|
</div>
|
||||||
<div className="flex justify-center flex-col items-center">
|
<div className="flex justify-center flex-col items-center">
|
||||||
<div className="m-2 p-2 w-80">
|
<div className="m-2 p-2 w-80">
|
||||||
|
|||||||
@ -1,27 +1,39 @@
|
|||||||
import { fabric } from 'fabric'
|
import { fabric } from 'fabric'
|
||||||
|
|
||||||
export default class QLine extends fabric.Line {
|
export class QLine extends fabric.Group {
|
||||||
|
line
|
||||||
|
text
|
||||||
|
fontSize
|
||||||
length
|
length
|
||||||
#text
|
x1
|
||||||
#viewLengthText
|
y1
|
||||||
#fontSize
|
x2
|
||||||
|
y2
|
||||||
|
direction
|
||||||
type = 'QLine'
|
type = 'QLine'
|
||||||
|
|
||||||
constructor(points, option) {
|
constructor(points, option) {
|
||||||
|
const [x1, y1, x2, y2] = points
|
||||||
|
|
||||||
if (!option.fontSize) {
|
if (!option.fontSize) {
|
||||||
throw new Error('Font size is required.')
|
throw new Error('Font size is required.')
|
||||||
}
|
}
|
||||||
super(points, option)
|
const line = new fabric.Line(points, { ...option, strokeWidth: 1 })
|
||||||
this.#fontSize = option.fontSize
|
super([line], {})
|
||||||
this.#init(option)
|
|
||||||
|
this.x1 = x1
|
||||||
|
this.y1 = y1
|
||||||
|
this.x2 = x2
|
||||||
|
this.y2 = y2
|
||||||
|
this.line = line
|
||||||
|
this.fontSize = option.fontSize
|
||||||
|
this.direction = option.direction
|
||||||
|
this.#init()
|
||||||
this.#addControl()
|
this.#addControl()
|
||||||
}
|
}
|
||||||
|
|
||||||
#init(option) {
|
#init() {
|
||||||
// 선의 길이를 계산하여 length 속성을 초기화합니다.
|
this.#addLengthText()
|
||||||
const dx = this.x2 - this.x1
|
|
||||||
const dy = this.y2 - this.y1
|
|
||||||
this.length = Number(Math.sqrt(dx * dx + dy * dy).toFixed(0))
|
|
||||||
this.#viewLengthText = option.viewLengthText ?? true
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#addControl() {
|
#addControl() {
|
||||||
@ -34,52 +46,46 @@ export default class QLine extends fabric.Line {
|
|||||||
})
|
})
|
||||||
|
|
||||||
this.on('modified', (e) => {
|
this.on('modified', (e) => {
|
||||||
const scaleX = this.scaleX
|
|
||||||
const scaleY = this.scaleY
|
|
||||||
|
|
||||||
// x1, y1, x2, y2 속성을 새로운 좌표로 설정합니다.
|
|
||||||
this.x1 = this.left
|
|
||||||
this.y1 = this.top
|
|
||||||
this.x2 = this.left + this.width * scaleX
|
|
||||||
this.y2 = this.top + this.height * scaleY
|
|
||||||
|
|
||||||
const dx = this.x2 - this.x1
|
|
||||||
const dy = this.y2 - this.y1
|
|
||||||
const length = Math.sqrt(dx * dx + dy * dy)
|
|
||||||
this.length = Number(length.toFixed(0)) // 선의 길이를 length 속성에 저장합니다.
|
|
||||||
this.#addLengthText()
|
this.#addLengthText()
|
||||||
})
|
})
|
||||||
|
|
||||||
this.on('removed', () => {
|
this.on('selected', () => {
|
||||||
this.canvas.remove(this.#text)
|
Object.keys(this.controls).forEach((controlKey) => {
|
||||||
this.#text = null
|
if (controlKey !== 'ml' && controlKey !== 'mr') {
|
||||||
|
this.setControlVisible(controlKey, false)
|
||||||
|
}
|
||||||
|
})
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
setViewLengthText(bool) {
|
#addLengthText() {
|
||||||
this.#viewLengthText = bool
|
if (this.text) {
|
||||||
this.#addLengthText()
|
this.removeWithUpdate(this.text)
|
||||||
|
this.text = null
|
||||||
|
}
|
||||||
|
|
||||||
|
const scaleX = this.scaleX
|
||||||
|
const scaleY = this.scaleY
|
||||||
|
const x1 = this.left
|
||||||
|
const y1 = this.top
|
||||||
|
const x2 = this.left + this.width * scaleX
|
||||||
|
const y2 = this.top + this.height * scaleY
|
||||||
|
const dx = x2 - x1
|
||||||
|
const dy = y2 - y1
|
||||||
|
this.length = Number(Math.sqrt(dx * dx + dy * dy).toFixed(0))
|
||||||
|
|
||||||
|
const text = new fabric.Textbox(this.length.toString(), {
|
||||||
|
left: (x1 + x2) / 2,
|
||||||
|
top: (y1 + y2) / 2,
|
||||||
|
fontSize: this.fontSize,
|
||||||
|
})
|
||||||
|
this.text = text
|
||||||
|
this.addWithUpdate(text)
|
||||||
}
|
}
|
||||||
|
|
||||||
setFontSize(fontSize) {
|
setFontSize(fontSize) {
|
||||||
this.#fontSize = fontSize
|
this.fontSize = fontSize
|
||||||
this.#addLengthText()
|
this.text.set({ fontSize })
|
||||||
}
|
this.addWithUpdate()
|
||||||
|
|
||||||
#addLengthText() {
|
|
||||||
if (this.#text) {
|
|
||||||
this.canvas.remove(this.#text)
|
|
||||||
}
|
|
||||||
|
|
||||||
if (this.#viewLengthText) {
|
|
||||||
const text = new fabric.Text(this.length.toString(), {
|
|
||||||
left: (this.x1 + this.x2) / 2,
|
|
||||||
top: (this.y1 + this.y2) / 2,
|
|
||||||
fontSize: this.#fontSize,
|
|
||||||
selectable: false,
|
|
||||||
})
|
|
||||||
this.#text = text
|
|
||||||
this.canvas.add(text)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -1,5 +1,4 @@
|
|||||||
import { useEffect, useRef, useState } from 'react'
|
import { useEffect, useRef, useState } from 'react'
|
||||||
import QLine from '@/components/fabric/QLine'
|
|
||||||
import QRect from '@/components/fabric/QRect'
|
import QRect from '@/components/fabric/QRect'
|
||||||
import QPolygon from '@/components/fabric/QPolygon'
|
import QPolygon from '@/components/fabric/QPolygon'
|
||||||
import {
|
import {
|
||||||
@ -9,6 +8,7 @@ import {
|
|||||||
} from '@/util/canvas-util'
|
} from '@/util/canvas-util'
|
||||||
import { useRecoilState } from 'recoil'
|
import { useRecoilState } from 'recoil'
|
||||||
import { fontSizeState, sortedPolygonArray } from '@/store/canvasAtom'
|
import { fontSizeState, sortedPolygonArray } from '@/store/canvasAtom'
|
||||||
|
import { QLine } from '@/components/fabric/QLine'
|
||||||
|
|
||||||
export const Mode = {
|
export const Mode = {
|
||||||
DRAW_LINE: 'drawLine', // 기준선 긋기모드
|
DRAW_LINE: 'drawLine', // 기준선 긋기모드
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user