mirror of
https://github.com/Hestia-Homes/Model.git
synced 2026-06-08 11:17:27 +00:00
delete historic mapping and client
This commit is contained in:
parent
452d7512df
commit
d3ca6bc7ff
12 changed files with 0 additions and 2433 deletions
|
|
@ -1,51 +0,0 @@
|
|||
import requests
|
||||
|
||||
from backend.magic_plan.models import (
|
||||
MagicPlanPlan,
|
||||
MagicPlanSummary,
|
||||
MagicPlanXMLDetail,
|
||||
MagicPlanXMLSummary,
|
||||
)
|
||||
from backend.magic_plan.xml_parser import parse_magicplan_xml
|
||||
|
||||
|
||||
def _parse_xml_summary(data: dict[str, object]) -> MagicPlanXMLSummary:
|
||||
return MagicPlanXMLSummary(
|
||||
id=str(data.get("id", "")),
|
||||
project_id=str(data.get("project_id", "")),
|
||||
name=str(data.get("name", "")),
|
||||
address=str(data.get("address", "")),
|
||||
creation_date=str(data.get("creation_date", "")),
|
||||
update_date=str(data.get("update_date", "")),
|
||||
workgroup_id=str(data.get("workgroup_id", "")),
|
||||
team_id=str(data.get("team_id", "")),
|
||||
created_by=str(data.get("created_by", "")),
|
||||
thumbnail_url=str(data.get("thumbnail_url", "")),
|
||||
public_url=str(data.get("public_url", "")),
|
||||
cloud_url=str(data.get("cloud_url", "")),
|
||||
url_3d=str(data.get("3d_url", "")),
|
||||
)
|
||||
|
||||
|
||||
class MagicPlanClient:
|
||||
BASE_URL = "https://cloud.magicplan.app/api/v2"
|
||||
|
||||
def __init__(self, api_key: str) -> None:
|
||||
self._session = requests.Session()
|
||||
self._session.headers.update({"Authorization": f"Bearer {api_key}"})
|
||||
|
||||
def get_plans(self, _project_id: str) -> list[MagicPlanSummary]:
|
||||
raise NotImplementedError
|
||||
|
||||
def get_plan_xml(self, plan_id: str) -> MagicPlanXMLDetail:
|
||||
resp = self._session.get(f"{self.BASE_URL}/plans/get/{plan_id}")
|
||||
resp.raise_for_status()
|
||||
data: dict[str, object] = resp.json()["data"]
|
||||
plan_data = data["plan"] # type: ignore[index]
|
||||
detail_data = data["plan_detail"] # type: ignore[index]
|
||||
summary = _parse_xml_summary(plan_data) # type: ignore[arg-type]
|
||||
plan_xml = parse_magicplan_xml(detail_data["magicplan_format_xml"]) # type: ignore[index]
|
||||
return MagicPlanXMLDetail(summary=summary, plan_xml=plan_xml)
|
||||
|
||||
def get_plan(self, _plan_id: str) -> MagicPlanPlan:
|
||||
raise NotImplementedError
|
||||
|
|
@ -1,417 +0,0 @@
|
|||
import re
|
||||
from dataclasses import dataclass
|
||||
from typing import Any, Optional
|
||||
|
||||
|
||||
def _camel_to_snake(name: str) -> str:
|
||||
return re.sub(r"(?<!^)(?=[A-Z])", "_", name).lower()
|
||||
|
||||
|
||||
def parse_displayable_fields(fields: list[dict[str, Any]]) -> dict[str, str]:
|
||||
result: dict[str, str] = {}
|
||||
for f in fields:
|
||||
if f.get("type_as_string") == "sectionTitle":
|
||||
continue
|
||||
v: dict[str, Any] = f.get("value") or {}
|
||||
if not v.get("has_value"):
|
||||
continue
|
||||
result[_camel_to_snake(str(f["id"]))] = str(v["value"])
|
||||
return result
|
||||
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# XML dataclasses (sourced from MagicPlan Exchange XML format)
|
||||
# ---------------------------------------------------------------------------
|
||||
|
||||
|
||||
@dataclass
|
||||
class MagicPlanXMLRoomPoint:
|
||||
snapped_x: float
|
||||
snapped_y: float
|
||||
height: float
|
||||
uid: str
|
||||
values: dict[str, str]
|
||||
|
||||
|
||||
@dataclass
|
||||
class MagicPlanXMLWallPoint:
|
||||
"""Point in <exploded><wall> — absolute coords, no uid or values."""
|
||||
|
||||
x: float
|
||||
y: float
|
||||
height: float
|
||||
|
||||
|
||||
@dataclass
|
||||
class MagicPlanXMLDoor:
|
||||
"""Door in <floorRoom> context — wall-relative position."""
|
||||
|
||||
wall_point_index: int
|
||||
type: str
|
||||
u: float
|
||||
width: float
|
||||
depth: float
|
||||
height: float
|
||||
orientation: int
|
||||
snapped_type: str
|
||||
snapped_position: float
|
||||
snapped_width: float
|
||||
snapped_depth: float
|
||||
snapped_height: float
|
||||
snapped_orientation: int
|
||||
inset_x: float
|
||||
inset_y: float
|
||||
inset_z: float
|
||||
symbol_instance: str
|
||||
twin_wall_item_uid: Optional[str] = None
|
||||
|
||||
|
||||
@dataclass
|
||||
class MagicPlanXMLWindow:
|
||||
"""Window in <floorRoom> context — wall-relative position."""
|
||||
|
||||
wall_point_index: int
|
||||
type: str
|
||||
u: float
|
||||
width: float
|
||||
depth: float
|
||||
height: float
|
||||
orientation: int
|
||||
snapped_type: str
|
||||
snapped_position: float
|
||||
snapped_width: float
|
||||
snapped_depth: float
|
||||
snapped_height: float
|
||||
snapped_orientation: int
|
||||
inset_x: float
|
||||
inset_y: float
|
||||
inset_z: float
|
||||
symbol_instance: str
|
||||
|
||||
|
||||
@dataclass
|
||||
class MagicPlanXMLExplodedOpening:
|
||||
"""Door or window in <exploded> context — absolute coords, no snapped* fields."""
|
||||
|
||||
type: str
|
||||
x1: float
|
||||
y1: float
|
||||
x2: float
|
||||
y2: float
|
||||
width: float
|
||||
depth: float
|
||||
height: float
|
||||
inset_x: float
|
||||
inset_y: float
|
||||
orientation: int
|
||||
symbol_instance: str
|
||||
|
||||
|
||||
@dataclass
|
||||
class MagicPlanXMLFurniture:
|
||||
type: str
|
||||
x: float
|
||||
y: float
|
||||
snapped_x: float
|
||||
snapped_y: float
|
||||
angle: float
|
||||
width: float
|
||||
depth: float
|
||||
height: float
|
||||
snapped_width: float
|
||||
snapped_depth: float
|
||||
snapped_height: float
|
||||
size_lock_0: str
|
||||
size_lock_1: str
|
||||
size_lock_2: str
|
||||
symbol_instance: str
|
||||
|
||||
|
||||
@dataclass
|
||||
class MagicPlanXMLMainDimension:
|
||||
from_point: int
|
||||
to_point: int
|
||||
dir_x: float
|
||||
dir_y: float
|
||||
value: float
|
||||
actual_value: float
|
||||
is_set: bool
|
||||
|
||||
|
||||
@dataclass
|
||||
class MagicPlanXMLExplodedWall:
|
||||
wall_type: str
|
||||
points: list[MagicPlanXMLWallPoint]
|
||||
|
||||
|
||||
@dataclass
|
||||
class MagicPlanXMLExploded:
|
||||
walls: list[MagicPlanXMLExplodedWall]
|
||||
doors: list[MagicPlanXMLExplodedOpening]
|
||||
windows: list[MagicPlanXMLExplodedOpening]
|
||||
furniture: list[MagicPlanXMLFurniture]
|
||||
|
||||
|
||||
@dataclass
|
||||
class MagicPlanXMLSymbolInstance:
|
||||
id: str
|
||||
uid: str
|
||||
parent_uid: str
|
||||
symbol: str
|
||||
values: dict[str, str]
|
||||
|
||||
|
||||
@dataclass
|
||||
class MagicPlanXMLRoom:
|
||||
uid: str
|
||||
type: str
|
||||
x: float
|
||||
y: float
|
||||
rotation: float
|
||||
was_modified: bool
|
||||
linked_room_0: str
|
||||
linked_room_1: str
|
||||
area: float
|
||||
perimeter: float
|
||||
values: dict[str, str]
|
||||
points: list[MagicPlanXMLRoomPoint]
|
||||
doors: list[MagicPlanXMLDoor]
|
||||
windows: list[MagicPlanXMLWindow]
|
||||
furniture: list[MagicPlanXMLFurniture]
|
||||
main_dimensions: list[MagicPlanXMLMainDimension]
|
||||
|
||||
|
||||
@dataclass
|
||||
class MagicPlanXMLFloor:
|
||||
uid: str
|
||||
name: str
|
||||
floor_type: str
|
||||
rotation: float
|
||||
compass_angle: float
|
||||
area_without_walls: float
|
||||
area_with_interior_walls_only: float
|
||||
area_with_walls: float
|
||||
symbol_instance: MagicPlanXMLSymbolInstance
|
||||
rooms: list[MagicPlanXMLRoom]
|
||||
furniture: list[MagicPlanXMLFurniture]
|
||||
exploded: MagicPlanXMLExploded
|
||||
|
||||
|
||||
@dataclass
|
||||
class MagicPlanXMLSummary:
|
||||
"""Plan metadata returned by the list-plans API endpoint (old string-address format)."""
|
||||
|
||||
id: str
|
||||
project_id: str
|
||||
name: str
|
||||
address: str
|
||||
creation_date: str
|
||||
update_date: str
|
||||
workgroup_id: str
|
||||
team_id: str
|
||||
created_by: str
|
||||
thumbnail_url: str
|
||||
public_url: str
|
||||
cloud_url: str
|
||||
url_3d: str
|
||||
|
||||
|
||||
@dataclass
|
||||
class MagicPlanXMLDetail:
|
||||
"""Full plan response: summary metadata + parsed XML plan."""
|
||||
|
||||
summary: MagicPlanXMLSummary
|
||||
plan_xml: "MagicPlanXMLPlan"
|
||||
|
||||
|
||||
@dataclass
|
||||
class MagicPlanXMLPlan:
|
||||
id: str
|
||||
uid: str
|
||||
name: str
|
||||
type: str
|
||||
interior_wall_width: float
|
||||
exterior_wall_width: float
|
||||
schematic: bool
|
||||
has_land_survey_address: bool
|
||||
last_patch_identifier: str
|
||||
last_roll_identifier: str
|
||||
values: dict[str, str]
|
||||
floors: list[MagicPlanXMLFloor]
|
||||
interior_room_floors: list[MagicPlanXMLFloor]
|
||||
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# JSON dataclasses (sourced from GET Plan API JSON response)
|
||||
# ---------------------------------------------------------------------------
|
||||
|
||||
|
||||
@dataclass
|
||||
class MagicPlanWall:
|
||||
uid: str
|
||||
symbol_id: str
|
||||
length: float
|
||||
fields: dict[str, str]
|
||||
custom_fields: dict[str, str]
|
||||
|
||||
|
||||
@dataclass
|
||||
class MagicPlanWallItem:
|
||||
"""Door or window — distinguished by symbol_id."""
|
||||
|
||||
uid: str
|
||||
symbol_id: str
|
||||
symbol_name: str
|
||||
width: float
|
||||
depth: float
|
||||
height: float
|
||||
pos_x: float
|
||||
pos_y: float
|
||||
pos_z: float
|
||||
rotation_z: float
|
||||
fields: dict[str, str]
|
||||
custom_fields: dict[str, str]
|
||||
|
||||
|
||||
@dataclass
|
||||
class MagicPlanFurniture:
|
||||
uid: str
|
||||
symbol_id: str
|
||||
symbol_name: str
|
||||
width: float
|
||||
depth: float
|
||||
height: float
|
||||
pos_x: float
|
||||
pos_y: float
|
||||
pos_z: float
|
||||
rotation_z: float
|
||||
fields: dict[str, str]
|
||||
custom_fields: dict[str, str]
|
||||
|
||||
|
||||
@dataclass
|
||||
class MagicPlanRoom:
|
||||
uid: str
|
||||
name: str
|
||||
area: float
|
||||
perimeter: float
|
||||
height: float
|
||||
width: float
|
||||
volume: float
|
||||
dimensions: str
|
||||
door_count: int
|
||||
window_count: int
|
||||
walls_surface: float
|
||||
walls_surface_without_openings: float
|
||||
doors_surface: float
|
||||
windows_surface: float
|
||||
wall_items: list[MagicPlanWallItem]
|
||||
furnitures: list[MagicPlanFurniture]
|
||||
walls: list[MagicPlanWall]
|
||||
fields: dict[str, str]
|
||||
custom_fields: dict[str, str]
|
||||
|
||||
|
||||
@dataclass
|
||||
class MagicPlanFloor:
|
||||
uid: str
|
||||
name: str
|
||||
floor_type: str
|
||||
area: float
|
||||
perimeter: float
|
||||
area_without_walls: float
|
||||
area_with_interior_walls_only: float
|
||||
area_with_walls: float
|
||||
wall_count: int
|
||||
wall_count_with_interior_walls: int
|
||||
door_count: int
|
||||
window_count: int
|
||||
room_count: int
|
||||
furniture_count: int
|
||||
doors_surface: float
|
||||
walls_surface: float
|
||||
walls_surface_without_openings: float
|
||||
windows_surface: float
|
||||
volume: float
|
||||
rooms: list[MagicPlanRoom]
|
||||
furnitures: list[MagicPlanFurniture]
|
||||
symbol_instances: list[MagicPlanFurniture]
|
||||
fields: dict[str, str]
|
||||
custom_fields: dict[str, str]
|
||||
|
||||
|
||||
@dataclass
|
||||
class MagicPlanPlan:
|
||||
"""GET /plans/{id} — merged data.plan + data.plan_detail.plan."""
|
||||
|
||||
id: str
|
||||
project_id: str
|
||||
uid: str
|
||||
name: str
|
||||
area: float
|
||||
perimeter: float
|
||||
area_without_walls: float
|
||||
area_with_interior_walls_only: float
|
||||
area_with_walls: float
|
||||
wall_count: int
|
||||
door_count: int
|
||||
window_count: int
|
||||
room_count: int
|
||||
furniture_count: int
|
||||
floor_count: int
|
||||
doors_surface: float
|
||||
walls_surface: float
|
||||
walls_surface_without_openings: float
|
||||
windows_surface: float
|
||||
volume: float
|
||||
living_area: float
|
||||
below_grade_living_area: float
|
||||
above_grade_living_area: float
|
||||
address_street: Optional[str]
|
||||
address_postal_code: Optional[str]
|
||||
address_city: Optional[str]
|
||||
address_country: Optional[str]
|
||||
address_longitude: Optional[float]
|
||||
address_latitude: Optional[float]
|
||||
creation_date: str
|
||||
update_date: str
|
||||
workgroup_id: str
|
||||
team_id: str
|
||||
created_by_id: str
|
||||
created_by_firstname: Optional[str]
|
||||
created_by_lastname: Optional[str]
|
||||
created_by_email: str
|
||||
thumbnail_url: str
|
||||
public_url: str
|
||||
cloud_url: str
|
||||
url_3d: str
|
||||
floors: list[MagicPlanFloor]
|
||||
fields: dict[str, str]
|
||||
custom_fields: dict[str, str]
|
||||
|
||||
|
||||
@dataclass
|
||||
class MagicPlanSummary:
|
||||
"""GET /plans list — lightweight, flat address and creator fields."""
|
||||
|
||||
id: str
|
||||
project_id: str
|
||||
name: str
|
||||
address_street: Optional[str]
|
||||
address_postal_code: Optional[str]
|
||||
address_city: Optional[str]
|
||||
address_country: Optional[str]
|
||||
address_longitude: Optional[float]
|
||||
address_latitude: Optional[float]
|
||||
creation_date: str
|
||||
update_date: str
|
||||
workgroup_id: str
|
||||
team_id: str
|
||||
created_by_id: str
|
||||
created_by_firstname: Optional[str]
|
||||
created_by_lastname: Optional[str]
|
||||
created_by_email: str
|
||||
thumbnail_url: str
|
||||
public_url: str
|
||||
cloud_url: str
|
||||
url_3d: str
|
||||
|
|
@ -1,195 +0,0 @@
|
|||
import json
|
||||
import xml.etree.ElementTree as ET
|
||||
from pathlib import Path
|
||||
from unittest.mock import MagicMock, patch
|
||||
|
||||
import pytest
|
||||
import requests
|
||||
|
||||
from backend.magic_plan.magic_plan_client import MagicPlanClient
|
||||
from backend.magic_plan.models import MagicPlanXMLDetail, MagicPlanXMLPlan, MagicPlanXMLSummary
|
||||
|
||||
FIXTURES = Path(__file__).parent.parent
|
||||
API_KEY = "test-api-key"
|
||||
PLAN_ID = "b66bb427-33fe-4865-8d57-bad7d9d3f2e5"
|
||||
PROJECT_ID = "test-project-123"
|
||||
BASE_URL = "https://cloud.magicplan.app/api/v2"
|
||||
|
||||
|
||||
def _load_xml() -> str:
|
||||
content = (FIXTURES / "xml_example.xml").read_text().strip()
|
||||
try:
|
||||
ET.fromstring(content)
|
||||
return content
|
||||
except ET.ParseError:
|
||||
return json.loads(content) # type: ignore[return-value]
|
||||
|
||||
|
||||
def _summary_payload(plan_id: str = PLAN_ID, index: int = 0) -> dict[str, str]:
|
||||
return {
|
||||
"id": plan_id,
|
||||
"project_id": PROJECT_ID,
|
||||
"name": f"Plan {index}",
|
||||
"address": f"Address {index}",
|
||||
"creation_date": "2026-04-20",
|
||||
"update_date": "2026-04-20",
|
||||
"workgroup_id": "wg-123",
|
||||
"team_id": "team-123",
|
||||
"created_by": "user-123",
|
||||
"thumbnail_url": "https://example.com/thumb.jpg",
|
||||
"public_url": "https://example.com/plan",
|
||||
"cloud_url": "https://example.com/cloud",
|
||||
"3d_url": "https://example.com/3d",
|
||||
}
|
||||
|
||||
|
||||
def _get_plan_response(xml_str: str) -> dict: # type: ignore[type-arg]
|
||||
return {
|
||||
"message": "success",
|
||||
"data": {
|
||||
"plan": _summary_payload(),
|
||||
"plan_detail": {
|
||||
"magicplan_format_xml": xml_str,
|
||||
},
|
||||
},
|
||||
}
|
||||
|
||||
|
||||
def _get_plans_response(plan_ids: list[str]) -> dict: # type: ignore[type-arg]
|
||||
return {
|
||||
"message": "success",
|
||||
"data": [_summary_payload(pid, i) for i, pid in enumerate(plan_ids)],
|
||||
}
|
||||
|
||||
|
||||
@pytest.fixture
|
||||
def mock_session() -> MagicMock:
|
||||
with patch("backend.magic_plan.magic_plan_client.requests.Session") as MockSession:
|
||||
session: MagicMock = MagicMock()
|
||||
MockSession.return_value = session
|
||||
yield session
|
||||
|
||||
|
||||
@pytest.fixture
|
||||
def client(mock_session: MagicMock) -> MagicPlanClient:
|
||||
return MagicPlanClient(api_key=API_KEY)
|
||||
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# Initialisation
|
||||
# ---------------------------------------------------------------------------
|
||||
|
||||
class TestInit:
|
||||
|
||||
def test_sets_bearer_auth_header(self, mock_session: MagicMock) -> None:
|
||||
MagicPlanClient(api_key=API_KEY)
|
||||
mock_session.headers.update.assert_called_once_with(
|
||||
{"Authorization": f"Bearer {API_KEY}"}
|
||||
)
|
||||
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# get_plan_xml
|
||||
# ---------------------------------------------------------------------------
|
||||
|
||||
class TestGetPlanXml:
|
||||
|
||||
def test_calls_correct_url(self, client: MagicPlanClient, mock_session: MagicMock) -> None:
|
||||
mock_session.get.return_value.json.return_value = _get_plan_response(_load_xml())
|
||||
client.get_plan_xml(PLAN_ID)
|
||||
mock_session.get.assert_called_once_with(f"{BASE_URL}/plans/get/{PLAN_ID}")
|
||||
|
||||
def test_calls_raise_for_status(self, client: MagicPlanClient, mock_session: MagicMock) -> None:
|
||||
mock_session.get.return_value.json.return_value = _get_plan_response(_load_xml())
|
||||
client.get_plan_xml(PLAN_ID)
|
||||
mock_session.get.return_value.raise_for_status.assert_called_once()
|
||||
|
||||
def test_returns_magic_plan_detail(self, client: MagicPlanClient, mock_session: MagicMock) -> None:
|
||||
mock_session.get.return_value.json.return_value = _get_plan_response(_load_xml())
|
||||
result = client.get_plan_xml(PLAN_ID)
|
||||
assert isinstance(result, MagicPlanXMLDetail)
|
||||
|
||||
def test_detail_contains_summary(self, client: MagicPlanClient, mock_session: MagicMock) -> None:
|
||||
mock_session.get.return_value.json.return_value = _get_plan_response(_load_xml())
|
||||
result = client.get_plan_xml(PLAN_ID)
|
||||
assert isinstance(result.summary, MagicPlanXMLSummary)
|
||||
|
||||
def test_detail_summary_id(self, client: MagicPlanClient, mock_session: MagicMock) -> None:
|
||||
mock_session.get.return_value.json.return_value = _get_plan_response(_load_xml())
|
||||
result = client.get_plan_xml(PLAN_ID)
|
||||
assert result.summary.id == PLAN_ID
|
||||
|
||||
def test_detail_summary_project_id(self, client: MagicPlanClient, mock_session: MagicMock) -> None:
|
||||
mock_session.get.return_value.json.return_value = _get_plan_response(_load_xml())
|
||||
result = client.get_plan_xml(PLAN_ID)
|
||||
assert result.summary.project_id == PROJECT_ID
|
||||
|
||||
def test_detail_contains_parsed_plan(self, client: MagicPlanClient, mock_session: MagicMock) -> None:
|
||||
mock_session.get.return_value.json.return_value = _get_plan_response(_load_xml())
|
||||
result = client.get_plan_xml(PLAN_ID)
|
||||
assert isinstance(result.plan_xml, MagicPlanXMLPlan)
|
||||
|
||||
def test_plan_xml_id_matches_xml(self, client: MagicPlanClient, mock_session: MagicMock) -> None:
|
||||
mock_session.get.return_value.json.return_value = _get_plan_response(_load_xml())
|
||||
result = client.get_plan_xml(PLAN_ID)
|
||||
assert result.plan_xml.id == PLAN_ID
|
||||
|
||||
def test_plan_xml_floor_count(self, client: MagicPlanClient, mock_session: MagicMock) -> None:
|
||||
mock_session.get.return_value.json.return_value = _get_plan_response(_load_xml())
|
||||
result = client.get_plan_xml(PLAN_ID)
|
||||
assert len(result.plan_xml.floors) == 2
|
||||
|
||||
def test_raises_on_http_error(self, client: MagicPlanClient, mock_session: MagicMock) -> None:
|
||||
mock_session.get.return_value.raise_for_status.side_effect = requests.HTTPError("404")
|
||||
with pytest.raises(requests.HTTPError):
|
||||
client.get_plan_xml(PLAN_ID)
|
||||
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# get_plans
|
||||
# ---------------------------------------------------------------------------
|
||||
|
||||
class TestGetPlans:
|
||||
|
||||
def test_calls_correct_url(self, client: MagicPlanClient, mock_session: MagicMock) -> None:
|
||||
mock_session.get.return_value.json.return_value = _get_plans_response([])
|
||||
client.get_plans(PROJECT_ID)
|
||||
mock_session.get.assert_called_once_with(
|
||||
f"{BASE_URL}/plans", params={"project_id": PROJECT_ID}
|
||||
)
|
||||
|
||||
def test_calls_raise_for_status(self, client: MagicPlanClient, mock_session: MagicMock) -> None:
|
||||
mock_session.get.return_value.json.return_value = _get_plans_response([])
|
||||
client.get_plans(PROJECT_ID)
|
||||
mock_session.get.return_value.raise_for_status.assert_called_once()
|
||||
|
||||
def test_returns_list_of_summaries(self, client: MagicPlanClient, mock_session: MagicMock) -> None:
|
||||
mock_session.get.return_value.json.return_value = _get_plans_response([PLAN_ID, "other-id"])
|
||||
result = client.get_plans(PROJECT_ID)
|
||||
assert len(result) == 2
|
||||
assert all(isinstance(s, MagicPlanXMLSummary) for s in result)
|
||||
|
||||
def test_summary_id(self, client: MagicPlanClient, mock_session: MagicMock) -> None:
|
||||
mock_session.get.return_value.json.return_value = _get_plans_response([PLAN_ID])
|
||||
result = client.get_plans(PROJECT_ID)
|
||||
assert result[0].id == PLAN_ID
|
||||
|
||||
def test_summary_project_id(self, client: MagicPlanClient, mock_session: MagicMock) -> None:
|
||||
mock_session.get.return_value.json.return_value = _get_plans_response([PLAN_ID])
|
||||
result = client.get_plans(PROJECT_ID)
|
||||
assert result[0].project_id == PROJECT_ID
|
||||
|
||||
def test_summary_name(self, client: MagicPlanClient, mock_session: MagicMock) -> None:
|
||||
mock_session.get.return_value.json.return_value = _get_plans_response([PLAN_ID])
|
||||
result = client.get_plans(PROJECT_ID)
|
||||
assert result[0].name == "Plan 0"
|
||||
|
||||
def test_returns_empty_list_when_no_plans(self, client: MagicPlanClient, mock_session: MagicMock) -> None:
|
||||
mock_session.get.return_value.json.return_value = _get_plans_response([])
|
||||
result = client.get_plans(PROJECT_ID)
|
||||
assert result == []
|
||||
|
||||
def test_raises_on_http_error(self, client: MagicPlanClient, mock_session: MagicMock) -> None:
|
||||
mock_session.get.return_value.raise_for_status.side_effect = requests.HTTPError("401")
|
||||
with pytest.raises(requests.HTTPError):
|
||||
client.get_plans(PROJECT_ID)
|
||||
|
|
@ -1,50 +0,0 @@
|
|||
import pytest
|
||||
|
||||
from backend.magic_plan.models import parse_displayable_fields
|
||||
|
||||
|
||||
SECTION_TITLE_FIELD = {
|
||||
"id": "measures.section.title",
|
||||
"type_as_string": "sectionTitle",
|
||||
"value": {"has_value": False, "value": ""},
|
||||
}
|
||||
|
||||
CEILING_HEIGHT_FIELD = {
|
||||
"id": "ceilingHeight",
|
||||
"type_as_string": "distance",
|
||||
"value": {"has_value": True, "value": "2.45"},
|
||||
}
|
||||
|
||||
NO_VALUE_FIELD = {
|
||||
"id": "label",
|
||||
"type_as_string": "text",
|
||||
"value": {"has_value": False, "value": ""},
|
||||
}
|
||||
|
||||
|
||||
class TestParseDisplayableFields:
|
||||
|
||||
def test_excludes_section_titles(self) -> None:
|
||||
result = parse_displayable_fields([SECTION_TITLE_FIELD])
|
||||
assert result == {}
|
||||
|
||||
def test_excludes_fields_without_value(self) -> None:
|
||||
result = parse_displayable_fields([NO_VALUE_FIELD])
|
||||
assert result == {}
|
||||
|
||||
def test_includes_field_with_value(self) -> None:
|
||||
result = parse_displayable_fields([CEILING_HEIGHT_FIELD])
|
||||
assert "ceiling_height" in result
|
||||
assert result["ceiling_height"] == "2.45"
|
||||
|
||||
def test_snake_cases_camel_key(self) -> None:
|
||||
result = parse_displayable_fields([CEILING_HEIGHT_FIELD])
|
||||
assert "ceiling_height" in result
|
||||
assert "ceilingHeight" not in result
|
||||
|
||||
def test_mixed_fields(self) -> None:
|
||||
result = parse_displayable_fields([SECTION_TITLE_FIELD, CEILING_HEIGHT_FIELD, NO_VALUE_FIELD])
|
||||
assert result == {"ceiling_height": "2.45"}
|
||||
|
||||
def test_empty_list(self) -> None:
|
||||
assert parse_displayable_fields([]) == {}
|
||||
|
|
@ -1,461 +0,0 @@
|
|||
import json
|
||||
import math
|
||||
import xml.etree.ElementTree as ET
|
||||
from pathlib import Path
|
||||
|
||||
import pytest
|
||||
|
||||
from backend.magic_plan.models import MagicPlanXMLPlan
|
||||
from backend.magic_plan.xml_parser import parse_magicplan_xml
|
||||
|
||||
FIXTURES = Path(__file__).parent.parent
|
||||
|
||||
|
||||
def _load(filename: str) -> str:
|
||||
content = (FIXTURES / filename).read_text().strip()
|
||||
try:
|
||||
ET.fromstring(content)
|
||||
return content
|
||||
except ET.ParseError:
|
||||
return json.loads(content) # type: ignore[return-value]
|
||||
|
||||
|
||||
@pytest.fixture(scope="module")
|
||||
def plan1() -> MagicPlanXMLPlan:
|
||||
return parse_magicplan_xml(_load("xml_example.xml"))
|
||||
|
||||
|
||||
@pytest.fixture(scope="module")
|
||||
def plan2() -> MagicPlanXMLPlan:
|
||||
return parse_magicplan_xml(_load("xml_example_2.xml"))
|
||||
|
||||
|
||||
@pytest.fixture(scope="module")
|
||||
def plan3() -> MagicPlanXMLPlan:
|
||||
return parse_magicplan_xml(_load("xml_example_3.xml"))
|
||||
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# Plan-level attributes
|
||||
# ---------------------------------------------------------------------------
|
||||
|
||||
class TestPlanAttributes:
|
||||
|
||||
def test_id(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.id == "b66bb427-33fe-4865-8d57-bad7d9d3f2e5"
|
||||
|
||||
def test_uid(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.uid == "69e5fafc.0890b3ff"
|
||||
|
||||
def test_name(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.name == "275 Carr Hill Rd NE9 5ND"
|
||||
|
||||
def test_type(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.type == "0"
|
||||
|
||||
def test_interior_wall_width(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.interior_wall_width, 0.12)
|
||||
|
||||
def test_exterior_wall_width(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.exterior_wall_width, 0.25)
|
||||
|
||||
def test_schematic_false(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.schematic is False
|
||||
|
||||
def test_has_land_survey_address_false(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.has_land_survey_address is False
|
||||
|
||||
def test_last_patch_identifier(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.last_patch_identifier == "0"
|
||||
|
||||
def test_last_roll_identifier(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.last_roll_identifier == "0"
|
||||
|
||||
|
||||
class TestPlanValues:
|
||||
|
||||
def test_date(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.values["date"] == "2026-04-20"
|
||||
|
||||
def test_statistics_area_of_height(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.values["statistics.areaOfHeight"] == "2.134"
|
||||
|
||||
def test_statistics_basement_account(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.values["statistics.basement.account"] == "100"
|
||||
|
||||
def test_statistics_exterior_walls(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.values["statistics.exteriorWalls"] == "0"
|
||||
|
||||
def test_statistics_interior_walls(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.values["statistics.interiorWalls"] == "0"
|
||||
|
||||
def test_plan2_date(self, plan2: MagicPlanXMLPlan) -> None:
|
||||
assert plan2.values["date"] == "2026-04-16"
|
||||
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# Floors
|
||||
# ---------------------------------------------------------------------------
|
||||
|
||||
class TestFloors:
|
||||
|
||||
def test_floor_count_plan1(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert len(plan1.floors) == 2
|
||||
|
||||
def test_floor_count_plan2(self, plan2: MagicPlanXMLPlan) -> None:
|
||||
assert len(plan2.floors) == 1
|
||||
|
||||
def test_floor_count_plan3(self, plan3: MagicPlanXMLPlan) -> None:
|
||||
assert len(plan3.floors) == 1
|
||||
|
||||
def test_ground_floor_name(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[0].name == "Ground Floor"
|
||||
|
||||
def test_first_floor_name(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[1].name == "1st Floor"
|
||||
|
||||
def test_ground_floor_type(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[0].floor_type == "0"
|
||||
|
||||
def test_upper_floor_type(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[1].floor_type == "1"
|
||||
|
||||
def test_floor_uid(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[0].uid == "69e5fb20.4feef7ff"
|
||||
|
||||
def test_ground_floor_area_without_walls(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.floors[0].area_without_walls, 40.20736)
|
||||
|
||||
def test_ground_floor_area_with_walls(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.floors[0].area_with_walls, 48.40593)
|
||||
|
||||
def test_ground_floor_area_with_interior_walls_only(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.floors[0].area_with_interior_walls_only, 40.67878)
|
||||
|
||||
def test_floor_rotation(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.floors[0].rotation, 0.0, abs_tol=1e-9)
|
||||
|
||||
def test_floor_compass_angle(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.floors[0].compass_angle, -1.0)
|
||||
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# Symbol instance
|
||||
# ---------------------------------------------------------------------------
|
||||
|
||||
class TestSymbolInstance:
|
||||
|
||||
def test_symbol_instance_id(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[0].symbol_instance.id == "floor"
|
||||
|
||||
def test_symbol_instance_uid(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[0].symbol_instance.uid == "69e5fb20.4feef7ff"
|
||||
|
||||
def test_symbol_instance_symbol(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[0].symbol_instance.symbol == "floor"
|
||||
|
||||
def test_symbol_instance_parent_uid(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[0].symbol_instance.parent_uid == ""
|
||||
|
||||
def test_symbol_instance_ceiling_height_value(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[0].symbol_instance.values["ceilingHeight"] == "2.323164"
|
||||
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# Rooms
|
||||
# ---------------------------------------------------------------------------
|
||||
|
||||
class TestRooms:
|
||||
|
||||
def test_ground_floor_room_count(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert len(plan1.floors[0].rooms) == 2
|
||||
|
||||
def test_first_floor_room_count(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert len(plan1.floors[1].rooms) == 4
|
||||
|
||||
def test_plan3_room_count(self, plan3: MagicPlanXMLPlan) -> None:
|
||||
assert len(plan3.floors[0].rooms) == 9
|
||||
|
||||
def test_room_type(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[0].rooms[0].type == "Kitchen"
|
||||
|
||||
def test_room_uid(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[0].rooms[0].uid == "69e5fbc8.71027bff"
|
||||
|
||||
def test_room_area(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.floors[0].rooms[0].area, 10.78332)
|
||||
|
||||
def test_room_perimeter(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.floors[0].rooms[0].perimeter, 13.32812)
|
||||
|
||||
def test_room_x(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.floors[0].rooms[0].x, 3.80616)
|
||||
|
||||
def test_room_y(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.floors[0].rooms[0].y, 0.23162)
|
||||
|
||||
def test_room_rotation(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.floors[0].rooms[0].rotation, 0.0, abs_tol=1e-9)
|
||||
|
||||
def test_room_was_modified_false(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[0].rooms[0].was_modified is False
|
||||
|
||||
def test_room_was_modified_true(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
closet = plan1.floors[1].rooms[1]
|
||||
assert closet.type == "Closet"
|
||||
assert closet.was_modified is True
|
||||
|
||||
def test_room_linked_room_0(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[0].rooms[0].linked_room_0 == "-1"
|
||||
|
||||
def test_room_linked_room_1(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[0].rooms[0].linked_room_1 == "-1"
|
||||
|
||||
def test_room_ceiling_height_value(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[0].rooms[0].values["ceilingHeight"] == "2.323164"
|
||||
|
||||
def test_room_label_value(self, plan2: MagicPlanXMLPlan) -> None:
|
||||
dining = plan2.floors[0].rooms[1]
|
||||
assert dining.type == "Dining Room"
|
||||
assert dining.values["label"] == "Room"
|
||||
|
||||
def test_room_no_label_when_absent(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert "label" not in plan1.floors[0].rooms[0].values
|
||||
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# Room points
|
||||
# ---------------------------------------------------------------------------
|
||||
|
||||
class TestRoomPoints:
|
||||
|
||||
def test_kitchen_point_count(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert len(plan1.floors[0].rooms[0].points) == 4
|
||||
|
||||
def test_living_room_point_count(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert len(plan1.floors[0].rooms[1].points) == 8
|
||||
|
||||
def test_point_snapped_x(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.floors[0].rooms[0].points[0].snapped_x, -1.44357)
|
||||
|
||||
def test_point_snapped_y(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.floors[0].rooms[0].points[0].snapped_y, -2.00846)
|
||||
|
||||
def test_point_height(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.floors[0].rooms[0].points[0].height, 2.323164)
|
||||
|
||||
def test_point_uid(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[0].rooms[0].points[0].uid == "69e5fbc8.710363ff"
|
||||
|
||||
def test_point_values_empty_when_absent(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[0].rooms[0].points[0].values == {}
|
||||
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# Doors (floorRoom context)
|
||||
# ---------------------------------------------------------------------------
|
||||
|
||||
class TestDoors:
|
||||
|
||||
def test_kitchen_door_count(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert len(plan1.floors[0].rooms[0].doors) == 5
|
||||
|
||||
def test_corridor_door_count(self, plan3: MagicPlanXMLPlan) -> None:
|
||||
assert len(plan3.floors[0].rooms[0].doors) == 9
|
||||
|
||||
def test_door_wall_point_index(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[0].rooms[0].doors[0].wall_point_index == 3
|
||||
|
||||
def test_door_type(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[0].rooms[0].doors[0].type == "4"
|
||||
|
||||
def test_door_u(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.floors[0].rooms[0].doors[0].u, 0.47585)
|
||||
|
||||
def test_door_snapped_width(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.floors[0].rooms[0].doors[0].snapped_width, 1.82394)
|
||||
|
||||
def test_door_snapped_height(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.floors[0].rooms[0].doors[0].snapped_height, 2.08411)
|
||||
|
||||
def test_door_snapped_orientation(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[0].rooms[0].doors[0].snapped_orientation == 3
|
||||
|
||||
def test_door_twin_wall_item_uid_present(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[0].rooms[0].doors[0].twin_wall_item_uid == "69e5fbc8.74614fff"
|
||||
|
||||
def test_door_twin_wall_item_uid_absent(self, plan2: MagicPlanXMLPlan) -> None:
|
||||
assert plan2.floors[0].rooms[0].doors[0].twin_wall_item_uid is None
|
||||
|
||||
def test_door_symbol_instance(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[0].rooms[0].doors[0].symbol_instance == "W-0-0"
|
||||
|
||||
def test_door_inset_x(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.floors[0].rooms[0].doors[0].inset_x, 0.0, abs_tol=1e-9)
|
||||
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# Windows (floorRoom context)
|
||||
# ---------------------------------------------------------------------------
|
||||
|
||||
class TestWindows:
|
||||
|
||||
def test_kitchen_window_count(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert len(plan1.floors[0].rooms[0].windows) == 1
|
||||
|
||||
def test_corridor_window_count_zero(self, plan3: MagicPlanXMLPlan) -> None:
|
||||
corridor = plan3.floors[0].rooms[0]
|
||||
assert corridor.type == "Corridor"
|
||||
assert len(corridor.windows) == 0
|
||||
|
||||
def test_window_wall_point_index(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[0].rooms[0].windows[0].wall_point_index == 1
|
||||
|
||||
def test_window_type(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[0].rooms[0].windows[0].type == "1"
|
||||
|
||||
def test_window_u(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.floors[0].rooms[0].windows[0].u, 0.68463)
|
||||
|
||||
def test_window_snapped_width(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.floors[0].rooms[0].windows[0].snapped_width, 1.71972)
|
||||
|
||||
def test_window_snapped_height(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.floors[0].rooms[0].windows[0].snapped_height, 0.94940)
|
||||
|
||||
def test_window_symbol_instance(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[0].rooms[0].windows[0].symbol_instance == "W-0-2"
|
||||
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# Furniture (room-level)
|
||||
# ---------------------------------------------------------------------------
|
||||
|
||||
class TestRoomFurniture:
|
||||
|
||||
def test_kitchen_furniture_count(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert len(plan1.floors[0].rooms[0].furniture) == 5
|
||||
|
||||
def test_bathroom_furniture_count_zero(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
bathroom = plan1.floors[1].rooms[0]
|
||||
assert bathroom.type == "Bathroom"
|
||||
assert len(bathroom.furniture) == 0
|
||||
|
||||
def test_furniture_type(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert isinstance(plan1.floors[0].rooms[0].furniture[0].type, str)
|
||||
|
||||
def test_furniture_symbol_instance(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert isinstance(plan1.floors[0].rooms[0].furniture[0].symbol_instance, str)
|
||||
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# Floor-level furniture (example 3)
|
||||
# ---------------------------------------------------------------------------
|
||||
|
||||
class TestFloorLevelFurniture:
|
||||
|
||||
def test_floor_furniture_count(self, plan3: MagicPlanXMLPlan) -> None:
|
||||
assert len(plan3.floors[0].furniture) == 1
|
||||
|
||||
def test_floor_furniture_x(self, plan3: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan3.floors[0].furniture[0].x, -2.09376)
|
||||
|
||||
def test_floor_furniture_y(self, plan3: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan3.floors[0].furniture[0].y, 3.13664)
|
||||
|
||||
def test_floor_furniture_absent_plan1(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert len(plan1.floors[0].furniture) == 0
|
||||
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# Main dimensions
|
||||
# ---------------------------------------------------------------------------
|
||||
|
||||
class TestMainDimensions:
|
||||
|
||||
def test_main_dimension_count(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert len(plan1.floors[0].rooms[0].main_dimensions) == 2
|
||||
|
||||
def test_main_dimension_from_point(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert isinstance(plan1.floors[0].rooms[0].main_dimensions[0].from_point, int)
|
||||
|
||||
def test_main_dimension_is_set(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert isinstance(plan1.floors[0].rooms[0].main_dimensions[0].is_set, bool)
|
||||
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# Exploded section
|
||||
# ---------------------------------------------------------------------------
|
||||
|
||||
class TestExploded:
|
||||
|
||||
def test_exploded_wall_count_ground_floor(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert len(plan1.floors[0].exploded.walls) == 11
|
||||
|
||||
def test_exploded_door_count_ground_floor(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert len(plan1.floors[0].exploded.doors) == 6
|
||||
|
||||
def test_exploded_window_count_ground_floor(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert len(plan1.floors[0].exploded.windows) == 2
|
||||
|
||||
def test_exploded_wall_type(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[0].exploded.walls[0].wall_type == "exterior"
|
||||
|
||||
def test_exploded_wall_points(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
pts = plan1.floors[0].exploded.walls[0].points
|
||||
assert len(pts) == 2
|
||||
assert math.isclose(pts[0].x, 2.363)
|
||||
assert math.isclose(pts[0].y, -1.778)
|
||||
assert math.isclose(pts[0].height, 2.323164)
|
||||
|
||||
def test_exploded_door_x1(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.floors[0].exploded.doors[0].x1, 5.24973)
|
||||
|
||||
def test_exploded_door_y1(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.floors[0].exploded.doors[0].y1, -1.333153)
|
||||
|
||||
def test_exploded_door_width(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.floors[0].exploded.doors[0].width, 0.773)
|
||||
|
||||
def test_exploded_door_height(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.floors[0].exploded.doors[0].height, 2.02225)
|
||||
|
||||
def test_exploded_door_symbol_instance(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[0].exploded.doors[0].symbol_instance == "W-0-1"
|
||||
|
||||
def test_exploded_window_x1(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.floors[0].exploded.windows[0].x1, 5.24973)
|
||||
|
||||
def test_exploded_window_width(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.floors[0].exploded.windows[0].width, 1.71972)
|
||||
|
||||
def test_exploded_window_height(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert math.isclose(plan1.floors[0].exploded.windows[0].height, 0.949396)
|
||||
|
||||
def test_exploded_window_symbol_instance(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.floors[0].exploded.windows[0].symbol_instance == "W-0-2"
|
||||
|
||||
def test_plan3_exploded_wall_count(self, plan3: MagicPlanXMLPlan) -> None:
|
||||
assert len(plan3.floors[0].exploded.walls) == 33
|
||||
|
||||
def test_plan3_exploded_door_count(self, plan3: MagicPlanXMLPlan) -> None:
|
||||
assert len(plan3.floors[0].exploded.doors) == 12
|
||||
|
||||
def test_plan3_exploded_window_count(self, plan3: MagicPlanXMLPlan) -> None:
|
||||
assert len(plan3.floors[0].exploded.windows) == 5
|
||||
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# Interior room points
|
||||
# ---------------------------------------------------------------------------
|
||||
|
||||
class TestInteriorRoomPoints:
|
||||
|
||||
def test_interior_room_floor_count_plan1(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert len(plan1.interior_room_floors) == 2
|
||||
|
||||
def test_interior_room_floor_count_plan2(self, plan2: MagicPlanXMLPlan) -> None:
|
||||
assert len(plan2.interior_room_floors) == 1
|
||||
|
||||
def test_interior_room_floor_uid_matches(self, plan1: MagicPlanXMLPlan) -> None:
|
||||
assert plan1.interior_room_floors[0].uid == plan1.floors[0].uid
|
||||
|
|
@ -1,985 +0,0 @@
|
|||
<plan name="275 Carr Hill Rd NE9 5ND" id="b66bb427-33fe-4865-8d57-bad7d9d3f2e5" uid="69e5fafc.0890b3ff" type="0" interiorWallWidth="0.12000" exteriorWallWidth="0.25000" schematic="0" hasLandSurveyAddress="0" lastPatchIdentifier="0" lastRollIdentifier="0">
|
||||
<values>
|
||||
<value key="date">2026-04-20</value>
|
||||
<value key="statistics.areaOfHeight">2.134</value>
|
||||
<value key="statistics.basement.account">100</value>
|
||||
<value key="statistics.exteriorWalls">0</value>
|
||||
<value key="statistics.interiorWalls">0</value>
|
||||
</values>
|
||||
<floor uid="69e5fb20.4feef7ff" floorType="0" rotation="0.00000" compassAngle="-1.000000" areaWithoutWalls="40.20736" areaWithInteriorWallsOnly="40.67878" areaWithWalls="48.40593">
|
||||
<name>Ground Floor</name>
|
||||
<symbolInstance id="floor" uid="69e5fb20.4feef7ff" parentUid="" symbol="floor">
|
||||
<values>
|
||||
<value key="ceilingHeight">2.323164</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-0-0" uid="69e5fbc8.711517ff" parentUid="" symbol="doordoublehinged">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">doors</value>
|
||||
<value key="wallItemHeight">2.084107</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-0-1" uid="69e5fbc8.71336fff" parentUid="" symbol="doorhinged">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">doors</value>
|
||||
<value key="wallItemHeight">2.02225</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-0-2" uid="69e5fbc8.713b47ff" parentUid="" symbol="windowfixed">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">doors</value>
|
||||
<value key="wallItemDistanceToFloor">1.124639</value>
|
||||
<value key="wallItemHeight">0.949396</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-0-3" uid="69e5fbc8.73e407ff" parentUid="" symbol="furniture-3740ec67-24f6-42e6-b7f9-40a88d3f84ee">
|
||||
<values>
|
||||
<value key="depth">0.397258</value>
|
||||
<value key="height">0.746826</value>
|
||||
<value key="symbolfilePrefix">furniture</value>
|
||||
<value key="wallItemDistanceToFloor">1.279293</value>
|
||||
<value key="wallItemHeight">0.746826</value>
|
||||
<value key="width">0.677733</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-0-4" uid="69e5fbc8.7408c7ff" parentUid="" symbol="furniture-3740ec67-24f6-42e6-b7f9-40a88d3f84ee">
|
||||
<values>
|
||||
<value key="depth">0.368615</value>
|
||||
<value key="height">0.723145</value>
|
||||
<value key="symbolfilePrefix">furniture</value>
|
||||
<value key="wallItemDistanceToFloor">1.311519</value>
|
||||
<value key="wallItemHeight">0.723145</value>
|
||||
<value key="width">0.398439</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-0-5" uid="69e5fbc8.742773ff" parentUid="" symbol="furniture-3740ec67-24f6-42e6-b7f9-40a88d3f84ee">
|
||||
<values>
|
||||
<value key="depth">0.604444</value>
|
||||
<value key="height">0.1</value>
|
||||
<value key="symbolfilePrefix">furniture</value>
|
||||
<value key="wallItemDistanceToFloor">0.851311</value>
|
||||
<value key="wallItemHeight">0.1</value>
|
||||
<value key="width">0.601075</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="F-0-0" uid="69e5fbc8.73d847ff" parentUid="" symbol="furniture-8285a785-4b2a-4a2a-904b-5fd5d91551d4">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">furniture</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="F-0-1" uid="69e5fbc8.73dfd3ff" parentUid="" symbol="appliances-378151a6-3e37-477c-a52d-7786fcff365a">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">appliances</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="F-0-2" uid="69e5fbc8.7400c7ff" parentUid="" symbol="appliances-f4803db0-8455-424c-a414-05a5498b9288">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">appliances</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="F-0-3" uid="69e5fbc8.7404e7ff" parentUid="" symbol="appliances-af014f7b-2135-4206-995c-7747bb425ed5">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">appliances</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="F-0-4" uid="69e5fdc5.226b2fff" parentUid="" symbol="hvac-650c5bce-e5fd-48e9-b3f9-1180a0f66cbc">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">hvac</value>
|
||||
<value key="wallItemDistanceToFloor">0.1500</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-1-0" uid="69e5fbc8.74614fff" parentUid="" symbol="doordoublehinged">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">doors</value>
|
||||
<value key="wallItemHeight">2.084107</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-1-1" uid="69e5fbc8.746863ff" parentUid="" symbol="doorhinged">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">doors</value>
|
||||
<value key="wallItemHeight">2.006357</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-1-2" uid="69e5fbc8.746f47ff" parentUid="" symbol="windowfixed">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">doors</value>
|
||||
<value key="wallItemDistanceToFloor">1.00597</value>
|
||||
<value key="wallItemHeight">1.026259</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="F-1-0" uid="69e5fbc8.7496abff" parentUid="" symbol="appliances-fee6a83d-7365-4cb3-89cb-26ffea1099e3">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">appliances</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="F-1-1" uid="69e5fbc8.74a363ff" parentUid="" symbol="furniture-f4c1d117-d87f-4ca4-b70f-7c1216e07f6d">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">furniture</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="F-1-2" uid="69e5fbc8.74a783ff" parentUid="" symbol="hvac-1489fe06-b5c5-40ce-b7fa-c0555750d8c9">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">hvac</value>
|
||||
<value key="wallItemDistanceToFloor">0.0000</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="F-1-3" uid="69e5fd95.4fd913ff" parentUid="" symbol="hvac-650c5bce-e5fd-48e9-b3f9-1180a0f66cbc">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">hvac</value>
|
||||
<value key="wallItemDistanceToFloor">0.1500</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="F-1-4" uid="69e5fda8.2e9b47ff" parentUid="" symbol="hvac-650c5bce-e5fd-48e9-b3f9-1180a0f66cbc">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">hvac</value>
|
||||
<value key="wallItemDistanceToFloor">0.1500</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<floorRoom type="Kitchen" uid="69e5fbc8.71027bff" x="3.80616" y="0.23162" rotation="0.00000" wasModified="0" linkedRoom0="-1" linkedRoom1="-1" area="10.78332" perimeter="13.32812">
|
||||
<values>
|
||||
<value key="ceilingHeight">2.323164</value>
|
||||
</values>
|
||||
<point snappedX="-1.44357" snappedY="-2.00846" height="2.323164" uid="69e5fbc8.710363ff" />
|
||||
<point snappedX="1.44357" snappedY="-2.00846" height="2.323164" uid="69e5fbc8.710a67ff" />
|
||||
<point snappedX="1.44357" snappedY="2.00846" height="2.323164" uid="69e5fbc8.710e47ff" />
|
||||
<point snappedX="-1.44357" snappedY="2.00846" height="2.323164" uid="69e5fbc8.7111afff" />
|
||||
<door point="3" type="4" u="0.47585" width="1.82394" depth="0.91197" height="2.08411" orientation="3" snappedType="4" snappedPosition="0.47585" snappedWidth="1.82394" snappedDepth="0.91197" snappedHeight="2.08411" snappedOrientation="3" insetX="0.00000" insetY="0.00000" insetZ="0.00000" twinWallItemUid="69e5fbc8.74614fff" symbolInstance="W-0-0" />
|
||||
<door point="1" type="2" u="0.19764" width="0.77300" depth="0.77300" height="2.02225" orientation="0" snappedType="2" snappedPosition="0.19764" snappedWidth="0.77300" snappedDepth="0.77300" snappedHeight="2.02225" snappedOrientation="0" insetX="0.00000" insetY="0.00000" insetZ="0.00000" symbolInstance="W-0-1" />
|
||||
<window point="1" type="1" u="0.68463" width="1.71972" depth="0.12000" height="0.94940" orientation="0" snappedType="1" snappedPosition="0.68463" snappedWidth="1.71972" snappedDepth="0.12000" snappedHeight="0.94940" snappedOrientation="0" insetX="0.00000" insetY="-0.06000" insetZ="-0.06000" symbolInstance="W-0-2" />
|
||||
<door point="2" type="0" u="0.14195" width="0.67773" depth="0.39726" height="0.74683" orientation="2" snappedType="0" snappedPosition="0.14195" snappedWidth="0.67773" snappedDepth="0.39726" snappedHeight="0.74683" snappedOrientation="2" insetX="0.00000" insetY="0.03000" insetZ="0.03000" symbolInstance="W-0-3" />
|
||||
<door point="2" type="0" u="0.63071" width="0.39844" depth="0.36861" height="0.72315" orientation="2" snappedType="0" snappedPosition="0.63071" snappedWidth="0.39844" snappedDepth="0.36861" snappedHeight="0.72315" snappedOrientation="2" insetX="0.00000" insetY="0.03000" insetZ="0.03000" symbolInstance="W-0-4" />
|
||||
<door point="2" type="0" u="0.40931" width="0.60107" depth="0.60444" height="0.10000" orientation="2" snappedType="0" snappedPosition="0.40931" snappedWidth="0.60107" snappedDepth="0.60444" snappedHeight="0.10000" snappedOrientation="2" insetX="0.00000" insetY="0.03000" insetZ="0.03000" symbolInstance="W-0-5" />
|
||||
<furniture type="0" x="-0.37437" y="1.64301" snappedX="-0.37437" snappedY="1.64301" angle="3.14159" width="0.73174" depth="0.61090" height="0.83418" snappedWidth="0.73174" snappedDepth="0.61090" snappedHeight="0.83418" sizeLock0="0" sizeLock1="0" sizeLock2="0" symbolInstance="F-0-0" />
|
||||
<furniture type="0" x="-1.07415" y="1.66141" snappedX="-1.07415" snappedY="1.66141" angle="3.14159" width="0.53467" depth="0.58310" height="1.30356" snappedWidth="0.53467" snappedDepth="0.58310" snappedHeight="1.30356" sizeLock0="0" sizeLock1="0" sizeLock2="0" symbolInstance="F-0-1" />
|
||||
<furniture type="0" x="0.29204" y="1.64624" snappedX="0.29204" snappedY="1.64624" angle="3.14159" width="0.60107" depth="0.60444" height="0.85131" snappedWidth="0.60107" snappedDepth="0.60444" snappedHeight="0.85131" sizeLock0="0" sizeLock1="0" sizeLock2="0" symbolInstance="F-0-2" />
|
||||
<furniture type="0" x="-1.02621" y="-1.62776" snappedX="-1.02621" snappedY="-1.62776" angle="0.00000" width="0.59317" depth="0.64140" height="0.80396" snappedWidth="0.59317" snappedDepth="0.64140" snappedHeight="0.80396" sizeLock0="0" sizeLock1="0" sizeLock2="0" symbolInstance="F-0-3" />
|
||||
<furniture type="0" x="0.10449" y="-1.89546" snappedX="0.10449" snappedY="-1.89546" angle="0.00000" width="1.00000" depth="0.10600" height="0.60000" snappedWidth="1.00000" snappedDepth="0.10600" snappedHeight="0.60000" sizeLock0="0" sizeLock1="0" sizeLock2="0" symbolInstance="F-0-4" />
|
||||
<mainDimension from="0" to="1" dir.x="-1.0000000000" dir.y="-0.0000000000" value="2.7671400000" actualValue="2.7671400000" isSet="0" />
|
||||
<mainDimension from="1" to="2" dir.x="-0.0000000000" dir.y="-1.0000000000" value="3.8969200000" actualValue="3.8969200000" isSet="0" />
|
||||
</floorRoom>
|
||||
<floorRoom type="Living Room" uid="69e5fbc8.74487bff" x="-1.61210" y="0.23162" rotation="0.00000" wasModified="0" linkedRoom0="-1" linkedRoom1="-1" area="29.44518" perimeter="24.13895">
|
||||
<values>
|
||||
<value key="ceilingHeight">3.285283</value>
|
||||
</values>
|
||||
<point snappedX="-3.97469" snappedY="-2.00846" height="3.285283" uid="69e5fbc8.7448bbff" />
|
||||
<point snappedX="3.97469" snappedY="-2.00846" height="3.285283" uid="69e5fbc8.744c47ff" />
|
||||
<point snappedX="3.97469" snappedY="2.00846" height="3.285283" uid="69e5fbc8.744f5bff" />
|
||||
<point snappedX="0.19116" snappedY="2.00846" height="3.285283" uid="69e5fbc8.745263ff" />
|
||||
<point snappedX="0.19116" snappedY="1.53785" height="3.285283" uid="69e5fbc8.74554fff" />
|
||||
<point snappedX="-1.57493" snappedY="1.53785" height="3.285283" uid="69e5fbc8.745867ff" />
|
||||
<point snappedX="-1.71730" snappedY="1.93998" height="3.285283" uid="69e5fbc8.745b7fff" />
|
||||
<point snappedX="-3.97469" snappedY="1.93998" height="3.285283" uid="69e5fbc8.745e5fff" />
|
||||
<door point="1" type="4" u="0.52415" width="1.82394" depth="0.91197" height="2.08411" orientation="0" snappedType="4" snappedPosition="0.52415" snappedWidth="1.82394" snappedDepth="0.91197" snappedHeight="2.08411" snappedOrientation="0" insetX="0.00000" insetY="0.00000" insetZ="0.00000" twinWallItemUid="69e5fbc8.711517ff" symbolInstance="W-1-0" />
|
||||
<door point="7" type="2" u="0.81578" width="0.83113" depth="0.83113" height="2.00636" orientation="0" snappedType="2" snappedPosition="0.81578" snappedWidth="0.83113" snappedDepth="0.83113" snappedHeight="2.00636" snappedOrientation="0" insetX="0.00000" insetY="0.00000" insetZ="0.00000" symbolInstance="W-1-1" />
|
||||
<window point="7" type="1" u="0.46552" width="1.85077" depth="0.12000" height="1.02626" orientation="0" snappedType="1" snappedPosition="0.46552" snappedWidth="1.85077" snappedDepth="0.12000" snappedHeight="1.02626" snappedOrientation="0" insetX="0.00000" insetY="-0.06000" insetZ="-0.06000" symbolInstance="W-1-2" />
|
||||
<furniture type="0" x="-3.26415" y="1.35928" snappedX="-3.26415" snappedY="1.35928" angle="3.72376" width="1.10000" depth="0.26400" height="0.71600" snappedWidth="1.10000" snappedDepth="0.26400" snappedHeight="0.71600" sizeLock0="0" sizeLock1="0" sizeLock2="0" symbolInstance="F-1-0" />
|
||||
<furniture type="0" x="-3.33464" y="1.37128" snappedX="-3.33464" snappedY="1.37128" angle="3.80141" width="1.01832" depth="0.49767" height="0.57273" snappedWidth="1.01832" snappedDepth="0.49767" snappedHeight="0.57273" sizeLock0="0" sizeLock1="0" sizeLock2="0" symbolInstance="F-1-1" />
|
||||
<furniture type="0" x="-0.60840" y="1.42589" snappedX="-0.60840" snappedY="1.42589" angle="3.14159" width="1.11379" depth="0.42391" height="1.10296" snappedWidth="1.11379" snappedDepth="0.42391" snappedHeight="1.10296" sizeLock0="0" sizeLock1="0" sizeLock2="0" symbolInstance="F-1-2" />
|
||||
<furniture type="0" x="2.08331" y="1.89546" snappedX="2.08331" snappedY="1.89546" angle="3.14159" width="1.00000" depth="0.10600" height="0.60000" snappedWidth="1.00000" snappedDepth="0.10600" snappedHeight="0.60000" sizeLock0="0" sizeLock1="0" sizeLock2="0" symbolInstance="F-1-3" />
|
||||
<furniture type="0" x="-3.86169" y="0.04424" snappedX="-3.86169" snappedY="0.04424" angle="4.71239" width="1.00000" depth="0.10600" height="0.60000" snappedWidth="1.00000" snappedDepth="0.10600" snappedHeight="0.60000" sizeLock0="0" sizeLock1="0" sizeLock2="0" symbolInstance="F-1-4" />
|
||||
<mainDimension from="0" to="1" dir.x="-1.0000000000" dir.y="-0.0000000000" value="7.8293800000" actualValue="7.8293800000" isSet="0" />
|
||||
<mainDimension from="1" to="2" dir.x="-0.0000000000" dir.y="-1.0000000000" value="3.8969200000" actualValue="3.8969200000" isSet="0" />
|
||||
</floorRoom>
|
||||
<exploded>
|
||||
<wall>
|
||||
<point x="2.363000" y="-1.778000" height="2.323164" />
|
||||
<point x="-5.586000" y="-1.777000" height="2.323164" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="5.249000" y="-1.777000" height="2.323164" />
|
||||
<point x="2.363000" y="-1.778000" height="2.323164" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="2.363000" y="2.240000" height="2.323164" />
|
||||
<point x="5.249000" y="2.239000" height="2.323164" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="-1.421000" y="2.239000" height="2.323164" />
|
||||
<point x="2.363000" y="2.240000" height="2.323164" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="5.249000" y="2.239000" height="2.323164" />
|
||||
<point x="5.249000" y="-1.777000" height="2.323164" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="-5.586000" y="-1.777000" height="2.323164" />
|
||||
<point x="-5.586000" y="2.170000" height="2.323164" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="2.363000" y="-1.778000" height="2.323164" />
|
||||
<point x="2.363000" y="2.240000" height="2.323164" />
|
||||
<type>interior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="-5.586000" y="2.170000" height="2.323164" />
|
||||
<point x="-3.328500" y="2.170000" height="2.323164" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="-1.421000" y="1.768000" height="2.323164" />
|
||||
<point x="-3.186500" y="1.768000" height="2.323164" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="-1.421000" y="1.768000" height="2.323164" />
|
||||
<point x="-1.421000" y="2.239000" height="2.323164" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="-3.328500" y="2.170000" height="2.323164" />
|
||||
<point x="-3.186500" y="1.768000" height="2.323164" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<door type="2" x1="5.249730" y1="-1.333153" x2="5.249730" y2="-0.560153" width="0.773000" depth="0.773000" height="2.022250" insetX="0.000000" insetY="0.000000" orientation="0" symbolInstance="W-0-1" />
|
||||
<window type="1" x1="5.249730" y1="0.091248" x2="5.249730" y2="1.810968" width="1.719720" depth="0.120000" height="0.949396" insetX="0.000000" insetY="-0.060000" orientation="0" symbolInstance="W-0-2" />
|
||||
<door type="0" x1="5.135799" y1="2.240080" x2="4.458069" y2="2.240080" width="0.677730" depth="0.397260" height="0.746826" insetX="0.000000" insetY="0.060000" orientation="2" symbolInstance="W-0-3" />
|
||||
<door type="0" x1="3.643687" y1="2.240080" x2="3.245247" y2="2.240080" width="0.398440" depth="0.368610" height="0.723145" insetX="0.000000" insetY="0.060000" orientation="2" symbolInstance="W-0-4" />
|
||||
<door type="0" x1="4.357647" y1="2.240080" x2="3.756577" y2="2.240080" width="0.601070" depth="0.604440" height="0.100000" insetX="0.000000" insetY="0.060000" orientation="2" symbolInstance="W-0-5" />
|
||||
<furniture type="0" x="3.431790" y="1.874630" angle="3.141590" width="0.731740" depth="0.610900" height="0.834180" symbolInstance="F-0-0" />
|
||||
<furniture type="0" x="2.732010" y="1.893030" angle="3.141590" width="0.534670" depth="0.583097" height="1.303560" symbolInstance="F-0-1" />
|
||||
<furniture type="0" x="4.098200" y="1.877860" angle="3.141590" width="0.601070" depth="0.604440" height="0.851310" symbolInstance="F-0-2" />
|
||||
<furniture type="0" x="2.779950" y="-1.396140" angle="0.000000" width="0.593170" depth="0.641400" height="0.803960" symbolInstance="F-0-3" />
|
||||
<furniture type="0" x="3.910650" y="-1.663840" angle="0.000000" width="1.000000" depth="0.106000" height="0.600000" symbolInstance="F-0-4" />
|
||||
<door type="2" x1="-5.586790" y1="-0.596000" x2="-5.586790" y2="-1.427130" width="0.831130" depth="0.831130" height="2.006357" insetX="0.000000" insetY="0.000000" orientation="0" symbolInstance="W-1-1" />
|
||||
<window type="1" x1="-5.586790" y1="1.254770" x2="-5.586790" y2="-0.596000" width="1.850770" depth="0.120000" height="1.026259" insetX="0.000000" insetY="-0.060000" orientation="0" symbolInstance="W-1-2" />
|
||||
<door type="4" x1="2.362590" y1="-0.586239" x2="2.362590" y2="1.237701" width="1.823940" depth="0.911970" height="2.084107" insetX="0.000000" insetY="0.000000" orientation="0" symbolInstance="W-1-0" />
|
||||
<furniture type="0" x="-4.876250" y="1.590900" angle="3.723760" width="1.100000" depth="0.264000" height="0.716000" symbolInstance="F-1-0" />
|
||||
<furniture type="0" x="-4.946740" y="1.602900" angle="3.801410" width="1.018320" depth="0.497670" height="0.572730" symbolInstance="F-1-1" />
|
||||
<furniture type="0" x="-2.220500" y="1.657510" angle="3.141590" width="1.113790" depth="0.423910" height="1.102960" symbolInstance="F-1-2" />
|
||||
<furniture type="0" x="0.471210" y="2.127080" angle="3.141590" width="1.000000" depth="0.106000" height="0.600000" symbolInstance="F-1-3" />
|
||||
<furniture type="0" x="-5.473790" y="0.275860" angle="4.712390" width="1.000000" depth="0.106000" height="0.600000" symbolInstance="F-1-4" />
|
||||
</exploded>
|
||||
</floor>
|
||||
<floor uid="69e5fbdd.882287ff" floorType="1" rotation="0.00000" compassAngle="-1.000000" areaWithoutWalls="29.34605" areaWithInteriorWallsOnly="30.52809" areaWithWalls="36.77256">
|
||||
<name>1st Floor</name>
|
||||
<symbolInstance id="floor" uid="69e5fbdd.882287ff" parentUid="" symbol="floor">
|
||||
<values>
|
||||
<value key="ceilingHeight">2.382467</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-0-0" uid="69e5fcf6.09fe63ff" parentUid="" symbol="doorhinged">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">doors</value>
|
||||
<value key="wallItemHeight">2.074757</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-0-1" uid="69e5fd68.8e2f33ff" parentUid="" symbol="plumbing-08aa18c5-ec1c-48f3-be68-431c07d4576c">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">plumbing</value>
|
||||
<value key="wallItemDistanceToFloor">1.5000</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-1-0" uid="69e5fcf6.09e257ff" parentUid="" symbol="doorhinged">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">doors</value>
|
||||
<value key="wallItemHeight">2.081704</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-1-1" uid="69e5fcf6.0a0f3bff" parentUid="" symbol="windowfixed">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">doors</value>
|
||||
<value key="wallItemDistanceToFloor">1.227592</value>
|
||||
<value key="wallItemHeight">0.88319</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="F-1-0" uid="69e5fd3d.4b9d17ff" parentUid="" symbol="hvac-650c5bce-e5fd-48e9-b3f9-1180a0f66cbc">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">hvac</value>
|
||||
<value key="wallItemDistanceToFloor">0.1500</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="F-1-1" uid="69e5fe3e.2db4abff" parentUid="" symbol="co-ed10aa18-b3ce-4f51-a5e8-9f0051663885">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">677d01685458a</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-2-0" uid="69e5fcf6.09e257ff.auto" parentUid="" symbol="doorhinged">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">doors</value>
|
||||
<value key="wallItemHeight">2.081704</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-2-1" uid="69e5fcf6.09fe63ff.auto" parentUid="" symbol="doorhinged">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">doors</value>
|
||||
<value key="wallItemHeight">2.074757</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-2-2" uid="69e5fcf6.0a077fff" parentUid="" symbol="doorhinged">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">doors</value>
|
||||
<value key="wallItemHeight">2.195494</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-3-0" uid="69e5fcf6.0a077fff.auto" parentUid="" symbol="doorhinged">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">doors</value>
|
||||
<value key="wallItemHeight">2.195494</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-3-1" uid="69e5fcf6.0b305fff" parentUid="" symbol="windowfixed">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">doors</value>
|
||||
<value key="wallItemDistanceToFloor">0.915306</value>
|
||||
<value key="wallItemHeight">1.180143</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-3-2" uid="69e5fcf6.0bf033ff" parentUid="" symbol="appliances-e648fc54-abba-402a-8313-f5523ec6e5cc">
|
||||
<values>
|
||||
<value key="depth">0.1</value>
|
||||
<value key="height">0.676758</value>
|
||||
<value key="symbolfilePrefix">appliances</value>
|
||||
<value key="wallItemDistanceToFloor">1.399472</value>
|
||||
<value key="wallItemHeight">0.676758</value>
|
||||
<value key="width">1.253952</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="F-3-0" uid="69e5fd4d.64215bff" parentUid="" symbol="hvac-650c5bce-e5fd-48e9-b3f9-1180a0f66cbc">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">hvac</value>
|
||||
<value key="wallItemDistanceToFloor">0.1500</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<floorRoom type="Bathroom" uid="69e5fcf6.08bec3ff" x="0.43937" y="2.21959" rotation="0.00000" wasModified="0" linkedRoom0="-1" linkedRoom1="-1" area="4.22940" perimeter="8.30295">
|
||||
<values>
|
||||
<value key="ceilingHeight">2.382467</value>
|
||||
</values>
|
||||
<point snappedX="0.95733" snappedY="-1.23850" height="2.382467" uid="69e5fcf6.08c07bff" />
|
||||
<point snappedX="0.95665" snappedY="1.23881" height="2.382467" uid="69e5fcf6.08d4cbff" />
|
||||
<point snappedX="-0.95733" snappedY="1.23850" height="2.382467" uid="69e5fcf6.08ce4bff" />
|
||||
<point snappedX="-0.95702" snappedY="-1.23881" height="2.382467" uid="69e5fcf6.08ca9fff" />
|
||||
<door point="2" type="2" u="0.20319" width="0.74796" depth="0.74796" height="2.07476" orientation="0" snappedType="2" snappedPosition="0.20319" snappedWidth="0.74796" snappedDepth="0.74796" snappedHeight="2.07476" snappedOrientation="0" insetX="0.00000" insetY="0.00000" insetZ="0.00000" twinWallItemUid="69e5fcf6.09fe63ff.auto" symbolInstance="W-0-0" />
|
||||
<door point="1" type="0" u="0.48552" width="0.67310" depth="0.13140" height="0.06000" orientation="2" snappedType="0" snappedPosition="0.48552" snappedWidth="0.67310" snappedDepth="0.13140" snappedHeight="0.06000" snappedOrientation="2" insetX="0.00000" insetY="0.03000" insetZ="0.03000" symbolInstance="W-0-1" />
|
||||
<mainDimension from="1" to="2" dir.x="-0.9999999620" dir.y="-0.0002757380" value="1.7943400118" actualValue="1.7943400118" isSet="0" />
|
||||
<mainDimension from="0" to="1" dir.x="0.0002757380" dir.y="-0.9999999620" value="2.3575147609" actualValue="2.3575147609" isSet="0" />
|
||||
</floorRoom>
|
||||
<floorRoom type="Closet" uid="69e5fcf6.08d80fff" x="-0.53205" y="-0.23901" rotation="0.00000" wasModified="1" linkedRoom0="-1" linkedRoom1="-1" area="8.65802" perimeter="12.11130">
|
||||
<values>
|
||||
<value key="ceilingHeight">2.382467</value>
|
||||
</values>
|
||||
<point snappedX="1.92843" snappedY="1.21239" height="2.382467" uid="69e5fcf6.08d833ff" />
|
||||
<point snappedX="-1.92405" snappedY="1.22579" height="2.382467" uid="69e5fcf6.08e7bbff" />
|
||||
<point snappedX="-1.93535" snappedY="-1.22579" height="2.382467" uid="69e5fcf6.08f1d3ff" />
|
||||
<point snappedX="1.93535" snappedY="-1.20402" height="2.382467" uid="69e5fcf6.08fa8bff" />
|
||||
<door point="0" type="2" u="0.64117" width="0.72408" depth="0.72408" height="2.08170" orientation="0" snappedType="2" snappedPosition="0.64117" snappedWidth="0.72408" snappedDepth="0.72408" snappedHeight="2.08170" snappedOrientation="0" insetX="0.00000" insetY="0.00000" insetZ="0.00000" twinWallItemUid="69e5fcf6.09e257ff.auto" symbolInstance="W-1-0" />
|
||||
<window point="2" type="1" u="0.57311" width="1.92450" depth="0.12000" height="0.88319" orientation="0" snappedType="1" snappedPosition="0.57311" snappedWidth="1.92450" snappedDepth="0.12000" snappedHeight="0.88319" snappedOrientation="0" insetX="0.00000" insetY="-0.06000" insetZ="-0.06000" symbolInstance="W-1-1" />
|
||||
<furniture type="0" x="0.58270" y="-1.09832" snappedX="0.58275" snappedY="-1.09825" angle="0.00000" width="1.00000" depth="0.10600" height="0.60000" snappedWidth="1.00000" snappedDepth="0.10600" snappedHeight="0.60000" sizeLock0="0" sizeLock1="0" sizeLock2="0" symbolInstance="F-1-0" />
|
||||
<furniture type="0" x="-1.51619" y="-0.80518" snappedX="-1.51614" snappedY="-0.80511" angle="0.00000" width="0.71386" depth="0.58230" height="1.00000" snappedWidth="0.71386" snappedDepth="0.58230" snappedHeight="1.00000" sizeLock0="0" sizeLock1="0" sizeLock2="0" symbolInstance="F-1-1" />
|
||||
<mainDimension from="2" to="3" dir.x="-0.9999939454" dir.y="0.0034798192" value="3.7501638695" actualValue="3.7501638695" isSet="0" />
|
||||
<mainDimension from="1" to="2" dir.x="-0.0034798192" dir.y="-0.9999939454" value="2.3310632946" actualValue="2.3310632946" isSet="0" />
|
||||
</floorRoom>
|
||||
<floorRoom type="Other" uid="69e5fcf6.0906ebff" x="-1.48849" y="2.21987" rotation="0.00000" wasModified="1" linkedRoom0="-1" linkedRoom1="-1" area="4.27518" perimeter="8.34147">
|
||||
<values>
|
||||
<value key="ceilingHeight">2.382467</value>
|
||||
</values>
|
||||
<point snappedX="0.97346" snappedY="-1.23218" height="2.382467" uid="69e5fcf6.09070fff" />
|
||||
<point snappedX="0.96799" snappedY="1.24087" height="2.382467" uid="69e5fcf6.09143bff" />
|
||||
<point snappedX="-0.95378" snappedY="1.23878" height="2.382467" uid="69e5fcf6.09106fff" />
|
||||
<point snappedX="-0.97346" snappedY="-1.24087" height="2.382467" uid="69e5fcf6.090d5bff" />
|
||||
<door point="3" type="2" u="0.73610" width="0.72408" depth="0.72408" height="2.08170" orientation="3" snappedType="2" snappedPosition="0.73610" snappedWidth="0.72408" snappedDepth="0.72408" snappedHeight="2.08170" snappedOrientation="3" insetX="0.00000" insetY="0.00000" insetZ="0.00000" twinWallItemUid="69e5fcf6.09e257ff" symbolInstance="W-2-0" />
|
||||
<door point="0" type="2" u="0.79528" width="0.74796" depth="0.74796" height="2.07476" orientation="3" snappedType="2" snappedPosition="0.79528" snappedWidth="0.74796" snappedDepth="0.74796" snappedHeight="2.07476" snappedOrientation="3" insetX="0.00000" insetY="0.00000" insetZ="0.00000" twinWallItemUid="69e5fcf6.09fe63ff" symbolInstance="W-2-1" />
|
||||
<door point="1" type="2" u="0.25222" width="0.76920" depth="0.76920" height="2.19549" orientation="0" snappedType="2" snappedPosition="0.25222" snappedWidth="0.76920" snappedDepth="0.76920" snappedHeight="2.19549" snappedOrientation="0" insetX="0.00000" insetY="0.00000" insetZ="0.00000" twinWallItemUid="69e5fcf6.0a077fff.auto" symbolInstance="W-2-2" />
|
||||
<mainDimension from="3" to="0" dir.x="-0.9999975492" dir.y="-0.0022139540" value="1.8263235678" actualValue="1.8263235678" isSet="0" />
|
||||
<mainDimension from="2" to="3" dir.x="0.0022139540" dir.y="-0.9999975492" value="2.3593927501" actualValue="2.3593927501" isSet="0" />
|
||||
</floorRoom>
|
||||
<floorRoom type="Bedroom" uid="69e5fcf6.091a43ff" x="-0.45645" y="5.11834" rotation="0.00000" wasModified="0" linkedRoom0="-1" linkedRoom1="-1" area="12.19886" perimeter="14.09693">
|
||||
<values>
|
||||
<value key="ceilingHeight">2.382467</value>
|
||||
</values>
|
||||
<point snappedX="1.98414" snappedY="-0.83873" height="2.382467" uid="69e5fcf6.091adbff" />
|
||||
<point snappedX="1.98413" snappedY="1.66009" height="2.382467" uid="69e5fcf6.091efbff" />
|
||||
<point snappedX="-1.98413" snappedY="1.66010" height="2.382467" uid="69e5fcf6.092f4bff" />
|
||||
<point snappedX="-1.98414" snappedY="-1.66010" height="2.382467" uid="69e5fcf6.0975d3ff" />
|
||||
<point snappedX="1.84248" snappedY="-1.66010" height="2.382467" uid="69e5fcf6.098c6bff" />
|
||||
<point snappedX="1.84248" snappedY="-0.83873" height="2.382467" uid="69e5fcf6.099a0fff" />
|
||||
<door point="3" type="2" u="0.36303" width="0.76920" depth="0.76920" height="2.19549" orientation="3" snappedType="2" snappedPosition="0.36303" snappedWidth="0.76920" snappedDepth="0.76920" snappedHeight="2.19549" snappedOrientation="3" insetX="0.00000" insetY="0.00000" insetZ="0.00000" twinWallItemUid="69e5fcf6.0a077fff" symbolInstance="W-3-0" />
|
||||
<window point="1" type="1" u="0.49053" width="2.41757" depth="0.12000" height="1.18014" orientation="0" snappedType="1" snappedPosition="0.49053" snappedWidth="2.41757" snappedDepth="0.12000" snappedHeight="1.18014" snappedOrientation="0" insetX="0.00000" insetY="-0.06000" insetZ="-0.06000" symbolInstance="W-3-1" />
|
||||
<door point="0" type="0" u="0.73832" width="1.25395" depth="0.10000" height="0.67676" orientation="2" snappedType="0" snappedPosition="0.73832" snappedWidth="1.25395" snappedDepth="0.10000" snappedHeight="0.67676" snappedOrientation="2" insetX="0.00000" insetY="0.03000" insetZ="0.03000" symbolInstance="W-3-2" />
|
||||
<furniture type="0" x="-0.12434" y="1.54710" snappedX="-0.12434" snappedY="1.54710" angle="3.14159" width="1.00000" depth="0.10600" height="0.60000" snappedWidth="1.00000" snappedDepth="0.10600" snappedHeight="0.60000" sizeLock0="0" sizeLock1="0" sizeLock2="0" symbolInstance="F-3-0" />
|
||||
<mainDimension from="1" to="2" dir.x="-1.0000000000" dir.y="-0.0000042038" value="3.8482834528" actualValue="3.8482834528" isSet="0" />
|
||||
<mainDimension from="2" to="3" dir.x="0.0000042038" dir.y="-1.0000000000" value="3.2002155817" actualValue="3.2002155817" isSet="0" />
|
||||
</floorRoom>
|
||||
<exploded>
|
||||
<wall>
|
||||
<point x="-2.461000" y="0.983500" height="2.382467" />
|
||||
<point x="-2.500460" y="3.458000" height="2.382467" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="-2.474000" y="-1.463000" height="2.382467" />
|
||||
<point x="-2.461000" y="0.983500" height="2.382467" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="-2.440000" y="6.778000" height="2.382467" />
|
||||
<point x="1.528000" y="6.778000" height="2.382467" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="1.402997" y="-1.441500" height="2.382467" />
|
||||
<point x="-2.474000" y="-1.463000" height="2.382467" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="-0.505800" y="0.968600" height="2.382467" />
|
||||
<point x="-2.461000" y="0.983500" height="2.382467" />
|
||||
<type>interior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="1.396000" y="0.978000" height="2.382467" />
|
||||
<point x="-0.505800" y="0.968600" height="2.382467" />
|
||||
<type>interior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="-0.520000" y="3.458500" height="2.382467" />
|
||||
<point x="1.394500" y="3.458000" height="2.382467" />
|
||||
<type>interior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="-2.500460" y="3.458000" height="2.382467" />
|
||||
<point x="-0.520000" y="3.458500" height="2.382467" />
|
||||
<type>interior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="-2.500460" y="3.458000" height="2.382467" />
|
||||
<point x="-2.440000" y="6.778000" height="2.382467" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="1.394500" y="3.458000" height="2.382467" />
|
||||
<point x="1.396000" y="0.978000" height="2.382467" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="1.390000" y="4.280000" height="2.382467" />
|
||||
<point x="1.394500" y="3.458000" height="2.382467" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="1.528000" y="6.778000" height="2.382467" />
|
||||
<point x="1.528000" y="4.280000" height="2.382467" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="1.396000" y="0.978000" height="2.382467" />
|
||||
<point x="1.402997" y="-1.441500" height="2.382467" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="-0.520000" y="3.458500" height="2.382467" />
|
||||
<point x="-0.505800" y="0.968600" height="2.382467" />
|
||||
<type>interior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="1.390000" y="4.280000" height="2.382467" />
|
||||
<point x="1.528000" y="4.280000" height="2.382467" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<door type="0" x1="0.801562" y1="3.458304" x2="0.128462" y2="3.458195" width="0.673100" depth="0.131400" height="0.060000" insetX="0.000000" insetY="0.060000" orientation="2" symbolInstance="W-0-1" />
|
||||
<door type="2" x1="-0.519034" y1="3.292995" x2="-0.518158" y2="2.545036" width="0.747960" depth="0.747960" height="2.074757" insetX="0.000000" insetY="0.000000" orientation="0" symbolInstance="W-0-0" />
|
||||
<door type="2" x1="-0.694971" y1="0.983772" x2="-1.419046" y2="0.983416" width="0.724080" depth="0.724080" height="2.081704" insetX="0.000000" insetY="0.000000" orientation="0" symbolInstance="W-1-0" />
|
||||
<window type="1" x1="-1.219716" y1="-1.457780" x2="0.704754" y2="-1.446953" width="1.924500" depth="0.120000" height="0.883190" insetX="0.000000" insetY="-0.060000" orientation="0" symbolInstance="W-1-1" />
|
||||
<furniture type="0" x="0.050700" y="-1.337260" angle="0.000000" width="1.000000" depth="0.106000" height="0.600000" symbolInstance="F-1-0" />
|
||||
<furniture type="0" x="-2.048190" y="-1.044120" angle="0.000000" width="0.713860" depth="0.582300" height="1.000000" symbolInstance="F-1-1" />
|
||||
<door type="2" x1="-0.650374" y1="3.459417" x2="-1.419574" y2="3.458999" width="0.769200" depth="0.769200" height="2.195494" insetX="0.000000" insetY="0.000000" orientation="0" symbolInstance="W-2-2" />
|
||||
<door type="0" x1="1.527685" y1="5.468966" x2="1.527680" y2="6.722916" width="1.253950" depth="0.100000" height="0.676758" insetX="0.000000" insetY="0.060000" orientation="2" symbolInstance="W-3-2" />
|
||||
<window type="1" x1="0.788778" y1="6.778432" x2="-1.628792" y2="6.778438" width="2.417570" depth="0.120000" height="1.180143" insetX="0.000000" insetY="-0.060000" orientation="0" symbolInstance="W-3-1" />
|
||||
<furniture type="0" x="-0.580790" y="6.665440" angle="3.141590" width="1.000000" depth="0.106000" height="0.600000" symbolInstance="F-3-0" />
|
||||
</exploded>
|
||||
</floor>
|
||||
<interiorRoomPoints>
|
||||
<floor uid="69e5fb20.4feef7ff" floorType="0" rotation="0.00000" compassAngle="-1.000000" areaWithoutWalls="40.20736" areaWithInteriorWallsOnly="40.67878" areaWithWalls="48.40593">
|
||||
<name>Ground Floor</name>
|
||||
<symbolInstance id="floor" uid="69e5fb20.4feef7ff" parentUid="" symbol="floor">
|
||||
<values>
|
||||
<value key="ceilingHeight">2.323164</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-0-0" uid="69e5fbc8.711517ff" parentUid="" symbol="doordoublehinged">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">doors</value>
|
||||
<value key="wallItemHeight">2.084107</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-0-1" uid="69e5fbc8.71336fff" parentUid="" symbol="doorhinged">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">doors</value>
|
||||
<value key="wallItemHeight">2.02225</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-0-2" uid="69e5fbc8.713b47ff" parentUid="" symbol="windowfixed">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">doors</value>
|
||||
<value key="wallItemDistanceToFloor">1.124639</value>
|
||||
<value key="wallItemHeight">0.949396</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-0-3" uid="69e5fbc8.73e407ff" parentUid="" symbol="furniture-3740ec67-24f6-42e6-b7f9-40a88d3f84ee">
|
||||
<values>
|
||||
<value key="depth">0.397258</value>
|
||||
<value key="height">0.746826</value>
|
||||
<value key="symbolfilePrefix">furniture</value>
|
||||
<value key="wallItemDistanceToFloor">1.279293</value>
|
||||
<value key="wallItemHeight">0.746826</value>
|
||||
<value key="width">0.677733</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-0-4" uid="69e5fbc8.7408c7ff" parentUid="" symbol="furniture-3740ec67-24f6-42e6-b7f9-40a88d3f84ee">
|
||||
<values>
|
||||
<value key="depth">0.368615</value>
|
||||
<value key="height">0.723145</value>
|
||||
<value key="symbolfilePrefix">furniture</value>
|
||||
<value key="wallItemDistanceToFloor">1.311519</value>
|
||||
<value key="wallItemHeight">0.723145</value>
|
||||
<value key="width">0.398439</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-0-5" uid="69e5fbc8.742773ff" parentUid="" symbol="furniture-3740ec67-24f6-42e6-b7f9-40a88d3f84ee">
|
||||
<values>
|
||||
<value key="depth">0.604444</value>
|
||||
<value key="height">0.1</value>
|
||||
<value key="symbolfilePrefix">furniture</value>
|
||||
<value key="wallItemDistanceToFloor">0.851311</value>
|
||||
<value key="wallItemHeight">0.1</value>
|
||||
<value key="width">0.601075</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="F-0-0" uid="69e5fbc8.73d847ff" parentUid="" symbol="furniture-8285a785-4b2a-4a2a-904b-5fd5d91551d4">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">furniture</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="F-0-1" uid="69e5fbc8.73dfd3ff" parentUid="" symbol="appliances-378151a6-3e37-477c-a52d-7786fcff365a">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">appliances</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="F-0-2" uid="69e5fbc8.7400c7ff" parentUid="" symbol="appliances-f4803db0-8455-424c-a414-05a5498b9288">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">appliances</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="F-0-3" uid="69e5fbc8.7404e7ff" parentUid="" symbol="appliances-af014f7b-2135-4206-995c-7747bb425ed5">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">appliances</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="F-0-4" uid="69e5fdc5.226b2fff" parentUid="" symbol="hvac-650c5bce-e5fd-48e9-b3f9-1180a0f66cbc">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">hvac</value>
|
||||
<value key="wallItemDistanceToFloor">0.1500</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-1-0" uid="69e5fbc8.74614fff" parentUid="" symbol="doordoublehinged">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">doors</value>
|
||||
<value key="wallItemHeight">2.084107</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-1-1" uid="69e5fbc8.746863ff" parentUid="" symbol="doorhinged">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">doors</value>
|
||||
<value key="wallItemHeight">2.006357</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-1-2" uid="69e5fbc8.746f47ff" parentUid="" symbol="windowfixed">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">doors</value>
|
||||
<value key="wallItemDistanceToFloor">1.00597</value>
|
||||
<value key="wallItemHeight">1.026259</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="F-1-0" uid="69e5fbc8.7496abff" parentUid="" symbol="appliances-fee6a83d-7365-4cb3-89cb-26ffea1099e3">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">appliances</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="F-1-1" uid="69e5fbc8.74a363ff" parentUid="" symbol="furniture-f4c1d117-d87f-4ca4-b70f-7c1216e07f6d">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">furniture</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="F-1-2" uid="69e5fbc8.74a783ff" parentUid="" symbol="hvac-1489fe06-b5c5-40ce-b7fa-c0555750d8c9">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">hvac</value>
|
||||
<value key="wallItemDistanceToFloor">0.0000</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="F-1-3" uid="69e5fd95.4fd913ff" parentUid="" symbol="hvac-650c5bce-e5fd-48e9-b3f9-1180a0f66cbc">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">hvac</value>
|
||||
<value key="wallItemDistanceToFloor">0.1500</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="F-1-4" uid="69e5fda8.2e9b47ff" parentUid="" symbol="hvac-650c5bce-e5fd-48e9-b3f9-1180a0f66cbc">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">hvac</value>
|
||||
<value key="wallItemDistanceToFloor">0.1500</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<floorRoom type="Kitchen" uid="69e5fbc8.71027bff" x="3.80616" y="0.23162" rotation="0.00000" wasModified="0" linkedRoom0="-1" linkedRoom1="-1" area="10.78332" perimeter="13.32812">
|
||||
<values>
|
||||
<value key="ceilingHeight">2.323164</value>
|
||||
</values>
|
||||
<point snappedX="-1.38357" snappedY="-1.94846" height="2.323164" uid="69e5fbc8.710363ff" />
|
||||
<point snappedX="1.38357" snappedY="-1.94846" height="2.323164" uid="69e5fbc8.710a67ff" />
|
||||
<point snappedX="1.38357" snappedY="1.94846" height="2.323164" uid="69e5fbc8.710e47ff" />
|
||||
<point snappedX="-1.38357" snappedY="1.94846" height="2.323164" uid="69e5fbc8.7111afff" />
|
||||
<door point="3" type="4" u="0.47585" width="1.82394" depth="0.91197" height="2.08411" orientation="3" snappedType="4" snappedPosition="0.47585" snappedWidth="1.82394" snappedDepth="0.91197" snappedHeight="2.08411" snappedOrientation="3" insetX="0.00000" insetY="0.00000" insetZ="0.00000" twinWallItemUid="69e5fbc8.74614fff" symbolInstance="W-0-0" />
|
||||
<door point="1" type="2" u="0.19764" width="0.77300" depth="0.77300" height="2.02225" orientation="0" snappedType="2" snappedPosition="0.19764" snappedWidth="0.77300" snappedDepth="0.77300" snappedHeight="2.02225" snappedOrientation="0" insetX="0.00000" insetY="0.00000" insetZ="0.00000" symbolInstance="W-0-1" />
|
||||
<window point="1" type="1" u="0.68463" width="1.71972" depth="0.12000" height="0.94940" orientation="0" snappedType="1" snappedPosition="0.68463" snappedWidth="1.71972" snappedDepth="0.12000" snappedHeight="0.94940" snappedOrientation="0" insetX="0.00000" insetY="-0.06000" insetZ="-0.06000" symbolInstance="W-0-2" />
|
||||
<door point="2" type="0" u="0.14195" width="0.67773" depth="0.39726" height="0.74683" orientation="2" snappedType="0" snappedPosition="0.14195" snappedWidth="0.67773" snappedDepth="0.39726" snappedHeight="0.74683" snappedOrientation="2" insetX="0.00000" insetY="0.03000" insetZ="0.03000" symbolInstance="W-0-3" />
|
||||
<door point="2" type="0" u="0.63071" width="0.39844" depth="0.36861" height="0.72315" orientation="2" snappedType="0" snappedPosition="0.63071" snappedWidth="0.39844" snappedDepth="0.36861" snappedHeight="0.72315" snappedOrientation="2" insetX="0.00000" insetY="0.03000" insetZ="0.03000" symbolInstance="W-0-4" />
|
||||
<door point="2" type="0" u="0.40931" width="0.60107" depth="0.60444" height="0.10000" orientation="2" snappedType="0" snappedPosition="0.40931" snappedWidth="0.60107" snappedDepth="0.60444" snappedHeight="0.10000" snappedOrientation="2" insetX="0.00000" insetY="0.03000" insetZ="0.03000" symbolInstance="W-0-5" />
|
||||
<furniture type="0" x="-0.37437" y="1.64301" snappedX="-0.37437" snappedY="1.64301" angle="3.14159" width="0.73174" depth="0.61090" height="0.83418" snappedWidth="0.73174" snappedDepth="0.61090" snappedHeight="0.83418" sizeLock0="0" sizeLock1="0" sizeLock2="0" symbolInstance="F-0-0" />
|
||||
<furniture type="0" x="-1.07415" y="1.66141" snappedX="-1.07415" snappedY="1.66141" angle="3.14159" width="0.53467" depth="0.58310" height="1.30356" snappedWidth="0.53467" snappedDepth="0.58310" snappedHeight="1.30356" sizeLock0="0" sizeLock1="0" sizeLock2="0" symbolInstance="F-0-1" />
|
||||
<furniture type="0" x="0.29204" y="1.64624" snappedX="0.29204" snappedY="1.64624" angle="3.14159" width="0.60107" depth="0.60444" height="0.85131" snappedWidth="0.60107" snappedDepth="0.60444" snappedHeight="0.85131" sizeLock0="0" sizeLock1="0" sizeLock2="0" symbolInstance="F-0-2" />
|
||||
<furniture type="0" x="-1.02621" y="-1.62776" snappedX="-1.02621" snappedY="-1.62776" angle="0.00000" width="0.59317" depth="0.64140" height="0.80396" snappedWidth="0.59317" snappedDepth="0.64140" snappedHeight="0.80396" sizeLock0="0" sizeLock1="0" sizeLock2="0" symbolInstance="F-0-3" />
|
||||
<furniture type="0" x="0.10449" y="-1.89546" snappedX="0.10449" snappedY="-1.89546" angle="0.00000" width="1.00000" depth="0.10600" height="0.60000" snappedWidth="1.00000" snappedDepth="0.10600" snappedHeight="0.60000" sizeLock0="0" sizeLock1="0" sizeLock2="0" symbolInstance="F-0-4" />
|
||||
<mainDimension from="0" to="1" dir.x="-1.0000000000" dir.y="-0.0000000000" value="2.7671400000" actualValue="2.7671400000" isSet="0" />
|
||||
<mainDimension from="1" to="2" dir.x="-0.0000000000" dir.y="-1.0000000000" value="3.8969200000" actualValue="3.8969200000" isSet="0" />
|
||||
</floorRoom>
|
||||
<floorRoom type="Living Room" uid="69e5fbc8.74487bff" x="-1.61210" y="0.23162" rotation="0.00000" wasModified="0" linkedRoom0="-1" linkedRoom1="-1" area="29.44518" perimeter="24.13895">
|
||||
<values>
|
||||
<value key="ceilingHeight">3.285283</value>
|
||||
</values>
|
||||
<point snappedX="-3.91469" snappedY="-1.94846" height="3.285283" uid="69e5fbc8.7448bbff" />
|
||||
<point snappedX="3.91469" snappedY="-1.94846" height="3.285283" uid="69e5fbc8.744c47ff" />
|
||||
<point snappedX="3.91469" snappedY="1.94846" height="3.285283" uid="69e5fbc8.744f5bff" />
|
||||
<point snappedX="0.25116" snappedY="1.94846" height="3.285283" uid="69e5fbc8.745263ff" />
|
||||
<point snappedX="0.25116" snappedY="1.47785" height="3.285283" uid="69e5fbc8.74554fff" />
|
||||
<point snappedX="-1.61734" snappedY="1.47785" height="3.285283" uid="69e5fbc8.745867ff" />
|
||||
<point snappedX="-1.75971" snappedY="1.87998" height="3.285283" uid="69e5fbc8.745b7fff" />
|
||||
<point snappedX="-3.91469" snappedY="1.87998" height="3.285283" uid="69e5fbc8.745e5fff" />
|
||||
<door point="1" type="4" u="0.52415" width="1.82394" depth="0.91197" height="2.08411" orientation="0" snappedType="4" snappedPosition="0.52415" snappedWidth="1.82394" snappedDepth="0.91197" snappedHeight="2.08411" snappedOrientation="0" insetX="0.00000" insetY="0.00000" insetZ="0.00000" twinWallItemUid="69e5fbc8.711517ff" symbolInstance="W-1-0" />
|
||||
<door point="7" type="2" u="0.81578" width="0.83113" depth="0.83113" height="2.00636" orientation="0" snappedType="2" snappedPosition="0.81578" snappedWidth="0.83113" snappedDepth="0.83113" snappedHeight="2.00636" snappedOrientation="0" insetX="0.00000" insetY="0.00000" insetZ="0.00000" symbolInstance="W-1-1" />
|
||||
<window point="7" type="1" u="0.46552" width="1.85077" depth="0.12000" height="1.02626" orientation="0" snappedType="1" snappedPosition="0.46552" snappedWidth="1.85077" snappedDepth="0.12000" snappedHeight="1.02626" snappedOrientation="0" insetX="0.00000" insetY="-0.06000" insetZ="-0.06000" symbolInstance="W-1-2" />
|
||||
<furniture type="0" x="-3.26415" y="1.35928" snappedX="-3.26415" snappedY="1.35928" angle="3.72376" width="1.10000" depth="0.26400" height="0.71600" snappedWidth="1.10000" snappedDepth="0.26400" snappedHeight="0.71600" sizeLock0="0" sizeLock1="0" sizeLock2="0" symbolInstance="F-1-0" />
|
||||
<furniture type="0" x="-3.33464" y="1.37128" snappedX="-3.33464" snappedY="1.37128" angle="3.80141" width="1.01832" depth="0.49767" height="0.57273" snappedWidth="1.01832" snappedDepth="0.49767" snappedHeight="0.57273" sizeLock0="0" sizeLock1="0" sizeLock2="0" symbolInstance="F-1-1" />
|
||||
<furniture type="0" x="-0.60840" y="1.42589" snappedX="-0.60840" snappedY="1.42589" angle="3.14159" width="1.11379" depth="0.42391" height="1.10296" snappedWidth="1.11379" snappedDepth="0.42391" snappedHeight="1.10296" sizeLock0="0" sizeLock1="0" sizeLock2="0" symbolInstance="F-1-2" />
|
||||
<furniture type="0" x="2.08331" y="1.89546" snappedX="2.08331" snappedY="1.89546" angle="3.14159" width="1.00000" depth="0.10600" height="0.60000" snappedWidth="1.00000" snappedDepth="0.10600" snappedHeight="0.60000" sizeLock0="0" sizeLock1="0" sizeLock2="0" symbolInstance="F-1-3" />
|
||||
<furniture type="0" x="-3.86169" y="0.04424" snappedX="-3.86169" snappedY="0.04424" angle="4.71239" width="1.00000" depth="0.10600" height="0.60000" snappedWidth="1.00000" snappedDepth="0.10600" snappedHeight="0.60000" sizeLock0="0" sizeLock1="0" sizeLock2="0" symbolInstance="F-1-4" />
|
||||
<mainDimension from="0" to="1" dir.x="-1.0000000000" dir.y="-0.0000000000" value="7.8293800000" actualValue="7.8293800000" isSet="0" />
|
||||
<mainDimension from="1" to="2" dir.x="-0.0000000000" dir.y="-1.0000000000" value="3.8969200000" actualValue="3.8969200000" isSet="0" />
|
||||
</floorRoom>
|
||||
<exploded>
|
||||
<wall>
|
||||
<point x="2.363000" y="-1.778000" height="2.323164" />
|
||||
<point x="-5.586000" y="-1.777000" height="2.323164" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="5.249000" y="-1.777000" height="2.323164" />
|
||||
<point x="2.363000" y="-1.778000" height="2.323164" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="2.363000" y="2.240000" height="2.323164" />
|
||||
<point x="5.249000" y="2.239000" height="2.323164" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="-1.421000" y="2.239000" height="2.323164" />
|
||||
<point x="2.363000" y="2.240000" height="2.323164" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="5.249000" y="2.239000" height="2.323164" />
|
||||
<point x="5.249000" y="-1.777000" height="2.323164" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="-5.586000" y="-1.777000" height="2.323164" />
|
||||
<point x="-5.586000" y="2.170000" height="2.323164" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="2.363000" y="-1.778000" height="2.323164" />
|
||||
<point x="2.363000" y="2.240000" height="2.323164" />
|
||||
<type>interior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="-5.586000" y="2.170000" height="2.323164" />
|
||||
<point x="-3.328500" y="2.170000" height="2.323164" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="-1.421000" y="1.768000" height="2.323164" />
|
||||
<point x="-3.186500" y="1.768000" height="2.323164" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="-1.421000" y="1.768000" height="2.323164" />
|
||||
<point x="-1.421000" y="2.239000" height="2.323164" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="-3.328500" y="2.170000" height="2.323164" />
|
||||
<point x="-3.186500" y="1.768000" height="2.323164" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<door type="2" x1="5.249730" y1="-1.333153" x2="5.249730" y2="-0.560153" width="0.773000" depth="0.773000" height="2.022250" insetX="0.000000" insetY="0.000000" orientation="0" symbolInstance="W-0-1" />
|
||||
<window type="1" x1="5.249730" y1="0.091248" x2="5.249730" y2="1.810968" width="1.719720" depth="0.120000" height="0.949396" insetX="0.000000" insetY="-0.060000" orientation="0" symbolInstance="W-0-2" />
|
||||
<door type="0" x1="5.135799" y1="2.240080" x2="4.458069" y2="2.240080" width="0.677730" depth="0.397260" height="0.746826" insetX="0.000000" insetY="0.060000" orientation="2" symbolInstance="W-0-3" />
|
||||
<door type="0" x1="3.643687" y1="2.240080" x2="3.245247" y2="2.240080" width="0.398440" depth="0.368610" height="0.723145" insetX="0.000000" insetY="0.060000" orientation="2" symbolInstance="W-0-4" />
|
||||
<door type="0" x1="4.357647" y1="2.240080" x2="3.756577" y2="2.240080" width="0.601070" depth="0.604440" height="0.100000" insetX="0.000000" insetY="0.060000" orientation="2" symbolInstance="W-0-5" />
|
||||
<furniture type="0" x="3.431790" y="1.874630" angle="3.141590" width="0.731740" depth="0.610900" height="0.834180" symbolInstance="F-0-0" />
|
||||
<furniture type="0" x="2.732010" y="1.893030" angle="3.141590" width="0.534670" depth="0.583097" height="1.303560" symbolInstance="F-0-1" />
|
||||
<furniture type="0" x="4.098200" y="1.877860" angle="3.141590" width="0.601070" depth="0.604440" height="0.851310" symbolInstance="F-0-2" />
|
||||
<furniture type="0" x="2.779950" y="-1.396140" angle="0.000000" width="0.593170" depth="0.641400" height="0.803960" symbolInstance="F-0-3" />
|
||||
<furniture type="0" x="3.910650" y="-1.663840" angle="0.000000" width="1.000000" depth="0.106000" height="0.600000" symbolInstance="F-0-4" />
|
||||
<door type="2" x1="-5.586790" y1="-0.596000" x2="-5.586790" y2="-1.427130" width="0.831130" depth="0.831130" height="2.006357" insetX="0.000000" insetY="0.000000" orientation="0" symbolInstance="W-1-1" />
|
||||
<window type="1" x1="-5.586790" y1="1.254770" x2="-5.586790" y2="-0.596000" width="1.850770" depth="0.120000" height="1.026259" insetX="0.000000" insetY="-0.060000" orientation="0" symbolInstance="W-1-2" />
|
||||
<door type="4" x1="2.362590" y1="-0.586239" x2="2.362590" y2="1.237701" width="1.823940" depth="0.911970" height="2.084107" insetX="0.000000" insetY="0.000000" orientation="0" symbolInstance="W-1-0" />
|
||||
<furniture type="0" x="-4.876250" y="1.590900" angle="3.723760" width="1.100000" depth="0.264000" height="0.716000" symbolInstance="F-1-0" />
|
||||
<furniture type="0" x="-4.946740" y="1.602900" angle="3.801410" width="1.018320" depth="0.497670" height="0.572730" symbolInstance="F-1-1" />
|
||||
<furniture type="0" x="-2.220500" y="1.657510" angle="3.141590" width="1.113790" depth="0.423910" height="1.102960" symbolInstance="F-1-2" />
|
||||
<furniture type="0" x="0.471210" y="2.127080" angle="3.141590" width="1.000000" depth="0.106000" height="0.600000" symbolInstance="F-1-3" />
|
||||
<furniture type="0" x="-5.473790" y="0.275860" angle="4.712390" width="1.000000" depth="0.106000" height="0.600000" symbolInstance="F-1-4" />
|
||||
</exploded>
|
||||
</floor>
|
||||
<floor uid="69e5fbdd.882287ff" floorType="1" rotation="0.00000" compassAngle="-1.000000" areaWithoutWalls="29.34605" areaWithInteriorWallsOnly="30.52809" areaWithWalls="36.77256">
|
||||
<name>1st Floor</name>
|
||||
<symbolInstance id="floor" uid="69e5fbdd.882287ff" parentUid="" symbol="floor">
|
||||
<values>
|
||||
<value key="ceilingHeight">2.382467</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-0-0" uid="69e5fcf6.09fe63ff" parentUid="" symbol="doorhinged">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">doors</value>
|
||||
<value key="wallItemHeight">2.074757</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-0-1" uid="69e5fd68.8e2f33ff" parentUid="" symbol="plumbing-08aa18c5-ec1c-48f3-be68-431c07d4576c">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">plumbing</value>
|
||||
<value key="wallItemDistanceToFloor">1.5000</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-1-0" uid="69e5fcf6.09e257ff" parentUid="" symbol="doorhinged">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">doors</value>
|
||||
<value key="wallItemHeight">2.081704</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-1-1" uid="69e5fcf6.0a0f3bff" parentUid="" symbol="windowfixed">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">doors</value>
|
||||
<value key="wallItemDistanceToFloor">1.227592</value>
|
||||
<value key="wallItemHeight">0.88319</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="F-1-0" uid="69e5fd3d.4b9d17ff" parentUid="" symbol="hvac-650c5bce-e5fd-48e9-b3f9-1180a0f66cbc">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">hvac</value>
|
||||
<value key="wallItemDistanceToFloor">0.1500</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="F-1-1" uid="69e5fe3e.2db4abff" parentUid="" symbol="co-ed10aa18-b3ce-4f51-a5e8-9f0051663885">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">677d01685458a</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-2-0" uid="69e5fcf6.09e257ff.auto" parentUid="" symbol="doorhinged">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">doors</value>
|
||||
<value key="wallItemHeight">2.081704</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-2-1" uid="69e5fcf6.09fe63ff.auto" parentUid="" symbol="doorhinged">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">doors</value>
|
||||
<value key="wallItemHeight">2.074757</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-2-2" uid="69e5fcf6.0a077fff" parentUid="" symbol="doorhinged">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">doors</value>
|
||||
<value key="wallItemHeight">2.195494</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-3-0" uid="69e5fcf6.0a077fff.auto" parentUid="" symbol="doorhinged">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">doors</value>
|
||||
<value key="wallItemHeight">2.195494</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-3-1" uid="69e5fcf6.0b305fff" parentUid="" symbol="windowfixed">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">doors</value>
|
||||
<value key="wallItemDistanceToFloor">0.915306</value>
|
||||
<value key="wallItemHeight">1.180143</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="W-3-2" uid="69e5fcf6.0bf033ff" parentUid="" symbol="appliances-e648fc54-abba-402a-8313-f5523ec6e5cc">
|
||||
<values>
|
||||
<value key="depth">0.1</value>
|
||||
<value key="height">0.676758</value>
|
||||
<value key="symbolfilePrefix">appliances</value>
|
||||
<value key="wallItemDistanceToFloor">1.399472</value>
|
||||
<value key="wallItemHeight">0.676758</value>
|
||||
<value key="width">1.253952</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<symbolInstance id="F-3-0" uid="69e5fd4d.64215bff" parentUid="" symbol="hvac-650c5bce-e5fd-48e9-b3f9-1180a0f66cbc">
|
||||
<values>
|
||||
<value key="symbolfilePrefix">hvac</value>
|
||||
<value key="wallItemDistanceToFloor">0.1500</value>
|
||||
</values>
|
||||
</symbolInstance>
|
||||
<floorRoom type="Bathroom" uid="69e5fcf6.08bec3ff" x="0.43937" y="2.21959" rotation="0.00000" wasModified="0" linkedRoom0="-1" linkedRoom1="-1" area="4.22940" perimeter="8.30295">
|
||||
<values>
|
||||
<value key="ceilingHeight">2.382467</value>
|
||||
</values>
|
||||
<point snappedX="0.89732" snappedY="-1.17851" height="2.382467" uid="69e5fcf6.08c07bff" />
|
||||
<point snappedX="0.89667" snappedY="1.17880" height="2.382467" uid="69e5fcf6.08d4cbff" />
|
||||
<point snappedX="-0.89732" snappedY="1.17851" height="2.382467" uid="69e5fcf6.08ce4bff" />
|
||||
<point snappedX="-0.89702" snappedY="-1.17880" height="2.382467" uid="69e5fcf6.08ca9fff" />
|
||||
<door point="2" type="2" u="0.20319" width="0.74796" depth="0.74796" height="2.07476" orientation="0" snappedType="2" snappedPosition="0.20319" snappedWidth="0.74796" snappedDepth="0.74796" snappedHeight="2.07476" snappedOrientation="0" insetX="0.00000" insetY="0.00000" insetZ="0.00000" twinWallItemUid="69e5fcf6.09fe63ff.auto" symbolInstance="W-0-0" />
|
||||
<door point="1" type="0" u="0.48552" width="0.67310" depth="0.13140" height="0.06000" orientation="2" snappedType="0" snappedPosition="0.48552" snappedWidth="0.67310" snappedDepth="0.13140" snappedHeight="0.06000" snappedOrientation="2" insetX="0.00000" insetY="0.03000" insetZ="0.03000" symbolInstance="W-0-1" />
|
||||
<mainDimension from="1" to="2" dir.x="-0.9999999620" dir.y="-0.0002757380" value="1.7943400118" actualValue="1.7943400118" isSet="0" />
|
||||
<mainDimension from="0" to="1" dir.x="0.0002757380" dir.y="-0.9999999620" value="2.3575147609" actualValue="2.3575147609" isSet="0" />
|
||||
</floorRoom>
|
||||
<floorRoom type="Closet" uid="69e5fcf6.08d80fff" x="-0.53200" y="-0.23894" rotation="0.00000" wasModified="1" linkedRoom0="-1" linkedRoom1="-1" area="8.65802" perimeter="12.11130">
|
||||
<values>
|
||||
<value key="ceilingHeight">2.382467</value>
|
||||
</values>
|
||||
<point snappedX="1.86855" snappedY="1.15253" height="2.382467" uid="69e5fcf6.08d833ff" />
|
||||
<point snappedX="-1.86438" snappedY="1.16552" height="2.382467" uid="69e5fcf6.08e7bbff" />
|
||||
<point snappedX="-1.87513" snappedY="-1.16552" height="2.382467" uid="69e5fcf6.08f1d3ff" />
|
||||
<point snappedX="1.87513" snappedY="-1.14442" height="2.382467" uid="69e5fcf6.08fa8bff" />
|
||||
<door point="0" type="2" u="0.64117" width="0.72408" depth="0.72408" height="2.08170" orientation="0" snappedType="2" snappedPosition="0.64117" snappedWidth="0.72408" snappedDepth="0.72408" snappedHeight="2.08170" snappedOrientation="0" insetX="0.00000" insetY="0.00000" insetZ="0.00000" twinWallItemUid="69e5fcf6.09e257ff.auto" symbolInstance="W-1-0" />
|
||||
<window point="2" type="1" u="0.57311" width="1.92450" depth="0.12000" height="0.88319" orientation="0" snappedType="1" snappedPosition="0.57311" snappedWidth="1.92450" snappedDepth="0.12000" snappedHeight="0.88319" snappedOrientation="0" insetX="0.00000" insetY="-0.06000" insetZ="-0.06000" symbolInstance="W-1-1" />
|
||||
<furniture type="0" x="0.58270" y="-1.09832" snappedX="0.58270" snappedY="-1.09832" angle="0.00000" width="1.00000" depth="0.10600" height="0.60000" snappedWidth="1.00000" snappedDepth="0.10600" snappedHeight="0.60000" sizeLock0="0" sizeLock1="0" sizeLock2="0" symbolInstance="F-1-0" />
|
||||
<furniture type="0" x="-1.51619" y="-0.80518" snappedX="-1.51619" snappedY="-0.80518" angle="0.00000" width="0.71386" depth="0.58230" height="1.00000" snappedWidth="0.71386" snappedDepth="0.58230" snappedHeight="1.00000" sizeLock0="0" sizeLock1="0" sizeLock2="0" symbolInstance="F-1-1" />
|
||||
<mainDimension from="2" to="3" dir.x="-0.9999939454" dir.y="0.0034798192" value="3.7501638695" actualValue="3.7501638695" isSet="0" />
|
||||
<mainDimension from="1" to="2" dir.x="-0.0034798192" dir.y="-0.9999939454" value="2.3310632946" actualValue="2.3310632946" isSet="0" />
|
||||
</floorRoom>
|
||||
<floorRoom type="Other" uid="69e5fcf6.0906ebff" x="-1.48831" y="2.21997" rotation="0.00000" wasModified="1" linkedRoom0="-1" linkedRoom1="-1" area="4.27518" perimeter="8.34147">
|
||||
<values>
|
||||
<value key="ceilingHeight">2.382467</value>
|
||||
</values>
|
||||
<point snappedX="0.91315" snappedY="-1.17255" height="2.382467" uid="69e5fcf6.09070fff" />
|
||||
<point snappedX="0.90794" snappedY="1.18070" height="2.382467" uid="69e5fcf6.09143bff" />
|
||||
<point snappedX="-0.89443" snappedY="1.17874" height="2.382467" uid="69e5fcf6.09106fff" />
|
||||
<point snappedX="-0.91316" snappedY="-1.18070" height="2.382467" uid="69e5fcf6.090d5bff" />
|
||||
<door point="3" type="2" u="0.73610" width="0.72408" depth="0.72408" height="2.08170" orientation="3" snappedType="2" snappedPosition="0.73610" snappedWidth="0.72408" snappedDepth="0.72408" snappedHeight="2.08170" snappedOrientation="3" insetX="0.00000" insetY="0.00000" insetZ="0.00000" twinWallItemUid="69e5fcf6.09e257ff" symbolInstance="W-2-0" />
|
||||
<door point="0" type="2" u="0.79528" width="0.74796" depth="0.74796" height="2.07476" orientation="3" snappedType="2" snappedPosition="0.79528" snappedWidth="0.74796" snappedDepth="0.74796" snappedHeight="2.07476" snappedOrientation="3" insetX="0.00000" insetY="0.00000" insetZ="0.00000" twinWallItemUid="69e5fcf6.09fe63ff" symbolInstance="W-2-1" />
|
||||
<door point="1" type="2" u="0.25222" width="0.76920" depth="0.76920" height="2.19549" orientation="0" snappedType="2" snappedPosition="0.25222" snappedWidth="0.76920" snappedDepth="0.76920" snappedHeight="2.19549" snappedOrientation="0" insetX="0.00000" insetY="0.00000" insetZ="0.00000" twinWallItemUid="69e5fcf6.0a077fff.auto" symbolInstance="W-2-2" />
|
||||
<mainDimension from="3" to="0" dir.x="-0.9999975492" dir.y="-0.0022139540" value="1.8263235678" actualValue="1.8263235678" isSet="0" />
|
||||
<mainDimension from="2" to="3" dir.x="0.0022139540" dir.y="-0.9999975492" value="2.3593927501" actualValue="2.3593927501" isSet="0" />
|
||||
</floorRoom>
|
||||
<floorRoom type="Bedroom" uid="69e5fcf6.091a43ff" x="-0.45645" y="5.11834" rotation="0.00000" wasModified="0" linkedRoom0="-1" linkedRoom1="-1" area="12.19886" perimeter="14.09693">
|
||||
<values>
|
||||
<value key="ceilingHeight">2.382467</value>
|
||||
</values>
|
||||
<point snappedX="1.92414" snappedY="-0.77873" height="2.382467" uid="69e5fcf6.091adbff" />
|
||||
<point snappedX="1.92413" snappedY="1.60009" height="2.382467" uid="69e5fcf6.091efbff" />
|
||||
<point snappedX="-1.92413" snappedY="1.60010" height="2.382467" uid="69e5fcf6.092f4bff" />
|
||||
<point snappedX="-1.92414" snappedY="-1.60010" height="2.382467" uid="69e5fcf6.0975d3ff" />
|
||||
<point snappedX="1.78248" snappedY="-1.60010" height="2.382467" uid="69e5fcf6.098c6bff" />
|
||||
<point snappedX="1.78248" snappedY="-0.77873" height="2.382467" uid="69e5fcf6.099a0fff" />
|
||||
<door point="3" type="2" u="0.36303" width="0.76920" depth="0.76920" height="2.19549" orientation="3" snappedType="2" snappedPosition="0.36303" snappedWidth="0.76920" snappedDepth="0.76920" snappedHeight="2.19549" snappedOrientation="3" insetX="0.00000" insetY="0.00000" insetZ="0.00000" twinWallItemUid="69e5fcf6.0a077fff" symbolInstance="W-3-0" />
|
||||
<window point="1" type="1" u="0.49053" width="2.41757" depth="0.12000" height="1.18014" orientation="0" snappedType="1" snappedPosition="0.49053" snappedWidth="2.41757" snappedDepth="0.12000" snappedHeight="1.18014" snappedOrientation="0" insetX="0.00000" insetY="-0.06000" insetZ="-0.06000" symbolInstance="W-3-1" />
|
||||
<door point="0" type="0" u="0.73832" width="1.25395" depth="0.10000" height="0.67676" orientation="2" snappedType="0" snappedPosition="0.73832" snappedWidth="1.25395" snappedDepth="0.10000" snappedHeight="0.67676" snappedOrientation="2" insetX="0.00000" insetY="0.03000" insetZ="0.03000" symbolInstance="W-3-2" />
|
||||
<furniture type="0" x="-0.12434" y="1.54710" snappedX="-0.12434" snappedY="1.54710" angle="3.14159" width="1.00000" depth="0.10600" height="0.60000" snappedWidth="1.00000" snappedDepth="0.10600" snappedHeight="0.60000" sizeLock0="0" sizeLock1="0" sizeLock2="0" symbolInstance="F-3-0" />
|
||||
<mainDimension from="1" to="2" dir.x="-1.0000000000" dir.y="-0.0000042038" value="3.8482834528" actualValue="3.8482834528" isSet="0" />
|
||||
<mainDimension from="2" to="3" dir.x="0.0000042038" dir.y="-1.0000000000" value="3.2002155817" actualValue="3.2002155817" isSet="0" />
|
||||
</floorRoom>
|
||||
<exploded>
|
||||
<wall>
|
||||
<point x="-2.461000" y="0.983500" height="2.382467" />
|
||||
<point x="-2.500460" y="3.458000" height="2.382467" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="-2.474000" y="-1.463000" height="2.382467" />
|
||||
<point x="-2.461000" y="0.983500" height="2.382467" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="-2.440000" y="6.778000" height="2.382467" />
|
||||
<point x="1.528000" y="6.778000" height="2.382467" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="1.402997" y="-1.441500" height="2.382467" />
|
||||
<point x="-2.474000" y="-1.463000" height="2.382467" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="-0.505800" y="0.968600" height="2.382467" />
|
||||
<point x="-2.461000" y="0.983500" height="2.382467" />
|
||||
<type>interior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="1.396000" y="0.978000" height="2.382467" />
|
||||
<point x="-0.505800" y="0.968600" height="2.382467" />
|
||||
<type>interior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="-0.520000" y="3.458500" height="2.382467" />
|
||||
<point x="1.394500" y="3.458000" height="2.382467" />
|
||||
<type>interior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="-2.500460" y="3.458000" height="2.382467" />
|
||||
<point x="-0.520000" y="3.458500" height="2.382467" />
|
||||
<type>interior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="-2.500460" y="3.458000" height="2.382467" />
|
||||
<point x="-2.440000" y="6.778000" height="2.382467" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="1.394500" y="3.458000" height="2.382467" />
|
||||
<point x="1.396000" y="0.978000" height="2.382467" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="1.390000" y="4.280000" height="2.382467" />
|
||||
<point x="1.394500" y="3.458000" height="2.382467" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="1.528000" y="6.778000" height="2.382467" />
|
||||
<point x="1.528000" y="4.280000" height="2.382467" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="1.396000" y="0.978000" height="2.382467" />
|
||||
<point x="1.402997" y="-1.441500" height="2.382467" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="-0.520000" y="3.458500" height="2.382467" />
|
||||
<point x="-0.505800" y="0.968600" height="2.382467" />
|
||||
<type>interior</type>
|
||||
</wall>
|
||||
<wall>
|
||||
<point x="1.390000" y="4.280000" height="2.382467" />
|
||||
<point x="1.528000" y="4.280000" height="2.382467" />
|
||||
<type>exterior</type>
|
||||
</wall>
|
||||
<door type="0" x1="0.801562" y1="3.458304" x2="0.128462" y2="3.458195" width="0.673100" depth="0.131400" height="0.060000" insetX="0.000000" insetY="0.060000" orientation="2" symbolInstance="W-0-1" />
|
||||
<door type="2" x1="-0.519034" y1="3.292995" x2="-0.518158" y2="2.545036" width="0.747960" depth="0.747960" height="2.074757" insetX="0.000000" insetY="0.000000" orientation="0" symbolInstance="W-0-0" />
|
||||
<door type="2" x1="-0.694971" y1="0.983772" x2="-1.419046" y2="0.983416" width="0.724080" depth="0.724080" height="2.081704" insetX="0.000000" insetY="0.000000" orientation="0" symbolInstance="W-1-0" />
|
||||
<window type="1" x1="-1.219716" y1="-1.457780" x2="0.704754" y2="-1.446953" width="1.924500" depth="0.120000" height="0.883190" insetX="0.000000" insetY="-0.060000" orientation="0" symbolInstance="W-1-1" />
|
||||
<furniture type="0" x="0.050700" y="-1.337260" angle="0.000000" width="1.000000" depth="0.106000" height="0.600000" symbolInstance="F-1-0" />
|
||||
<furniture type="0" x="-2.048190" y="-1.044120" angle="0.000000" width="0.713860" depth="0.582300" height="1.000000" symbolInstance="F-1-1" />
|
||||
<door type="2" x1="-0.650374" y1="3.459417" x2="-1.419574" y2="3.458999" width="0.769200" depth="0.769200" height="2.195494" insetX="0.000000" insetY="0.000000" orientation="0" symbolInstance="W-2-2" />
|
||||
<door type="0" x1="1.527685" y1="5.468966" x2="1.527680" y2="6.722916" width="1.253950" depth="0.100000" height="0.676758" insetX="0.000000" insetY="0.060000" orientation="2" symbolInstance="W-3-2" />
|
||||
<window type="1" x1="0.788778" y1="6.778432" x2="-1.628792" y2="6.778438" width="2.417570" depth="0.120000" height="1.180143" insetX="0.000000" insetY="-0.060000" orientation="0" symbolInstance="W-3-1" />
|
||||
<furniture type="0" x="-0.580790" y="6.665440" angle="3.141590" width="1.000000" depth="0.106000" height="0.600000" symbolInstance="F-3-0" />
|
||||
</exploded>
|
||||
</floor>
|
||||
</interiorRoomPoints>
|
||||
</plan>
|
||||
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
|
|
@ -1,224 +0,0 @@
|
|||
import xml.etree.ElementTree as ET
|
||||
|
||||
from backend.magic_plan.models import (
|
||||
MagicPlanXMLDoor,
|
||||
MagicPlanXMLExploded,
|
||||
MagicPlanXMLExplodedOpening,
|
||||
MagicPlanXMLExplodedWall,
|
||||
MagicPlanXMLFloor,
|
||||
MagicPlanXMLFurniture,
|
||||
MagicPlanXMLMainDimension,
|
||||
MagicPlanXMLPlan,
|
||||
MagicPlanXMLRoom,
|
||||
MagicPlanXMLRoomPoint,
|
||||
MagicPlanXMLSymbolInstance,
|
||||
MagicPlanXMLWallPoint,
|
||||
MagicPlanXMLWindow,
|
||||
)
|
||||
|
||||
|
||||
def _values(el: ET.Element) -> dict[str, str]:
|
||||
return {v.get("key", ""): (v.text or "") for v in el.findall("values/value")}
|
||||
|
||||
|
||||
def _parse_room_point(el: ET.Element) -> MagicPlanXMLRoomPoint:
|
||||
return MagicPlanXMLRoomPoint(
|
||||
snapped_x=float(el.get("snappedX", "0")),
|
||||
snapped_y=float(el.get("snappedY", "0")),
|
||||
height=float(el.get("height", "0")),
|
||||
uid=el.get("uid", ""),
|
||||
values=_values(el),
|
||||
)
|
||||
|
||||
|
||||
def _parse_wall_point(el: ET.Element) -> MagicPlanXMLWallPoint:
|
||||
return MagicPlanXMLWallPoint(
|
||||
x=float(el.get("x", "0")),
|
||||
y=float(el.get("y", "0")),
|
||||
height=float(el.get("height", "0")),
|
||||
)
|
||||
|
||||
|
||||
def _parse_door(el: ET.Element) -> MagicPlanXMLDoor:
|
||||
return MagicPlanXMLDoor(
|
||||
wall_point_index=int(el.get("point", "0")),
|
||||
type=el.get("type", ""),
|
||||
u=float(el.get("u", "0")),
|
||||
width=float(el.get("width", "0")),
|
||||
depth=float(el.get("depth", "0")),
|
||||
height=float(el.get("height", "0")),
|
||||
orientation=int(el.get("orientation", "0")),
|
||||
snapped_type=el.get("snappedType", ""),
|
||||
snapped_position=float(el.get("snappedPosition", "0")),
|
||||
snapped_width=float(el.get("snappedWidth", "0")),
|
||||
snapped_depth=float(el.get("snappedDepth", "0")),
|
||||
snapped_height=float(el.get("snappedHeight", "0")),
|
||||
snapped_orientation=int(el.get("snappedOrientation", "0")),
|
||||
inset_x=float(el.get("insetX", "0")),
|
||||
inset_y=float(el.get("insetY", "0")),
|
||||
inset_z=float(el.get("insetZ", "0")),
|
||||
symbol_instance=el.get("symbolInstance", ""),
|
||||
twin_wall_item_uid=el.get("twinWallItemUid"),
|
||||
)
|
||||
|
||||
|
||||
def _parse_window(el: ET.Element) -> MagicPlanXMLWindow:
|
||||
return MagicPlanXMLWindow(
|
||||
wall_point_index=int(el.get("point", "0")),
|
||||
type=el.get("type", ""),
|
||||
u=float(el.get("u", "0")),
|
||||
width=float(el.get("width", "0")),
|
||||
depth=float(el.get("depth", "0")),
|
||||
height=float(el.get("height", "0")),
|
||||
orientation=int(el.get("orientation", "0")),
|
||||
snapped_type=el.get("snappedType", ""),
|
||||
snapped_position=float(el.get("snappedPosition", "0")),
|
||||
snapped_width=float(el.get("snappedWidth", "0")),
|
||||
snapped_depth=float(el.get("snappedDepth", "0")),
|
||||
snapped_height=float(el.get("snappedHeight", "0")),
|
||||
snapped_orientation=int(el.get("snappedOrientation", "0")),
|
||||
inset_x=float(el.get("insetX", "0")),
|
||||
inset_y=float(el.get("insetY", "0")),
|
||||
inset_z=float(el.get("insetZ", "0")),
|
||||
symbol_instance=el.get("symbolInstance", ""),
|
||||
)
|
||||
|
||||
|
||||
def _parse_exploded_opening(el: ET.Element) -> MagicPlanXMLExplodedOpening:
|
||||
return MagicPlanXMLExplodedOpening(
|
||||
type=el.get("type", ""),
|
||||
x1=float(el.get("x1", "0")),
|
||||
y1=float(el.get("y1", "0")),
|
||||
x2=float(el.get("x2", "0")),
|
||||
y2=float(el.get("y2", "0")),
|
||||
width=float(el.get("width", "0")),
|
||||
depth=float(el.get("depth", "0")),
|
||||
height=float(el.get("height", "0")),
|
||||
inset_x=float(el.get("insetX", "0")),
|
||||
inset_y=float(el.get("insetY", "0")),
|
||||
orientation=int(el.get("orientation", "0")),
|
||||
symbol_instance=el.get("symbolInstance", ""),
|
||||
)
|
||||
|
||||
|
||||
def _parse_furniture(el: ET.Element) -> MagicPlanXMLFurniture:
|
||||
return MagicPlanXMLFurniture(
|
||||
type=el.get("type", ""),
|
||||
x=float(el.get("x", "0")),
|
||||
y=float(el.get("y", "0")),
|
||||
snapped_x=float(el.get("snappedX", "0")),
|
||||
snapped_y=float(el.get("snappedY", "0")),
|
||||
angle=float(el.get("angle", "0")),
|
||||
width=float(el.get("width", "0")),
|
||||
depth=float(el.get("depth", "0")),
|
||||
height=float(el.get("height", "0")),
|
||||
snapped_width=float(el.get("snappedWidth", "0")),
|
||||
snapped_depth=float(el.get("snappedDepth", "0")),
|
||||
snapped_height=float(el.get("snappedHeight", "0")),
|
||||
size_lock_0=el.get("sizeLock0", ""),
|
||||
size_lock_1=el.get("sizeLock1", ""),
|
||||
size_lock_2=el.get("sizeLock2", ""),
|
||||
symbol_instance=el.get("symbolInstance", ""),
|
||||
)
|
||||
|
||||
|
||||
def _parse_main_dimension(el: ET.Element) -> MagicPlanXMLMainDimension:
|
||||
return MagicPlanXMLMainDimension(
|
||||
from_point=int(el.get("from", "0")),
|
||||
to_point=int(el.get("to", "0")),
|
||||
dir_x=float(el.get("dir.x", "0")),
|
||||
dir_y=float(el.get("dir.y", "0")),
|
||||
value=float(el.get("value", "0")),
|
||||
actual_value=float(el.get("actualValue", "0")),
|
||||
is_set=el.get("isSet", "0") == "1",
|
||||
)
|
||||
|
||||
|
||||
def _parse_exploded_wall(el: ET.Element) -> MagicPlanXMLExplodedWall:
|
||||
type_el = el.find("type")
|
||||
return MagicPlanXMLExplodedWall(
|
||||
wall_type=(type_el.text or "") if type_el is not None else "",
|
||||
points=[_parse_wall_point(p) for p in el.findall("point")],
|
||||
)
|
||||
|
||||
|
||||
def _parse_exploded(el: ET.Element) -> MagicPlanXMLExploded:
|
||||
return MagicPlanXMLExploded(
|
||||
walls=[_parse_exploded_wall(w) for w in el.findall("wall")],
|
||||
doors=[_parse_exploded_opening(d) for d in el.findall("door")],
|
||||
windows=[_parse_exploded_opening(w) for w in el.findall("window")],
|
||||
furniture=[_parse_furniture(f) for f in el.findall("furniture")],
|
||||
)
|
||||
|
||||
|
||||
def _parse_symbol_instance(el: ET.Element) -> MagicPlanXMLSymbolInstance:
|
||||
return MagicPlanXMLSymbolInstance(
|
||||
id=el.get("id", ""),
|
||||
uid=el.get("uid", ""),
|
||||
parent_uid=el.get("parentUid", ""),
|
||||
symbol=el.get("symbol", ""),
|
||||
values=_values(el),
|
||||
)
|
||||
|
||||
|
||||
def _parse_floor(el: ET.Element) -> MagicPlanXMLFloor:
|
||||
si_el = el.find("symbolInstance")
|
||||
exploded_el = el.find("exploded")
|
||||
return MagicPlanXMLFloor(
|
||||
uid=el.get("uid", ""),
|
||||
name=el.findtext("name") or "",
|
||||
floor_type=el.get("floorType", "0"),
|
||||
rotation=float(el.get("rotation", "0")),
|
||||
compass_angle=float(el.get("compassAngle", "0")),
|
||||
area_without_walls=float(el.get("areaWithoutWalls", "0")),
|
||||
area_with_interior_walls_only=float(el.get("areaWithInteriorWallsOnly", "0")),
|
||||
area_with_walls=float(el.get("areaWithWalls", "0")),
|
||||
symbol_instance=_parse_symbol_instance(si_el) if si_el is not None
|
||||
else MagicPlanXMLSymbolInstance(id="", uid="", parent_uid="", symbol="", values={}),
|
||||
rooms=[_parse_room(r) for r in el.findall("floorRoom")],
|
||||
furniture=[_parse_furniture(f) for f in el.findall("furniture")],
|
||||
exploded=_parse_exploded(exploded_el) if exploded_el is not None
|
||||
else MagicPlanXMLExploded(walls=[], doors=[], windows=[], furniture=[]),
|
||||
)
|
||||
|
||||
|
||||
def _parse_room(el: ET.Element) -> MagicPlanXMLRoom:
|
||||
return MagicPlanXMLRoom(
|
||||
uid=el.get("uid", ""),
|
||||
type=el.get("type", ""),
|
||||
x=float(el.get("x", "0")),
|
||||
y=float(el.get("y", "0")),
|
||||
rotation=float(el.get("rotation", "0")),
|
||||
was_modified=el.get("wasModified", "0") == "1",
|
||||
linked_room_0=el.get("linkedRoom0", "-1"),
|
||||
linked_room_1=el.get("linkedRoom1", "-1"),
|
||||
area=float(el.get("area", "0")),
|
||||
perimeter=float(el.get("perimeter", "0")),
|
||||
values=_values(el),
|
||||
points=[_parse_room_point(p) for p in el.findall("point")],
|
||||
doors=[_parse_door(d) for d in el.findall("door")],
|
||||
windows=[_parse_window(w) for w in el.findall("window")],
|
||||
furniture=[_parse_furniture(f) for f in el.findall("furniture")],
|
||||
main_dimensions=[_parse_main_dimension(d) for d in el.findall("mainDimension")],
|
||||
)
|
||||
|
||||
|
||||
def parse_magicplan_xml(xml_str: str) -> MagicPlanXMLPlan:
|
||||
root = ET.fromstring(xml_str)
|
||||
irp_el = root.find("interiorRoomPoints")
|
||||
return MagicPlanXMLPlan(
|
||||
id=root.get("id", ""),
|
||||
uid=root.get("uid", ""),
|
||||
name=root.get("name", ""),
|
||||
type=root.get("type", ""),
|
||||
interior_wall_width=float(root.get("interiorWallWidth", "0")),
|
||||
exterior_wall_width=float(root.get("exteriorWallWidth", "0")),
|
||||
schematic=root.get("schematic", "0") == "1",
|
||||
has_land_survey_address=root.get("hasLandSurveyAddress", "0") == "1",
|
||||
last_patch_identifier=root.get("lastPatchIdentifier", ""),
|
||||
last_roll_identifier=root.get("lastRollIdentifier", ""),
|
||||
values=_values(root),
|
||||
floors=[_parse_floor(f) for f in root.findall("floor")],
|
||||
interior_room_floors=[_parse_floor(f) for f in irp_el.findall("floor")]
|
||||
if irp_el is not None else [],
|
||||
)
|
||||
|
|
@ -1,48 +0,0 @@
|
|||
# MagicPlan Exchange XML Schema Reference
|
||||
# Derived from xml_example.xml and https://apidocs.magicplan.app/guide/basic-concepts/plan-exchange-xml-format
|
||||
#
|
||||
# <plan>
|
||||
# attrs: name, id, uid, type, interiorWallWidth (m), exteriorWallWidth (m),
|
||||
# schematic, hasLandSurveyAddress, lastPatchIdentifier, lastRollIdentifier
|
||||
# children: <values>, <floor>+, <interiorRoomPoints>
|
||||
#
|
||||
# <values> (plan-level metadata)
|
||||
# children: <value key="...">text</value>
|
||||
# known keys: date, statistics.areaOfHeight, statistics.basement.account,
|
||||
# statistics.exteriorWalls, statistics.interiorWalls
|
||||
#
|
||||
# <floor>
|
||||
# attrs: uid, floorType (0=ground 1=upper), rotation, compassAngle,
|
||||
# areaWithoutWalls (m²), areaWithInteriorWallsOnly (m²), areaWithWalls (m²)
|
||||
# children: <name>, <symbolInstance>, <floorRoom>+, <exploded>
|
||||
#
|
||||
# <floorRoom>
|
||||
# attrs: type (room label e.g. "Kitchen"), uid, x, y, rotation,
|
||||
# wasModified, linkedRoom0, linkedRoom1, area (m²), perimeter (m)
|
||||
# children: <values> (key: ceilingHeight m), <point>+, <door>*, <window>*, <furniture>*, <mainDimension>*
|
||||
#
|
||||
# <point> (room corner polygon)
|
||||
# attrs: snappedX (m), snappedY (m), height (m), uid
|
||||
#
|
||||
# <door>
|
||||
# attrs: point, type, u, width (m), depth (m), height (m), orientation,
|
||||
# snappedType, snappedPosition, snappedWidth, snappedDepth, snappedHeight, snappedOrientation,
|
||||
# insetX, insetY, insetZ, twinWallItemUid, symbolInstance
|
||||
#
|
||||
# <window>
|
||||
# attrs: point, type, u, width (m), depth (m), height (m), orientation,
|
||||
# snappedType, snappedPosition, snappedWidth, snappedDepth, snappedHeight, snappedOrientation,
|
||||
# insetX, insetY, insetZ, symbolInstance
|
||||
#
|
||||
# <exploded> (wall geometry per floor)
|
||||
# children: <wall>, <door>, <window>, <furniture>
|
||||
# <wall> children: <point x y height>, <type> (text: "exterior" | "interior")
|
||||
#
|
||||
# <interiorRoomPoints>
|
||||
# children: <floor> (same structure as top-level floor, interior wall room shapes)
|
||||
#
|
||||
# All distances in metres. All areas in m².
|
||||
|
||||
FLOOR_TYPE_GROUND = "0"
|
||||
FLOOR_TYPE_UPPER = "1"
|
||||
FLOOR_TYPE_BASEMENT = "2"
|
||||
Loading…
Add table
Reference in a new issue