/* ==========================================================================
   Craftoplan — интерфейс проектировщика
   Шапка на всю ширину + три колонки: элементы / сцена / свойства.
   На узких экранах боковые колонки превращаются в выдвижные панели.
   ========================================================================== */

/* Две темы: тёмная (по умолчанию) и светлая — html[data-theme="light"]. Переключатель — в меню
   (designer-ui.js), выбор помнит браузер, тема ставится до отрисовки (скрипт в <head>).
   Палитра — спокойная, как в профессиональных CAD: нейтральный серый с лёгким холодным оттенком,
   чёрный, акцент — фирменный синий #0D99FF. Сцена — в тон теме (--viewport); линии и подписи
   в сцене подстраиваются из JS (edgelines.js, sizeDraw.js). Все цвета интерфейса — через
   переменные ниже, своих цветов у блоков нет */
:root{
	color-scheme: dark;

	--accent: #0D99FF;          /* совпадает с цветом выделения в сцене (controlSelectColor); заливки */
	--accent-hover: #38ABFF;
	--accent-soft: rgba(13, 153, 255, .16);
	--accent-ink: #0D99FF;      /* акцент текстом и значком */
	--formula: #A877FF;         /* формулы: поле с формулой; в сцене — выделенный объект с формулами (formulaColor #9747FF) */
	--danger: #EF5B54;          /* замок, удаление */
	--danger-soft: rgba(239, 91, 84, .14);
	--warn-bg: rgba(242, 184, 97, .12);
	--warn-text: #F2B861;
	--warn-line: #B7843A;

	--text: #E8E9EB;
	--text-2: #B4B8BE;
	--text-3: #8C9198;

	--surface: #3A3D41;         /* колонки, окна — мягкий тёмно-серый, не чёрный */
	--surface-2: #45484D;       /* поля, наведение, подложки */
	--line: #4E5156;
	--line-strong: #5E6268;
	--btn: #4B4E53;             /* кнопки — заливкой, без рамки (рамки кнопок — лишние линии) */
	--btn-hover: #56595E;

	--viewport: #73767B;        /* сцена: средне-серая — на ней читаются чёрные размеры и белые детали */
	--viewport-bg: linear-gradient(180deg, #7D8085 0%, #686B70 100%);   /* мягкий градиент, как в CAD */
	--viewport-text: #FFFFFF;   /* подписи поверх сцены (карточки материалов) */
	--viewport-text-shadow: 0 1px 2px rgba(0, 0, 0, .6);

	--shadow-pop: 0 8px 24px rgba(0, 0, 0, .35);
	--shadow-window: 0 16px 48px rgba(0, 0, 0, .45);
	--veil: rgba(58, 61, 65, .72);

	/* всплывающие подсказки (кнопки инструментов, коннекторы) — тёмные в обеих темах, как шапка */
	--tip-bg: #28282A;
	--tip-text: #F2F2F3;

	/* цвета осей как у AxesHelper */
	--ax-x: #E5484D;
	--ax-y: #2F9E5F;
	--ax-z: #3B6FE0;

	--header-h: 48px;
	--left-w: 300px;
	--right-w: 300px;
	--chat-w: clamp(320px, 27vw, 420px);	/* колонка чата в режиме AI */

	--r-sm: 5px;
	--r: 7px;
	--r-lg: 10px;

	--font: "IBM Plex Sans", system-ui, -apple-system, "Segoe UI", Roboto, Arial, sans-serif;
}

:root[data-theme="light"]{
	color-scheme: light;

	--accent-hover: #0A86E0;
	--accent-soft: #E6F4FF;
	--accent-ink: #0D99FF;
	--formula: #8338E8;
	--danger: #E5484D;
	--danger-soft: #FDECEC;
	--warn-bg: #FFF4E5;
	--warn-text: #8A5300;
	--warn-line: #F5B66B;

	--text: #1C1F24;
	--text-2: #5B616A;
	--text-3: #959BA4;

	--surface: #FFFFFF;
	--surface-2: #F3F4F6;
	--line: #E4E6EA;
	--line-strong: #D0D4DA;
	--btn: #ECEEF1;
	--btn-hover: #E1E4E8;

	--viewport: #E4E6E9;
	--viewport-bg: linear-gradient(180deg, #EEF0F2 0%, #DCDFE3 100%);
	--viewport-text: #1C1F24;
	--viewport-text-shadow: 0 0 3px rgba(255, 255, 255, .9);

	--shadow-pop: 0 8px 24px rgba(20, 24, 30, .12);
	--shadow-window: 0 16px 48px rgba(20, 24, 30, .28);
	--veil: rgba(255, 255, 255, .72);
}

/* шапка — всегда тёмная (#28282A) в обеих темах: свои значения переменных, всё внутри шапки
   (кнопки, поле названия, меню) берёт их отсюда */
.header{
	color-scheme: dark;

	--surface: #28282A;
	--surface-2: #36363A;
	--line: #3A3A3E;
	--line-strong: #4A4A4F;
	--btn: #3E3E43;
	--btn-hover: #4A4A4F;
	--text: #E6E7E9;
	--text-2: #B0B4BA;
	--text-3: #85898F;
	--accent-soft: rgba(13, 153, 255, .18);
	--shadow-pop: 0 8px 24px rgba(0, 0, 0, .4);

	color: var(--text);
}


*, *::before, *::after{
	box-sizing: border-box;
	margin: 0;
	padding: 0;
}

html, body{
	width: 100%;
	height: 100%;
	overflow: hidden;
}

body{
	display: grid;
	grid-template-rows: var(--header-h) minmax(0, 1fr);
	grid-template-columns: var(--left-w) minmax(0, 1fr) var(--right-w);
	grid-template-areas:
		"header header header"
		"left   view   right";
	height: 100vh;
	height: 100dvh;
	font-family: var(--font);
	font-size: 13px;
	line-height: 1.4;
	color: var(--text);
	background: var(--surface);
	-webkit-font-smoothing: antialiased;
	-webkit-tap-highlight-color: transparent;
}

button, input, select{
	font: inherit;
	color: inherit;
}

button{
	cursor: pointer;
	background: none;
	border: 0;
}

:focus-visible{
	outline: 2px solid var(--accent);
	outline-offset: 1px;
}

.sprite{
	position: absolute;
	width: 0;
	height: 0;
	overflow: hidden;
}

.i{
	width: 18px;
	height: 18px;
	flex: none;
	fill: none;
	stroke: currentColor;
	stroke-width: 1.6;
	stroke-linecap: round;
	stroke-linejoin: round;
}

.show{ display: block; }
.hide{ display: none; }


/* ---------- Кнопки и поля ---------- */

.btn{
	display: inline-flex;
	align-items: center;
	justify-content: center;
	gap: 6px;
	height: 30px;
	padding: 0 12px;
	border: 1px solid transparent;	/* рамки нет — заливка --btn; прозрачная держит размер, как у btn_primary */
	border-radius: var(--r-sm);
	background: var(--btn);
	font-weight: 500;
	line-height: 1;
	white-space: nowrap;
}
.btn .i{
	width: 16px;
	height: 16px;
	color: var(--text-2);
}
.btn:disabled{
	opacity: .6;
	cursor: default;
}
.btn_primary{
	background: var(--accent);
	border-color: var(--accent);
	color: #fff;
}
.btn_block{
	width: 100%;
}

.icon_btn{
	display: inline-grid;
	place-items: center;
	width: 30px;
	height: 30px;
	border-radius: var(--r-sm);
	color: var(--text-2);
	flex: none;
}
/* кнопки, которых у объекта нет (шапка Properties: elementActions) — inline-grid выше перебил бы hidden */
.icon_btn[hidden]{
	display: none;
}

@media (pointer: fine){
	.btn:hover:not(:disabled){ background: var(--btn-hover); }
	.btn_primary:hover:not(:disabled){ background: var(--accent-hover); border-color: var(--accent-hover); }
	.icon_btn:hover{ background: var(--surface-2); color: var(--text); }
	.icon_danger:hover{ color: var(--danger); }
}

.input{
	width: 100%;
	height: 30px;
	padding: 0 8px;
	border: 1px solid var(--line-strong);
	border-radius: var(--r-sm);
	background: var(--surface);
	outline: 0;
	font-variant-numeric: tabular-nums;
}
.input:focus{
	border-color: var(--accent);
	box-shadow: 0 0 0 3px var(--accent-soft);
}
select.input{
	appearance: none;
	-webkit-appearance: none;
	cursor: pointer;
}
/* стрелка списка — у select и у поля с выпадающим списком (город в js/makers.js) */
select.input,
.input.input_drop{
	padding-right: 26px;
	background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 12 12'%3E%3Cpath d='M3 4.5l3 3 3-3' fill='none' stroke='%235E646D' stroke-width='1.4' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E");
	background-repeat: no-repeat;
	background-position: right 7px center;
	background-size: 12px;
}

.range{
	width: 100%;
	height: 20px;
	background: transparent;
	-webkit-appearance: none;
	appearance: none;
	cursor: pointer;
}
.range::-webkit-slider-runnable-track{
	height: 4px;
	border-radius: 2px;
	background: var(--line-strong);
}
.range::-webkit-slider-thumb{
	-webkit-appearance: none;
	width: 14px;
	height: 14px;
	margin-top: -5px;
	border-radius: 50%;
	background: var(--surface);
	border: 2px solid var(--accent);
}
.range::-moz-range-track{
	height: 4px;
	border-radius: 2px;
	background: var(--line-strong);
}
.range::-moz-range-thumb{
	width: 10px;
	height: 10px;
	border-radius: 50%;
	background: var(--surface);
	border: 2px solid var(--accent);
}


/* ---------- Шапка ---------- */

/* слева — меню, логотип, название проекта с его меню и запись; посередине — режим студии; справа — токены и
   действия с проектом. Края — поровну, правый не уже своих кнопок, левый сжимается (название — многоточием) */
.header{
	grid-area: header;
	display: grid;
	grid-template-columns: 1fr auto 1fr;
	align-items: center;
	gap: 12px;
	padding: 0 12px 0 8px;
	border-bottom: 1px solid var(--line);
	background: var(--surface);
	position: relative;
	z-index: 60;
}
.header_left{
	display: flex;
	align-items: center;
	gap: 8px;
	min-width: 0;
}
.header_center{
	position: relative;
	display: flex;
	align-items: center;
	justify-content: center;
	gap: 6px;
	min-width: 0;
}
.header_right{
	display: flex;
	align-items: center;
	justify-content: flex-end;
	gap: 8px;
}

/* режим студии (designer-ui.js: setUi): «✦ AI | Editor» посередине шапки — два способа работы рядом, выбранный
   светлее; на телефоне его нет — он в меню ☰ (.menu_mode, там — только на телефоне) */
/* заметен сразу, но не кричит: дорожка — светлее шапки, выбранный — мягкий синий (заливка акцента ~30%, белый
   текст, значок — акцентом), невыбранный — светлый текст, не серый */
.ui_mode{
	display: flex;
	flex: none;
	gap: 2px;
	padding: 3px;
	border-radius: var(--r);
	background: var(--btn);
}
.ui_mode_btn{
	display: inline-flex;
	align-items: center;
	gap: 7px;
	height: 30px;
	padding: 0 16px;
	border-radius: var(--r-sm);
	color: var(--text);
	font-size: 13px;
	font-weight: 600;
	white-space: nowrap;
	transition: background .15s, color .15s;
}
.ui_mode_btn .i{
	width: 16px;
	height: 16px;
	color: var(--text-2);
}
.ui_mode_btn[aria-pressed="true"]{
	background: rgba(13, 153, 255, .3);
	color: #FFFFFF;
}
.ui_mode_btn[aria-pressed="true"] .i{
	color: var(--accent-hover);
}
.ui_mode_btn[hidden]{
	display: none;
}
@media (pointer: fine){
	.ui_mode_btn:hover:not([aria-pressed="true"]){
		background: var(--btn-hover);
	}
}
/* подсказка под переключателем после первого ответа AI (designer-ui.js: modeTip): «руками — Editor» */
.ui_tip{
	position: absolute;
	top: calc(100% + 10px);
	left: 50%;
	display: flex;
	align-items: center;
	gap: 8px;
	padding: 6px 6px 6px 12px;
	border: 1px solid var(--line-strong);
	border-radius: var(--r);
	background: var(--surface);
	box-shadow: var(--shadow-pop);
	color: var(--text);
	font-size: 12.5px;
	white-space: nowrap;
	transform: translateX(-50%);
}
.ui_tip::before{
	content: "";
	position: absolute;
	top: -6px;
	left: 50%;
	width: 10px;
	height: 10px;
	border-top: 1px solid var(--line-strong);
	border-left: 1px solid var(--line-strong);
	background: var(--surface);
	transform: translateX(-50%) rotate(45deg);
}
.ui_tip[hidden]{
	display: none;
}
@media (max-width: 899px){
	.header_center{
		display: none;
	}
}
/* .menu_phone — пункты меню ☰ вместо кнопок шапки, которых на телефоне нет (часы версий, Plans) */
@media (min-width: 900px){
	.menu_theme.menu_mode,
	.menu_link.menu_phone{
		display: none;
	}
}
/* средние экраны: у кнопок справа только значки (подпись — в title), у токенов гостя — «Get 3 free», как на
   телефоне */
@media (max-width: 1199px){
	.header_right .btn_label,
	.header_right .tokens_word{
		display: none;
	}
}

/* всё о проекте (название, варианты, запись, замечания, «Public») — одной обёрткой: на широком экране её нет,
   это продолжение левой части шапки; на телефоне — своя полоса под кнопками (мобильная версия ниже) */
.header_project{
	display: contents;
}

/* название проекта: поле — слева, у логотипа; внутри справа — часы истории версий (versions.js, сразу панель
   версий); за полем — кнопка «Variants» (variants.js), окно вариантов — под ней. Поле и часы — одно поле в рамке,
   чтобы длина читалась. От ширины названия растёт в свободное место левой половины шапки — вдвое скромнее строки
   записи, до 312px вместе с часами; тесно (узкий экран, значки Public / Remarks) — сжимается, ничего не наезжает.
   Поле — заливкой, без рамки (рамка — только у поля в фокусе) */
.project_title{
	position: relative;
	display: flex;
	flex: .5 1 auto;
	align-items: center;
	gap: 2px;
	min-width: 0;
	max-width: 312px;
	padding-right: 1px;
	border: 1px solid transparent;
	border-radius: var(--r-sm);
	background: var(--surface-2);
}
@media (pointer: fine){
	.project_title:hover{
		background: var(--btn);
	}
}
.project_title:has(.header_input:focus){
	border-color: var(--accent);
	box-shadow: 0 0 0 3px var(--accent-soft);
}
.project_title .header_input{
	flex: 1 1 auto;
	width: 160px;
	height: 30px;
	min-width: 40px;
	text-align: left;
}
.project_title .header_input:hover,
.project_title .header_input:focus{
	border-color: transparent;
	background: transparent;
	box-shadow: none;
}
.project_title .versions_btn{
	width: 28px;
	height: 28px;
}
/* просмотр по ссылке: название только читать — без заливки поля */
body[data-view] .project_title{
	background: transparent;
}
/* от ширины названия (где браузер умеет; иначе — от 160px): длинное название поле не обрезает, пока есть место */
@supports (field-sizing: content){
	.project_title .header_input{
		field-sizing: content;
		width: auto;
	}
}
/* тесно — первой сжимается строка записи, потом название; на строку осталось меньше 120px — её не видно (обрывок
   «Sav…» не нужен: состояние — и в подсказке облака, autosave.js) */
.save_status_case{
	flex: 1 1 0;
	min-width: 0;
	container-type: inline-size;
}
.save_status_case .save_status{
	display: block;
}
@container (max-width: 119px){
	.save_status_case .save_status{
		opacity: 0;
	}
}

/* логотип — SVG прямо в разметке (index.php), цвет — currentColor: в шапке белый */
.logo{
	display: block;
	flex: none;
	width: 93px;
	height: 14px;
	color: #FFFFFF;
}
.logo_svg{
	display: block;
	width: 100%;
	height: 100%;
}
/* сайт фирмы: её знак (логотип или буква на светлом круге) и название */
.logo.logo_firm{
	display: flex;
	align-items: center;
	gap: 8px;
	width: auto;
	max-width: 200px;
	height: auto;
	text-decoration: none;
}
.logo_mark{
	display: grid;
	flex: none;
	place-items: center;
	width: 24px;
	height: 24px;
	overflow: hidden;
	border-radius: 50%;
	background: #FFFFFF;
	color: #161514;
	font-size: 13px;
	font-weight: 600;
}
.logo_mark img{
	width: 100%;
	height: 100%;
	object-fit: cover;
}
.logo_name{
	overflow: hidden;
	font-size: 13px;
	font-weight: 500;
	white-space: nowrap;
	text-overflow: ellipsis;
}

/* клиент на сайте фирмы (designer-new/index.php: data-site-visitor): проект — черновиком в браузере, к фирме — заявкой;
   записи на сервер, версий, вариантов, ссылки «Share», документов (раскрой, чертежи, скачивание), входа и своих
   деталей в аккаунте у него нет */
html[data-site-visitor] #saveProject,
html[data-site-visitor] #versionsBtn,
html[data-site-visitor] #publicBadge,
html[data-site-visitor] .variants,
html[data-site-visitor] #cutting,
html[data-site-visitor] #shareProject,
html[data-site-visitor] #menuAccount,
html[data-site-visitor] #partLibrary{
	display: none !important;
}

.save_status{
	min-width: 0;
	overflow: hidden;
	font-size: 12px;
	color: var(--text-3);
	text-overflow: ellipsis;
	white-space: nowrap;
}

.header_input{
	width: 100%;
	height: 32px;
	padding: 0 10px;
	border: 1px solid transparent;
	border-radius: var(--r-sm);
	background: transparent;
	outline: 0;
	text-align: center;
	font-size: 14px;
	font-weight: 500;
	text-overflow: ellipsis;
}
.header_input::placeholder{
	color: var(--text-3);
	font-weight: 400;
}
.header_input:hover{
	background: var(--surface-2);
}
.header_input:focus{
	background: var(--surface);
	border-color: var(--accent);
	box-shadow: 0 0 0 3px var(--accent-soft);
}

.menu_case{
	position: relative;
}
.menu *{
	pointer-events: none;   /* клик всегда приходит на саму кнопку меню */
}
.menu .i{
	width: 20px;
	height: 20px;
}
.menu_link_case{
	position: absolute;
	top: calc(100% + 8px);
	left: 0;
	min-width: 230px;
	padding: 4px;
	background: var(--surface);
	border: 1px solid var(--line);
	border-radius: var(--r);
	box-shadow: var(--shadow-pop);
	z-index: 1000;
}
.menu_link{
	display: block;
	height: 32px;
	line-height: 32px;
	padding: 0 10px;
	border-radius: var(--r-sm);
	color: var(--text);
	text-decoration: none;
}
.menu_link:hover{
	background: var(--surface-2);
}

/* переключатель темы в меню: две кнопки рядом */
.menu_theme{
	display: flex;
	align-items: center;
	justify-content: space-between;
	gap: 8px;
	margin-top: 4px;
	padding: 6px 4px 2px 10px;
	border-top: 1px solid var(--line);
}
.menu_theme_label{
	color: var(--text-2);
}
/* Advanced tools: под строкой — что это (designer-new/index.php) */
.menu_theme.menu_advanced{
	flex-wrap: wrap;
	row-gap: 2px;
}
.menu_advanced .menu_theme_label{
	color: var(--text);
	white-space: nowrap;
}
.menu_theme_hint{
	flex: 1 0 100%;
	width: 0;
	padding-bottom: 4px;
	color: var(--text-3);
	font-size: 11px;
	line-height: 1.35;
}
.menu_theme_seg{
	display: flex;
	gap: 2px;
	padding: 2px;
	border-radius: var(--r);
	background: var(--surface-2);
}
.menu_link.menu_theme_btn{
	height: 26px;
	line-height: 26px;
	padding: 0 10px;
	font-size: 12px;
	font-weight: 500;
	color: var(--text-2);
}
.menu_link.menu_theme_btn[aria-pressed="true"]{
	background: var(--surface);
	color: var(--text);
	box-shadow: 0 1px 2px rgba(0, 0, 0, .18);
}

/* выбор языка в меню (lang-lib.php: langPicker — тот же, что в подвале страниц): список — под строкой,
   от левого края меню (меню — у левого края экрана) */
.menu_lang{
	position: relative;
}
.menu_lang .lang_picker_btn{
	display: flex;
	align-items: center;
	gap: 6px;
	height: 28px;
	line-height: 28px;
	padding: 0 8px;
	list-style: none;
	cursor: pointer;
	user-select: none;
}
.menu_lang .lang_picker_btn::-webkit-details-marker{ display: none; }
.menu_lang .lang_picker_btn *{ pointer-events: none; }
.menu_lang .lang_picker_list{
	position: absolute;
	top: calc(100% + 4px);
	left: 0;
	z-index: 1001;
	display: grid;
	grid-template-columns: repeat(2, minmax(120px, 1fr));
	gap: 2px;
	margin: 0;
	padding: 4px;
	list-style: none;
	background: var(--surface);
	border: 1px solid var(--line);
	border-radius: var(--r);
	box-shadow: var(--shadow-pop);
}
.menu_lang .lang_picker_list a{
	display: block;
	padding: 0 10px;
	height: 30px;
	line-height: 30px;
	border-radius: var(--r-sm);
	color: var(--text);
	text-decoration: none;
	white-space: nowrap;
}
.menu_lang .lang_picker_list a:hover,
.menu_lang .lang_picker_list a[aria-current="true"]{
	background: var(--surface-2);
}


/* ---------- Боковые колонки ---------- */

.panel{
	display: flex;
	flex-direction: column;
	min-height: 0;
	min-width: 0;
	background: var(--surface);
	overflow: hidden;
}
.panel_left{
	grid-area: left;
	border-right: 1px solid var(--line);
}
.panel_right{
	grid-area: right;
	border-left: 1px solid var(--line);
}

.panel_head{
	display: flex;
	align-items: center;
	justify-content: space-between;
	gap: 8px;
	height: 40px;
	padding: 0 8px 0 14px;
	flex: none;
}
.panel_head_sub{
	border-top: 1px solid var(--line);
	margin-top: 12px;
}
.panel_title{
	font-size: 12px;
	font-weight: 600;
}
.panel_close{
	display: none;
}
.panel_scroll{
	flex: 1;
	min-height: 0;
	overflow-y: auto;
	overscroll-behavior: contain;
}
.count{
	min-width: 20px;
	padding: 0 6px;
	border-radius: 10px;
	background: var(--surface-2);
	color: var(--text-2);
	font-size: 11.5px;
	line-height: 18px;
	text-align: center;
	font-variant-numeric: tabular-nums;
}


/* Окружение сцены: пол или комната */

.scene_env{
	padding: 0 12px;
}
#editRoom[hidden],
#roomEye[hidden]{
	display: none;
}

/* Добавление фигур */

.shapes{
	display: grid;
	grid-template-columns: repeat(3, 1fr);
	gap: 6px;
	padding: 0 12px;
}
.shape{
	display: flex;
	flex-direction: column;
	align-items: center;
	justify-content: center;
	gap: 5px;
	height: 60px;
	border: 1px solid var(--line);
	border-radius: var(--r);
	color: var(--text-2);
	font-size: 12px;
}
.shape .i{
	width: 22px;
	height: 22px;
	stroke-width: 1.4;
	color: var(--text);
}
.shape:active{
	background: var(--accent-soft);
	border-color: var(--accent);
}
@media (pointer: fine){
	.shape:hover{
		border-color: var(--accent);
		color: var(--text);
	}
	.shape:hover .i{
		color: var(--accent-ink);
	}
}


/* Список элементов */

.elements{
	list-style: none;
	padding: 2px 6px 12px;
}
.element{
	display: flex;
	align-items: center;
	gap: 8px;
	width: 100%;
	height: 30px;
	padding: 0 8px;
	border-radius: var(--r-sm);
	text-align: left;
}
.element .i{
	width: 16px;
	height: 16px;
	color: var(--text-2);
}
.element_name{
	flex: 1;
	min-width: 0;
	overflow: hidden;
	text-overflow: ellipsis;
	white-space: nowrap;
}
/* номер детали на чертежах и в спецификации (designer-panels.js: elementNumbers) — перед названием;
   у группы, покупного и «для вида» номера нет */
.element_no{
	flex: none;
	max-width: 45%;
	overflow: hidden;
	text-overflow: ellipsis;
	white-space: nowrap;
	margin-right: -3px;
	color: var(--text-3);
	font-size: 11.5px;
	font-variant-numeric: tabular-nums;
}
.element_no:empty{
	display: none;
}
/* действия строки: название, линейка, глаз, замок — видны при наведении и у выбранной строки;
   не по умолчанию (замок, скрыт, без размеров) — всегда */
.element_acts{
	display: flex;
	flex: none;
	gap: 1px;
	margin-left: auto;
}
.element_act{
	display: grid;
	place-items: center;
	width: 22px;
	height: 22px;
	border-radius: 4px;
	color: var(--text-3);
	opacity: 0;
}
.element_act .i{
	width: 14px;
	height: 14px;
}
.element:hover .element_act,
.element:focus-visible .element_act,
.element.is_selected .element_act,
.element_act.is_on{
	opacity: 1;
}
.element_act.is_on{
	color: var(--text-2);
}
.element_act_lock.is_on{
	color: var(--danger);
}
@media (pointer: fine){
	.element_act:hover{
		background: var(--line);
		color: var(--text);
	}
}
.element.is_hidden .element_name,
.element.is_hidden .element_no,
.element.is_hidden .element_icon{
	opacity: .45;
}
/* нет в модели по формуле «In the model when» (place.visible): зачёркнуто */
.element.is_absent .element_name{
	opacity: .45;
	text-decoration: line-through;
}
/* покупное и «только для вида» (designer-panels.js: setMake) — метка после названия */
.element_tag{
	flex: none;
	padding: 1px 5px;
	border-radius: 4px;
	background: var(--line);
	color: var(--text-2);
	font-size: 10.5px;
	font-weight: 500;
	line-height: 1.4;
}
.element.is_selected{
	background: var(--accent-soft);
	font-weight: 500;
}
.element.is_selected .element_icon{
	color: var(--accent-ink);
}
@media (pointer: fine){
	.element:hover:not(.is_selected){
		background: var(--surface-2);
	}
}

.elements_empty{
	padding: 4px 14px 16px;
	color: var(--text-3);
	font-size: 12.5px;
}
body.has_elements .elements_empty{
	display: none;
}
body[data-mode="part"] .empty_scene,
body:not([data-mode="part"]) .empty_part{
	display: none;
}

/* левая колонка: вкладки «Library» / «Elements» (те же .rtabs, что справа) */
.lpane_elems{
	display: none;
}
body[data-ltab="elements"] .lpane_lib{
	display: none;
}
body[data-ltab="elements"] .lpane_elems{
	display: block;
}
/* библиотека — колонкой: сцена, фигуры, детали проекта (список прокручивается сам), под ними чат AI
   до низа колонки (ai.css) */
body:not([data-ltab="elements"]) .lpane_lib{
	display: flex;
	flex-direction: column;
}
.lpane_lib > *{
	flex: none;
}

