Merge pull request '[2316] 방위 표시 16방위화(22.5° 균등) + 북면 판정 ±135° 고정(표시와 분리)' (#946) from dev into dev-deploy
Reviewed-on: #946
This commit is contained in:
commit
8ebb9eeb5c
@ -14,7 +14,7 @@ import {
|
||||
toggleManualSetupModeState,
|
||||
} from '@/store/canvasAtom'
|
||||
|
||||
import { calculateVisibleModuleHeight, getDegreeByChon, polygonToTurfPolygon, rectToPolygon, toFixedWithoutRounding } from '@/util/canvas-util'
|
||||
import { calculateVisibleModuleHeight, getDegreeByChon, getRoofAzimuthDeg, polygonToTurfPolygon, rectToPolygon, toFixedWithoutRounding } from '@/util/canvas-util'
|
||||
import '@/util/fabric-extensions' // fabric 객체들에 getCurrentPoints 메서드 추가
|
||||
import { basicSettingState, roofDisplaySelector } from '@/store/settingAtom'
|
||||
import offsetPolygon, { calculateAngle, cleanSelfIntersectingPolygon, clipOffsetToOriginal, createLinesFromPolygon } from '@/util/qpolygon-utils'
|
||||
@ -422,8 +422,9 @@ export function useModuleBasicSetting(tabNum) {
|
||||
if (canvasSetting.roofSizeSet != '3') {
|
||||
//북면이 있지만
|
||||
if (roof.directionText && roof.directionText.indexOf('北') > -1) {
|
||||
//북쪽일때 해당 서북서, 동북동은 제외한다고 한다
|
||||
if (!(roof.directionText.indexOf('西北西') > -1 || roof.directionText.indexOf('東北東') > -1)) {
|
||||
// [方位16分割 2026-07-02] 표시는 16방위지만 북면 판정은 종전 ±135°로 고정(일본 요청).
|
||||
// 라벨 문자열(西北西/東北東) 제외가 아니라 실제 방위각으로 판정 → 124~134°는 北西/北東로 표시돼도 비북면.
|
||||
if (Math.abs(getRoofAzimuthDeg(roof)) >= 135) {
|
||||
isNorth = true
|
||||
}
|
||||
}
|
||||
@ -478,8 +479,9 @@ export function useModuleBasicSetting(tabNum) {
|
||||
if (canvasSetting.roofSizeSet != '3') {
|
||||
//북면이 있지만
|
||||
if (roof.directionText && roof.directionText.indexOf('北') > -1) {
|
||||
//북쪽일때 해당 서북서, 동북동은 제외한다고 한다
|
||||
if (!(roof.directionText.indexOf('西北西') > -1 || roof.directionText.indexOf('東北東') > -1)) {
|
||||
// [方位16分割 2026-07-02] 표시는 16방위지만 북면 판정은 종전 ±135°로 고정(일본 요청).
|
||||
// 라벨 문자열(西北西/東北東) 제외가 아니라 실제 방위각으로 판정 → 124~134°는 北西/北東로 표시돼도 비북면.
|
||||
if (Math.abs(getRoofAzimuthDeg(roof)) >= 135) {
|
||||
isNorth = true
|
||||
}
|
||||
}
|
||||
|
||||
@ -2,7 +2,7 @@ import { useRecoilValue } from 'recoil'
|
||||
import { canvasState, currentAngleTypeSelector, currentCanvasPlanState } from '@/store/canvasAtom'
|
||||
import { POLYGON_TYPE, TRESTLE_MATERIAL } from '@/common/common'
|
||||
import { moduleSelectionDataState } from '@/store/selectedModuleOptions'
|
||||
import { getDegreeByChon } from '@/util/canvas-util'
|
||||
import { getDegreeByChon, getRoofAzimuthDeg } from '@/util/canvas-util'
|
||||
import { v4 as uuidv4 } from 'uuid'
|
||||
import { useMasterController } from '@/hooks/common/useMasterController'
|
||||
import { basicSettingState, trestleDisplaySelector } from '@/store/settingAtom'
|
||||
@ -926,8 +926,9 @@ export const useTrestle = () => {
|
||||
surfaces.forEach((surface) => {
|
||||
const parent = canvas.getObjects().find((obj) => obj.id === surface.parentId)
|
||||
const directionText = parent.directionText
|
||||
// ['西北西','東北東'] 의 경우를 제외하고는 北이 들어간 경우 전부 북면으로 간주
|
||||
if (directionText.includes('北') && !directionText.includes('西北西') && !directionText.includes('東北東')) {
|
||||
// [方位16分割 2026-07-02] 표시는 16방위지만 북면 판정은 종전 ±135°로 고정(일본 요청).
|
||||
// 라벨 문자열(西北西/東北東) 제외가 아니라 실제 방위각으로 판정 → 124~134°는 北西/北東로 표시돼도 비북면.
|
||||
if (directionText && directionText.includes('北') && Math.abs(getRoofAzimuthDeg(parent)) >= 135) {
|
||||
if (surface.modules.length > 0) {
|
||||
northArrangement = '1'
|
||||
}
|
||||
|
||||
@ -407,56 +407,21 @@ export const usePolygon = () => {
|
||||
// 각도 -90: 동, 남, 서, 북
|
||||
// 각도 -135: 북동, 남동, 남서, 북서
|
||||
|
||||
let mapping
|
||||
// 정확한 각도 먼저 체크
|
||||
if (normalizedAngle === 0) {
|
||||
mapping = { south: '南', west: '西', north: '北', east: '東' }
|
||||
} else if (normalizedAngle === 45) {
|
||||
mapping = { south: '南西', west: '北西', north: '北東', east: '南東' }
|
||||
} else if (normalizedAngle === 90) {
|
||||
mapping = { south: '西', west: '北', north: '東', east: '南' }
|
||||
} else if (normalizedAngle === 135) {
|
||||
mapping = { south: '北西', west: '北東', north: '南東', east: '南西' }
|
||||
} else if (normalizedAngle === 180 || normalizedAngle === -180) {
|
||||
mapping = { south: '北', west: '東', north: '南', east: '西' }
|
||||
} else if (normalizedAngle === -45) {
|
||||
mapping = { south: '南東', west: '南西', north: '北西', east: '北東' }
|
||||
} else if (normalizedAngle === -90) {
|
||||
mapping = { south: '東', west: '南', north: '西', east: '北' }
|
||||
} else if (normalizedAngle === -135) {
|
||||
mapping = { south: '北東', west: '南東', north: '南西', east: '北西' }
|
||||
}
|
||||
// 범위 각도 체크
|
||||
else if (normalizedAngle >= 1 && normalizedAngle <= 44) {
|
||||
// 1~44: 남남서, 서북서, 북북동, 동남동
|
||||
mapping = { south: '南南西', west: '西北西', north: '北北東', east: '東南東' }
|
||||
} else if (normalizedAngle >= 46 && normalizedAngle <= 89) {
|
||||
// 46~89: 서남서, 북북서, 동북동, 남남동
|
||||
mapping = { south: '西南西', west: '北北西', north: '東北東', east: '南南東' }
|
||||
} else if (normalizedAngle >= 91 && normalizedAngle <= 134) {
|
||||
// 91~134: 서북서, 북북동, 동남동, 남남서
|
||||
mapping = { south: '西北西', west: '北北東', north: '東南東', east: '南南西' }
|
||||
} else if (normalizedAngle >= 136 && normalizedAngle <= 179) {
|
||||
// 136~179: 북북서, 동북동, 남남동, 서남서
|
||||
mapping = { south: '北北西', west: '東北東', north: '南南東', east: '西南西' }
|
||||
} else if (normalizedAngle >= -44 && normalizedAngle <= -1) {
|
||||
// -1~-44: 남남동, 서남서, 북북서, 동북동
|
||||
mapping = { south: '南南東', west: '西南西', north: '北北西', east: '東北東' }
|
||||
} else if (normalizedAngle >= -89 && normalizedAngle <= -46) {
|
||||
// -46~-89: 동남동, 남남서, 서북서, 북북동
|
||||
mapping = { south: '東南東', west: '南南西', north: '西北西', east: '北北東' }
|
||||
} else if (normalizedAngle >= -134 && normalizedAngle <= -91) {
|
||||
// -91~-134: 동북동, 남남동, 서남서, 북북서
|
||||
mapping = { south: '東北東', west: '南南東', north: '西南西', east: '北北西' }
|
||||
} else if (normalizedAngle >= -179 && normalizedAngle <= -136) {
|
||||
// -136~-179: 북북동, 동남동, 남남서, 서북서
|
||||
mapping = { south: '北北東', west: '東南東', north: '南南西', east: '西北西' }
|
||||
} else {
|
||||
// 기본값: 0도
|
||||
mapping = { south: '南', west: '西', north: '北', east: '東' }
|
||||
// [方位16分割 2026-07-02] 표준 16방위(22.5° 균등, 정수 각도 기준)로 표시.
|
||||
// 양수 각도: 남→남남서→남서→…→북 / 음수 각도: 남→남남동→남동→…→북
|
||||
const positive = ['南', '南南西', '南西', '西南西', '西', '西北西', '北西', '北北西', '北']
|
||||
const negative = ['南', '南南東', '南東', '東南東', '東', '東北東', '北東', '北北東', '北']
|
||||
const to16 = (deg) => {
|
||||
let a = Math.round(deg) // 티켓: 정수 각도 기준 (소수 입력은 반올림)
|
||||
while (a > 180) a -= 360
|
||||
while (a < -180) a += 360
|
||||
const i = Math.round(a / 22.5) // -8 ~ 8
|
||||
return i >= 0 ? positive[i] : negative[-i]
|
||||
}
|
||||
|
||||
return mapping[dir] || '南'
|
||||
// direction(지붕면 흐름): 남(0) 기준 90° 회전 — 서 +90, 북 +180, 동 -90
|
||||
const offset = { south: 0, west: 90, north: 180, east: -90 }
|
||||
return to16(normalizedAngle + (offset[dir] ?? 0))
|
||||
}
|
||||
|
||||
text = getDirectionText(moduleCompass, direction)
|
||||
|
||||
@ -272,6 +272,24 @@ export const getChonByDegree = (degree) => {
|
||||
return Number((Math.tan((degree * Math.PI) / 180) * 10).toFixed(2))
|
||||
}
|
||||
|
||||
// [方位16分割 2026-07-02] 지붕면의 실제 방위각(南=0, +=서쪽, -180~180)을 저장 데이터에서 계산.
|
||||
// 북면 판정을 라벨(directionText) 대신 각도로 하기 위함 — 16방위 표시로 라벨이 바뀌어도
|
||||
// 북면 판정 경계는 종전 ±135°로 고정(일본 요청). moduleCompass/surfaceCompass 두 경로 모두 커버.
|
||||
const AZIMUTH_DIR_OFFSET = { south: 0, west: 90, north: 180, east: -90 }
|
||||
export const getRoofAzimuthDeg = (roof) => {
|
||||
const normalize = (deg) => {
|
||||
let a = Number(deg)
|
||||
while (a > 180) a -= 360
|
||||
while (a < -180) a += 360
|
||||
return a
|
||||
}
|
||||
// surfaceCompass(면별 유수방향)가 있으면 그 값이 곧 면의 방위각
|
||||
if (roof?.surfaceCompass !== null && roof?.surfaceCompass !== undefined) {
|
||||
return normalize(roof.surfaceCompass)
|
||||
}
|
||||
return normalize(Number(roof?.moduleCompass ?? 0) + (AZIMUTH_DIR_OFFSET[roof?.direction] ?? 0))
|
||||
}
|
||||
|
||||
/**
|
||||
* 두 점 사이의 방향을 반환합니다.
|
||||
* @param a {fabric.Object}
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user