/* ---------- Колонки спрятаны (designer-ui.js: setPanels — режим AI и просмотр по ссылке) ----------
   Сцена на всю ширину (на телефоне — без выдвижных колонок и их кнопок; в режиме AI на широком
   экране — рядом с колонкой чата, ниже); на сцене с отступом 15px от краёв: слева — панель
   инструментов, справа — материалы карточками, на телефоне под ними — чат окном или кнопкой (ai.css).
   Это те же элементы страницы, переставленные скриптом; здесь — их вид на новом месте. Пока открыт
   инструмент, гибка или участки, правая колонка с их настройками видна */
body[data-panels="off"] .panel_left,
body[data-panels="off"] .panel_right,
body[data-panels="off"] .mobile_bar{
	display: none;
}
body[data-panels="off"]:is([data-tool], [data-bend], [data-press]) .panel_right{
	display: flex;
}
body[data-panels="off"] [data-open-panel="elements"]{
	visibility: hidden;
}
@media (min-width: 900px){
	body[data-panels="off"]{
		grid-template-columns: 0 minmax(0, 1fr) 0;
	}
	body[data-panels="off"]:is([data-tool], [data-bend], [data-press]){
		grid-template-columns: 0 minmax(0, 1fr) var(--right-w);
	}
}
/* на телефоне настройки инструмента — в нижнем листе: его кнопка остаётся */
@media (max-width: 899px){
	body[data-panels="off"]:is([data-tool], [data-bend], [data-press]) .mobile_bar{
		display: flex;
	}
}
body[data-panels="off"] .tools{
	top: 15px;
	left: 15px;
}
/* колонки спрятаны: слева — undo / redo и под ними кнопки вида (#toolsView переезжает сюда,
   designer-ui.js: setPanels); инструменты правки спрятаны. В просмотре по ссылке линейка остаётся */
body[data-panels="off"] #toolSep,
body[data-panels="off"] #toolSelect,
body[data-panels="off"] #toolSaw,
body[data-panels="off"] #toolDrill,
body[data-panels="off"] #toolMill,
body[data-panels="off"] #toolLathe,
body[data-panels="off"] #toolBend,
body[data-panels="off"] #toolPress,
body[data-panels="off"]:not([data-view]) #toolMeasure{
	display: none;
}
.tools > .tools_case + .tools_case{
	margin-top: 8px;
}
/* панель вида справа — только когда колонки видны */
body[data-panels="off"] .tools.tools_view{
	display: none;
}

/* ---------- Режим AI (designer-ui.js: setUi) ----------
   Широкий экран: чат — колонкой слева на всю высоту под шапкой (ai-chat.js: chatHome кладёт его прямо в
   .panel_left, остальное в ней спрятано), сцена — справа от него. Пока чат на первом экране посередине
   сцены (is_start) или спрятан, колонки нет — сцена на всю ширину. В шапке нет вариантов и истории версий */
@media (min-width: 900px){
	body[data-ui="ai"]:has(.panel_left > .ai_panel:not([hidden])){
		grid-template-columns: var(--chat-w) minmax(0, 1fr) 0;
	}
	body[data-ui="ai"]:is([data-tool], [data-bend], [data-press]):has(.panel_left > .ai_panel:not([hidden])){
		grid-template-columns: var(--chat-w) minmax(0, 1fr) var(--right-w);
	}
	body[data-ui="ai"] .panel_left:has(> .ai_panel:not([hidden])){
		display: flex;
	}
	body[data-ui="ai"] .panel_left > :not(.ai_panel){
		display: none;
	}
}

/* материалы на сцене: колонка карточек справа, 15px от края (панель вида при скрытых колонках
   спрятана), без фона — цвет квадратом, название под ним. Снизу — место под свёрнутый чат
   (кнопка 48px в углу) */
.canvas_case > .rpane_mats{
	display: block;
	position: absolute;
	top: 15px;
	right: 15px;
	bottom: 75px;
	width: 88px;
	z-index: 5;
	background: none;
	pointer-events: none;
	scrollbar-width: none;
}
.canvas_case > .rpane_mats::-webkit-scrollbar{
	display: none;
}
body[data-mode="part"] .canvas_case > .rpane_mats{
	top: 56px;
}
.canvas_case > .rpane_mats .mats_scope,
.canvas_case > .rpane_mats .mats_empty,
.canvas_case > .rpane_mats .mat_params,
.canvas_case > .rpane_mats .mat_count{
	display: none;
}
.canvas_case > .rpane_mats .mats_list{
	gap: 10px;
	padding: 0;
}
.canvas_case > .rpane_mats .mat_card{
	flex-direction: column;
	align-items: center;
	gap: 4px;
	padding: 0;
	border: 0;
	background: none;
	text-align: center;
	pointer-events: auto;
}
.canvas_case > .rpane_mats .mat_swatch{
	width: 40px;
	height: 40px;
	border-radius: var(--r);
	border: 1px solid rgba(255, 255, 255, .35);
	box-shadow: 0 1px 4px rgba(0, 0, 0, .3);
}
.canvas_case > .rpane_mats .mat_card.is_warn .mat_swatch{
	box-shadow: 0 0 0 2px var(--warn-line), 0 1px 4px rgba(0, 0, 0, .3);
}
.canvas_case > .rpane_mats .mat_text{
	align-items: center;
	width: 100%;
}
.canvas_case > .rpane_mats .mat_name{
	max-width: 100%;
	color: var(--viewport-text);
	font-size: 11px;
	font-weight: 500;
	text-shadow: var(--viewport-text-shadow);
}
@media (pointer: fine){
	.canvas_case > .rpane_mats .mat_card:hover{
		background: none;
	}
	.canvas_case > .rpane_mats .mat_card:hover .mat_swatch{
		box-shadow: 0 0 0 2px var(--accent), 0 1px 4px rgba(0, 0, 0, .3);
	}
}

/* дерево элементов: стрелка группы, перетаскивание мышкой */
.element_toggle{
	flex: none;
	display: inline-grid;
	place-items: center;
	width: 14px;
	height: 14px;
	margin-right: -4px;
	border-radius: 3px;
}
.element .element_toggle .i{
	width: 14px;
	height: 14px;
	color: var(--text-3);
	transition: transform .15s;
}
.element.is_collapsed .element_toggle .i{
	transform: rotate(-90deg);
}
@media (pointer: fine){
	.element_toggle[data-toggle]:hover{ background: var(--line); }
}
.elements .element.is_dragging{
	opacity: .45;
}
.elements .element.drop_into{
	background: var(--accent-soft);
	box-shadow: inset 0 0 0 1px var(--accent);
}
.elements .element.drop_before{
	box-shadow: inset 0 2px 0 var(--accent);
}
.elements .element.drop_after{
	box-shadow: inset 0 -2px 0 var(--accent);
}
.elements.drop_end{
	box-shadow: inset 0 -2px 0 var(--accent);
}
body.is_list_drag,
body.is_list_drag *{
	cursor: grabbing !important;
	user-select: none;
}


/* Правая колонка: вкладки «Properties» / «Materials» (designer-stock.js). Пока открыт инструмент,
   гибка или участки, видны свойства — там их настройки; вкладки тогда не переключаются */
.rtabs{
	display: flex;
	gap: 2px;
	padding: 2px;
	border-radius: var(--r);
	background: var(--surface-2);
}
.rtab{
	height: 26px;
	padding: 0 10px;
	border-radius: var(--r-sm);
	color: var(--text-2);
	font-size: 12px;
	font-weight: 600;
}
.rtab[aria-selected="true"]{
	background: var(--surface);
	color: var(--text);
	box-shadow: 0 1px 2px rgba(0, 0, 0, .1);
}
@media (pointer: fine){
	.rtab:hover{ color: var(--text); }
}
.panel_head:has(.rtabs){
	padding-left: 8px;
}
.rpane_mats{
	display: none;
}
body[data-rtab="materials"]:not([data-tool]):not([data-bend]):not([data-press]) .rpane_props{
	display: none;
}
body[data-rtab="materials"]:not([data-tool]):not([data-bend]):not([data-press]) .rpane_mats{
	display: block;
}
body[data-tool] .rtabs,
body[data-bend] .rtabs,
body[data-press] .rtabs{
	opacity: .5;
	pointer-events: none;
}

/* карточки материалов: цвет квадратом, название, основные параметры, сколько деталей */
.mats_scope{
	padding: 2px 14px 8px;
	color: var(--text-3);
	font-size: 12px;
}
.mats_list{
	display: flex;
	flex-direction: column;
	gap: 6px;
	padding: 0 8px 12px;
}
.mats_empty{
	padding: 0 14px;
}
.mat_card{
	display: flex;
	align-items: flex-start;
	gap: 10px;
	width: 100%;
	padding: 8px 10px;
	border: 1px solid var(--line);
	border-radius: var(--r);
	background: var(--surface);
	text-align: left;
}
@media (pointer: fine){
	.mat_card:hover{ border-color: var(--line-strong); background: var(--surface-2); }
}
.mat_card.is_warn{
	border-color: var(--warn-line);
}
/* кромка — сразу под карточкой своего листа, со сдвигом (designer-stock.js: renderMaterials) */
.mat_card.is_edge{
	width: calc(100% - 18px);
	margin: -2px 0 0 18px;
}
.canvas_case > .rpane_mats .mat_card.is_edge{
	width: 100%;
	margin: 0;
}
.mat_swatch{
	flex: none;
	width: 28px;
	height: 28px;
	border-radius: var(--r-sm);
	border: 1px solid rgba(0, 0, 0, .12);
}
.mat_text{
	display: flex;
	flex-direction: column;
	gap: 1px;
	min-width: 0;
}
.mat_name{
	font-size: 12.5px;
	font-weight: 600;
	color: var(--text);
	overflow: hidden;
	text-overflow: ellipsis;
	white-space: nowrap;
}
.mat_params{
	font-size: 12px;
	color: var(--text-2);
	font-variant-numeric: tabular-nums;
}
.mat_count{
	font-size: 11.5px;
	color: var(--text-3);
}
.mat_card.is_warn .mat_count{
	color: var(--warn-text);
}
.mat_params:empty,
.mat_count:empty{
	display: none;
}
/* декор кромки «как у листа» — поля не правятся */
.color_field:has(input:disabled){
	opacity: .55;
}
#matParams{
	display: flex;
	flex-direction: column;
	gap: 8px;
}
#matParams:empty,
#matWindow [hidden],
.rpane_mats [hidden]{
	display: none;
}

/* окно материала: слева поля основы и декора, справа выбор готового для одной из них — основы того же
   вида или декоры (designer-stock.js: openMaterial). У кромки — только поля, окно узкое */
.mat_window{
	flex-direction: column;
}
.mat_window.has_lib{
	width: min(820px, calc(100vw - 32px));
}
.mat_head_text{
	display: flex;
	flex-direction: column;
	gap: 2px;
	min-width: 0;
}
.mat_scope{
	color: var(--text-3);
	font-size: 12.5px;
}
.window_note:empty{
	display: none;
}
.mat_window.has_lib .mat_body{
	display: grid;
	grid-template-columns: 320px minmax(0, 1fr);
	height: min(520px, calc(100vh - 180px));
	height: min(520px, calc(100dvh - 180px));
	margin-top: 8px;
	border-top: 1px solid var(--line);
	border-bottom: 1px solid var(--line);
}
.mat_window.has_lib .mat_form{
	min-height: 0;
	overflow-y: auto;
	padding: 14px 18px;
	border-right: 1px solid var(--line);
}
.mat_lib{
	display: flex;
	flex-direction: column;
	min-height: 0;
	min-width: 0;
}
/* группы слева: заголовок переключает выбор справа; группа, для которой выбор, — акцентом и стрелкой */
.mat_group{
	display: flex;
	flex-direction: column;
	gap: 8px;
}
.mat_window.has_lib .mat_group:not([hidden]) + .mat_group{
	margin-top: 6px;
	padding-top: 12px;
	border-top: 1px solid var(--line);
}
.mat_group_head{
	display: inline-flex;
	align-items: center;
	gap: 4px;
	align-self: flex-start;
	padding: 2px 0;
	color: var(--text-3);
	font-size: 11px;
	font-weight: 600;
	letter-spacing: .06em;
	text-transform: uppercase;
}
.mat_group_head::after{
	content: "›";
	visibility: hidden;
	font-size: 14px;
	line-height: 1;
}
.mat_window.has_lib .mat_group.is_active .mat_group_head{
	color: var(--accent-ink);
}
.mat_window.has_lib .mat_group.is_active .mat_group_head::after{
	visibility: visible;
}
@media (pointer: fine){
	.mat_window.has_lib .mat_group_head:hover{
		color: var(--text);
	}
}
/* справа: основа | декор */
.mat_lib_sides{
	display: flex;
	flex: none;
	gap: 2px;
	margin: 10px 10px 0;
	padding: 2px;
	border-radius: var(--r);
	background: var(--surface-2);
}
.mat_lib_side{
	flex: 1;
	height: 28px;
	border-radius: var(--r-sm);
	color: var(--text-2);
	font-size: 13px;
}
.mat_lib_side[aria-selected="true"]{
	background: var(--surface);
	color: var(--text);
	font-weight: 500;
	box-shadow: 0 1px 2px rgba(0, 0, 0, .25);
}
.mat_lib_pane{
	display: flex;
	flex: 1;
	flex-direction: column;
	min-height: 0;
}
.mat_lib_tabs{
	display: flex;
	flex: none;
	gap: 2px;
	padding: 10px 10px 6px;
}
.mat_lib_tab{
	display: inline-flex;
	align-items: center;
	gap: 5px;
	height: 30px;
	padding: 0 10px;
	border-radius: var(--r-sm);
	color: var(--text-2);
	font-size: 13px;
}
.mat_lib_tab[aria-selected="true"]{
	background: var(--accent-soft);
	color: var(--text);
	font-weight: 500;
}
.mat_lib_tab_count{
	color: var(--text-3);
	font-size: 11.5px;
	font-variant-numeric: tabular-nums;
}
/* материалы фирмы (js/firm-materials.js) — первой вкладкой с её названием: длинное — многоточием */
.mat_lib_tab.is_firm > span:first-child{
	max-width: 140px;
	overflow: hidden;
	text-overflow: ellipsis;
	white-space: nowrap;
}
/* человеку фирмы под полями основы: эта основа в прайсе фирмы (js/designer-stock.js: renderMatPrice) */
.mat_price{
	display: flex;
	flex-wrap: wrap;
	align-items: center;
	gap: 6px 8px;
	margin-top: 10px;
	padding: 8px 10px;
	border-radius: var(--r-sm);
	background: var(--surface-2);
	font-size: 12.5px;
}
.mat_price[hidden]{
	display: none;
}
.mat_price_text{
	flex: 1 1 160px;
	margin: 0;
	color: var(--text-2);
}
.mat_price .field_label,
.mat_price .pair,
.mat_price_acts,
.mat_price_err{
	flex: 1 1 100%;
}
.mat_price_acts{
	display: flex;
	justify-content: flex-end;
	gap: 6px;
}
.mat_price_err{
	margin: 0;
	color: var(--warn-text);
}
.mat_price_err[hidden]{
	display: none;
}
.mat_lib_rows{
	display: flex;
	flex: 1;
	flex-direction: column;
	gap: 1px;
	min-height: 0;
	overflow-y: auto;
	overscroll-behavior: contain;
	padding: 0 8px 10px;
}
.mat_lib_row{
	display: flex;
	align-items: center;
	gap: 10px;
	width: 100%;
	padding: 6px 8px;
	border-radius: var(--r-sm);
	text-align: left;
}
.mat_lib_text{
	display: flex;
	flex: 1;
	flex-direction: column;
	gap: 1px;
	min-width: 0;
}
.mat_lib_name{
	overflow: hidden;
	text-overflow: ellipsis;
	white-space: nowrap;
	font-size: 13px;
	font-weight: 500;
}
.mat_lib_params{
	color: var(--text-3);
	font-size: 12px;
	font-variant-numeric: tabular-nums;
}
.mat_lib_warn{
	color: var(--warn-text);
	font-size: 11.5px;
}
.mat_lib_row.is_chosen{
	background: var(--accent-soft);
	box-shadow: inset 0 0 0 1px var(--accent);
}
.mat_lib_row:active{
	background: var(--accent-soft);
}
@media (pointer: fine){
	.mat_lib_row:not(.is_chosen):hover{
		background: var(--surface-2);
	}
}
.mat_lib_icon{
	display: grid;
	flex: none;
	place-items: center;
	width: 28px;
	height: 28px;
	border-radius: var(--r-sm);
	background: var(--surface-2);
	color: var(--text-2);
}
.mat_lib_empty{
	padding: 14px 8px;
	color: var(--text-3);
	font-size: 12.5px;
}
/* библиотека видами (designer-stock.js: matTypeBlocks): заголовок — образец, название, что есть, стрелка;
   открытый — кнопки толщин и форматов (у профиля — сечений и длин); текущий вид — название акцентом;
   своя основа (Custom) — последней. Образец стекла — блик, матового — точки, зеркала — металлом */
.mat_type{
	flex: none;
	border-radius: var(--r-sm);
}
.mat_type.is_open{
	background: var(--surface-2);
}
.mat_type_head{
	display: flex;
	align-items: center;
	gap: 10px;
	width: 100%;
	padding: 6px 8px;
	border-radius: var(--r-sm);
	text-align: left;
}
@media (pointer: fine){
	.mat_type:not(.is_open) .mat_type_head:hover{
		background: var(--surface-2);
	}
}
.mat_type.is_current .mat_lib_name{
	color: var(--accent-ink);
}
.mat_type_swatch{
	display: grid;
	flex: none;
	place-items: center;
	width: 28px;
	height: 28px;
	border-radius: var(--r-sm);
	border: 1px solid rgba(0, 0, 0, .16);
	color: var(--text-2);
}
.mat_type_swatch[data-optic="gloss"]{
	background-image: linear-gradient(155deg, rgba(255, 255, 255, .95) 0 16%, rgba(255, 255, 255, 0) 42%, rgba(0, 0, 0, .1) 100%);
}
.mat_type_swatch[data-optic="metal"]{
	background-image: linear-gradient(160deg, rgba(255, 255, 255, .6) 0%, rgba(255, 255, 255, 0) 38%, rgba(255, 255, 255, .35) 55%, rgba(0, 0, 0, .18) 100%);
}
.mat_type_swatch[data-optic="glass"]{
	background-image: linear-gradient(135deg, rgba(255, 255, 255, .7) 0 20%, transparent 20% 46%, rgba(255, 255, 255, .45) 46% 55%, transparent 55%);
}
.mat_type_swatch[data-optic="frosted"]{
	background-image: radial-gradient(rgba(255, 255, 255, .7) 1px, transparent 1.5px);
	background-size: 4px 4px;
}
.mat_type_swatch[data-optic="mirror"]{
	background-image: linear-gradient(135deg, #f8fafb 0%, #b7bfc5 42%, #eef1f3 54%, #8c959c 100%);
}
.mat_type.is_custom .mat_type_swatch{
	border: 1px dashed var(--line-strong);
	background: var(--surface);
}
.mat_type_chev{
	flex: none;
	color: var(--text-3);
	transition: transform .15s;
}
.mat_type.is_open .mat_type_chev{
	transform: rotate(180deg);
}
.mat_type.is_custom .mat_type_chev{
	display: none;
}
.mat_type_body{
	padding: 0 10px 10px 46px;
}
.mat_chips_label{
	margin: 6px 0 4px;
	color: var(--text-3);
	font-size: 11.5px;
}
.mat_chips{
	display: flex;
	flex-wrap: wrap;
	gap: 4px;
}
.mat_chip{
	height: 26px;
	padding: 0 9px;
	border-radius: var(--r-sm);
	background: var(--btn);
	color: var(--text);
	font-size: 12.5px;
	font-variant-numeric: tabular-nums;
	white-space: nowrap;
}
@media (pointer: fine){
	.mat_chip:not(.is_chosen):hover{
		background: var(--btn-hover);
	}
}
.mat_chip.is_chosen{
	background: var(--accent);
	color: #fff;
}
.mat_chip.is_warn:not(.is_chosen){
	color: var(--warn-text);
}
/* декоры: поиск, разделы, плитки — образец и название; рисунок (дерево, камень) — лёгкой штриховкой */
.mat_decor_search{
	flex: none;
	padding: 10px 10px 4px;
}
.mat_decor_list{
	flex: 1;
	min-height: 0;
	overflow-y: auto;
	overscroll-behavior: contain;
	padding: 0 10px 12px;
}
.mat_decor_title{
	margin: 12px 2px 6px;
	color: var(--text-3);
	font-size: 11px;
	font-weight: 600;
	letter-spacing: .06em;
	text-transform: uppercase;
}
.mat_decor_title:first-child{
	margin-top: 6px;
}
.mat_decor_grid{
	display: grid;
	grid-template-columns: repeat(auto-fill, minmax(84px, 1fr));
	gap: 4px;
}
.mat_decor{
	display: flex;
	flex-direction: column;
	gap: 4px;
	min-width: 0;
	padding: 4px;
	border-radius: var(--r-sm);
	text-align: left;
}
.mat_decor_swatch{
	display: block;
	height: 38px;
	border-radius: 4px;
	border: 1px solid rgba(0, 0, 0, .16);
}
/* образец текстуры (js/textures.js): картинка поверх её среднего цвета */
.mat_swatch.is_texture,
.mat_decor_swatch.is_texture,
.part_icon.is_texture,
.mat_texture_swatch.is_texture{
	background-size: cover;
	background-position: center;
}
.mat_texture{
	display: flex;
	align-items: center;
	gap: 8px;
	padding: 6px;
	border: 1px solid var(--line);
	border-radius: var(--r-sm);
}
.mat_texture_swatch{
	flex: none;
	width: 36px;
	height: 36px;
	border-radius: 4px;
	border: 1px solid rgba(0, 0, 0, .16);
}
.mat_texture_text{
	display: flex;
	flex: 1;
	flex-direction: column;
	gap: 1px;
	min-width: 0;
}
.mat_texture_name{
	overflow: hidden;
	color: var(--text);
	font-size: 13px;
	text-overflow: ellipsis;
	white-space: nowrap;
}
.mat_texture_off{
	flex: none;
	padding: 4px 8px;
	border-radius: var(--r-sm);
	color: var(--text-2);
	font-size: 12.5px;
}
@media (pointer: fine){
	.mat_texture_off:hover{
		background: var(--surface-2);
		color: var(--text);
	}
}
.mat_decor_name{
	overflow: hidden;
	color: var(--text-2);
	font-size: 11.5px;
	text-overflow: ellipsis;
	white-space: nowrap;
}
.mat_decor.is_chosen{
	background: var(--accent-soft);
	box-shadow: inset 0 0 0 1px var(--accent);
}
.mat_decor.is_chosen .mat_decor_name{
	color: var(--text);
}
@media (pointer: fine){
	.mat_decor:not(.is_chosen):hover{
		background: var(--surface-2);
	}
}
.mat_fit{
	color: var(--warn-text);
	font-size: 12.5px;
}
.mat_fit[hidden]{
	display: none;
}
.mat_foot{
	display: flex;
	flex-direction: column;
	gap: 8px;
}
.mat_window.has_lib .mat_foot{
	flex-direction: row;
	align-items: center;
	justify-content: flex-end;
	gap: 14px;
	padding-top: 12px;
}
.mat_window.has_lib .mat_foot .btn{
	width: auto;
	min-width: 140px;
}
.mat_window.has_lib .mat_fit{
	flex: 1;
}
@media (max-width: 899px){
	.mat_window.has_lib{
		width: 100%;
	}
	.mat_window.has_lib .mat_body{
		display: flex;
		flex-direction: column;
		height: auto;
		max-height: 72vh;
		max-height: 72dvh;
		overflow-y: auto;
	}
	.mat_window.has_lib .mat_form{
		overflow: visible;
		border-right: 0;
		border-bottom: 1px solid var(--line);
	}
	.mat_window.has_lib .mat_form,
	.mat_window.has_lib .mat_lib,
	.mat_lib_pane{
		flex: none;
		min-height: auto;
	}
	.mat_lib_rows,
	.mat_decor_list{
		overflow: visible;
	}
}


/* Библиотека деталей проекта: «Project parts» (designer-parts.js: renderPartsList) — крупные строки:
   значок на плашке, название до двух строк, цена и карандаш справа. Булавка — маленький кружок в
   углу плашки, места в строке не занимает: закреплённая видна всегда, остальные — при наведении;
   под закреплёнными — черта */

.panel_head_end{
	display: flex;
	align-items: center;
	gap: 4px;
}
/* видны 4 детали (строка — 48px, .part) и отступы списка; больше — прокрутка, чат под списком (ai.css) */
.parts{
	list-style: none;
	max-height: calc( 4 * 48px + 6px );
	overflow-y: auto;
	overscroll-behavior: contain;
	padding: 4px 6px 2px;
}
.part_row{
	position: relative;
	display: flex;
	align-items: center;
	gap: 2px;
	padding-right: 4px;
	border-radius: var(--r);
}
.part_row.is_editing{
	background: var(--accent-soft);
	box-shadow: inset 0 0 0 1px var(--accent);
}
.part_row.is_editing .part .i{
	color: var(--accent-ink);
}
.part_edit{
	flex: none;
	color: var(--text-3);
}
.part_edit:disabled,
.part:disabled{
	cursor: default;
}
.part_edit:disabled{
	opacity: .35;
}
.part{
	display: flex;
	flex: 1;
	min-width: 0;
	align-items: center;
	gap: 10px;
	min-height: 48px;
	padding: 7px 8px;
	border-radius: var(--r);
	font-size: 14px;
	line-height: 1.3;
	text-align: left;
}
.part_icon{
	display: grid;
	place-items: center;
	flex: none;
	width: 34px;
	height: 34px;
	border-radius: var(--r);
	background: var(--surface-2);
}
.part .i{
	width: 18px;
	height: 18px;
	color: var(--text-2);
}
.part_name{
	flex: 1;
	min-width: 0;
	display: -webkit-box;
	-webkit-box-orient: vertical;
	-webkit-line-clamp: 2;
	overflow: hidden;
	overflow-wrap: anywhere;
}
.part_price{
	flex: none;
	color: var(--text-3);
	font-size: 13px;
	font-variant-numeric: tabular-nums;
}
.part_row:active{
	background: var(--accent-soft);
}

/* материал (designer-parts.js: materialPartRow): плашка — цветом материала, значок — контрастный */
.part_row.is_material .part_icon{
	box-shadow: inset 0 0 0 1px rgba(0, 0, 0, .1);
}
.part_row.is_material .part:not(:disabled) .i{
	color: inherit;
}

/* булавка в углу плашки */
.part_pin{
	position: absolute;
	top: calc(50% - 22px);
	left: 3px;
	z-index: 1;
	display: grid;
	place-items: center;
	width: 17px;
	height: 17px;
	padding: 0;
	border-radius: 50%;
	background: var(--surface);
	box-shadow: 0 0 0 1px var(--line-strong);
	color: var(--text-2);
	opacity: 0;
}
.part_pin .i{
	width: 11px;
	height: 11px;
}
.part_row:hover .part_pin,
.part_pin:focus-visible,
.part_pin[aria-pressed="true"]{
	opacity: 1;
}
.part_pin[aria-pressed="true"]{
	background: var(--accent);
	box-shadow: none;
	color: #fff;
}
.part_pin:disabled{
	cursor: default;
}
.part_pin:disabled:not([aria-pressed="true"]){
	opacity: 0;
}
@media (pointer: coarse){
	.part_pin:not(:disabled){
		opacity: .7;
	}
	.part_pin[aria-pressed="true"]{
		opacity: 1;
	}
}

/* черта под закреплёнными */
.part_row.pin_end{
	margin-bottom: 7px;
}
.part_row.pin_end::after{
	content: "";
	position: absolute;
	left: 8px;
	right: 8px;
	bottom: -4px;
	border-bottom: 1px solid var(--line);
}

@media (pointer: fine){
	.part_row:hover{
		background: var(--surface-2);
	}
	.part_row:hover .part_icon{
		background: var(--surface);
	}
	.part:hover:not(:disabled) .i{
		color: var(--accent-ink);
	}
	.part_edit:hover:not(:disabled){
		color: var(--accent-ink);
	}
	.part_pin:hover:not(:disabled){
		color: var(--accent-ink);
	}
	.part_pin[aria-pressed="true"]:hover:not(:disabled){
		color: #fff;
		filter: brightness(1.08);
	}
}


/* Режим редактирования детали: синяя рамка вокруг сцены и плашка сверху */

.part_bar{
	position: absolute;
	top: 0;
	left: 0;
	right: 0;
	z-index: 6;
	display: flex;
	align-items: center;
	gap: 8px;
	height: 44px;
	padding: 0 8px 0 14px;
	background: var(--accent);
	color: #fff;
}
.part_bar[hidden]{
	display: none;
}
.part_bar_icon{
	flex: none;
	width: 18px;
	height: 18px;
}
.part_bar_text{
	flex: 1;
	min-width: 0;
	overflow: hidden;
	text-overflow: ellipsis;
	white-space: nowrap;
	font-size: 13px;
}
.part_bar_label{
	opacity: .8;
	margin-right: 4px;
}
.part_bar_name{
	font-weight: 600;
}
.part_bar_price{
	margin-left: 6px;
	opacity: .8;
	font-variant-numeric: tabular-nums;
}
.part_bar .btn{
	flex: none;
	border-color: transparent;
	background: rgba(255, 255, 255, .16);
	color: #fff;
}
.part_bar .btn .i{
	color: #fff;
}
.part_bar .btn_primary{
	background: #fff;
	color: var(--accent-ink);
}
@media (pointer: fine){
	.part_bar .btn:hover:not(:disabled){
		background: rgba(255, 255, 255, .28);
	}
	.part_bar .btn_primary:hover:not(:disabled){
		background: var(--accent-soft);
	}
}
.canvas_case::after{
	content: "";
	position: absolute;
	inset: 0;
	z-index: 4;
	border: 2px solid var(--accent);
	pointer-events: none;
	opacity: 0;
}
body[data-mode="part"] .canvas_case::after{
	opacity: 1;
}
body[data-mode="part"] .tools{
	top: 56px;
}
body[data-mode="part"] .group_bar{
	top: 56px;
}
#newPart:disabled{
	opacity: .35;
	cursor: default;
}
.parts_empty{
	padding: 0 14px 4px;
	color: var(--text-3);
	font-size: 12.5px;
}
body.has_parts .parts_empty{
	display: none;
}


/* ---------- Сцена ---------- */

.canvas_case{
	grid-area: view;
	position: relative;
	min-width: 0;
	min-height: 0;
	overflow: hidden;
	background: var(--viewport);
	background: var(--viewport-bg);
}
.canvas{
	position: absolute;
	inset: 0;
	display: block;
	width: 100%;
	height: 100%;
}

.tools{
	position: absolute;
	top: 12px;
	left: 12px;
	z-index: 5;
}
/* панель вида (контуры, рёбра, тени, прозрачность, проекция, виды по осям) — справа; подсказки —
   слева от кнопок. Кнопки осей — буквы цветом оси, знак — когда вид с минуса на плюс */
.tools.tools_view{
	left: auto;
	right: 12px;
}
@media (pointer: fine){
	.tools_view .tbtn[data-tip]:hover::after{
		left: auto;
		right: calc(100% + 10px);
	}
}
/* панель вида свёрнута (designer-ui.js: setViewTools): стрелка, 3D-перспектива, виды по осям и смена
   стороны (.vkeep); у рамки на чужой странице свой набор кнопок — ниже, body[data-embed] */
body:not([data-embed]) #toolsView:not([data-open]) > :not(.vkeep){
	display: none;
}
/* режим AI: свёрнутая — ещё «к модели» и просвет у камеры (без заморозки — она по стрелке), черта перед 3D */
body[data-ui="ai"] #toolsView:not([data-open]) > .tbtn.aikeep:not([hidden]){
	display: grid;
}
body[data-ui="ai"] #toolsView:not([data-open]) > .tsep.aikeep{
	display: block;
}
.tbtn_more .i{
	transition: transform .15s;
}
#toolsView[data-open] .tbtn_more .i{
	transform: rotate(180deg);
}
.tbtn_axis{
	font-size: 12.5px;
	font-weight: 700;
	line-height: 1;
	font-variant-numeric: tabular-nums;
}
.tbtn_axis[data-view-axis="x"]{ color: var(--ax-x); }
.tbtn_axis[data-view-axis="y"]{ color: var(--ax-y); }
.tbtn_axis[data-view-axis="z"]{ color: var(--ax-z); }
.tbtn_axis[aria-pressed="true"]{
	background: var(--accent-soft);
}
.tbtn_axis{
	display: inline-flex;
	align-items: center;
	justify-content: center;
}
.tbtn_sign:empty{
	display: none;
}
/* обратная сторона вида по оси: низкая кнопка прямо под активной осью */
.tbtn.tbtn_flip{
	height: 20px;
	margin-top: -1px;
	border-radius: 0 0 var(--r-sm) var(--r-sm);
	color: var(--text-2);
}
.tbtn.tbtn_flip .i{
	width: 14px;
	height: 14px;
}
.tbtn.tbtn_flip[hidden]{
	display: none;
}
.tbtn_axis[aria-pressed="true"]:has( + .tbtn_flip:not([hidden]) ){
	border-bottom-left-radius: 0;
	border-bottom-right-radius: 0;
}
.tbtn_axis[aria-pressed="true"] + .tbtn_flip{
	background: var(--accent-soft);
}
/* под включённой кнопкой — её низкая кнопка (заморозка просвета, view.js): как переключатель стороны */
.tbtn.tbtn_sub{
	height: 20px;
	margin-top: -1px;
	border-radius: 0 0 var(--r-sm) var(--r-sm);
	color: var(--text-2);
}
.tbtn.tbtn_sub .i{
	width: 14px;
	height: 14px;
}
.tbtn.tbtn_sub[hidden]{
	display: none;
}
.tbtn[aria-pressed="true"]:has( + .tbtn_sub:not([hidden]) ){
	border-bottom-left-radius: 0;
	border-bottom-right-radius: 0;
}
.tbtn[aria-pressed="true"] + .tbtn_sub{
	background: var(--accent-soft);
}
.tbtn.tbtn_sub[aria-pressed="true"]{
	background: var(--accent);
	color: #fff;
}
.tools_case{
	display: flex;
	flex-direction: column;
	gap: 2px;
	padding: 4px;
	background: var(--surface);
	border-radius: var(--r);
	box-shadow: 0 1px 2px rgba(0, 0, 0, .18), 0 6px 16px rgba(0, 0, 0, .14);
}
.tbtn{
	position: relative;
	display: grid;
	place-items: center;
	width: 32px;
	height: 32px;
	border-radius: var(--r-sm);
	color: var(--text-2);
}
.tbtn.aux_active,
.tbtn.select_button,
.tbtn[aria-pressed="true"]{
	background: var(--accent-soft);
	color: var(--accent-ink);
}
.tsep{
	display: block;
	height: 1px;
	margin: 3px 4px;
	background: var(--line);
}

@media (pointer: fine){
	.tbtn:hover:not(.aux_active):not(.select_button):not([aria-pressed="true"]):not(:disabled){
		background: var(--surface-2);
		color: var(--text);
	}
	/* подсказка справа от кнопки */
	.tbtn[data-tip]:hover::after{
		content: attr(data-tip);
		position: absolute;
		left: calc(100% + 10px);
		top: 50%;
		transform: translateY(-50%);
		padding: 4px 8px;
		border-radius: var(--r-sm);
		background: var(--tip-bg);
		color: var(--tip-text);
		box-shadow: 0 2px 8px rgba(0, 0, 0, .25);
		font-size: 12px;
		white-space: nowrap;
		pointer-events: none;
		z-index: 10;
	}
}

/* кнопки треугольников доступны, только когда ничего не выбрано */
.only-none{
	display: none;
}
body[data-selection="none"] .tbtn.only-none{
	display: grid;
}
body[data-selection="none"] .tsep.only-none{
	display: block;
}

.mobile_bar{
	display: none;
}


/* недоступная кнопка панели инструментов */
.tbtn:disabled{
	opacity: .4;
	cursor: default;
}


/* ---------- Расширенный режим (designer-ui.js) ---------- */

/* переменные, формулы, массивы, участки, крепёж, список операций и их привязка при растяжении,
   разделы, цветовые группы — видны только при body[data-advanced] */
body:not([data-advanced]) .adv{
	display: none !important;
}
/* блок операций с не применённой операцией (ops.js: op.refused) — виден всегда: причину видно */
body:not([data-advanced]) .group.fold.adv.is_alert{
	display: flex !important;
}
/* дополнительные блоки свойств (положение, поворот, отступы, анимация): в простом режиме — по ссылке «Additional
   settings» в конце свойств (designer-ui.js: setMore), в расширенном видны всегда и ссылки нет */
body:not([data-more]):not([data-advanced]) .more{
	display: none !important;
}
body[data-advanced] .more_link{
	display: none;
}
.more_link{
	align-self: flex-start;
	margin: 4px 14px 14px;
	padding: 0;
	color: var(--accent-ink);
	font-size: 12px;
	font-weight: 500;
	text-align: left;
}
@media (pointer: fine){
	.more_link:hover{ text-decoration: underline; }
}
/* строки элементов, которых нет при нынешних значениях формул (place.visible), — только в расширенном */
body:not([data-advanced]) .elements li:has(> .element.is_absent){
	display: none;
}


/* ---------- Свойства ---------- */

.props_empty,
.props_body{
	display: none;
}
.props_empty{
	padding: 4px 14px 16px;
	color: var(--text-3);
	font-size: 12.5px;
}
body[data-selection="none"] .props_empty{
	display: block;
}

/* ничего не выделено: общий размер сцены, очистка, пересечения */
.props_scene{
	display: none;
}
body[data-selection="none"] .props_scene{
	display: block;
}

/* крепёж выбран, но не поставлен (fasteners.js: fastenProblemsHtml): правая колонка, окна Documents,
   Download и заявки фирме (makers.js); красный — как его показ на сцене */
.fasten_alert{
	display: flex;
	flex-direction: column;
	gap: 2px;
	margin-top: 8px;
	padding: 8px;
	border-left: 3px solid var(--danger);
	border-radius: var(--r);
	background: var(--danger-soft);
	max-height: 220px;
	overflow-y: auto;
}
.fasten_alert[hidden]{
	display: none;
}
.fasten_alert_title{
	margin: 0 0 4px;
	font-size: 12.5px;
	font-weight: 600;
}
/* строка: что и почему (кнопка — выделить деталь; у выделенной — просто текст), справа — исправление */
.fasten_problem{
	display: flex;
	align-items: center;
	gap: 6px;
}
.fasten_problem_main{
	flex: 1;
	min-width: 0;
	display: flex;
	flex-direction: column;
	align-items: flex-start;
	gap: 1px;
	padding: 4px 6px;
	border: 0;
	border-radius: var(--r);
	background: none;
	color: inherit;
	font: inherit;
	font-size: 12.5px;
	text-align: left;
}
button.fasten_problem_main{
	cursor: pointer;
}
@media (pointer: fine){
	button.fasten_problem_main:hover{ background: var(--surface-2); }
}
.fasten_fix{
	flex: none;
	min-height: 28px;
	padding: 0 10px;
	font-size: 12.5px;
	white-space: nowrap;
}
#fastenWarns{
	margin: 8px 0 0;
}
.fasten_problem_why{
	color: var(--text-3);
	font-size: 12px;
}
.cut_fasten_alert{
	flex: none;
	margin: 8px 16px 0;
	max-height: 120px;
}
#downloadFastenAlert{
	margin: 0 0 12px;
}

/* пересечения (clash.js): пара деталей и размер общей части */
.clash_list{
	display: flex;
	flex-direction: column;
	gap: 2px;
	max-height: 260px;
	overflow-y: auto;
}
.clash_list:empty{
	display: none;
}
.clash_row{
	display: flex;
	align-items: center;
	gap: 8px;
	min-height: 30px;
	padding: 0 8px;
	border-radius: var(--r);
	font-size: 12.5px;
	cursor: pointer;
}
@media (pointer: fine){
	.clash_row:hover{ background: var(--surface-2); }
}
.clash_names{
	flex: 1;
	min-width: 0;
	overflow: hidden;
	text-overflow: ellipsis;
	white-space: nowrap;
}
.clash_size{
	color: var(--text-3);
	font-variant-numeric: tabular-nums;
	white-space: nowrap;
}
body[data-selection="figure"] .props_body{
	display: block;
}

.identity{
	display: flex;
	align-items: center;
	gap: 8px;
	padding: 2px 8px 12px 14px;
	border-bottom: 1px solid var(--line);
}
.identity_icon{
	color: var(--accent-ink);
}
/* карандаш, линейка, глаз, замок, удалить — плотнее: имени остаётся место */
.identity .icon_btn{
	width: 28px;
	margin-left: -4px;
}
/* шапка выделенного в Properties: значок и название — первой строкой на всю ширину, действия — второй
   (карандаш, копия, линейка, глаз, замок; удалить — отдельно справа) */
.identity_sel{
	flex-wrap: wrap;
	row-gap: 6px;
}
/* длинное название — в две строки, дальше многоточие */
.identity_sel .identity_name{
	display: -webkit-box;
	-webkit-box-orient: vertical;
	-webkit-line-clamp: 2;
	white-space: normal;
	overflow-wrap: anywhere;
	line-height: 1.3;
}
.identity_acts{
	display: flex;
	flex-basis: 100%;
	align-items: center;
	gap: 2px;
	margin-left: -7px;
}
.identity_acts .icon_btn{
	width: 30px;
	margin-left: 0;
}
.identity_acts #removeMesh{
	margin-left: auto;
}
/* не по умолчанию (не в размерах, скрыт) — как в строке списка Elements, только заметнее */
.identity .icon_btn.is_on{
	color: var(--accent-ink);
}
.identity_name{
	flex: 1;
	min-width: 0;
	overflow: hidden;
	text-overflow: ellipsis;
	white-space: nowrap;
	font-size: 14px;
	font-weight: 600;
}

#lock .i_locked{ display: none; }
#lock.icon_lock .i_locked{ display: block; }
#lock.icon_lock .i_unlocked{ display: none; }
#lock.icon_lock{ color: var(--danger); }

/* ---------- линейка (measure.js): линии, маркеры и числа поверх сцены ---------- */
.measure_layer{
	position: absolute;
	inset: 0;
	z-index: 6;
	pointer-events: none;
	overflow: hidden;
}
.measure_layer[hidden]{
	display: none;
}
.measure_svg{
	position: absolute;
	inset: 0;
	width: 100%;
	height: 100%;
}
.measure_line{
	stroke: var(--accent);
	stroke-width: 1.5;
}
.measure_line.is_live{
	stroke-dasharray: 5 4;
}
.measure_end{
	fill: #FFFFFF;
	stroke: var(--accent);
	stroke-width: 1.5;
}
.measure_line.ax_x, .measure_end.ax_x{ stroke: var(--ax-x); }
.measure_line.ax_y, .measure_end.ax_y{ stroke: var(--ax-y); }
.measure_line.ax_z, .measure_end.ax_z{ stroke: var(--ax-z); }
.measure_snap{
	fill: none;
	stroke: var(--accent);
	stroke-width: 2;
}
.measure_snap.is_face{
	fill: var(--accent);
	stroke: none;
}
.measure_label{
	position: absolute;
	left: 0;
	top: 0;
	display: flex;
	flex-direction: column;
	align-items: center;
	gap: 1px;
	padding: 3px 7px;
	border: 0;
	border-radius: 6px;
	background: var(--tip-bg);
	color: var(--tip-text);
	font: 500 12px/1.2 var(--font);
	font-variant-numeric: tabular-nums;
	white-space: nowrap;
	box-shadow: 0 2px 8px rgba(0, 0, 0, .25);
	pointer-events: none;
}
.measure_label[hidden]{
	display: none;
}
/* готовое измерение: число (клик — убрать) и замок (закрепить на сцене, measure.js: setPinned) */
.measure_label.is_done{
	flex-direction: row;
	align-items: stretch;
	gap: 0;
	padding: 0;
	overflow: hidden;
	pointer-events: auto;
}
.measure_num{
	display: flex;
	flex-direction: column;
	align-items: center;
	gap: 1px;
	padding: 3px 3px 3px 7px;
	border: 0;
	background: none;
	color: inherit;
	font: inherit;
	cursor: pointer;
}
.measure_pin{
	display: flex;
	align-items: center;
	padding: 0 6px 0 4px;
	border: 0;
	background: none;
	color: inherit;
	opacity: .5;
	cursor: pointer;
}
.measure_pin .i{
	width: 13px;
	height: 13px;
	stroke-width: 2;
}
.measure_label.is_pinned .measure_pin{
	opacity: 1;
	color: #6CC0FF;
}
@media (pointer: fine){
	.measure_num:hover{
		background: var(--danger);
		color: #FFFFFF;
	}
	.measure_num:hover .measure_value::after{
		content: " ×";
	}
	.measure_pin:hover{
		opacity: 1;
		background: rgba(255, 255, 255, .14);
	}
}
/* ручка конца закреплённого: тянут — конец прилипает (measure.js: gripMove) */
.measure_grip{
	position: absolute;
	left: 0;
	top: 0;
	width: 18px;
	height: 18px;
	border-radius: 50%;
	pointer-events: auto;
	touch-action: none;
	cursor: grab;
}
.measure_grip::after{
	content: "";
	position: absolute;
	inset: 4px;
	border-radius: 50%;
	background: #FFFFFF;
	box-shadow: 0 0 0 2px var(--accent), 0 1px 4px rgba(0, 0, 0, .35);
}
.measure_grip.ax_x::after{ box-shadow: 0 0 0 2px var(--ax-x), 0 1px 4px rgba(0, 0, 0, .35); }
.measure_grip.ax_y::after{ box-shadow: 0 0 0 2px var(--ax-y), 0 1px 4px rgba(0, 0, 0, .35); }
.measure_grip.ax_z::after{ box-shadow: 0 0 0 2px var(--ax-z), 0 1px 4px rgba(0, 0, 0, .35); }
.measure_grip.is_drag{
	cursor: grabbing;
}
.measure_grip[hidden]{
	display: none;
}
@media (pointer: coarse){
	.measure_grip{
		width: 32px;
		height: 32px;
	}
	.measure_grip::after{
		inset: 10px;
	}
}
/* открыт другой инструмент — клик сквозь ручку и число его: точка Move прилипает к концу сама (SnapPicker);
   клик по числу убрал бы измерение, а инструмент не получил бы клика */
body[data-move] .measure_grip,
body[data-tool] .measure_grip,
body[data-bend] .measure_grip,
body[data-press] .measure_grip,
body[data-mill] .measure_grip,
body[data-move] .measure_label,
body[data-tool] .measure_label,
body[data-bend] .measure_label,
body[data-press] .measure_label,
body[data-mill] .measure_label{
	pointer-events: none;
}
.measure_hint[hidden]{
	display: none;
}
.measure_value{
	font-size: 13px;
	font-weight: 600;
}
.measure_sub{
	font-size: 10.5px;
	opacity: .8;
}
.measure_sub i{
	font-style: normal;
	font-weight: 600;
}
.measure_sub i.ax_x{ color: #FF8A8D; }
.measure_sub i.ax_y{ color: #6FD39A; }
.measure_sub i.ax_z{ color: #8CA8FF; }
.measure_hint{
	position: absolute;
	left: 50%;
	bottom: 15px;
	transform: translateX(-50%);
	display: flex;
	align-items: center;
	gap: 10px;
	padding: 6px 8px 6px 14px;
	border-radius: 999px;
	background: var(--tip-bg);
	color: var(--tip-text);
	font-size: 12px;
	white-space: nowrap;
	box-shadow: 0 4px 16px rgba(0, 0, 0, .25);
	pointer-events: auto;
}
.measure_hint b{
	font-weight: 600;
}
.measure_clear{
	height: 24px;
	padding: 0 10px;
	border: 0;
	border-radius: 999px;
	background: rgba(255, 255, 255, .14);
	color: inherit;
	font: inherit;
	cursor: pointer;
}
.measure_clear[hidden]{
	display: none;
}
@media (pointer: fine){
	.measure_clear:hover{
		background: rgba(255, 255, 255, .24);
	}
}
@media (max-width: 760px){
	.measure_hint_text{
		display: none;
	}
	.measure_hint{
		padding: 6px;
	}
	.measure_hint::before{
		content: "Tap two points";
		padding-left: 6px;
	}
	/* перемещение по точкам (move.js) — та же плашка */
	.measure_hint.move_hint::before{
		content: "Tap the point to move from, then where to";
	}
	.measure_hint.move_hint.is_stretch::before{
		content: "Tap where this corner goes";
	}
}

/* размеры и поворот одной строкой: три колонки, в каждой подпись и замок над полем */
.axes3,
.axes3.field_size{
	display: grid;
	grid-template-columns: repeat(3, minmax(0, 1fr));
	gap: 6px;
}
.axes3_cell{
	display: flex;
	flex-direction: column;
	gap: 3px;
	min-width: 0;
}
.axes3_head{
	display: flex;
	align-items: center;
	justify-content: space-between;
	height: 22px;
	min-width: 0;
}
.axes3_head > label{
	color: var(--text-2);
	font-size: 12px;
	overflow: hidden;
	text-overflow: ellipsis;
	white-space: nowrap;
}
.axes3_head > label.ax_x{ color: var(--ax-x); font-weight: 600; }
.axes3_head > label.ax_y{ color: var(--ax-y); font-weight: 600; }
.axes3_head > label.ax_z{ color: var(--ax-z); font-weight: 600; }
.axes3 .size_lock{
	width: 22px;
	height: 22px;
}
.axes3 .size_lock .i{
	width: 14px;
	height: 14px;
}
.axes3 .input{
	width: 100%;
	min-width: 0;
	padding-left: 7px;
	padding-right: 7px;
}
.axes3 .input_suffix{
	min-width: 0;
}

/* габариты: подпись, поле, замок оси */
.field_size{
	grid-template-columns: 84px minmax(0, 1fr) auto;
	gap: 4px 8px;
}
.field_size .input{ font-variant-numeric: tabular-nums; }
.field_size .input:focus{ box-shadow: 0 0 0 3px var(--accent-soft); }
.size_lock .i_locked{ display: none; }
.size_lock.is_locked .i_locked{ display: block; }
.size_lock.is_locked .i_unlocked{ display: none; }
.size_lock.is_locked{ color: var(--danger); }
.size_lock:disabled{ opacity: .4; pointer-events: none; }

.group{
	display: flex;
	flex-direction: column;
	gap: 10px;
	padding: 14px;
	border-bottom: 1px solid var(--line);
}
/* блок, которому нечего показать (Parameters копии, Variables объекта, Fasteners): display: flex выше
   иначе перебил бы атрибут hidden */
.group[hidden]{
	display: none;
}
.group_title{
	font-size: 12px;
	font-weight: 600;
}

.field{
	display: grid;
	grid-template-columns: 84px minmax(0, 1fr);
	align-items: center;
	gap: 8px;
	min-height: 30px;
}
.field_top{
	align-items: start;
}
.field_top > label,
.field_top > .field_label{
	line-height: 30px;
}
/* поле на всю ширину, подпись над ним: точки ломаной — три числа в строку (в колонке у подписи «−1000» не влезало) */
.field_wide{
	grid-template-columns: minmax(0, 1fr);
	gap: 4px;
}
.field_wide > .field_label{
	line-height: normal;
}
.field > label,
.field_label{
	color: var(--text-2);
	font-size: 12.5px;
}
.stack{
	display: flex;
	flex-direction: column;
	gap: 6px;
	min-width: 0;
}

.color_field{
	display: flex;
	align-items: center;
	gap: 8px;
	height: 30px;
	padding: 3px 8px 3px 3px;
	border: 1px solid var(--line-strong);
	border-radius: var(--r-sm);
	cursor: pointer;
	font-variant-numeric: tabular-nums;
}
.color_field:focus-within{
	border-color: var(--accent);
	box-shadow: 0 0 0 3px var(--accent-soft);
}
.color_field input{
	width: 22px;
	height: 22px;
	padding: 0;
	border: 0;
	border-radius: 3px;
	background: none;
	cursor: pointer;
	-webkit-appearance: none;
	appearance: none;
}
.color_field input::-webkit-color-swatch-wrapper{ padding: 0; }
.color_field input::-webkit-color-swatch{ border: 1px solid rgba(0, 0, 0, .12); border-radius: 3px; }
.color_field input::-moz-color-swatch{ border: 1px solid rgba(0, 0, 0, .12); border-radius: 3px; }

/* сегментированный переключатель осей */
.seg{
	display: grid;
	grid-template-columns: repeat(3, 1fr);
	gap: 2px;
	padding: 2px;
	border-radius: var(--r-sm);
	background: var(--surface-2);
}
.seg_item{
	position: relative;
	cursor: pointer;
}
.seg_item input{
	position: absolute;
	opacity: 0;
	pointer-events: none;
}
.seg_item span,
.seg_buttons button{
	display: grid;
	place-items: center;
	height: 24px;
	border-radius: 4px;
	font-size: 12px;
	font-weight: 600;
}
.seg_item input:checked + span{
	background: var(--surface);
	box-shadow: 0 1px 2px rgba(0, 0, 0, .12);
}
.seg_item input:focus-visible + span{
	outline: 2px solid var(--accent);
}
.seg_buttons button:active{
	background: var(--surface);
}
@media (pointer: fine){
	.seg_buttons button:hover,
	.seg_item:hover span{
		background: var(--surface);
	}
}
.ax_x{ color: var(--ax-x); }
.ax_y{ color: var(--ax-y); }
.ax_z{ color: var(--ax-z); }

.rotate_row{
	display: grid;
	grid-template-columns: minmax(0, 1fr) auto;
	gap: 6px;
}
.input_suffix{
	position: relative;
}
.input_suffix .input{
	padding-right: 22px;
}
.input_suffix span{
	position: absolute;
	right: 8px;
	top: 50%;
	transform: translateY(-50%);
	color: var(--text-3);
	pointer-events: none;
}



/* ---------- Диалоги ---------- */

.overlay{
	position: fixed;
	inset: 0;
	background: rgba(24, 27, 32, .45);
	z-index: 99999;
}

.window{
	position: fixed;
	top: 50%;
	left: 50%;
	transform: translate(-50%, -50%);
	width: min(380px, calc(100vw - 32px));
	background: var(--surface);
	border-radius: var(--r-lg);
	box-shadow: var(--shadow-window);
	z-index: 100000;
}
.window_head{
	display: flex;
	align-items: center;
	justify-content: space-between;
	padding: 12px 10px 4px 18px;
}
.window_title{
	font-size: 15px;
	font-weight: 600;
}
.window_body{
	display: flex;
	flex-direction: column;
	gap: 8px;
	padding: 10px 18px;
}
.window_field{
	display: flex;
	flex-direction: column;
	gap: 6px;
}
.window_field + .window_field{
	margin-top: 4px;
}
.input[aria-invalid="true"]{
	border-color: var(--danger);
}
.window_note{
	color: var(--text-3);
	font-size: 12.5px;
}
.window_foot{
	padding: 8px 18px 18px;
}
.window_foot .btn{
	height: 36px;
}
.props_hint.props_warn{
	margin-bottom: 8px;
	padding: 8px 10px;
	border-radius: var(--r-sm);
	background: var(--warn-bg);
	color: var(--warn-text);
}
.props_hint.props_warn[hidden]{
	display: none;
}
.btn_danger_text{
	margin-top: 6px;
	border-color: transparent;
	background: none;
	color: var(--danger);
}
.btn_danger_text .i{
	color: var(--danger);
}
.btn_danger_text[hidden]{
	display: none;
}
@media (pointer: fine){
	.btn_danger_text:hover:not(:disabled){
		background: var(--danger-soft);
	}
}

.option{
	display: flex;
	align-items: center;
	gap: 10px;
	padding: 10px 12px;
	border: 1px solid var(--line);
	border-radius: var(--r);
	cursor: pointer;
}
.option:has(input[name="format"]:checked){
	border-color: var(--accent);
	background: var(--accent-soft);
}
/* строка с двумя форматами (окно Download: 3D model, Parts list): своя метка у радио строки, справа —
   переключатель формата; щелчок по нему выбирает и строку (designer-ui.js: pickDownloadRow) */
.option_main{
	display: flex;
	flex: 1;
	align-items: center;
	gap: 10px;
	min-width: 0;
	cursor: pointer;
}
.seg.option_seg{
	flex: none;
	width: 116px;
	margin: 0;
}
/* выбранный формат — подложкой и ярким текстом, другой — бледным (в тёмной теме подложки почти не различить) */
.option_seg .seg_item span{
	height: 26px;
	color: var(--text-2);
}
.option_seg .seg_item input:checked + span{
	color: var(--text);
}
.option input[type="radio"]{
	width: 16px;
	height: 16px;
	accent-color: var(--accent);
	flex: none;
}
.option_text{
	display: flex;
	flex-direction: column;
	flex: 1;
	min-width: 0;
}
.option_text strong{
	font-weight: 600;
}
.option_text span{
	color: var(--text-2);
	font-size: 12.5px;
}
.option_select{
	width: auto;
	flex: none;
}
/* окно скачивания длиннее экрана ноутбука, когда открыто превью бирки */
#downloadWindow{
	max-height: calc(100dvh - 32px);
	overflow-y: auto;
}
/* бирки деталей (labels.js): размер, превью первой бирки (белая, как бумага — и в тёмной теме) и
   сколько их — только когда выбраны */
.labels_setup{
	display: none;
	flex-direction: column;
	align-items: center;
	gap: 8px;
	padding: 2px 0 4px;
}
.option_labels:has(input:checked) + .labels_setup{
	display: flex;
}
.labels_setup .input{
	width: 100%;
}
.labels_preview{
	line-height: 0;
}
.labels_preview svg{
	background: #FFF;
	border-radius: 3px;
	box-shadow: 0 0 0 1px var(--line), 0 2px 8px rgba(0, 0, 0, .18);
}
.labels_note{
	margin: 0;
	color: var(--text-2);
	font-size: 12.5px;
	text-align: center;
}


/* ---------- Загрузка ---------- */

/* экран загрузки (designer-new/index.php): сплошной, в тон теме — знак, слоган и полоска хода загрузки
   (её длину ставит скрипт рядом с разметкой: transform: scaleX) */
.preloader{
	position: fixed;
	inset: 0;
	z-index: 999999;
	display: grid;
	place-items: center;
	background: var(--surface);
	color: var(--text);
}
.preloader_box{
	display: flex;
	flex-direction: column;
	align-items: center;
	width: min(240px, calc(100vw - 64px));
}
.preloader_logo{
	width: 172px;
	height: 26px;
}
.preloader_slogan{
	margin: 14px 0 0;
	color: var(--text-2);
	font-size: 14px;
	letter-spacing: .01em;
}
.preloader_bar{
	width: 100%;
	height: 3px;
	margin-top: 28px;
	overflow: hidden;
	border-radius: 2px;
	background: var(--line);
}
.preloader_fill{
	display: block;
	height: 100%;
	background: var(--accent);
	transform: scaleX(0);
	transform-origin: left;
	transition: transform .15s linear;
}
/* сайт фирмы: её знак и название, крупнее, чем в шапке */
.preloader_firm{
	display: flex;
	align-items: center;
	gap: 12px;
	max-width: 100%;
}
.preloader_firm .logo_mark{
	width: 44px;
	height: 44px;
	box-shadow: 0 0 0 1px var(--line);
	font-size: 20px;
}
.preloader_firm .logo_name{
	font-size: 18px;
	font-weight: 600;
}

.scrim{
	display: none;
}


/* ==========================================================================
   Средние экраны: колонки уже
   ========================================================================== */



/* ==========================================================================
   Мобильная версия: сцена на весь экран, колонки — выдвижные панели
   ========================================================================== */

@media (max-width: 899px){

	body{
		grid-template-columns: minmax(0, 1fr);
		grid-template-areas:
			"header"
			"view";
	}

	/* шапка — в две полосы, в одну всё не влезает: сверху меню, логотип и кнопки, под ними — проект (название,
	   варианты, запись, «Public»). Режим студии, часы версий и Plans — в меню ☰. Что стоит под шапкой (панели,
	   окно вариантов, версии), берёт её высоту из --header-h */
	:root{
		--buttons-row: 48px;
		--project-row: 40px;
		--header-h: calc(var(--buttons-row) + var(--project-row));
	}
	.header{
		grid-template-columns: auto auto minmax(0, 1fr) auto;
		grid-template-rows: minmax(0, 1fr) var(--project-row);
		grid-template-areas:
			"menu    logo    .       right"
			"project project project project";
		column-gap: 6px;
		row-gap: 0;
		padding: 0 8px 0 4px;
	}
	.header_left{
		display: contents;
	}
	.menu_case{
		grid-area: menu;
	}
	.logo{
		grid-area: logo;
	}
	.header_right{
		grid-area: right;
	}
	.header_project{
		grid-area: project;
		display: flex;
		align-items: center;
		gap: 6px;
		min-width: 0;
		margin: 0 -8px 0 -4px;
		padding: 0 8px;
		border-top: 1px solid var(--line);
	}
	.project_title{
		flex: 1 1 auto;
		max-width: none;
	}
	.project_title .versions_btn,
	#plansBtn{
		display: none;
	}
	.project_title .header_input{
		flex: 1 1 auto;
		min-width: 40px;
	}
	.header_input{
		text-align: left;
		padding: 0 8px;
	}
	/* 16px — чтобы iOS не увеличивал страницу при фокусе на поле */
	.header_input,
	.input{
		font-size: 16px;
	}
	.btn_label{
		display: none;
	}
	.part_bar_label{
		display: none;
	}
	.part_bar_details{
		width: 34px;
		padding: 0;
	}

	.panel{
		position: fixed;
		z-index: 50;
		transition: transform .22s ease;
	}
	.panel_close{
		display: inline-grid;
	}

	/* элементы — выезжают слева */
	.panel_left{
		top: var(--header-h);
		bottom: 0;
		left: 0;
		width: min(300px, 86vw);
		border-right: 0;
		transform: translateX(-100%);
		padding-bottom: env(safe-area-inset-bottom);
	}
	body[data-panel="elements"] .panel_left{
		transform: none;
		box-shadow: 8px 0 32px rgba(0, 0, 0, .18);
	}

	/* свойства — нижний лист */
	.panel_right{
		left: 0;
		right: 0;
		bottom: 0;
		max-height: 72vh;
		max-height: 72dvh;
		border-left: 0;
		border-radius: 14px 14px 0 0;
		transform: translateY(100%);
		padding-bottom: env(safe-area-inset-bottom);
	}
	body[data-panel="props"] .panel_right{
		transform: none;
		box-shadow: 0 -8px 32px rgba(0, 0, 0, .18);
	}
	.panel_right .panel_head{
		height: 48px;
	}

	.scrim{
		display: block;
		position: fixed;
		inset: var(--header-h) 0 0 0;
		background: rgba(24, 27, 32, .32);
		opacity: 0;
		pointer-events: none;
		transition: opacity .22s ease;
		z-index: 40;
	}
	body[data-panel] .scrim{
		opacity: 1;
		pointer-events: auto;
	}

	.shape{
		height: 64px;
	}
	.element{
		height: 40px;
	}

	.tools{
		top: 10px;
		left: 10px;
	}
	.tbtn{
		width: 40px;
		height: 40px;
	}

	.mobile_bar{
		display: flex;
		justify-content: space-between;
		position: absolute;
		left: 10px;
		right: 10px;
		bottom: calc(10px + env(safe-area-inset-bottom));
		pointer-events: none;
		z-index: 5;
	}
	.mbtn{
		position: relative;
		display: inline-flex;
		align-items: center;
		gap: 8px;
		height: 40px;
		padding: 0 14px 0 12px;
		border-radius: 20px;
		background: var(--surface);
		box-shadow: 0 1px 2px rgba(0, 0, 0, .18), 0 6px 16px rgba(0, 0, 0, .14);
		font-weight: 500;
		pointer-events: auto;
	}
	.mbtn .i{
		color: var(--text-2);
	}
	/* инструменты и вид — по кнопке «Tools» (designer-ui.js: body[data-mtools]); во встроенной 3D и со
	   спрятанными колонками (просмотр по ссылке — там нижней строки нет) — как были */
	body:not([data-mtools]):not([data-embed]):not([data-panels="off"]) .tools{
		display: none;
	}
	.mbtn_tools[aria-pressed="true"]{
		background: var(--accent-soft);
	}
	/* точка: есть выбранный элемент со свойствами */
	body[data-selection="figure"] .mbtn_props::after,
	body[data-selection="group"] .mbtn_props::after,
	body[data-selection="multi"] .mbtn_props::after,
	body[data-selection="connector"] .mbtn_props::after{
		content: "";
		position: absolute;
		top: 8px;
		right: 8px;
		width: 7px;
		height: 7px;
		border-radius: 50%;
		background: var(--accent);
	}

	.window{
		top: auto;
		bottom: 0;
		left: 0;
		right: 0;
		transform: none;
		width: 100%;
		border-radius: 14px 14px 0 0;
		padding-bottom: env(safe-area-inset-bottom);
	}
}

@media (max-width: 599px){
	.logo{
		display: none;
	}
}

@media (prefers-reduced-motion: reduce){
	.panel,
	.scrim{
		transition: none;
	}
	.loader{
		animation-duration: 2s;
	}
}


/* ---------- Группы ---------- */

/* вложенные элементы списка сдвинуты вправо, открытая группа обведена */
.element{
	padding-left: calc(8px + var(--depth, 0) * 14px);
}
.element.is_open{
	box-shadow: inset 0 0 0 1px var(--line-strong);
}

/* правая панель: мультивыделение и свойства группы */
.props_multi,
.only-group{
	display: none;
}
body[data-selection="multi"] .props_multi{
	display: flex;
	flex-direction: column;
	gap: 10px;
	padding: 4px 14px 16px;
}
body[data-selection="group"] .props_body{
	display: block;
}
body[data-selection="group"] .only-figure{
	display: none;
}
body[data-selection="group"] .only-group{
	display: flex;
}
.props_multi_title{
	font-size: 14px;
	font-weight: 600;
}
.props_hint{
	color: var(--text-3);
	font-size: 12px;
}
/* «How it works» в конце блока правой колонки — статья справочника в новой вкладке (designer-new/index.php:
   helpLink); мелко и не вровень с полями: не кнопка */
.help_link{
	align-self: flex-start;
	color: var(--text-3);
	font-size: 11px;
	line-height: 1.3;
	text-decoration: underline;
	text-decoration-color: color-mix(in srgb, currentColor 40%, transparent);
	text-underline-offset: 2px;
}
.help_link:hover{
	color: var(--accent);
	text-decoration-color: currentColor;
}
.rpane_mats .help_link{
	display: inline-block;
	margin: 4px 14px 14px;
}
/* режим AI: карточки материалов — на сцене (designer-ui.js: setPanels), ссылки там нет */
.canvas_case > .rpane_mats .help_link{
	display: none;
}

/* плашка открытой группы над сценой */
.group_bar{
	position: absolute;
	top: 12px;
	left: 50%;
	z-index: 5;
	display: flex;
	align-items: center;
	gap: 8px;
	max-width: calc(100% - 140px);
	padding: 4px 4px 4px 10px;
	transform: translateX(-50%);
	background: var(--surface);
	border-radius: var(--r);
	box-shadow: 0 1px 2px rgba(0, 0, 0, .18), 0 6px 16px rgba(0, 0, 0, .14);
	font-size: 12.5px;
}
.group_bar[hidden]{
	display: none;
}
.group_bar > .i{
	flex: none;
	width: 16px;
	height: 16px;
	color: var(--text-2);
}
.group_bar_path{
	min-width: 0;
	overflow: hidden;
	text-overflow: ellipsis;
	white-space: nowrap;
	font-weight: 500;
}
.group_bar .btn{
	flex: none;
	height: 26px;
}

/* коннектор: свойства в правой колонке и подсказка с типом над сценой */
.only-connector{
	display: none;
}
body[data-selection="connector"] .props_body{
	display: block;
}
body[data-selection="connector"] .only-figure,
body[data-selection="connector"] .no-connector{
	display: none;
}
body[data-selection="connector"] .only-connector{
	display: flex;
}
.xyz{
	display: grid;
	grid-template-columns: repeat(3, minmax(0, 1fr));
	gap: 4px;
}
.xyz .input{
	padding-left: 6px;
	padding-right: 6px;
	font-variant-numeric: tabular-nums;
}
.xyz .input:focus{
	box-shadow: 0 0 0 3px var(--accent-soft);
}
.connector_tip{
	position: absolute;
	z-index: 7;
	padding: 3px 7px;
	border-radius: var(--r-sm);
	background: var(--tip-bg);
	color: var(--tip-text);
	font-size: 12px;
	font-weight: 500;
	white-space: nowrap;
	pointer-events: none;
	transform: translate(-50%, calc(-100% - 10px));
}
.connector_tip[hidden]{
	display: none;
}


/* ---------- Переключатели ---------- */
/* сегментный переключатель: кнопки в ряд, нажатая — подложкой; hidden — спрятан (display: grid ниже
   перебил бы атрибут) */
.seg[hidden]{
	display: none;
}
.seg{
	display: grid;
	grid-template-columns: 1fr 1fr;
	gap: 2px;
	margin-bottom: 10px;
	padding: 2px;
	border-radius: var(--r);
	background: var(--surface-2);
}
.seg_btn{
	height: 28px;
	border-radius: var(--r-sm);
	color: var(--text-2);
	font-size: 12.5px;
	font-weight: 500;
}
.seg_btn[aria-pressed="true"]{
	background: var(--surface);
	color: var(--text);
	box-shadow: 0 1px 2px rgba(0, 0, 0, .1);
}
@media (pointer: fine){
	.seg_btn:hover{ color: var(--text); }
}

.group_pick{
	display: flex;
	gap: 4px;
	min-width: 0;
}
.group_pick select{
	flex: 1;
	min-width: 0;
}
.group_pick .icon_btn{
	flex: none;
}


/* ---------- Разделы библиотеки деталей ---------- */

.section_row{
	display: flex;
	align-items: center;
	gap: 2px;
	height: 30px;
	margin-top: 8px;
	padding-left: 8px;
	border-top: 1px solid var(--line);
	padding-top: 6px;
	box-sizing: content-box;
}
.section_name{
	flex: 1;
	min-width: 0;
	font-size: 12px;
	font-weight: 600;
	overflow: hidden;
	text-overflow: ellipsis;
	white-space: nowrap;
}
.section_count{
	margin-right: 2px;
	color: var(--text-3);
	font-size: 11.5px;
	font-variant-numeric: tabular-nums;
}
.section_btn{
	width: 26px;
	height: 26px;
	color: var(--text-3);
}
.section_btn .i{
	width: 15px;
	height: 15px;
}
.section_btn:disabled{
	opacity: .35;
	cursor: default;
}
.section_input{
	height: 28px;
	margin-right: 2px;
	font-weight: 600;
}
.section_empty{
	padding: 2px 8px 6px;
	color: var(--text-3);
	font-size: 12px;
}
.part_row.in_section .part{
	padding-left: 14px;
}
#addSection:disabled{
	opacity: .35;
	cursor: default;
}
#partSectionField[hidden]{
	display: none;
}

@media (pointer: fine){
	.section_btn:hover:not(:disabled){
		color: var(--text);
	}
}

/* ---------- Ссылка «Configurator» в шапке: кнопка-ссылка ---------- */

a.btn{
	color: var(--text);
	text-decoration: none;
}
.btn[hidden]{
	display: none;
}

/* ---------- Окно пола / комнаты ---------- */

/* поля в ряд; скрытые (.room_only у пола) не занимают колонку */
.window_row{
	display: grid;
	grid-auto-flow: column;
	grid-auto-columns: minmax(0, 1fr);
	gap: 8px;
}
.window_row + .window_row{
	margin-top: 4px;
}
.window_row > .window_field{
	margin-top: 0;
}
#roomWindow[data-type="floor"] .room_only{
	display: none;
}


/* ---------- Пила и сверло (tools.js) ---------- */

.tbtn[hidden],
.tsep[hidden]{
	display: none;
}

/* настройки инструмента вместо свойств выделения */
.props_tool{
	display: none;
}
body[data-tool] .props_tool{
	display: block;
}
body[data-tool] .panel_right .props_empty,
body[data-tool] .panel_right .props_scene,
body[data-tool] .panel_right .props_vars,
body[data-tool] .panel_right .props_multi,
body[data-tool] .panel_right .props_body{
	display: none;
}
body[data-tool="saw"] .tool_drill,
body[data-tool="drill"] .tool_saw{
	display: none;
}
/* окно операции фигурой (op-edit.js) — на месте окна пилы и сверла, body[data-tool="op"] */
.props_op,
body[data-tool="op"] .props_tool{
	display: none;
}
body[data-tool="op"] .props_op{
	display: block;
}
.props_op .btn_block + .btn_block{
	margin-top: 6px;
}
/* общие настройки операции в окне инструмента (op-settings.js): повтор, привязка при растяжении */
.op_settings{
	display: flex;
	flex-direction: column;
	gap: 10px;
}
.op_settings[hidden]{
	display: none;
}
/* в окне пилы и сверла — отдельным разделом, как группа свойств */
#toolSettings{
	padding: 14px;
	border-bottom: 1px solid var(--line);
}
#toolSettings:has(> .op_settings[hidden]){
	display: none;
}

.seg.seg_4{
	grid-template-columns: repeat(4, 1fr);
}
.tool_hint{
	padding: 10px 14px 0;
}
.tool_hint.tool_hint_warn{
	color: var(--warn-text);
}
.tool_value{
	font-variant-numeric: tabular-nums;
	color: var(--text-2);
}
/* итог инструмента строкой: куски после пропила, длина реза, наклон сверла (tools.js: updateUI) */
.tool_result{
	margin: 0;
	color: var(--text-2);
	font-size: 12px;
	font-variant-numeric: tabular-nums;
}
.tool_row{
	display: flex;
	align-items: baseline;
	justify-content: space-between;
	gap: 10px;
}
/* сверло с крепежом (tools.js: updateUI): поля Ø, глубины и «насквозь» спрятаны — отверстие по крепежу; не встанет — итог
   цветом предупреждения */
.tool_drill .field[hidden],
.tool_result[hidden]{
	display: none;
}
.tool_result.is_warn{
	color: var(--warn-text);
}
.input.drill_fasten{
	padding-right: 20px;
}
/* действие строкой рядом с итогом: «In half» у пилы */
.tool_link{
	flex: none;
	padding: 0;
	color: var(--accent-ink);
	font-size: 12px;
	font-weight: 500;
}
.tool_link[hidden]{
	display: none;
}
@media (pointer: fine){
	.tool_link:hover{ text-decoration: underline; }
}
/* низ окна инструмента: отмена и действие, у каждой — её клавиша */
.tool_foot{
	display: grid;
	grid-template-columns: 1fr 1.4fr;
	gap: 6px;
}
.tool_foot .btn{
	justify-content: center;
}
.tool_foot kbd{
	margin-left: 6px;
	font: 500 10px/1 ui-monospace, "Cascadia Mono", Consolas, monospace;
	opacity: .7;
}
.input:disabled{
	opacity: .5;
}
/* размер детали со связями: не меняется, но кликается — клик объясняет, чем менять (designer-ui.js) */
.input[data-size-axis][readonly]{
	color: var(--text-2);
	cursor: help;
}
.input[aria-invalid="true"]{
	border-color: var(--danger);
}

.check{
	display: flex;
	align-items: center;
	gap: 8px;
	min-height: 24px;
	font-size: 12.5px;
	cursor: pointer;
}
.check[hidden]{
	display: none;
}
/* ряд кнопок под полями (гибка, пресс) */
.fasten_btns{
	display: flex;
	gap: 8px;
	margin: 8px 0 4px;
}
/* вид у стороны — кнопкой с видом поля-списка (стрелка справа): открывает окно каталога крепежа для стороны */
.fasten_kind{
	display: block;
	width: 100%;
	min-width: 0;
	overflow: hidden;
	text-align: left;
	white-space: nowrap;
	text-overflow: ellipsis;
	cursor: pointer;
	background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 12 12'%3E%3Cpath d='M3 4.5l3 3 3-3' fill='none' stroke='%235E646D' stroke-width='1.4' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E");
	background-repeat: no-repeat;
	background-position: right 5px center;
	background-size: 12px;
}
/* у ячейки креста отступы поля — свои (.sc_cell .input): справа — место стрелке */
.sc_cell .input.fasten_kind{
	padding-right: 20px;
}
.fasten_kind:disabled{
	cursor: default;
}
/* крепёж: вид — крестом сторон; под крестом — строка закреплённой стороны: точка её цвета, с кем
   стык (сосед, зазор) и поля — количество, редкое; не влезают рядом — переносятся под подпись */
#fastenRows{
	display: flex;
	flex-direction: column;
	gap: 8px;
}
.fasten_row{
	display: flex;
	flex-wrap: wrap;
	align-items: center;
	gap: 4px 8px;
	min-height: 30px;
}
.fasten_row[hidden],
body:not([data-advanced]) .fasten_row.is_bare{
	display: none;
}
.fasten_row > .sc_cap{
	flex: 1 1 110px;
	font-size: 12px;
}
.fasten_row .group_pick{
	flex: 0 1 auto;
	max-width: 100%;
}
.fasten_row select.input{
	width: 92px;
	flex: none;
	padding: 0 20px 0 7px;
	background-position: right 5px center;
}
.fasten_row .group_pick .input[data-fasten="count"]{
	width: 64px;
	flex: none;
}
.fasten_row .group_pick .input[data-fasten="shift"]{
	width: 48px;
	flex: none;
}
/* с какой пласти эксцентрик, карман, уголок («Auto: bottom», «Top face») — шире: подпись целиком */
.fasten_row select.input[data-fasten="edge"]{
	width: 124px;
}
#fastenNote{
	margin: 0;
}
.check input{
	width: 15px;
	height: 15px;
	accent-color: var(--accent);
}

/* подпись у инструмента в сцене */
.tool_label{
	position: absolute;
	z-index: 4;
	transform: translate(-50%, calc(-100% - 14px));
	padding: 3px 8px;
	border-radius: 10px;
	background: rgba(24, 27, 32, .78);
	color: #fff;
	font-size: 12px;
	font-variant-numeric: tabular-nums;
	white-space: pre;
	pointer-events: none;
}
.tool_label[hidden]{
	display: none;
}

/* ---------- Гибка (bend.js) и пресс (press.js) ---------- */

.props_bend,
.props_press{
	display: none;
}
body[data-bend] .props_bend,
body[data-press] .props_press{
	display: block;
}
body[data-bend] .panel_right .props_empty,
body[data-bend] .panel_right .props_scene,
body[data-bend] .panel_right .props_vars,
body[data-bend] .panel_right .props_multi,
body[data-bend] .panel_right .props_body,
body[data-press] .panel_right .props_empty,
body[data-press] .panel_right .props_scene,
body[data-press] .panel_right .props_vars,
body[data-press] .panel_right .props_multi,
body[data-press] .panel_right .props_body{
	display: none;
}
.point_row.point_row_2{
	grid-template-columns: 16px repeat(2, minmax(0, 1fr)) 30px;
}
.point_head{
	font-size: 11.5px;
	font-weight: 600;
	text-align: center;
}
.props_bend .btn_block + .btn_block,
.props_press .btn_block + .btn_block{
	margin-top: 6px;
}
/* плечо (у пресса — место) с кнопкой «мерить с другой стороны» */
.props_bend .bend_leg,
.props_press .bend_leg{
	display: flex;
	gap: 4px;
	align-items: center;
}
.props_bend .bend_leg .input,
.props_press .bend_leg .input{
	flex: 1;
	min-width: 0;
}
.props_bend .bend_presets{
	margin: 0 0 10px;
}
/* заготовка и вырезы, итог пресса, предупреждения — несколько строк */
.props_bend .bend_flat,
.props_bend #bendWarn,
.props_press .bend_flat,
.props_press #pressWarn,
#millWarn{
	white-space: pre-line;
}
.props_warn[data-level="error"]{
	background: var(--danger-soft);
	color: var(--danger);
}

/* ---------- Переменные, операции, крепёж (variables.js, opspanel.js, joints.js) ---------- */

/* переменные проекта: когда ничего не выделено; у инструмента, гибки и пресса — их настройки */
.props_vars{
	display: none;
}
body[data-selection="none"] .props_vars{
	display: block;
}
body[data-tool] .panel_right .props_vars,
body[data-bend] .panel_right .props_vars,
body[data-press] .panel_right .props_vars{
	display: none;
}
.vars_list{
	display: flex;
	flex-direction: column;
	gap: 4px;
}
.var_row{
	display: grid;
	grid-template-columns: minmax(0, 1fr) minmax(0, 1.3fr) minmax(0, 0.8fr) 30px;
	gap: 4px;
	align-items: center;
}
.var_row .input{
	padding-left: 6px;
	padding-right: 6px;
	font-variant-numeric: tabular-nums;
}
/* поле размера или положения с формулой (formula-fields.js): фиолетовым, как выделенный объект с
   формулами в сцене; в фокусе — сама формула */
.input.is_formula{
	color: var(--formula);
}

/* значение переменной детали у копии: имя — значение копии — что получилось */
.copy_param{
	display: grid;
	grid-template-columns: minmax(0, 1fr) minmax(0, 1.3fr) minmax(0, 0.8fr);
	gap: 4px;
	align-items: center;
}
.copy_param_name{
	min-width: 0;
	overflow: hidden;
	text-overflow: ellipsis;
	white-space: nowrap;
	color: var(--text-2);
}

/* поле переменной, на которое увела попытка растянуть размер по ней (formula-fields.js: focusSizeDriver) */
.input.is_attention{
	animation: field_attention 1.6s ease-out;
}
@keyframes field_attention{
	0%, 40%{
		box-shadow: 0 0 0 3px var(--accent-soft);
		border-color: var(--accent);
	}
	100%{
		box-shadow: 0 0 0 0 transparent;
	}
}

/* что получилось у формулы: «ƒ 768» */
.var_value{
	min-width: 0;
	overflow: hidden;
	text-overflow: ellipsis;
	white-space: nowrap;
	color: var(--text-3);
	font-size: 12px;
	font-variant-numeric: tabular-nums;
	text-align: right;
}

/* ---------- итог транзакции на сцене (transaction.js): «Links replaced by numbers: N» со списком
   или «Not changed: причина» ---------- */
.tx_note{
	position: absolute;
	left: 50%;
	bottom: 16px;
	z-index: 20;
	transform: translateX(-50%);
	width: max-content;
	max-width: min(560px, calc(100% - 32px));
	padding: 8px 6px 8px 14px;
	border: 1px solid var(--line);
	border-radius: var(--r);
	background: var(--surface);
	box-shadow: var(--shadow-pop);
	color: var(--text);
	font-size: 13px;
}
.tx_note[hidden]{
	display: none;
}
.tx_note.is_error{
	border-color: var(--danger);
}
.tx_note.is_error .tx_note_title{
	color: var(--danger);
}
.tx_note_head{
	display: flex;
	align-items: flex-start;
	gap: 6px;
}
.tx_note_title{
	flex: 1;
	min-width: 0;
	padding-top: 4px;
	font-weight: 500;
	overflow-wrap: anywhere;
}
.tx_note_close{
	flex: none;
	width: 26px;
	height: 26px;
}
.tx_note_list{
	max-height: 160px;
	margin: 4px 8px 0 0;
	padding: 0 0 0 16px;
	overflow-y: auto;
	color: var(--text-2);
	font-size: 12px;
	line-height: 1.45;
}
.tx_note_list:empty{
	display: none;
}
.ops_list{
	display: flex;
	flex-direction: column;
	gap: 4px;
}
/* строка операции: клик — окно инструмента (opspanel.js) */
.op_row{
	display: flex;
	align-items: center;
	gap: 6px;
	min-height: 32px;
	padding: 0 4px 0 8px;
	border: 1px solid transparent;
	border-radius: var(--r);
	font-size: 12.5px;
	cursor: pointer;
}
.op_row.is_linked{
	color: var(--text-2);
	cursor: default;
}
/* операция, которую пересборка не применила (ops.js: op.refused): строка и причина под ней — красным */
.op_row.is_refused .op_label{
	color: var(--danger);
	text-decoration: line-through;
}
.op_refused{
	margin: -2px 0 2px;
	padding: 4px 8px;
	border-radius: var(--r);
	background: var(--danger-soft);
	color: var(--danger);
	font-size: 11.5px;
	line-height: 1.35;
}
@media (pointer: fine){
	.op_row:hover{ background: var(--surface-2); }
}
.op_label{
	flex: 1;
	min-width: 0;
	overflow: hidden;
	text-overflow: ellipsis;
	white-space: nowrap;
	font-variant-numeric: tabular-nums;
}
.op_fx{
	color: var(--accent-ink);
	font-style: italic;
	font-weight: 600;
}
.op_link{
	color: var(--text-3);
	margin-right: 6px;
}
/* два поля в строке (крепёж коннектора) */
.pair{
	display: grid;
	grid-template-columns: repeat(2, minmax(0, 1fr));
	gap: 4px;
}
.pair .input{
	padding-left: 6px;
	padding-right: 6px;
	font-variant-numeric: tabular-nums;
}
#jointFields{
	display: flex;
	flex-direction: column;
	gap: 10px;
}

/* кромка листа (edges.js): по строке на торец — сторона с длиной и режим Auto / None */
#edgeSection[hidden],
.edge_body[hidden]{
	display: none;
}
.edge_body{
	display: flex;
	flex-direction: column;
	gap: 10px;
}

/* крест сторон детали (side-cross.js) — Offsets, Edge banding, Fasteners: поля вокруг значка по
   сторонам самой детали, без подписей; место не меняется при повороте: +Y сверху, +X справа, −Z по
   диагонали вверх-вправо (вглубь), +Z вниз-влево; куда сторона смотрит сейчас — в подсказке поля */
.side_cross{
	display: grid;
	grid-template-columns: repeat(3, minmax(0, 1fr));
	grid-template-areas:
		".     top    back"
		"left  icon   right"
		"front bottom .";
	align-items: center;
	gap: 6px;
}
.sc_cell{
	display: flex;
	flex-direction: column;
	gap: 3px;
	min-width: 0;
}
.sc_cell[hidden]{
	display: none;
}
.sc_cell[data-slot="top"]{ grid-area: top; }
.sc_cell[data-slot="bottom"]{ grid-area: bottom; }
.sc_cell[data-slot="left"]{ grid-area: left; }
.sc_cell[data-slot="right"]{ grid-area: right; }
.sc_cell[data-slot="back"]{ grid-area: back; }
.sc_cell[data-slot="front"]{ grid-area: front; }
.sc_cell .input{
	height: 28px;
	padding: 0 7px;
	font-size: 12.5px;
}
.sc_cell select.input{
	padding-right: 20px;
	background-position: right 5px center;
}
/* строка стороны под крестом крепежа (fasteners.js): «Left → side_l»; длинное — многоточием, целиком — в
   подсказке */
.sc_cap{
	display: block;
	min-width: 0;
	overflow: hidden;
	color: var(--text-2);
	font-size: 11.5px;
	line-height: 15px;
	white-space: nowrap;
	text-overflow: ellipsis;
}
/* у стыка что-то не так (крепёж): поле — цветом предупреждения, что именно — в подсказке */
.sc_cell.is_warn .input{
	color: var(--warn-text);
}
/* сторона без стыка (крепёж): место в кресте есть, поле недоступно */
.sc_cell.is_off .input{
	opacity: .55;
	cursor: default;
}
.sc_icon{
	grid-area: icon;
	justify-self: center;
	width: 56px;
	height: 56px;
}
.sc_icon line{
	stroke: var(--text-3);
	stroke-width: 1.4;
	stroke-linecap: round;
}
.sc_icon rect{
	fill: var(--surface-2);
	stroke: var(--text-2);
	stroke-width: 1.4;
}
#edgeColorReset[hidden]{
	display: none;
}
#jointFields[hidden]{
	display: none;
}


/* сворачиваемый блок свойств: заголовок-кнопка со сводкой, тело скрыто, пока блок свёрнут */
.fold_btn{
	display: flex;
	align-items: center;
	gap: 6px;
	width: calc(100% + 8px);
	min-height: 24px;
	margin: -4px -4px;
	padding: 2px 4px;
	border-radius: var(--r-sm);
	font-size: 12px;
	font-weight: 600;
	text-align: left;
}
.fold_btn:focus-visible{
	outline-offset: 0;
}
@media (pointer: fine){
	.fold_btn:hover{ background: var(--surface-2); }
}
.fold_chev{
	width: 14px;
	height: 14px;
	color: var(--text-3);
	transform: rotate(-90deg);
	transition: transform .15s;
}
.fold.is_open .fold_chev{
	transform: none;
}
.fold_name{
	flex: none;
}
.fold_sum{
	flex: 1;
	min-width: 0;
	overflow: hidden;
	color: var(--text-3);
	font-weight: 400;
	text-align: right;
	text-overflow: ellipsis;
	white-space: nowrap;
}
.fold.is_open .fold_sum{
	display: none;
}
.fold.is_alert .fold_sum{
	color: var(--danger);
}
.fold_body{
	display: flex;
	flex-direction: column;
	gap: 10px;
}
.fold:not(.is_open) .fold_body{
	display: none;
}

/* AI-рендер вида сцены (ai-render.js): блок под «Check intersections» — пожелание и Generate; окно — снимок бледно
   с кругом, пока рисует (data-state="wait"), потом картинка и Download; не вышло — строка, что не так */
.render_wish{
	height: auto;
	min-height: 52px;
	padding: 6px 8px;
	font: inherit;		/* textarea шрифт страницы сам не берёт */
	font-size: 12.5px;
	line-height: 1.4;
	resize: vertical;
}
/* модель — подпись над списком: название с ценой целиком */
.render_model{
	display: flex;
	flex-direction: column;
	gap: 4px;
}
.render_model label{
	color: var(--text-2);
	font-size: 12px;
}
.render_window{
	width: min(880px, calc(100vw - 32px));
}
/* рамка — по картинке (снимок бывает и квадратным, и широким): без полос по бокам */
.render_stage{
	position: relative;
	width: fit-content;
	max-width: calc(100% - 36px);
	min-width: 220px;
	min-height: 160px;
	margin: 4px auto 0;
	overflow: hidden;
	border-radius: var(--r);
	background: var(--viewport-bg);
}
.render_img{
	display: block;
	width: auto;
	max-width: 100%;
	height: auto;
	max-height: calc(100vh - 230px);
}
.render_img:not([src]){
	display: none;
}
.render_wait{
	position: absolute;
	inset: 0;
	display: none;
	place-items: center;
	background: rgba(24, 27, 32, .28);
}
.render_window[data-state="wait"] .render_wait{
	display: grid;
}
.render_window[data-state="wait"] .render_img{
	filter: grayscale(.35) brightness(.85);
}
.render_spin{
	width: 38px;
	height: 38px;
	border: 3px solid rgba(255, 255, 255, .35);
	border-top-color: #FFFFFF;
	border-radius: 50%;
	animation: render_spin .9s linear infinite;
}
@keyframes render_spin{
	to{ transform: rotate(360deg); }
}
@media (prefers-reduced-motion: reduce){
	.render_spin{ animation-duration: 2.4s; }
}
.render_note{
	margin: 10px 18px 0;
	color: var(--text-2);
	font-size: 13px;
}
.render_window[data-state="fail"] .render_note{
	color: var(--warn-text);
}
.render_window .window_foot{
	display: flex;
	justify-content: flex-end;
	gap: 8px;
	min-height: 18px;
}

/* повтор: один компонент у массивов и операций (repeat-ui.js) */
.repeat{
	display: flex;
	flex-direction: column;
	gap: 10px;
}
.repeat .seg{
	margin: 0;
}

/* привязка операции при растяжении: строка на ось */
.op_bind{
	display: flex;
	flex-direction: column;
	gap: 4px;
	min-width: 0;
}
.op_bind_row{
	display: grid;
	grid-template-columns: 14px minmax(0, 1fr);
	gap: 6px;
	align-items: center;
}
.op_bind_ax{
	font-size: 11.5px;
	font-weight: 600;
	text-align: center;
}

/* профиль — внутри блока «Geometry» (не сворачивается): поля размеров пути, поля другого режима скрыты */
.profile_box{
	display: flex;
	flex-direction: column;
	gap: 10px;
}
#profileSection[hidden],
#profileSection [data-profile-for][hidden]{
	display: none;
}
.profile_params{
	display: flex;
	flex-direction: column;
	gap: 10px;
}

/* проводка: поля пути другого вида скрыты; точки ломаной — строка на точку */
#profileSection [data-path-for][hidden]{
	display: none;
}
.points_list{
	display: flex;
	flex-direction: column;
	gap: 4px;
}
.point_row{
	display: grid;
	grid-template-columns: 16px repeat(3, minmax(0, 1fr)) 30px;
	gap: 4px;
	align-items: center;
}
.point_row .input{
	padding-left: 6px;
	padding-right: 6px;
	font-variant-numeric: tabular-nums;
}
.point_n{
	color: var(--text-3);
	font-size: 11.5px;
	text-align: right;
}
.seg.seg_3{
	grid-template-columns: repeat(3, 1fr);
}

/* ---------- Редактор своей формы профиля (sketch-editor.js) ---------- */

.window.window_wide{
	width: min(900px, calc(100vw - 32px));
}
.sketch_body{
	display: grid;
	grid-template-columns: minmax(0, 1fr) 230px;
	gap: 14px;
	align-items: start;
}
@media (max-width: 720px){
	.sketch_body{
		grid-template-columns: 1fr;
	}
}
/* чертёж и его кнопки, как у плана комнаты (plan.css): сверху слева — что добавить, справа — вид,
   снизу — подсказка, что можно сделать сейчас (sketch-editor.js: hintText) */
.sketch_stage{
	position: relative;
	min-width: 0;
	overflow: hidden;
	border-radius: var(--r);
	background: var(--surface-2);
}
.sketch_canvas{
	display: block;
	width: 100%;
	height: auto;
	aspect-ratio: 640 / 420;
	touch-action: none;
	user-select: none;
}
#sketchWindow [hidden]{
	display: none;
}
.sketch_tools{
	position: absolute;
	top: 10px;
	left: 10px;
	right: 10px;
	display: flex;
	align-items: center;
	gap: 6px;
	pointer-events: none;
}
.sketch_tools > *{
	pointer-events: auto;
}
.sketch_tools .btn{
	box-shadow: 0 1px 2px rgba(0, 0, 0, .12);
}
.sketch_view{
	display: flex;
	align-items: center;
	gap: 2px;
	margin-left: auto;
	padding: 2px;
	border-radius: var(--r-sm);
	background: var(--surface);
	box-shadow: 0 1px 2px rgba(0, 0, 0, .12);
}
.sketch_view .icon_btn{
	width: 28px;
	height: 28px;
}
.sk_grid_pick{
	display: flex;
	align-items: center;
	gap: 2px;
	padding-left: 8px;
	color: var(--text-2);
	font-size: 12px;
}
.sk_grid_pick .input{
	width: 62px;
	height: 28px;
	border-color: transparent;
}
/* список под видом кнопки (Add фрезы): на виду — кнопка, по клику — список браузера, прозрачный поверх неё */
.sk_menu{
	position: relative;
}
.sk_menu select{
	position: absolute;
	inset: 0;
	width: 100%;
	height: 100%;
	opacity: 0;
	cursor: pointer;
	font: inherit;
}
.sk_menu:focus-within{
	border-color: var(--accent);
	box-shadow: 0 0 0 3px var(--accent-soft);
}
.btn .i.sk_menu_chev{
	width: 12px;
	height: 12px;
	margin-right: -4px;
}
/* подсказка — плашкой посередине снизу: читается поверх сетки и линий чертежа */
.sketch_hint{
	position: absolute;
	left: 50%;
	bottom: 6px;
	transform: translateX(-50%);
	max-width: calc(100% - 24px);
	margin: 0;
	padding: 2px 10px;
	overflow: hidden;
	border-radius: var(--r-sm);
	background: var(--surface);
	background: color-mix(in srgb, var(--surface) 88%, transparent);
	color: var(--text-2);
	font-size: 12px;
	line-height: 16px;
	white-space: nowrap;
	text-overflow: ellipsis;
	pointer-events: none;
}
.sketch_hint:empty{
	display: none;
}
@media (max-width: 480px){
	.sk_btn_label,
	.sk_grid_pick > span{
		display: none;
	}
	.sketch_hint{
		display: -webkit-box;
		width: max-content;
		white-space: normal;
		text-align: center;
		-webkit-box-orient: vertical;
		-webkit-line-clamp: 2;
	}
}
.sketch_side{
	/* колонка — сеткой: широкое поле не распирает её и не обрезает остальные справа; прокручивается
	   сама — окно не выше экрана, кнопки внизу видны */
	display: grid;
	grid-template-columns: minmax(0, 1fr);
	align-content: start;
	gap: 10px;
	max-height: calc(100vh - 150px);
	max-height: calc(100dvh - 150px);
	overflow-y: auto;
	padding-right: 2px;
}
/* фреза и токарка (sketch-editor.js: setFull): окно на весь экран в три колонки — что есть (список и «Add»),
   чертёж, настройки выбранного; сверху — заголовок с отменой, внизу — проверки и кнопки. Рамку рисует
   sketch-chrome.js. Уже 720 px — колонкой: список полосой, чертёж, настройки. Чертёж — в пикселях холста
   (sketch-editor.js: measure) */
#sketchWindow.window_full{
	inset: 0;
	transform: none;
	width: auto;
	grid-template-columns: 228px minmax(0, 1fr) 320px;
	grid-template-rows: auto minmax(0, 1fr) auto;
	border-radius: 0;
	box-shadow: none;
}
/* лобзик (jigsaw.js), токарка (lathe.js) и сечение профиля (section-edit.js): контур один — без списка
   слева, чертёж и настройки */
#sketchWindow.window_full.is_jigsaw,
#sketchWindow.window_full.is_lathe,
#sketchWindow.window_full.is_section{
	grid-template-columns: minmax(0, 1fr) 320px;
}
#sketchWindow.window_full.is_jigsaw .sketch_stage,
#sketchWindow.window_full.is_lathe .sketch_stage,
#sketchWindow.window_full.is_section .sketch_stage{
	grid-column: 1;
}
#sketchWindow.window_full.is_jigsaw .sketch_side,
#sketchWindow.window_full.is_lathe .sketch_side,
#sketchWindow.window_full.is_section .sketch_side{
	grid-column: 2;
}
#sketchWindow.window_full .window_head{
	grid-column: 1 / -1;
	justify-content: flex-start;
	gap: 14px;
	padding: 10px 10px 10px 20px;
	border-bottom: 1px solid var(--line);
}
#sketchWindow.window_full .sketch_body{
	display: contents;
}
#sketchWindow.window_full .sk_list{
	grid-row: 2;
	grid-column: 1;
	display: flex;
	flex-direction: column;
	min-height: 0;
	border-right: 1px solid var(--line);
}
/* хозяин без списка (лобзик, токарка, сечение): display выше перебил бы hidden */
#sketchWindow.window_full .sk_list[hidden]{
	display: none;
}
#sketchWindow.window_full .sketch_stage{
	grid-row: 2;
	grid-column: 2;
	display: flex;
	flex-direction: column;
	min-height: 0;
	border-radius: 0;
}
#sketchWindow.window_full .sketch_area{
	flex: 1;
	min-height: 0;
}
#sketchWindow.window_full .sketch_canvas{
	position: absolute;
	inset: 0;
	height: 100%;
	aspect-ratio: auto;
}
#sketchWindow.window_full .sketch_hint{
	position: static;
	transform: none;
	max-width: none;
	padding: 8px 16px;
	border-top: 1px solid var(--line);
	border-radius: 0;
	background: var(--surface);
}
#sketchWindow.window_full .sketch_side{
	grid-row: 2;
	grid-column: 3;
	/* строки — по содержимому: колонка прокручивается, сжимать разделы (до min-height полей) нельзя */
	grid-auto-rows: max-content;
	gap: 0;
	max-height: none;
	padding: 0;
	border-left: 1px solid var(--line);
}
#sketchWindow.window_full .sketch_side > .props_warn{
	margin: 12px 16px 0;
}
/* контуры элемента (острова кармана): раздел, как остальные — подпись сверху, список с + и корзиной */
#sketchWindow.window_full .sk_holes{
	display: flex;
	flex-direction: column;
	align-items: stretch;
	gap: 8px;
	padding: 14px 16px;
	border-top: 1px solid var(--line);
}
#sketchWindow.window_full .sk_holes[hidden]{
	display: none;
}
#sketchWindow.window_full .sk_holes > label{
	color: var(--text-3);
	font: 600 11px/1 ui-monospace, "Cascadia Mono", Consolas, monospace;
	letter-spacing: .08em;
	text-transform: uppercase;
}
#sketchWindow.window_full .sketch_point{
	margin: 0 16px 14px;
}
#sketchWindow.window_full .sketch_foot{
	grid-row: 3;
	grid-column: 1 / -1;
	align-items: center;
	gap: 10px;
	padding: 12px 16px;
	border-top: 1px solid var(--line);
}
@media (max-width: 720px){
	#sketchWindow.window_full{
		grid-template-columns: minmax(0, 1fr);
		grid-template-rows: auto auto minmax(0, 1fr) minmax(0, 1fr) auto;
	}
	#sketchWindow.window_full .window_head{
		gap: 8px;
		padding-left: 14px;
	}
	#sketchWindow.window_full .sk_undo_label,
	#sketchWindow.window_full .sk_sub,
	#sketchWindow.window_full .sk_legend,
	#sketchWindow.window_full .sk_note,
	#sketchWindow.window_full .sk_list_head,
	#sketchWindow.window_full .sk_list_keys{
		display: none;
	}
	/* список — полосой: строки в ряд, «Add» в конце */
	#sketchWindow.window_full .sk_list{
		grid-row: 2;
		flex-direction: row;
		align-items: center;
		border-right: 0;
		border-bottom: 1px solid var(--line);
	}
	#sketchWindow.window_full .sk_items{
		flex-direction: row;
		padding: 6px 8px;
		overflow-x: auto;
		overflow-y: hidden;
	}
	#sketchWindow.window_full .sk_item{
		width: auto;
		flex: none;
		max-width: 180px;
	}
	#sketchWindow.window_full .sk_list_foot{
		flex: none;
		padding: 6px 8px;
		border-top: 0;
	}
	#sketchWindow.window_full .sk_add_btn .sk_add_label{
		display: none;
	}
	#sketchWindow.window_full .sk_add_menu{
		right: 0;
		left: auto;
		top: calc(100% + 6px);
		bottom: auto;
		width: 240px;
	}
	#sketchWindow.window_full .sketch_stage{
		grid-row: 3;
		grid-column: 1;
	}
	#sketchWindow.window_full .sketch_side{
		grid-row: 4;
		grid-column: 1;
		border-left: 0;
		border-top: 1px solid var(--line);
	}
	#sketchWindow.window_full .sketch_foot{
		grid-row: 5;
	}
	#sketchWindow.window_full.is_jigsaw,
	#sketchWindow.window_full.is_lathe,
	#sketchWindow.window_full.is_section{
		grid-template-columns: minmax(0, 1fr);
	}
	#sketchWindow.window_full.is_jigsaw .sketch_side,
	#sketchWindow.window_full.is_lathe .sketch_side,
	#sketchWindow.window_full.is_section .sketch_side{
		grid-column: 1;
	}
}

/* шапка: подзаголовок, отмена с подписью, сколько правок не применено */
.sk_titles{
	min-width: 0;
}
.sk_sub{
	margin: 3px 0 0;
	overflow: hidden;
	color: var(--text-3);
	font: 11.5px/1.3 ui-monospace, "Cascadia Mono", Consolas, monospace;
	white-space: nowrap;
	text-overflow: ellipsis;
}
.sk_undo{
	display: flex;
	align-items: center;
	gap: 4px;
	min-width: 0;
	margin-right: auto;
	padding-left: 14px;
	border-left: 1px solid var(--line);
}
.sk_undo[hidden]{
	display: none;
}
.sk_undo .icon_btn{
	background: var(--btn);
}
.sk_undo .icon_btn:disabled{
	opacity: .45;
	cursor: default;
}
.sk_undo_label{
	margin-left: 6px;
	overflow: hidden;
	color: var(--text-3);
	font-size: 12px;
	white-space: nowrap;
	text-overflow: ellipsis;
}
.sk_dirty{
	display: inline-flex;
	align-items: center;
	gap: 6px;
	flex: none;
	padding: 4px 10px;
	border-radius: 999px;
	background: var(--accent-soft);
	color: var(--accent-ink);
	font-size: 12px;
	font-weight: 500;
	white-space: nowrap;
}
.sk_dirty::before{
	content: "";
	width: 6px;
	height: 6px;
	border-radius: 50%;
	background: currentColor;
}
.sk_dirty[hidden]{
	display: none;
}
/* блок повтора (tool-repeat.js): строки — с тем же шагом, что в разделе */
#millRepeat{
	display: flex;
	flex-direction: column;
	gap: 10px;
}

/* слева: что есть на стороне (детали) и «Add» */
.sk_list[hidden]{
	display: none;
}
.sk_list_head{
	display: flex;
	justify-content: space-between;
	padding: 16px 18px 8px;
	color: var(--text-3);
	font: 600 11px/1 ui-monospace, "Cascadia Mono", Consolas, monospace;
	letter-spacing: .08em;
	text-transform: uppercase;
}
.sk_items{
	display: flex;
	flex: 1;
	flex-direction: column;
	gap: 2px;
	min-height: 0;
	padding: 0 8px;
	overflow-y: auto;
}
.sk_item{
	display: flex;
	align-items: center;
	gap: 10px;
	width: 100%;
	padding: 8px 10px;
	border-radius: var(--r);
	color: var(--text);
	text-align: left;
}
.sk_item.is_active{
	background: var(--surface-2);
}
@media (pointer: fine){
	.sk_item:hover{ background: var(--surface-2); }
}
.sk_item_text{
	display: flex;
	flex: 1;
	flex-direction: column;
	gap: 2px;
	min-width: 0;
}
.sk_item_name,
.sk_item_sub{
	overflow: hidden;
	white-space: nowrap;
	text-overflow: ellipsis;
}
.sk_item_name{
	font-size: 13px;
	font-weight: 500;
}
.sk_item_sub{
	color: var(--text-3);
	font-size: 11.5px;
}
.sk_tag{
	margin-left: 6px;
	color: var(--accent-ink);
	font: 500 10.5px ui-monospace, "Cascadia Mono", Consolas, monospace;
	font-style: normal;
}
.sk_dot{
	flex: none;
	width: 7px;
	height: 7px;
	border-radius: 50%;
	background: #F5A524;
}
.sk_dot.is_error{
	background: var(--danger);
}
/* значки строк: что делает элемент — цветом, как на чертеже */
.sk_icon{
	flex: none;
	width: 16px;
	height: 16px;
	border-radius: 3px;
	box-sizing: border-box;
}
.sk_icon_outline{
	background: #E9D3AE;
	border: 1px solid #B89A6C;
}
.sk_icon_cutout{
	background: var(--surface);
	border: 1.5px solid var(--text-2);
}
.sk_icon_pocket{
	background: #C9A473;
	border: 1px solid #8C7155;
}
.sk_icon_groove{
	height: 4px;
	border-radius: 2px;
	background: #C9A473;
}
.sk_icon_hole{
	width: 14px;
	height: 14px;
	margin: 0 1px;
	border-radius: 50%;
	background: #C9A473;
	border: 1px solid #8C7155;
}
.sk_icon_turning{
	height: 12px;
	border-radius: 3px 7px 7px 3px;
	background: rgba(13, 153, 255, .3);
	border: 1px solid var(--accent);
}
.sk_list_foot{
	padding: 12px 14px 14px;
}
.sk_add{
	position: relative;
}
.sk_add[hidden]{
	display: none;
}
.sk_add_btn{
	width: 100%;
	height: 38px;
	border-color: var(--text);
	background: var(--text);
	color: var(--surface);
}
.sk_add_btn .i{
	color: inherit;
}
@media (pointer: fine){
	.sk_add_btn:hover:not(:disabled){ background: var(--text-2); border-color: var(--text-2); }
}
.sk_add_menu{
	position: absolute;
	left: 0;
	right: 0;
	bottom: calc(100% + 6px);
	z-index: 5;
	display: flex;
	flex-direction: column;
	padding: 6px;
	border: 1px solid var(--line);
	border-radius: var(--r-lg);
	background: var(--surface);
	box-shadow: var(--shadow-pop);
}
.sk_add_menu[hidden]{
	display: none;
}
.sk_menu_item{
	display: flex;
	flex-direction: column;
	align-items: flex-start;
	gap: 2px;
	padding: 7px 10px;
	border-radius: var(--r);
	text-align: left;
}
.sk_menu_item b{
	font-size: 13px;
	font-weight: 600;
}
.sk_menu_item span{
	color: var(--text-3);
	font-size: 11.5px;
}
.sk_menu_item:hover,
.sk_menu_item:focus-visible{
	background: var(--surface-2);
	outline: 0;
}
.sk_menu_group{
	margin-top: 4px;
	padding: 9px 10px 4px;
	border-top: 1px solid var(--line);
	color: var(--text-3);
	font: 600 10.5px ui-monospace, "Cascadia Mono", Consolas, monospace;
	letter-spacing: .08em;
	text-transform: uppercase;
}
.sk_list_keys{
	margin: 8px 0 0;
	color: var(--text-3);
	font-size: 11px;
	text-align: center;
}

/* над чертежом — готовые фигуры кнопками; в углу — где начало; под ним — легенда цветов */
.sk_bar{
	display: flex;
	align-items: center;
	gap: 6px;
	min-height: 48px;
	padding: 8px 14px;
	overflow-x: auto;
	border-bottom: 1px solid var(--line);
	background: var(--surface);
}
.sk_bar[hidden]{
	display: none;
}
.sk_bar_label{
	margin-right: 4px;
	color: var(--text-3);
	font-size: 12px;
}
.sk_chip{
	flex: none;
	height: 28px;
	padding: 0 12px;
	border: 1px solid transparent;
	border-radius: 999px;
	background: var(--btn);
	color: var(--text);
	font-size: 12.5px;
	white-space: nowrap;
}
.sk_chip.is_active{
	border-color: var(--text);
	background: var(--text);
	color: var(--surface);
}
@media (pointer: fine){
	.sk_chip:not(.is_active):hover{ background: var(--surface-2); }
}
.sk_bar_sep{
	flex: none;
	width: 1px;
	height: 20px;
	margin: 0 4px;
	background: var(--line);
}
.sk_bar_text{
	margin-left: 4px;
	color: var(--text-2);
	font-size: 12.5px;
	white-space: nowrap;
}
.sketch_area{
	position: relative;
}
.sk_origin{
	position: absolute;
	left: 14px;
	bottom: 8px;
	margin: 0;
	color: var(--text-3);
	font: 11px ui-monospace, "Cascadia Mono", Consolas, monospace;
	pointer-events: none;
}
.sk_origin[hidden],
.sk_legend[hidden]{
	display: none;
}
.sk_legend{
	display: flex;
	flex-wrap: wrap;
	gap: 6px 16px;
	padding: 8px 16px;
	border-top: 1px solid var(--line);
	background: var(--surface);
	color: var(--text-2);
	font-size: 11.5px;
}
.sk_leg{
	display: inline-flex;
	align-items: center;
	gap: 6px;
}
.sk_sw{
	flex: none;
	width: 12px;
	height: 12px;
	border-radius: 2px;
	box-sizing: border-box;
}
.sk_sw_fill{
	background: var(--sw);
	border: 1px solid rgba(0, 0, 0, .18);
}
.sk_sw_hollow{
	background: var(--surface);
	border: 1px solid var(--text-2);
}
.sk_sw_line{
	width: 14px;
	height: 2px;
	border-radius: 1px;
	background: var(--sw);
}
.sk_sw_dash,
.sk_sw_axis{
	width: 14px;
	height: 0;
	border-radius: 0;
	border-top: 1.5px dashed var(--sw, var(--text-2));
}
.sk_sw_axis{
	border-top-style: dotted;
}
.sk_sw_dots{
	border: 1.5px dotted var(--text-2);
	border-radius: 50%;
}

/* внизу окна: проверки одной строкой (клик — к элементу), что значит Apply */
.sk_status{
	display: flex;
	align-items: center;
	gap: 8px;
	min-width: 0;
	margin-right: auto;
	padding: 4px 8px;
	border-radius: var(--r);
	color: var(--text-2);
	font-size: 12.5px;
	text-align: left;
}
.sk_status span{
	overflow: hidden;
	white-space: nowrap;
	text-overflow: ellipsis;
}
.sk_status[hidden]{
	display: none;
}
.sk_status[data-level="warn"]{
	color: var(--warn-text);
}
.sk_status[data-level="error"]{
	color: var(--danger);
}
@media (pointer: fine){
	.sk_status:hover{ background: var(--surface-2); }
}
.sk_note{
	margin-left: auto;
	color: var(--text-3);
	font-size: 12px;
	white-space: nowrap;
}
.sk_status:not([hidden]) + .sk_note{
	margin-left: 0;
}
.sk_note[hidden]{
	display: none;
}

/* справа: настройки выбранного разделами (фреза, токарка) */
.tp{
	display: flex;
	flex-direction: column;
}
.tp[hidden],
.tp [hidden]{
	display: none;
}
.tp_head{
	display: flex;
	align-items: center;
	justify-content: space-between;
	gap: 8px;
	padding: 16px 16px 4px;
}
.tp_name{
	margin: 0;
	overflow: hidden;
	font-size: 15px;
	font-weight: 600;
	white-space: nowrap;
	text-overflow: ellipsis;
}
.tp_head_btns{
	display: flex;
	flex: none;
	gap: 6px;
}
.tp_btn{
	height: 28px;
	padding: 0 10px;
	font-size: 12.5px;
}
.tp_btn_danger{
	border-color: var(--danger-soft);
	color: var(--danger);
}
.tp_about{
	margin: 0;
	padding: 4px 16px 14px;
	color: var(--text-2);
	font-size: 12.5px;
	line-height: 1.45;
}
.tp > .props_warn{
	margin: 0 16px 14px;
}
.tp_sec{
	display: flex;
	flex-direction: column;
	gap: 10px;
	padding: 14px 16px;
	border-top: 1px solid var(--line);
}
.tp_sec_title{
	margin: 0;
	color: var(--text-3);
	font: 600 11px/1 ui-monospace, "Cascadia Mono", Consolas, monospace;
	letter-spacing: .08em;
	text-transform: uppercase;
}
.tp_grid{
	display: grid;
	grid-template-columns: repeat(2, minmax(0, 1fr));
	gap: 10px;
}
.tp_f{
	display: flex;
	flex-direction: column;
	gap: 5px;
	min-width: 0;
}
.tp_wide{
	grid-column: 1 / -1;
}
.tp_label{
	color: var(--text-2);
	font-size: 12.5px;
}
.tp_in{
	position: relative;
	display: flex;
	align-items: center;
}
.tp_in .input{
	height: 34px;
	padding-right: 42px;
}
.tp_in i{
	position: absolute;
	right: 9px;
	color: var(--text-3);
	font: 11px ui-monospace, "Cascadia Mono", Consolas, monospace;
	font-style: normal;
	pointer-events: none;
}
.tp_in .input[readonly]{
	color: var(--text-2);
}
.tp_note{
	margin: 0;
	color: var(--text-3);
	font-size: 11.5px;
	line-height: 1.4;
}
.tp_text{
	margin: 0;
	font-size: 13px;
}
.tp_toggle{
	display: flex;
	align-items: center;
	justify-content: space-between;
	gap: 12px;
	font-size: 13px;
	cursor: pointer;
}
.tp_toggle small{
	display: block;
	margin-top: 2px;
	color: var(--text-3);
	font-size: 11.5px;
}
.tp_switch{
	position: relative;
	flex: none;
	width: 34px;
	height: 20px;
	margin: 0;
	border-radius: 999px;
	background: var(--line-strong);
	appearance: none;
	-webkit-appearance: none;
	cursor: pointer;
	transition: background .15s;
}
.tp_switch::after{
	content: "";
	position: absolute;
	top: 2px;
	left: 2px;
	width: 16px;
	height: 16px;
	border-radius: 50%;
	background: #fff;
	box-shadow: 0 1px 2px rgba(0, 0, 0, .3);
	transition: left .15s;
}
.tp_switch:checked{
	background: var(--accent);
}
.tp_switch:checked::after{
	left: 16px;
}
.tp_switch:focus-visible{
	outline: 2px solid var(--accent);
	outline-offset: 2px;
}
.tp_bar{
	height: 4px;
	overflow: hidden;
	border-radius: 2px;
	background: var(--surface-2);
}
.tp_bar > span{
	display: block;
	height: 100%;
	background: #C9A473;
}
.tp .seg{
	margin-bottom: 0;
}
.seg.seg_2{
	grid-template-columns: repeat(2, 1fr);
}
.tp .seg_btn{
	padding: 0 4px;
	white-space: nowrap;
}
/* фреза (mill.js: renderCutter): карточка выбранной — кнопка, виды — плитками с силуэтом, разрез */
.tp_cutter{
	display: flex;
	align-items: center;
	gap: 10px;
	width: 100%;
	padding: 6px 10px 6px 6px;
	border: 1px solid transparent;
	border-radius: var(--r);
	background: var(--btn);
	color: var(--text);
	text-align: left;
	cursor: pointer;
}
@media (pointer: fine){
	.tp_cutter:hover{ background: var(--btn-hover); }
}
.tp_cutter:focus-visible{
	outline: 2px solid var(--accent);
	outline-offset: 1px;
}
.tp_cutter_icon{
	flex: none;
	width: 36px;
	height: 36px;
	border-radius: var(--r);
	background: var(--surface-2);
	color: var(--text-2);
}
.tp_cutter_text{
	display: flex;
	flex: 1;
	flex-direction: column;
	gap: 1px;
	min-width: 0;
}
.tp_cutter_text b{
	font-size: 13px;
	font-weight: 600;
}
.tp_cutter_text span{
	overflow: hidden;
	color: var(--text-3);
	font: 11.5px ui-monospace, "Cascadia Mono", Consolas, monospace;
	white-space: nowrap;
	text-overflow: ellipsis;
}
.tp_cutter_chev{
	flex: none;
	color: var(--text-3);
	transition: transform .15s;
}
.tp_cutter[aria-expanded="true"] .tp_cutter_chev{
	transform: rotate(180deg);
}
.tp_cutters{
	display: grid;
	grid-template-columns: repeat(3, minmax(0, 1fr));
	gap: 6px;
	padding: 8px;
	border-radius: var(--r);
	background: var(--surface-2);
}
.tp_cutters_group{
	grid-column: 1 / -1;
	padding: 4px 2px 0;
	color: var(--text-3);
	font: 600 10px ui-monospace, "Cascadia Mono", Consolas, monospace;
	letter-spacing: .08em;
	text-transform: uppercase;
}
.tp_cutters_group:first-child{
	padding-top: 0;
}
.tp_cutter_tile{
	display: flex;
	flex-direction: column;
	align-items: center;
	gap: 3px;
	min-width: 0;
	padding: 6px 4px 7px;
	border: 1px solid var(--line);
	border-radius: var(--r);
	background: var(--surface);
	color: var(--text-2);
	font-size: 11.5px;
	line-height: 1.2;
	text-align: center;
	cursor: pointer;
}
.tp_cutter_tile svg{
	width: 34px;
	height: 34px;
}
.tp_cutter_tile span{
	max-width: 100%;
	overflow: hidden;
	text-overflow: ellipsis;
}
@media (pointer: fine){
	.tp_cutter_tile:hover{ border-color: var(--text-3); color: var(--text); }
}
.tp_cutter_tile:focus-visible{
	outline: 2px solid var(--accent);
	outline-offset: 1px;
}
.tp_cutter_tile[aria-pressed="true"]{
	border-color: var(--accent);
	background: var(--accent-soft);
	color: var(--accent);
}
.mcut_body{
	fill: currentColor;
}
.mcut_shank{
	fill: currentColor;
	opacity: .4;
}
.tp_cutter_view{
	display: block;
	width: 100%;
	height: auto;
	aspect-ratio: 280 / 118;
	border-radius: var(--r);
	background: var(--surface-2);
}
.tp_cutter_view .mpv_cut{
	fill: var(--surface-2);
	stroke: #f39c12;
	stroke-width: 1.5;
}
.tp_cutter_view .mpv_face{
	stroke: var(--text-3);
	stroke-width: 1;
}
.tp_cutter_view .mpv_break{
	stroke: var(--text-3);
	stroke-width: 1;
	stroke-dasharray: 4 3;
}
.tp_cutter_view .mpv_tool{
	fill: var(--accent);
	fill-opacity: .14;
	stroke: var(--accent);
	stroke-width: 1;
	stroke-linejoin: round;
}
.tp_cutter_view .mpv_shank{
	fill: var(--text-3);
	fill-opacity: .25;
	stroke: var(--text-3);
	stroke-width: 1;
}
.tp_cutter_view .mpv_dim{
	stroke: var(--text-2);
	stroke-width: 1;
}
.tp_cutter_view .mpv_txt{
	fill: var(--text-2);
	font: 10px ui-monospace, "Cascadia Mono", Consolas, monospace;
}
.tp_cutter_view .mpv_halo{
	paint-order: stroke;
	stroke: var(--surface-2);
	stroke-width: 3px;
	stroke-linejoin: round;
}
/* блок настроек операции (op-settings.js) в узкой колонке: вид повтора — во всю ширину, подпись над ним */
.sketch_side .repeat .field:has(> .seg_4){
	grid-template-columns: minmax(0, 1fr);
	gap: 4px;
}
.sketch_point{
	display: flex;
	flex-direction: column;
	gap: 10px;
	padding: 10px;
	border-radius: var(--r);
	background: var(--accent-soft);
}
.sketch_point[hidden]{
	display: none;
}
.sk_point_head{
	display: flex;
	align-items: center;
	justify-content: space-between;
	margin: -4px -4px -4px 0;
}
.sk_point_name{
	font-size: 12.5px;
	font-weight: 600;
}
/* список и кнопки к нему в одной строке: элемент фрезы и корзина, контур и + / корзина */
.sk_with_btn{
	display: flex;
	align-items: center;
	gap: 2px;
	min-width: 0;
}
.sk_with_btn .input{
	flex: 1;
	min-width: 0;
}
.sketch_foot{
	display: flex;
	justify-content: flex-end;
	gap: 8px;
}
.sk_grid line{
	stroke: var(--line);
	stroke-width: 1;
}
.sk_grid line.sk_axis{
	stroke: var(--text-3);
}
.sk_shape{
	fill: rgba(13, 153, 255, .16);
	stroke: var(--accent);
	stroke-width: 1.5;
}
.sk_shape.is_bad{
	fill: rgba(229, 72, 77, .16);
	stroke: #E5484D;
}
.sk_ctrl{
	fill: none;
	stroke: var(--text-3);
	stroke-width: 1;
	stroke-dasharray: 4 4;
	opacity: .5;
}
.sk_ctrl.is_active{
	opacity: 1;
}
.sk_pt{
	fill: #fff;
	stroke: var(--accent);
	stroke-width: 2;
	cursor: grab;
}
.sk_pt.is_sel{
	fill: var(--accent);
}
/* лобзик: ручка дуги в середине ребра (у дуги — в вершине, закрашена) и заготовка вокруг контура */
.sk_mid{
	fill: var(--surface);
	stroke: var(--accent);
	stroke-width: 1.5;
	cursor: grab;
}
.sk_mid.is_arc{
	fill: var(--accent);
}
.sk_frame{
	stroke: var(--accent);
	pointer-events: none;
}

/* токарный станок (lathe.js) в том же окне */
.sk_profile_only[hidden],
.sk_lathe_only[hidden]{
	display: none;
}
.sk_blank{
	fill: var(--text-3);
	fill-opacity: .14;
	stroke: var(--text-3);
	stroke-width: 1;
}
.sk_mirror{
	fill: rgba(13, 153, 255, .08);
	stroke: var(--accent);
	stroke-width: 1;
	stroke-dasharray: 3 3;
	opacity: .7;
}
.sk_center{
	stroke: var(--text-2);
	stroke-width: 1;
	stroke-dasharray: 12 3 2 3;
}

/* фреза (mill.js): поля в окне контура, след фрезы, подсказка выбора стороны */
.sk_mill_only[hidden],
.sk_jigsaw_only[hidden],
.sk_section_only[hidden],
.sk_full_only[hidden],
.sk_holes[hidden]{
	display: none;
}
.sk_shape.is_line{
	fill: none;
}
/* сообщение студии вместо alert (notice.js): строка внизу сцены, сама уходит; клик — убрать */
.notice{
	position: absolute;
	left: 50%;
	bottom: 60px;
	transform: translateX(-50%);
	z-index: 30;
	display: flex;
	align-items: center;
	gap: 10px;
	max-width: min(560px, calc(100% - 32px));
	padding: 8px 8px 8px 14px;
	border-radius: var(--r);
	background: var(--tip-bg);
	color: var(--tip-text);
	font-size: 12.5px;
	line-height: 1.4;
	box-shadow: 0 4px 16px rgba(0, 0, 0, .25);
	cursor: pointer;
}
body > .notice{
	position: fixed;
}
.notice[hidden]{
	display: none;
}
.notice.is_warn{
	box-shadow: inset 3px 0 0 var(--warn-text), 0 4px 16px rgba(0, 0, 0, .25);
}
.notice_close{
	flex: none;
	width: 22px;
	height: 22px;
	border-radius: 50%;
	color: inherit;
	opacity: .7;
}

/* меню правой кнопки по детали (designer-ui.js): те же действия, что в шапке свойств */
.ctx_menu{
	position: fixed;
	z-index: 1000;
	display: flex;
	flex-direction: column;
	min-width: 190px;
	padding: 4px;
	border-radius: var(--r);
	background: var(--surface);
	box-shadow: var(--shadow-pop);
}
.ctx_menu[hidden]{
	display: none;
}
.ctx_item{
	display: flex;
	align-items: center;
	justify-content: space-between;
	gap: 16px;
	height: 30px;
	padding: 0 10px;
	border-radius: var(--r-sm);
	color: var(--text);
	font-size: 13px;
	text-align: left;
}
.ctx_item kbd{
	color: var(--text-3);
	font: 500 11px/1 ui-monospace, "Cascadia Mono", Consolas, monospace;
}
.ctx_item.is_danger{
	color: var(--danger);
}
.ctx_item:hover,
.ctx_item:focus-visible{
	background: var(--surface-2);
}

/* окно «Keyboard and mouse» (#keysWindow) */
.keys_list{
	display: grid;
	grid-template-columns: max-content 1fr;
	gap: 8px 16px;
	margin: 0;
	font-size: 13px;
}
.keys_list dt{
	color: var(--text);
	font-weight: 600;
	white-space: nowrap;
}
.keys_list dd{
	margin: 0;
	color: var(--text-2);
}
.keys_list kbd{
	display: inline-block;
	min-width: 18px;
	padding: 1px 5px;
	border: 1px solid var(--line-strong);
	border-radius: 4px;
	font: 500 11px/1.4 ui-monospace, "Cascadia Mono", Consolas, monospace;
	text-align: center;
}

/* подсказка фрезы — внизу сцены, как строка линейки (.measure_hint): сверху её закрывала плашка группы */
.mill_hint{
	position: absolute;
	bottom: 15px;
	left: 50%;
	transform: translateX(-50%);
	z-index: 5;
	padding: 6px 14px;
	border-radius: 999px;
	background: var(--tip-bg);
	color: var(--tip-text);
	font-size: 12px;
	white-space: nowrap;
	box-shadow: 0 4px 16px rgba(0, 0, 0, .25);
	pointer-events: none;
}
.mill_hint[hidden]{
	display: none;
}
/* «Select several» (main.js: setPickMany) — та же плашка; на телефоне Esc нет — выключает та же кнопка */
@media (max-width: 760px){
	.pick_hint_esc{
		display: none;
	}
}


/* ---------- Карты раскроя (cutting-ui.js) ---------- */

/* кнопка в шапке: пока идёт расчёт — значок мерцает */
#cutting.is_busy .i{
	animation: cut_pulse 1s ease-in-out infinite;
}
@keyframes cut_pulse{
	50%{ opacity: .3; }
}
/* правка детали библиотеки: на сцене только она — раскрой проекта не про неё */
body[data-mode="part"] #cutting{
	display: none;
}

/* окно на почти весь экран: шапка, слева настройки и материалы, справа карты и детали */
.cut_window{
	width: min(1280px, calc(100vw - 32px));
	height: min(880px, calc(100vh - 32px));
	height: min(880px, calc(100dvh - 32px));
	flex-direction: column;
	overflow: hidden;
}
.cut_head{
	display: flex;
	align-items: center;
	gap: 10px;
	padding: 10px 10px 10px 18px;
	border-bottom: 1px solid var(--line);
	flex: none;
}
.cut_status{
	flex: 1;
	min-width: 0;
	color: var(--text-3);
	font-size: 12px;
}
.cut_body{
	flex: 1;
	min-height: 0;
	display: grid;
	grid-template-columns: 272px minmax(0, 1fr);
}
.cut_side{
	overflow: auto;
	border-right: 1px solid var(--line);
}
.cut_block{
	display: flex;
	flex-direction: column;
	gap: 10px;
	padding: 12px 14px 14px;
	border-bottom: 1px solid var(--line);
}
.cut_block_title{
	font-size: 12px;
	font-weight: 600;
}
.cut_fields{
	display: grid;
	grid-template-columns: 1fr 1fr;
	gap: 8px;
}
.cut_field{
	display: flex;
	flex-direction: column;
	gap: 5px;
	min-width: 0;
	color: var(--text-2);
	font-size: 12px;
}
.cut_inline{
	display: grid;
	grid-template-columns: minmax(0, 1fr) 72px;
	align-items: center;
	gap: 8px;
	color: var(--text-2);
	font-size: 12px;
}
.cut_window [data-cut-for][hidden]{
	display: none;
}
.seg.cut_first{
	grid-template-columns: repeat(3, 1fr);
	margin: 0;
}

/* материалы */
.cut_mats{
	display: flex;
	flex-direction: column;
	gap: 4px;
}
.cut_mat{
	display: flex;
	align-items: flex-start;
	gap: 10px;
	width: 100%;
	padding: 8px;
	border: 1px solid transparent;
	border-radius: var(--r);
	text-align: left;
}
.cut_mat.is_active{
	border-color: var(--accent);
	background: var(--accent-soft);
}
.cut_swatch{
	flex: none;
	width: 18px;
	height: 18px;
	margin-top: 1px;
	border: 1px solid var(--line-strong);
	border-radius: 4px;
}
.cut_mat_text{
	display: flex;
	flex-direction: column;
	min-width: 0;
}
.cut_mat_name{
	font-weight: 600;
	overflow: hidden;
	text-overflow: ellipsis;
	white-space: nowrap;
}
.cut_mat_params{
	color: var(--text-2);
	font-size: 12px;
}
.cut_mat_res{
	color: var(--text-3);
	font-size: 12px;
}
.cut_mat.is_warn .cut_mat_res{
	color: var(--warn-text);
}
@media (pointer: fine){
	.cut_mat:hover:not(.is_active){ background: var(--surface-2); }
}

/* карты выбранного материала */
.cut_main{
	display: flex;
	flex-direction: column;
	min-width: 0;
	min-height: 0;
}
.cut_bar{
	display: flex;
	flex-direction: column;
	gap: 6px;
	padding: 10px 16px;
	border-bottom: 1px solid var(--line);
	flex: none;
}
.cut_bar:empty{
	display: none;
}
.cut_bar_row{
	display: flex;
	align-items: center;
	flex-wrap: wrap;
	gap: 6px 12px;
	min-height: 30px;
}
.cut_bar_title{
	font-size: 14px;
	font-weight: 600;
}
.cut_stats{
	color: var(--text-2);
	font-size: 12.5px;
}
.cut_spacer{
	flex: 1;
}
.cut_selrow{
	padding: 4px 4px 4px 10px;
	border-radius: var(--r-sm);
	background: var(--accent-soft);
}
.cut_note{
	color: var(--text-3);
	font-size: 12px;
}
.cut_warn{
	padding: 6px 10px;
	border-radius: var(--r-sm);
	background: var(--warn-bg);
	color: var(--warn-text);
	font-size: 12px;
}
.cut_scroll{
	flex: 1;
	min-height: 0;
	overflow: auto;
}
.cut_maps{
	display: grid;
	grid-template-columns: repeat(auto-fill, minmax(400px, 1fr));
	gap: 18px;
	padding: 16px;
}
.cut_maps.is_bars{
	display: flex;
	flex-direction: column;
	gap: 10px;
}
.cut_sheet{
	display: flex;
	flex-direction: column;
	gap: 6px;
	margin: 0;
	min-width: 0;
}
.cut_sheet figcaption{
	display: flex;
	gap: 6px;
	color: var(--text-2);
	font-size: 12px;
}
.cut_cap_warn{
	color: var(--warn-text);
}
/* цель «новый лист» — пока деталь тянут */
.cut_new{
	display: none;
}
.cut_window[data-drag] .cut_new{
	display: flex;
}
.cut_new .cut_svg{
	opacity: .7;
	outline: 2px dashed var(--accent);
	outline-offset: -2px;
}

/* лист: SVG в мм; толщины линий — в пикселях экрана */
.cut_svg{
	display: block;
	width: 100%;
	height: auto;
	user-select: none;
	-webkit-user-select: none;
	overflow: visible;
}
.cut_window[data-edit="on"] .cut_svg{
	touch-action: none;
}
.cs_hatch_bg{ fill: var(--surface-2); }
.cs_hatch_ln{ stroke: var(--line-strong); }
.cs_grain_ln{ stroke: rgba(0, 0, 0, .1); }
.cs_sheet{
	stroke: var(--text-3);
	stroke-width: 1;
	vector-effect: non-scaling-stroke;
}
.cs_field{
	fill: none;
	stroke: var(--text-3);
	stroke-width: 1;
	stroke-dasharray: 4 3;
	vector-effect: non-scaling-stroke;
}
.cs_new{
	fill: var(--accent-ink);
	font-family: var(--font);
}
.cs_part .cs_body{
	stroke: rgba(0, 0, 0, .55);
	stroke-width: 1;
	vector-effect: non-scaling-stroke;
}
.cs_grain{
	pointer-events: none;
}
.cs_lbl{
	pointer-events: none;
	font-family: var(--font);
	text-anchor: middle;
	dominant-baseline: central;
}
.cut_window[data-edit="on"] .cs_part{
	cursor: grab;
}
.cs_part.is_drag{
	cursor: grabbing;
	opacity: .85;
}
.cs_part.is_hl .cs_body{
	stroke: var(--accent);
	stroke-width: 2;
	stroke-dasharray: 5 3;
}
.cs_part.is_sel .cs_body{
	stroke: var(--accent);
	stroke-width: 3;
	stroke-dasharray: none;
}
.cs_part.is_bad .cs_body{
	stroke: var(--danger);
	stroke-width: 3;
}
.cs_part.is_bad{
	opacity: .7;
}
.cs_cut{
	fill: none;
	stroke: #E5484D;
	stroke-width: 1;
	vector-effect: non-scaling-stroke;
	pointer-events: none;
}
.cs_cut.cs_l1{
	stroke-width: 2;
}
.cs_cut.cs_l3{
	stroke-dasharray: 4 3;
}
.cs_off{
	pointer-events: none;
}
.cs_off rect{
	fill: rgba(47, 158, 95, .16);
	stroke: #2F9E5F;
	stroke-width: 1;
	stroke-dasharray: 4 3;
	vector-effect: non-scaling-stroke;
}
.cs_off text{
	fill: #2F9E5F;
}

/* хлысты профилей */
.cut_barrow{
	display: flex;
	flex-direction: column;
	gap: 4px;
}
.cut_barcap{
	display: flex;
	gap: 8px;
	color: var(--text-2);
	font-size: 12px;
}
.cut_barcap b{
	color: var(--text);
}
.cut_times{
	color: var(--accent-ink);
	font-weight: 600;
}
.cut_bartrack{
	position: relative;
	height: 30px;
	border: 1px solid var(--line-strong);
	border-radius: 3px;
	background: repeating-linear-gradient(45deg, var(--surface-2) 0 6px, var(--line) 6px 7px);
	overflow: hidden;
}
.cut_bartrack > span{
	position: absolute;
	top: 0;
	bottom: 0;
	display: grid;
	place-items: center;
	overflow: hidden;
	font-size: 11px;
	white-space: nowrap;
}
.cut_bartrack > span > span{
	overflow: hidden;
	text-overflow: ellipsis;
	padding: 0 3px;
	max-width: 100%;
}
.cb_trim{
	background: var(--line-strong);
}
.cb_piece{
	background: var(--surface);
	border-left: 1px solid rgba(0, 0, 0, .45);
	border-right: 1px solid rgba(0, 0, 0, .45);
}
.cb_rest{
	color: var(--text-3);
}
.cb_rest.is_use{
	background: rgba(47, 158, 95, .16);
	color: #2F9E5F;
}

/* детали материала */
.cut_parts{
	padding: 0 16px 16px;
}
.cut_table{
	width: 100%;
	border-collapse: collapse;
	font-size: 12.5px;
}
.cut_table th{
	padding: 7px 8px;
	border-bottom: 1px solid var(--line-strong);
	color: var(--text-3);
	font-weight: 500;
	text-align: left;
	white-space: nowrap;
}
.cut_table td{
	padding: 6px 8px;
	border-bottom: 1px solid var(--line);
}
.cut_table .num{
	text-align: right;
	font-variant-numeric: tabular-nums;
	white-space: nowrap;
}
.cut_table tbody tr{
	cursor: pointer;
}
.cut_table tr.is_hl td{
	background: var(--accent-soft);
}
.cut_parts .cut_note{
	margin-top: 8px;
}
.cut_grain{
	white-space: nowrap;
}
@media (pointer: fine){
	.cut_table tbody tr:hover td{ background: var(--surface-2); }
}

/* узкий экран: окно на весь экран, всё одной колонкой с прокруткой */
@media (max-width: 899px){
	#cutting{
		width: 34px;
		padding: 0;
	}
	#cutting .i{
		width: 18px;
		height: 18px;
		color: var(--text);
	}
	.cut_window{
		width: 100vw;
		height: 100vh;
		height: 100dvh;
		border-radius: 0;
	}
	.cut_head{
		flex-wrap: wrap;
		padding: 8px 8px 8px 14px;
	}
	.cut_body{
		display: block;
		overflow: auto;
	}
	.cut_side{
		overflow: visible;
		border-right: 0;
	}
	.cut_main{
		min-height: 70vh;
	}
	.cut_scroll{
		overflow: visible;
	}
	.cut_maps{
		grid-template-columns: minmax(0, 1fr);
		padding: 12px;
	}
	.cut_parts{
		padding: 0 12px 16px;
		overflow-x: auto;
	}
}

/* кромка: отрезки на картах, чёрточки под размерами, образец в легенде */
.cut_window{
	--cut-band: #E8833A;
}
:root[data-theme="light"] .cut_window{
	--cut-band: #D0650F;
}
.cs_band{
	fill: none;
	stroke: var(--cut-band);
	stroke-width: 3;
	stroke-linecap: butt;
	vector-effect: non-scaling-stroke;
	pointer-events: none;
}
.cs_band.is_thick{
	stroke-width: 5;
}
.cut_dim{
	display: inline-block;
	padding-bottom: 2px;
	line-height: 1.2;
}
.cut_dim[data-band="1"]{
	border-bottom: 2px solid var(--cut-band);
}
.cut_dim[data-band="2"]{
	border-bottom: 5px double var(--cut-band);
}
.cut_dim.is_thick[data-band="1"]{
	border-bottom-width: 3px;
}
.cut_dim.is_thick[data-band="2"]{
	border-bottom-width: 7px;
}
.cut_band_key{
	display: inline-block;
	width: 18px;
	height: 3px;
	margin-right: 4px;
	vertical-align: middle;
	background: var(--cut-band);
}
.cut_band_sw{
	display: inline-block;
	width: 10px;
	height: 10px;
	margin-right: 6px;
	border: 1px solid var(--line-strong);
	border-radius: 2px;
	vertical-align: -1px;
}

/* чертежи (cutting-draw.js): лист A4 на белой бумаге, клик — просмотр на весь экран (drawing-view.js) */
.cut_window [data-cut-draw][hidden]{
	display: none;
}
.cut_maps.is_draws{
	grid-template-columns: repeat(auto-fill, minmax(440px, 1fr));
	align-items: start;
}
.cut_draw{
	display: flex;
	flex-direction: column;
	gap: 6px;
	margin: 0;
	min-width: 0;
	cursor: zoom-in;
}
.cut_draw figcaption{
	display: flex;
	gap: 8px;
	color: var(--text-2);
	font-size: 12px;
}
.cut_draw figcaption b{
	color: var(--text);
	font-weight: 600;
}
.cut_paper{
	display: grid;
	place-items: center;
	aspect-ratio: 297 / 210;
	border: 1px solid var(--line);
	border-radius: 4px;
	background: #FFFFFF;
	box-shadow: 0 1px 3px rgba(0, 0, 0, .18);
	overflow: hidden;
}
.cut_paper svg{
	display: block;
	width: 100%;
	height: auto;
}
.cut_paper_wait{
	color: #8C9198;
	font-size: 12px;
}
@media (max-width: 899px){
	.cut_maps.is_draws{
		grid-template-columns: minmax(0, 1fr);
	}
}
/* надписи чертежа — как в PDF (Roboto), без шрифта с засечками по умолчанию */
.cut_paper svg text,
.dv_svg text{
	font-family: Roboto, "IBM Plex Sans", Arial, sans-serif;
}

/* просмотр чертежа на весь экран (drawing-view.js): шапка — соседние листы, надпись, масштаб; ниже — лист
   на подложке в тон сцене. Приближение — viewBox самого SVG (чёткий вблизи), элемент — во всё окно */
.dv{
	position: fixed;
	inset: 0;
	z-index: 100100;	/* над окнами (.window — 100000) */
	display: flex;
	flex-direction: column;
	background: var(--surface);
	color: var(--text);
}
.dv_head{
	display: flex;
	align-items: center;
	gap: 4px;
	padding: 8px 10px;
	border-bottom: 1px solid var(--line);
	flex: none;
}
.dv .icon_btn:disabled{
	opacity: .35;
	cursor: default;
	pointer-events: none;
}
.dv_prev .i{
	transform: rotate(90deg);
}
.dv_next .i{
	transform: rotate(-90deg);
}
.dv_count{
	min-width: 48px;
	color: var(--text-2);
	font-size: 12px;
	font-variant-numeric: tabular-nums;
	text-align: center;
}
.dv_count:empty{
	display: none;
}
.dv_title{
	display: flex;
	align-items: baseline;
	gap: 8px;
	flex: 1;
	min-width: 0;
	margin-left: 8px;
	overflow: hidden;
	color: var(--text-2);
	font-size: 12px;
	white-space: nowrap;
}
.dv_title b{
	flex: none;
	max-width: 60%;
	overflow: hidden;
	text-overflow: ellipsis;
	color: var(--text);
	font-size: 13px;
	font-weight: 600;
}
.dv_title span{
	min-width: 0;
	overflow: hidden;
	text-overflow: ellipsis;
}
.dv_zoom{
	display: flex;
	align-items: center;
	gap: 2px;
	flex: none;
	margin-right: 6px;
}
.dv_pct{
	min-width: 58px;
	height: 30px;
	padding: 0 6px;
	border-radius: var(--r-sm);
	color: var(--text-2);
	font-size: 12px;
	font-variant-numeric: tabular-nums;
}
@media (pointer: fine){
	.dv_pct:hover{ background: var(--surface-2); color: var(--text); }
}
.dv_stage{
	position: relative;
	flex: 1;
	min-height: 0;
	overflow: hidden;
	background: var(--viewport);
	outline: 0;
	cursor: grab;
	touch-action: none;
	user-select: none;
	-webkit-user-select: none;
}
.dv_stage.is_drag{
	cursor: grabbing;
}
.dv_svg{
	position: absolute;
	inset: 0;
	display: block;
	width: 100%;
	height: 100%;
}
.dv_wait{
	position: absolute;
	inset: 0;
	display: grid;
	place-items: center;
	color: var(--viewport-text);
	font-size: 13px;
	pointer-events: none;
}
.dv_wait[hidden]{
	display: none;
}
/* подсказка — в шапке, не поверх листа (внизу листа — основная надпись) */
.dv_hint{
	flex: none;
	margin: 0 8px;
	color: var(--text-3);
	font-size: 12px;
	white-space: nowrap;
}
@media (max-width: 1099px){
	.dv_hint{
		display: none;
	}
}
@media (max-width: 899px){
	/* на телефоне масштаб — щипком: + и − не нужны, надпись — только имя */
	.dv [data-dv="in"],
	.dv [data-dv="out"],
	.dv_title span{
		display: none;
	}
}

/* полоса под шапкой окна раскроя: станок, установленные настройки, кнопка Settings */
.cut_strip{
	display: flex;
	align-items: center;
	gap: 12px;
	padding: 8px 16px;
	border-bottom: 1px solid var(--line);
	flex: none;
}
.cut_machine{
	flex: none;
	width: 150px;
}
.cut_summary{
	flex: 1;
	min-width: 0;
}
.cut_settings_btn{
	flex: none;
}
.cut_settings_btn .cut_chev{
	width: 16px;
	height: 16px;
	transition: transform .15s;
}
.cut_settings_btn[aria-expanded="true"]{
	border-color: var(--accent);
}
.cut_settings_btn[aria-expanded="true"] .cut_chev{
	transform: rotate(180deg);
}
.cut_head .cut_status{
	flex: 1;
	text-align: right;
}

/* раскрывающаяся секция настроек: группы в одну строку, поля — подписью сверху */
.cut_settings{
	display: flex;
	flex-wrap: wrap;
	flex: none;
	max-height: 45%;
	overflow: auto;
	border-bottom: 1px solid var(--line);
	background: var(--surface-2);
}
.cut_settings[hidden]{
	display: none;
}
.cut_group{
	display: flex;
	flex-direction: column;
	gap: 8px;
	padding: 10px 16px 12px;
}
.cut_group + .cut_group{
	border-left: 1px solid var(--line);
}
.cut_group_title{
	font-weight: 600;
}
.cut_group_row{
	display: flex;
	flex-wrap: wrap;
	align-items: flex-end;
	gap: 10px 12px;
}
.cut_ctl{
	display: flex;
	flex-direction: column;
	gap: 4px;
	color: var(--text-2);
	font-size: 12.5px;
}
.cut_ctl .input{
	width: 76px;
}
.cut_ctl .seg.cut_first{
	width: 210px;
}
.cut_ctl_check{
	min-height: 32px;
	align-items: center;
	white-space: nowrap;
}
.cut_side{
	padding: 10px;
}
@media (max-width: 899px){
	.cut_strip{
		flex-wrap: wrap;
		padding: 8px 12px;
	}
	.cut_summary{
		order: 5;
		flex-basis: 100%;
	}
	.cut_machine{
		flex: 1;
		width: auto;
	}
	.cut_settings{
		max-height: none;
	}
	.cut_group{
		flex-basis: 100%;
		padding: 10px 12px 12px;
	}
	.cut_group + .cut_group{
		border-left: 0;
		border-top: 1px solid var(--line);
	}
	.cut_side{
		padding: 8px;
	}
}

/* варианты проекта (variants.js): кнопка за названием и окно под ней; до 1199px — только значок */
.variants{
	position: relative;
	flex: none;
}
.variants_btn .variants_chev{
	width: 16px;
	height: 16px;
	transition: transform .15s;
}
.variants_btn[aria-expanded="true"]{
	background: var(--btn-hover);
}
.variants_btn[aria-expanded="true"] .variants_chev{
	transform: rotate(180deg);
}
@media (max-width: 1199px){
	.variants_btn{
		width: 34px;
		padding: 0;
	}
	.variants_btn .btn_label,
	.variants_btn .variants_chev{
		display: none;
	}
}
.variants_menu{
	position: absolute;
	top: calc(100% + 8px);
	left: 0;
	z-index: 1000;
	width: 320px;
	padding: 10px;
	border: 1px solid var(--line);
	border-radius: var(--r);
	background: var(--surface);
	box-shadow: var(--shadow-pop);
}
.variants_menu[hidden]{
	display: none;
}
.variants_head{
	display: flex;
	align-items: center;
	gap: 10px;
}
.variants_save{
	flex: 1;
}
/* тариф без вариантов (Free): кнопка — как неактивная, но нажимается — окно тарифов (variants.js); корона — яркая */
.variants_save.is_locked{
	background: var(--btn);
	border-color: var(--btn);
	color: var(--text-3);
}
@media (pointer: fine){
	.variants_save.is_locked:hover{ background: var(--btn-hover); border-color: var(--btn-hover); color: var(--text-2); }
}
.variants_count{
	flex: none;
	min-width: 36px;
	text-align: right;
	font-variant-numeric: tabular-nums;
	font-weight: 600;
}
.variants_hint{
	margin-top: 10px;
	color: var(--text-2);
}
.variants_hint.is_warn{
	color: var(--warn-text);
}
.variants_list{
	display: flex;
	flex-direction: column;
	gap: 2px;
	margin: 10px 0 0;
	padding: 8px 0 0;
	border-top: 1px solid var(--line);
	list-style: none;
}
.variants_item{
	display: flex;
	align-items: center;
	gap: 4px;
}
.variants_link{
	display: flex;
	align-items: center;
	gap: 8px;
	flex: 1;
	min-width: 0;
	height: 34px;
	padding: 0 8px;
	border-radius: var(--r-sm);
	color: var(--text);
	text-decoration: none;
}
.variants_item.is_current .variants_link{
	background: var(--accent-soft);
}
.variants_name{
	flex: 1;
	min-width: 0;
	overflow: hidden;
	text-overflow: ellipsis;
	white-space: nowrap;
}
.variants_tag{
	flex: none;
	padding: 1px 6px;
	border: 1px solid var(--line-strong);
	border-radius: 10px;
	color: var(--text-2);
	font-size: 11px;
}
.variants_check{
	flex: none;
	width: 16px;
	height: 16px;
	color: var(--accent);
}
.variants_del{
	flex: none;
}
@media (pointer: fine){
	.variants_item:not(.is_current) .variants_link:hover{ background: var(--surface-2); }
}
/* телефон: кнопка — в полосе проекта под кнопками шапки, места там хватает и на подпись; окно — под шапкой */
@media (max-width: 899px){
	.variants_btn{
		width: auto;
		padding: 0 10px;
	}
	.variants_btn .btn_label{
		display: inline;
	}
	.variants_btn .variants_chev{
		display: none;
	}
	.variants_menu{
		position: fixed;
		top: calc(var(--header-h) + 4px);
		left: 8px;
		right: 8px;
		width: auto;
	}
}

/* сохранение (autosave.js): кнопка «Save» — точка, пока есть что отправить на сервер; состояние */
.save_btn{
	position: relative;
}
.save_btn.is_dirty::after{
	content: "";
	position: absolute;
	top: 5px;
	right: 5px;
	width: 7px;
	height: 7px;
	border-radius: 50%;
	background: var(--accent);
}
.save_btn.is_warn::after{
	background: var(--warn-text);
}
.save_status.is_warn{
	color: var(--warn-text);
}

/* история версий (versions.js): часы в поле названия и панель поверх правой колонки, как в Figma */
.versions_btn[aria-pressed="true"]{
	color: var(--accent);
}
body[data-view] .versions_btn,
body[data-view] .versions_panel{
	display: none;
}
.versions_panel{
	position: fixed;
	top: var(--header-h);
	right: var(--ads-w, 0px);	/* левее колонки рекламы */
	bottom: 0;
	z-index: 50;
	display: flex;
	flex-direction: column;
	width: min(var(--right-w), 100vw);
	border-left: 1px solid var(--line);
	background: var(--surface);
	box-shadow: var(--shadow-pop);
}
.versions_panel[hidden]{
	display: none;
}
.versions_list{
	padding: 2px 0 16px;
}
.versions_current{
	display: flex;
	flex-direction: column;
	gap: 2px;
	margin: 2px 8px 4px;
	padding: 10px;
	border-radius: var(--r);
	background: var(--accent-soft);
}
.versions_title{
	font-weight: 600;
}
.versions_meta{
	color: var(--text-2);
	font-size: 12px;
}
.versions_day{
	margin: 14px 18px 4px;
	color: var(--text-3);
	font-size: 11px;
	font-weight: 600;
	letter-spacing: .04em;
	text-transform: uppercase;
}
.versions_item{
	display: flex;
	align-items: center;
	gap: 8px;
	margin: 0 8px;
	padding: 7px 8px 7px 10px;
	border-radius: var(--r);
}
.versions_text{
	display: flex;
	flex-direction: column;
	gap: 1px;
	flex: 1;
	min-width: 0;
}
.versions_time{
	font-weight: 600;
	font-variant-numeric: tabular-nums;
}
.versions_text .versions_meta{
	overflow: hidden;
	text-overflow: ellipsis;
	white-space: nowrap;
}
.versions_restore{
	flex: none;
	height: 28px;
}
@media (pointer: fine){
	.versions_item:hover{ background: var(--surface-2); }
	.versions_restore{ opacity: 0; }
	.versions_item:hover .versions_restore,
	.versions_restore:focus-visible{ opacity: 1; }
}
.versions_hint{
	margin: 8px 18px;
	color: var(--text-2);
}
.versions_hint.is_warn{
	color: var(--warn-text);
}
.versions_foot{
	margin: 16px 18px 0;
	color: var(--text-3);
	font-size: 12px;
}
.versions_foot a{
	color: var(--accent);
}

/* проект на сервер не пишется — тариф или корзина (autosave.js: renderBar): полоса над сценой,
   инструменты сцены — ниже неё */
.plan_bar{
	position: absolute;
	top: 0;
	left: 0;
	right: 0;
	z-index: 6;
	display: flex;
	align-items: center;
	gap: 8px;
	min-height: 44px;
	padding: 6px 8px 6px 14px;
	border-bottom: 1px solid var(--warn-line);
	background: linear-gradient(var(--warn-bg), var(--warn-bg)), var(--surface);
	color: var(--warn-text);
}
.plan_bar[hidden]{
	display: none;
}
.plan_bar_icon{
	flex: none;
	width: 18px;
	height: 18px;
}
.plan_bar_text{
	flex: 1;
	min-width: 0;
	font-size: 13px;
}
.plan_bar .btn{
	flex: none;
	height: 30px;
}
body.has_plan_bar .tools,
body.has_plan_bar .group_bar{
	top: 56px;
}
body.has_plan_bar[data-mode="part"] .plan_bar{
	top: 44px;
}
body.has_plan_bar[data-mode="part"] .tools,
body.has_plan_bar[data-mode="part"] .group_bar{
	top: 100px;
}

/* Free, публикации ещё нет — напоминание мягче: не предупреждение, а подсказка */
.plan_bar.is_soft{
	border-bottom-color: var(--line);
	background: linear-gradient(var(--accent-soft), var(--accent-soft)), var(--surface);
	color: var(--text);
}
.plan_bar.is_soft .plan_bar_icon{
	color: var(--accent);
}

/* Free: значок «Public» у «Save» (autosave.js: renderBar) */
.public_badge{
	flex: none;
	padding: 1px 7px;
	border: 1px solid rgba(255, 255, 255, .28);
	border-radius: 10px;
	color: var(--text-2);
	font-size: 11px;
	font-weight: 600;
	cursor: default;
}
.public_badge[hidden],
body[data-view] .public_badge{
	display: none;
}

/* окно публикации (publish.js) */
.publish_window{
	width: min(520px, calc(100vw - 32px));
}
.publish_body{
	max-height: min(76vh, 760px);
	overflow-y: auto;
}
.publish_cover{
	position: relative;
	aspect-ratio: 16 / 10;
	border-radius: var(--r);
	overflow: hidden;
	background: var(--viewport);
	background: var(--viewport-bg);
}
.publish_cover img{
	display: block;
	width: 100%;
	height: 100%;
	object-fit: cover;
}
.publish_cover img:not([src]){
	visibility: hidden;
}
.publish_shot{
	position: absolute;
	right: 8px;
	bottom: 8px;
	height: 28px;
	background: var(--surface);
	box-shadow: var(--shadow-pop);
}
.publish_sections{
	display: flex;
	flex-wrap: wrap;
	gap: 6px;
	padding: 2px;
	border-radius: var(--r);
}
.publish_sections[aria-invalid="true"]{
	box-shadow: 0 0 0 1px var(--danger);
}
.publish_section{
	height: 30px;
	padding: 0 11px;
	border: 1px solid var(--line-strong);
	border-radius: 15px;
	color: var(--text);
	font-size: 12.5px;
}
.publish_section[aria-checked="true"]{
	border-color: var(--accent);
	background: var(--accent-soft);
	color: var(--accent-ink);
	font-weight: 600;
}
@media (pointer: fine){
	.publish_section[aria-checked="false"]:hover{ border-color: var(--text-3); }
}
.publish_desc_label{
	display: flex;
	align-items: center;
	justify-content: space-between;
}
.publish_ai{
	color: var(--accent);
	font-size: 12.5px;
	font-weight: 600;
}
.publish_ai:disabled{
	color: var(--text-3);
}
.publish_body .window_field[hidden]{
	display: none;
}
.publish_desc{
	height: auto;
	font: inherit;
	min-height: 84px;
	padding: 6px 8px;
	line-height: 1.45;
	resize: vertical;
	font-variant-numeric: normal;
}
.publish_terms{
	color: var(--text-3);
	font-size: 12px;
}
.publish_terms[hidden]{
	display: none;
}
.publish_terms a{
	color: var(--text-2);
}
.publish_error{
	color: var(--danger);
	font-size: 12.5px;
}
.publish_error[hidden]{
	display: none;
}
.publish_foot{
	display: flex;
	justify-content: flex-end;
	gap: 8px;
}

/* окно «Share»: публикация проекта (share.js: renderPub) */
.share_pub{
	margin-top: 4px;
	padding: 10px 12px;
	border-radius: var(--r);
	background: var(--surface-2);
}
.share_pub[hidden]{
	display: none;
}
.share_pub_text{
	margin-top: 2px;
	color: var(--text-2);
	font-size: 12.5px;
}
.share_pub_actions{
	display: flex;
	gap: 8px;
	margin-top: 8px;
}
.share_pub_actions .btn{
	height: 30px;
}

.draft_foot{
	display: flex;
	justify-content: flex-end;
	flex-direction: column;
	gap: 8px;
}
#draftWindow{
	width: min(420px, calc(100vw - 32px));
}
@media (max-width: 899px){
	.save_btn{
		width: 34px;
		padding: 0;
	}
	/* в узкой шапке нет места для строки — состояние на кнопке (точка) и в её подсказке */
	.save_status_case{
		display: none;
	}
}

/* вход и аккаунт в меню (account.js) */
.menu_account{
	display: flex;
	flex-direction: column;
}
/* кнопка меню видом ссылки: клавиши и мышь (designer-ui.js: openKeysWindow) */
.menu_link.menu_btn{
	width: 100%;
	border: 0;
	background: none;
	font: inherit;
	text-align: left;
	cursor: pointer;
}
/* пункт меню на платных — корона справа (.paid_mark), пока тариф его не даёт (designer-ui.js: paidMarks) */
.menu_link.menu_paid{
	display: flex;
	align-items: center;
	justify-content: space-between;
	gap: 8px;
}
.menu_account button.menu_link{
	width: 100%;
	border: 0;
	background: none;
	font: inherit;
	text-align: left;
	cursor: pointer;
}
.menu_user{
	display: block;
	padding: 6px 10px 2px;
	overflow: hidden;
	color: var(--text-2);
	font-size: 12.5px;
	text-overflow: ellipsis;
	white-space: nowrap;
}
.menu_badge{
	padding: 1px 6px;
	border: 1px solid var(--line-strong);
	border-radius: 10px;
	font-size: 11px;
}

/* токены сервиса (tokens.js): кнопка в шапке — заметная, окошко баланса, строка в панели AI */
.tokens{
	position: relative;
	flex: none;
}
.tokens_pill{
	gap: 6px;
	padding: 0 6px 0 10px;
	border-color: transparent;
	background: rgba(245, 184, 61, .18);
	white-space: nowrap;
}
.tokens_spark{
	color: #F5B83D;
}
.tokens_text b{
	font-weight: 700;
	font-variant-numeric: tabular-nums;
}
.tokens_plus{
	display: grid;
	place-items: center;
	width: 20px;
	height: 20px;
	border-radius: 50%;
	background: #F5B83D;
	color: #1C1F24;
	font-weight: 700;
	line-height: 1;
}
.tokens_pill.is_guest .tokens_plus{
	display: none;
}
/* у вошедшего — только число: слова «AI tokens» — в подсказке (tokens.js: render) и для экранных
   дикторов; у гостя «Get 3 free AI tokens» — приглашение, целиком */
.tokens_pill:not(.is_guest) .tokens_word{
	position: absolute;
	width: 1px;
	height: 1px;
	overflow: hidden;
	clip-path: inset(50%);
	white-space: nowrap;
}
.tokens_pill.is_low{
	background: rgba(245, 184, 61, .3);
}
.tokens_pill.is_empty{
	background: var(--warn-bg);
}
@media (pointer: fine){
	.tokens_pill:hover{ background: rgba(245, 184, 61, .28); }
}
.tokens_menu{
	position: absolute;
	top: calc(100% + 8px);
	right: 0;
	z-index: 70;
	width: 260px;
	padding: 14px;
	border: 1px solid var(--line);
	border-radius: var(--r);
	background: var(--surface);
	box-shadow: var(--shadow-pop);
}
.tokens_menu[hidden]{
	display: none;
}
.tokens_big{
	display: flex;
	align-items: baseline;
	gap: 8px;
}
.tokens_big b{
	font-size: 28px;
	font-variant-numeric: tabular-nums;
}
.tokens_big span{
	color: var(--text-2);
}
.tokens_info{
	margin: 8px 0 12px;
	color: var(--text-2);
	line-height: 1.45;
}
/* тарифные и свои токены — отдельно (tokens.js) */
.tokens_split{
	display: grid;
	gap: 4px;
	margin: 10px 0 0;
	padding: 0;
	list-style: none;
	color: var(--text-2);
	line-height: 1.45;
}
.tokens_split b{
	color: var(--text);
	font-variant-numeric: tabular-nums;
}
.tokens_warn{
	margin: -4px 0 12px;
	color: var(--warn-text);
}
.ai_tokens{
	display: flex;
	align-items: center;
	justify-content: space-between;
	gap: 8px;
	padding: 0 10px 10px;
	color: var(--text-2);
	font-size: 12px;
}
.ai_tokens:empty{
	display: none;
}
.ai_tokens b{
	color: var(--text);
}
.tokens_none{
	color: var(--warn-text);
}
.tokens_link{
	padding: 0;
	border: 0;
	background: none;
	color: var(--accent);
	font: inherit;
	font-weight: 600;
	cursor: pointer;
	white-space: nowrap;
}
.tokens_buy_small{
	height: 28px;
	padding: 0 10px;
}
.ai_buy{
	display: flex;
	flex-direction: column;
	align-items: flex-start;
	gap: 8px;
}
@media (max-width: 899px){
	.tokens_word{
		display: none;
	}
	.tokens_pill{
		padding: 0 4px 0 8px;
	}
	/* под полосой кнопок, где сама кнопка токенов, — поверх полосы проекта */
	.tokens_menu{
		position: fixed;
		top: calc(var(--buttons-row) + 6px);
		right: 8px;
		left: auto;
	}
}

/* ---------- Просмотр по ссылке (body[data-view], share.js) ----------
   Колонки спрятаны (designer-ui.js), правки модели нет: в шапке — название «только просмотр»,
   без сохранения, вариантов, токенов и настроек; на панели инструментов — только линейка;
   материалы на карточках менять можно (не сохраняется). Документация разрешена
   (body[data-docs]) — Cutting и Download, в окне скачивания — только документация и бирки деталей */
body[data-view] .variants,
body[data-view] .tokens,
body[data-view] #shareProject,
body[data-view] #saveProject,
body[data-view] .save_status_case,
body[data-view] #toolsMain > :not(#toolMeasure),
body[data-view]:not([data-docs]) #cutting,
body[data-view] #downloadWindow .option:not(.option_docs):not(.option_labels){
	display: none;
}
/* материалы — менять можно (окно материала); своя форма профиля — только в редакторе */
body[data-view] #matEditShape{
	display: none !important;
}
body[data-view] .header_input{
	cursor: default;
}

/* копия редакции заказа (order-view.js): полоса над сценой — какая редакция какого заказа и по ней ли производство;
   заменена — предупреждение, что с деталью из адреса, ссылка на текущую */
.order_bar{
	position: fixed;
	top: calc(var(--header-h) + 8px);
	left: 50%;
	z-index: 20;
	transform: translateX(-50%);
	width: max-content;
	max-width: min(640px, calc(100vw - 32px));
	padding: 8px 14px;
	border: 1px solid var(--line);
	border-radius: 10px;
	background: var(--surface);
	color: var(--text);
	box-shadow: var(--shadow-pop);
	font-size: 13px;
	line-height: 1.4;
}
.order_bar.is_warn{ border-color: var(--warn-line); }
.order_bar.is_warn b{ color: var(--warn-text); }
.order_bar a{
	color: var(--accent-ink);
	white-space: nowrap;
}

/* сборка (assembly.js, ссылка просмотра с &assembly): панель деталей колонкой справа — сцена уже на её ширину
   (ResizeObserver студии пересчитывает кадр), на телефоне — полосой под сценой. Карточки материалов на сцене
   на это время спрятаны: справа — панель */
.assembly_btn[aria-expanded="true"],
.assembly_btn[aria-expanded="true"] .i{
	color: var(--accent);
}
.assembly_panel{
	grid-area: right;
	display: flex;
	flex-direction: column;
	min-width: 0;
	min-height: 0;
	border-left: 1px solid var(--line);
	background: var(--surface);
}
.assembly_panel[hidden]{
	display: none;
}
.assembly_panel .panel_title{
	display: flex;
	align-items: center;
	gap: 6px;
}
@media (min-width: 900px){
	body[data-assembly]{
		grid-template-columns: 0 minmax(0, 1fr) var(--right-w);
	}
}
@media (max-width: 899px){
	body[data-assembly]{
		grid-template-rows: var(--header-h) minmax(0, 1fr) minmax(0, 42%);
		grid-template-areas:
			"header"
			"view"
			"right";
	}
	.assembly_panel{
		border-left: 0;
		border-top: 1px solid var(--line);
		padding-bottom: env(safe-area-inset-bottom);
	}
}
body[data-assembly] .canvas_case > .rpane_mats{
	display: none;
}
.asm_search{
	flex: none;
	padding: 0 12px 8px;
	border-bottom: 1px solid var(--line);
}
.asm_hint{
	margin: 6px 2px 0;
	color: var(--text-3);
	font-size: 12px;
}
.asm_search_row{
	display: flex;
	gap: 6px;
}
/* QR-код камерой (qr-scan.js) — на телефонах и планшетах: с мышью этикетку к камере не поднесёшь */
.asm_scan_btn{
	width: 36px;
	background: var(--btn);
}
@media (pointer: fine){
	.asm_scan_btn{
		display: none;
	}
}

/* окно камеры: видео на весь экран, рамка (вокруг темнее), подсказка снизу, крестик сверху */
.asm_scan{
	position: fixed;
	inset: 0;
	z-index: 300;
	display: grid;
	place-items: center;
	background: #000;
}
.asm_scan[hidden]{
	display: none;
}
.asm_scan_video{
	position: absolute;
	inset: 0;
	width: 100%;
	height: 100%;
	object-fit: cover;
}
.asm_scan_frame{
	position: relative;
	width: min(68vw, 68vh, 320px);
	height: min(68vw, 68vh, 320px);
	border: 2px solid rgba(255, 255, 255, .9);
	border-radius: 18px;
	box-shadow: 0 0 0 100vmax rgba(0, 0, 0, .45);
}
.asm_scan_status{
	position: absolute;
	left: 16px;
	right: 16px;
	bottom: calc(28px + env(safe-area-inset-bottom));
	margin: 0;
	padding: 10px 14px;
	border-radius: 12px;
	background: rgba(0, 0, 0, .6);
	color: #fff;
	font-size: 15px;
	text-align: center;
}
.asm_scan_status.is_warn{
	color: #FFD27A;
}
.asm_scan_close{
	position: absolute;
	top: calc(12px + env(safe-area-inset-top));
	right: 12px;
	display: grid;
	place-items: center;
	width: 44px;
	height: 44px;
	border-radius: 22px;
	background: rgba(0, 0, 0, .55);
	color: #fff;
}
.asm_scan_close .i{
	width: 22px;
	height: 22px;
}
.asm_list{
	padding: 4px 0 16px;
}
.asm_row{
	display: flex;
	align-items: center;
	gap: 10px;
	width: calc(100% - 16px);
	margin: 0 8px;
	padding: 6px 8px;
	border-radius: var(--r);
	text-align: left;
}
.asm_row[hidden]{
	display: none;
}
.asm_row[aria-pressed="true"]{
	background: var(--accent-soft);
}
@media (pointer: fine){
	.asm_row:hover:not([aria-pressed="true"]){ background: var(--surface-2); }
}
.asm_no{
	flex: none;
	min-width: 28px;
	height: 24px;
	padding: 0 6px;
	border: 1px solid var(--line-strong);
	border-radius: var(--r-sm);
	color: var(--text);
	font-weight: 600;
	line-height: 22px;
	text-align: center;
	font-variant-numeric: tabular-nums;
}
.asm_row[aria-pressed="true"] .asm_no{
	border-color: var(--accent);
	background: var(--accent);
	color: #fff;
}
.asm_text{
	display: flex;
	flex-direction: column;
	gap: 1px;
	flex: 1;
	min-width: 0;
}
.asm_name,
.asm_meta{
	overflow: hidden;
	text-overflow: ellipsis;
	white-space: nowrap;
}
.asm_name{
	font-weight: 500;
}
.asm_meta{
	color: var(--text-2);
	font-size: 12px;
	font-variant-numeric: tabular-nums;
}
.asm_qty{
	flex: none;
	color: var(--text-2);
	font-variant-numeric: tabular-nums;
}
.asm_section{
	margin: 14px 18px 4px;
	color: var(--text-3);
	font-size: 11px;
	font-weight: 600;
	letter-spacing: .04em;
	text-transform: uppercase;
}
.asm_section[hidden],
.asm_group[hidden]{
	display: none;
}
/* изделие — заголовок раздела (assembly.js: cutProducts): клик — всё изделие на сцене */
.asm_product{
	display: flex;
	align-items: baseline;
	gap: 8px;
	width: calc(100% - 16px);
	margin: 12px 8px 2px;
	padding: 6px 8px;
	border-radius: var(--r);
	text-align: left;
}
.asm_group:first-child .asm_product{
	margin-top: 4px;
}
.asm_product_no{
	flex: none;
	color: var(--text-3);
	font-size: 11px;
	font-weight: 600;
	letter-spacing: .04em;
	text-transform: uppercase;
}
.asm_product .asm_name{
	flex: 1;
	min-width: 0;
	font-weight: 600;
}
.asm_product[aria-pressed="true"]{
	background: var(--accent-soft);
}
@media (pointer: fine){
	.asm_product:hover:not([aria-pressed="true"]){ background: var(--surface-2); }
}
.asm_empty{
	margin: 12px 18px;
	color: var(--text-2);
}
.view_badge{
	flex: none;
	padding: 3px 10px;
	border: 1px solid var(--line-strong);
	border-radius: 12px;
	color: var(--text-2);
	font-size: 12px;
	white-space: nowrap;
}

/* встроенная 3D (body[data-embed]: коммерческое предложение — offer-new/index.php, потом страница проекта;
   iframe того же сайта): только сцена и то, что помогает рассмотреть модель, — линейка (как в просмотре по
   ссылке), «к модели», просвет у камеры (включён сразу, designer-ui.js), прозрачность, крепёж. Без шапки,
   чата, карточек материалов и остальных кнопок вида. Крупнее — рамку разворачивает страница (js/model-embed.js) */
body[data-embed]{
	grid-template-rows: 0 minmax(0, 1fr);
}
body[data-embed] .header,
body[data-embed] #aiPanel,
body[data-embed] .rpane_mats,
body[data-embed] .plan_bar,
body[data-embed] .mobile_bar,
body[data-embed] #toolsView > :not(#viewFit):not(#seeNearToggle):not(#opacity):not(#fastenersToggle){
	display: none !important;
}
/* пока студия не собралась (designer-ui.js: setDesigner ставит data-ready), кнопок не видно, а экран
   загрузки — сплошной, цветом сцены: ни колонок, ни инструментов не мелькает. Колонки в просмотре по ссылке
   спрятаны сразу разметкой (designer-new/index.php: data-panels="off") */
body[data-embed]:not([data-ready]) .tools{
	visibility: hidden;
}
body[data-embed] .preloader{
	background: var(--viewport-bg);
}
/* во встроенной 3D (КП, страница проекта) — только полоска: знак и название уже на странице вокруг */
body[data-embed] .preloader_box > :not(.preloader_bar){
	display: none;
}
body[data-embed] .preloader_bar{
	margin-top: 0;
	background: rgba(0, 0, 0, .14);
}

/* окно «Share for viewing» */
.share_window{
	width: min(460px, calc(100vw - 32px));
}
.share_link{
	display: flex;
	gap: 8px;
}
.share_link .input{
	flex: 1;
	min-width: 0;
}
/* фильм проекта по ссылке (share.js: render): карточка, как блок публикации, — что это и кнопка Create */
.share_film{
	display: flex;
	flex-wrap: wrap;
	align-items: center;
	gap: 10px 12px;
	margin-top: 12px;
	padding: 10px 12px;
	border-radius: var(--r);
	background: var(--surface-2);
}
.share_film[hidden]{
	display: none;
}
.share_film_text{
	display: flex;
	flex: 1 1 220px;
	flex-direction: column;
	gap: 2px;
	min-width: 0;
}
.share_film_text span{
	color: var(--text-2);
	font-size: 12.5px;
}
.share_film_btn{
	flex: none;
	text-decoration: none;
}
.share_msg{
	min-height: 18px;
	color: var(--text-2);
	font-size: 12.5px;
}
.share_msg.is_warn{
	color: var(--warn-text);
}
.share_foot{
	display: flex;
	justify-content: flex-start;
}

/* ---------- Анимация объектов (anim-panel.js) ---------- */
.anim_card{
	display: flex;
	flex-direction: column;
	gap: 6px;
	margin-bottom: 8px;
	padding-bottom: 8px;
	border-bottom: 1px solid var(--line);
}
.anim_card_head{
	display: flex;
	align-items: center;
	justify-content: space-between;
	font-size: 12.5px;
	font-weight: 600;
}
.anim_x{
	width: 26px;
	height: 26px;
}
.anim_x .i{
	width: 14px;
	height: 14px;
}
.anim_time{
	color: var(--text-3);
	font-size: 11.5px;
}
.anim_play{
	margin-top: 6px;
}

/* ---------- заявка с сайта компании (js/site-request.js): кнопка в шапке и окно ---------- */

.site_req_btn{ white-space: nowrap; }
/* примерная цена на кнопке заявки (site-request.js: showPrice): «≈ 1,240 EUR | Send request» */
.site_req_price{
	margin-right: 9px;
	padding-right: 9px;
	border-right: 1px solid rgba(255, 255, 255, .45);
	font-weight: 600;
	font-variant-numeric: tabular-nums;
}
.site_req_price[hidden]{ display: none; }
/* телефон, сайт фирмы: в шапке — заявка с ценой; карты раскроя и «поделиться» — в меню нет, их прячем,
   у токенов гостя — только значок */
@media (max-width: 560px){
	.header_right:has(#siteRequest) #cutting,
	.header_right:has(#siteRequest) #shareProject,
	.header_right:has(#siteRequest) .tokens_pill.is_guest .tokens_text{
		display: none;
	}
	.header_right:has(#siteRequest){ gap: 6px; }
	.header_right .site_req_btn{ padding: 0 10px; }
	/* цена есть — на кнопке только она (заявка — в окне, оно же «Send your project…») */
	.site_req_price:not([hidden]){
		margin-right: 0;
		padding-right: 0;
		border-right: 0;
	}
	.site_req_price:not([hidden]) + .site_req_label{ display: none; }
}
.site_req{
	width: min(460px, calc(100vw - 32px));
	margin: auto;		/* окно — по центру: общий сброс отступов студии снял центрирование браузера */
	padding: 0;
	border: 1px solid var(--line);
	border-radius: var(--r-lg, 14px);
	background: var(--surface);
	color: var(--text);
	box-shadow: var(--shadow-pop);
}
.site_req::backdrop{ background: rgba(0, 0, 0, .45); }
.site_req_form{
	display: flex;
	flex-direction: column;
	gap: 14px;
	padding: 22px;
}
.site_req_form h2{
	margin: 0;
	font-size: 18px;
	font-weight: 600;
}
.site_req_lead,
.site_req_terms{
	margin: 0;
	color: var(--text-2);
	line-height: 1.5;
}
.site_req_terms{ font-size: 12px; }
.site_req_field{
	display: flex;
	flex-direction: column;
	gap: 6px;
}
.site_req_field span{ font-weight: 500; }
.site_req_field span i{
	color: var(--text-2);
	font-style: normal;
	font-weight: 400;
}
.site_req_field input,
.site_req_field textarea{
	width: 100%;
	padding: 9px 11px;
	border: 1px solid var(--line);
	border-radius: var(--r);
	background: var(--surface-2);
	color: var(--text);
	font: inherit;
	resize: vertical;
}
.site_req_field input:focus,
.site_req_field textarea:focus{
	border-color: var(--accent);
	outline: 0;
}
.site_req_field.is_invalid input,
.site_req_field.is_invalid textarea{ border-color: #E5484D; }
.site_req_field em,
.site_req_msg{
	color: #E5484D;
	font-size: 12px;
	font-style: normal;
}
.site_req_msg{ margin: 0; }
.site_req_actions{
	display: flex;
	gap: 8px;
}
/* заявка ушла: её страница у клиента (offer-new/request-page.php) — открыть, скопировать ссылку */
.site_req_link{
	display: flex;
	flex-wrap: wrap;
	gap: 8px;
	margin: 0;
}
/* примерная цена в окне заявки, над полями: итог крупно, суммы разделов строками, что это примерно */
.site_est{
	display: flex;
	flex-direction: column;
	gap: 10px;
	padding: 14px 16px;
	border-radius: var(--r);
	background: var(--surface-2);
}
.site_est_note{
	margin: 0;
	color: var(--text-2);
	font-size: 12px;
	line-height: 1.45;
}
.site_est_total{
	margin: 0;
	font-size: 28px;
	font-weight: 600;
	letter-spacing: -0.01em;
}
.site_est_rows{
	display: flex;
	flex-direction: column;
	gap: 6px;
	margin: 0;
}
.site_est_rows div{
	display: flex;
	justify-content: space-between;
	gap: 12px;
	padding-bottom: 6px;
	border-bottom: 1px solid var(--line);
}
.site_est_rows dt{ color: var(--text-2); }
.site_est_rows dd{
	margin: 0;
	font-variant-numeric: tabular-nums;
}

/* ---------- каталог Flatma (js/makers.js): «Get it made» — фирмы города и заявка выбранной ---------- */

.makers_hint_row{
	margin: 10px 0 0;
	color: var(--text-2);
	font-size: 12.5px;
	text-align: center;
}
.makers{
	width: min(640px, calc(100vw - 32px));
	max-height: min(86vh, 860px);
	/* по горизонтали — по центру (общий сброс отступов студии снял центрирование браузера), верх — на месте:
	   открылся список городов, сменился шаг — окно растёт вниз, поле не уезжает из-под мыши */
	margin: 7vh auto auto;
	padding: 0;
	overflow: hidden;
	border: 1px solid var(--line);
	border-radius: var(--r-lg, 14px);
	background: var(--surface);
	color: var(--text);
	box-shadow: var(--shadow-pop);
}
.makers[open]{
	display: flex;
	flex-direction: column;
}
.makers::backdrop{ background: rgba(0, 0, 0, .45); }
.makers_head{
	display: flex;
	align-items: center;
	justify-content: space-between;
	gap: 12px;
	padding: 16px 16px 0 22px;
}
.makers_head h2{
	margin: 0;
	font-size: 18px;
	font-weight: 600;
}
.makers_body{
	display: flex;
	flex-direction: column;
	gap: 12px;
	min-height: 0;
	padding: 14px 22px 18px;
	overflow-y: auto;
}
.makers_lead{
	margin: 0;
	color: var(--text-2);
	line-height: 1.5;
}
.makers_lead b{ color: var(--text); }
.makers_link{
	padding: 0;
	color: var(--accent-ink);
	font: inherit;
	text-decoration: underline;
	text-underline-offset: 2px;
}
.makers_field{
	display: flex;
	flex-direction: column;
	gap: 6px;
}
.makers_field span{ font-weight: 500; }
/* город: выпадающий список под полем */
.makers_drop{
	max-height: 272px;
	margin: 4px 0 0;
	padding: 4px;
	overflow-y: auto;
	list-style: none;
	border: 1px solid var(--line);
	border-radius: var(--r-sm);
	background: var(--surface);
	box-shadow: var(--shadow-pop);
}
.makers_opt{
	display: flex;
	align-items: baseline;
	gap: 8px;
	padding: 7px 9px;
	border-radius: var(--r-sm);
	cursor: pointer;
}
.makers_opt b{ font-weight: 500; }
.makers_opt .makers_count{ margin-left: auto; }
.makers_opt[aria-selected="true"]{ background: var(--surface-2); }
.makers_drop .makers_none{ padding: 7px 9px; }
.makers_chips:empty{ display: none; }
.makers_chips{
	display: flex;
	flex-wrap: wrap;
	gap: 6px;
}
.makers_chips_title{
	width: 100%;
	color: var(--text-3);
	font-size: 12px;
}
.makers_city{
	display: inline-flex;
	align-items: baseline;
	gap: 6px;
	padding: 6px 11px;
	border: 1px solid var(--line);
	border-radius: 999px;
	background: var(--surface-2);
	color: var(--text);
}
.makers_state,
.makers_count{
	color: var(--text-3);
	font-size: 12px;
}
.makers_none{
	margin: 0;
	color: var(--text-3);
}
@media (pointer: fine){
	.makers_city:hover{ border-color: var(--accent); }
}
.makers_tabs{ margin: 0; }
.makers_hint{
	margin: -4px 0 0;
	color: var(--text-3);
	font-size: 12.5px;
}
.makers_error{
	margin: 0;
	color: var(--danger);
}
.makers_list{
	display: flex;
	flex-direction: column;
	gap: 10px;
}
.makers_card{
	display: grid;
	grid-template-columns: 48px minmax(0, 1fr) auto;
	align-items: start;
	gap: 12px;
	padding: 14px;
	border: 1px solid var(--line);
	border-radius: var(--r-lg, 10px);
}
.makers_logo{
	display: grid;
	place-items: center;
	width: 48px;
	height: 48px;
	overflow: hidden;
	border-radius: var(--r);
	background: var(--surface-2);
	color: var(--text-2);
	font-size: 20px;
	font-weight: 600;
}
.makers_logo img{
	width: 100%;
	height: 100%;
	object-fit: cover;
}
.makers_info{
	display: flex;
	flex-direction: column;
	gap: 4px;
	min-width: 0;
}
.makers_name{
	display: flex;
	flex-wrap: wrap;
	align-items: center;
	gap: 6px 8px;
	margin: 0;
	font-size: 15px;
	font-weight: 600;
}
.makers_badge{
	padding: 2px 8px;
	border-radius: 999px;
	background: var(--accent-soft);
	color: var(--accent-ink);
	font-size: 11.5px;
	font-weight: 500;
}
.makers_makes{
	margin: 0;
	font-size: 13px;
}
.makers_meta{
	margin: 0;
	color: var(--text-2);
	font-size: 12.5px;
}
.makers_tags{
	display: flex;
	flex-wrap: wrap;
	gap: 6px;
	margin: 2px 0 0;
}
.makers_tags i{
	padding: 1px 8px;
	border: 1px solid var(--line);
	border-radius: 999px;
	color: var(--text-2);
	font-size: 11.5px;
	font-style: normal;
}
.makers_links{
	display: flex;
	flex-wrap: wrap;
	gap: 4px 12px;
	margin: 4px 0 0;
	font-size: 12.5px;
}
.makers_links a{ color: var(--accent-ink); }
.makers_send{ white-space: nowrap; }
.makers_sent{
	padding: 6px 0;
	color: var(--text-2);
	font-size: 12.5px;
	white-space: nowrap;
}
.makers_empty{
	padding: 28px 16px;
	border: 1px dashed var(--line);
	border-radius: var(--r-lg, 10px);
	text-align: center;
}
.makers_empty p{
	margin: 6px 0 0;
	color: var(--text-2);
}
.makers_docs{
	margin-top: 14px;
}
.makers_actions{
	display: flex;
	flex-wrap: wrap;
	gap: 8px;
}
.makers_foot{
	margin: 0;
	padding: 12px 22px;
	border-top: 1px solid var(--line);
	color: var(--text-3);
	font-size: 12.5px;
}
.makers_foot a{ color: var(--accent-ink); }
@media (max-width: 560px){
	.makers_card{ grid-template-columns: 40px minmax(0, 1fr); }
	.makers_logo{
		width: 40px;
		height: 40px;
	}
	.makers_send,
	.makers_sent{ grid-column: 1 / -1; }
}

/* ---------- Тарифы окном (js/plans-window.js) ----------
   Страница тарифов (/prices/?embed=1, светлая — как на сайте) во фрейме на всё окно; над ней — почему
   показали (строка предупреждения) */
.window.plans_window{
	flex-direction: column;
	width: min(1180px, calc(100vw - 32px));
	height: min(880px, calc(100dvh - 32px));
	overflow: hidden;
}
.plans_reason{
	margin: 4px 18px 10px;
	padding: 8px 12px;
	border-radius: var(--r-sm);
	background: var(--warn-bg);
	color: var(--warn-text);
	font-size: 13px;
}
.plans_reason[hidden]{
	display: none;
}
.plans_frame{
	flex: 1;
	min-height: 0;
	width: 100%;
	border: 0;
	border-radius: 0 0 var(--r-lg) var(--r-lg);
	background: #FFFFFF;
}

/* ---------- Реклама (ads-lib.php, js/ads.js) ----------
   Free и гостям — колонкой справа на всю высоту, как в старом Flatma: сверху «Remove ads» (окно тарифов),
   ниже блоки сети. Только на широком экране (от 1600px — ads.js: WIDE; решение владельца): уже сцене не хватило бы места.
   Студия уже на её ширину (--ads-w: отступ body; панели, прижатые к правому краю, — левее неё) */
.ads_col{
	display: none;
}
@media (min-width: 1600px){
	html[data-ads]{
		--ads-w: 300px;
	}
	html[data-ads] body{
		padding-right: var(--ads-w);
	}
	html[data-ads] .ads_col{
		position: fixed;
		top: 0;
		right: 0;
		bottom: 0;
		z-index: 40;
		display: flex;
		flex-direction: column;
		width: var(--ads-w);
		border-left: 1px solid var(--line);
		background: var(--surface);
	}
}
.ads_off{
	display: flex;
	flex: none;
	align-items: center;
	justify-content: center;
	gap: 8px;
	height: var(--header-h);
	border-bottom: 1px solid var(--line);
	color: var(--text);
	font-weight: 500;
}
.ads_off:hover{
	background: var(--btn-hover);
}
/* значок платного — корона кнопки Plans (#i-plans) на жёлтом: «Remove ads», меню ☰ «Open file…» и «Save as
   file», поле Name и «Save as variant» на Free — только там, где функции у человека нет. span. — сильнее
   «.option_text span» окна Download */
span.paid_mark{
	display: inline-flex;
	align-items: center;
	justify-content: center;
	flex: none;
	width: 20px;
	height: 18px;
	border-radius: 4px;
	background: #FFB82E;
	color: #000000;
	vertical-align: -3px;
}
span.paid_mark .i{
	width: 14px;
	height: 14px;
	color: #000000;		/* в кнопке .btn значок иначе серый (.btn .i) */
	stroke-width: 1.8;
}
span.paid_mark[hidden]{
	display: none;
}
/* поле Name окна элемента на Free и у гостя (designer-panels.js: lockElementTitle): только читается,
   клик — вход или окно тарифов */
#elementTitle.is_locked{
	cursor: pointer;
	color: var(--text-2);
}
.ads_slots{
	display: flex;
	flex: 1;
	flex-direction: column;
	justify-content: space-between;
	min-height: 0;
	overflow: hidden;
}
.ads_slot{
	display: flex;
	flex: 1;
	align-items: center;
	justify-content: center;
	min-height: 0;
	overflow: hidden;
}
.ads_slot > div{
	width: 100%;
}
