Design rework
This commit is contained in:
parent
7be963bc36
commit
8b964fc8ff
@ -87,12 +87,12 @@ app.post(
|
|||||||
let text = `🧼 <b>Расчёт мыла:</b> <i>${soapName}</i>\n\n`;
|
let text = `🧼 <b>Расчёт мыла:</b> <i>${soapName}</i>\n\n`;
|
||||||
|
|
||||||
text += `🔹 <b>Вес мыла:</b> ${weight} г\n`;
|
text += `🔹 <b>Вес мыла:</b> ${weight} г\n`;
|
||||||
text += `🔹 <b>Цена за 1 кг основы:</b> ${basePrice} ₽/кг\n\n`;
|
// text += `🔹 <b>Цена за 1 кг основы:</b> ${basePrice} ₽/кг\n\n`;
|
||||||
|
|
||||||
text += `🔹 <b>Отдушка:</b> ${aromaWeight} г по ${aromaPrice} ₽/фасовка\n`;
|
// text += `🔹 <b>Отдушка:</b> ${aromaWeight} г по ${aromaPrice} ₽/фасовка\n`;
|
||||||
text += `🔹 <b>Пигмент:</b> ${pigmentWeight} г по ${pigmentPrice} ₽/фасовка\n\n`;
|
// text += `🔹 <b>Пигмент:</b> ${pigmentWeight} г по ${pigmentPrice} ₽/фасовка\n\n`;
|
||||||
|
|
||||||
text += `🔹 <b>Цена формы:</b> ${moldPrice} ₽\n\n`;
|
// text += `🔹 <b>Цена формы:</b> ${moldPrice} ₽\n\n`;
|
||||||
|
|
||||||
text += `🔹 <b>Упаковка:</b>\n`;
|
text += `🔹 <b>Упаковка:</b>\n`;
|
||||||
text += ` • Пакет/коробка: ${box} ₽\n`;
|
text += ` • Пакет/коробка: ${box} ₽\n`;
|
||||||
|
|||||||
@ -1,3 +1,5 @@
|
|||||||
|
@import url('https://fonts.googleapis.com/css2?family=Sofia+Sans+Condensed:ital,wght@0,100..900;1,100..900&display=swap');
|
||||||
|
|
||||||
@import "tailwindcss";
|
@import "tailwindcss";
|
||||||
|
|
||||||
:root {
|
:root {
|
||||||
@ -8,5 +10,43 @@
|
|||||||
body {
|
body {
|
||||||
background: var(--background);
|
background: var(--background);
|
||||||
color: var(--foreground);
|
color: var(--foreground);
|
||||||
font-family: Arial, Helvetica, sans-serif;
|
font-family: "Sofia Sans Condensed", sans-serif;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Скрываем стрелочки у input[type=number] */
|
||||||
|
input[type='number']::-webkit-outer-spin-button,
|
||||||
|
input[type='number']::-webkit-inner-spin-button {
|
||||||
|
-webkit-appearance: none;
|
||||||
|
margin: 0;
|
||||||
|
}
|
||||||
|
input[type='number'] {
|
||||||
|
appearance: textfield;
|
||||||
|
-moz-appearance: textfield;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Скрываем надпись «файл не выбран» и название файла */
|
||||||
|
input[type="file"] {
|
||||||
|
color: transparent; /* сам путь/имя файла и надписи станут прозрачными */
|
||||||
|
position: relative;
|
||||||
|
z-index: 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Стилизуем кнопку «Выбрать файл» отдельно (псевдо-элемент, у разных браузеров он может называться по-разному) */
|
||||||
|
input[type="file"]::file-selector-button {
|
||||||
|
color: #e5e7eb; /* текст кнопки (gray-200) */
|
||||||
|
background-color: #374151; /* фон кнопки (gray-700) */
|
||||||
|
border: none;
|
||||||
|
padding: 0.5rem 1rem;
|
||||||
|
border-radius: 0.375rem; /* rounded-md */
|
||||||
|
cursor: pointer;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Для старых версий IE/Edge: */
|
||||||
|
input[type="file"]::-ms-browse {
|
||||||
|
color: #e5e7eb;
|
||||||
|
background-color: #374151;
|
||||||
|
border: none;
|
||||||
|
padding: 0.5rem 1rem;
|
||||||
|
border-radius: 0.375rem;
|
||||||
|
cursor: pointer;
|
||||||
}
|
}
|
||||||
@ -1,66 +1,81 @@
|
|||||||
// components/SoapCalculator.tsx
|
// components/SoapCalculator.tsx
|
||||||
'use client';
|
'use client';
|
||||||
|
|
||||||
import { useState, useEffect, ChangeEvent } from 'react';
|
import { useState, useEffect, ChangeEvent, FormEvent } from 'react';
|
||||||
import { calculateTotal } from '@/lib/calc';
|
import { calculateTotal } from '@/lib/calc';
|
||||||
|
import Image from 'next/image';
|
||||||
|
|
||||||
type InputNumberProps = {
|
type InputNumberProps = {
|
||||||
label: string;
|
label: string;
|
||||||
value: string;
|
value: string;
|
||||||
onChange: (v: string) => void;
|
onChange: (v: string) => void;
|
||||||
placeholder?: string;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
const InputNumber = ({ label, value, onChange, placeholder }: InputNumberProps) => (
|
const InputNumber = ({ label, value, onChange }: InputNumberProps) => {
|
||||||
<label className="flex flex-col gap-1">
|
// Генерируем id на основе текста лейбла (без пробелов)
|
||||||
<span>{label}</span>
|
const id = label.toLowerCase().replace(/\s+/g, '-');
|
||||||
<input
|
|
||||||
type="number"
|
|
||||||
className="border px-2 py-1 rounded text-black"
|
|
||||||
value={value}
|
|
||||||
placeholder={placeholder}
|
|
||||||
onChange={(e) => onChange(e.target.value)}
|
|
||||||
/>
|
|
||||||
</label>
|
|
||||||
);
|
|
||||||
|
|
||||||
const CostBlock = ({
|
return (
|
||||||
title,
|
<div className="relative mt-6">
|
||||||
value,
|
<input
|
||||||
highlight = false,
|
id={id}
|
||||||
}: {
|
type="number"
|
||||||
title: string;
|
value={value}
|
||||||
value: number;
|
onChange={(e) => onChange(e.target.value)}
|
||||||
highlight?: boolean;
|
placeholder=" "
|
||||||
}) => (
|
className={`
|
||||||
<div
|
peer
|
||||||
className={`p-2 ${highlight ? 'bg-red-200 font-semibold' : 'bg-lime-100'}`}
|
h-10 w-full
|
||||||
>
|
bg-gray-700
|
||||||
{title}: {value.toFixed(1)} руб
|
border-2 border-gray-600
|
||||||
</div>
|
rounded-md
|
||||||
);
|
text-gray-200
|
||||||
|
placeholder-transparent
|
||||||
|
pl-3
|
||||||
|
focus:outline-none focus:border-sky-500
|
||||||
|
appearance-none
|
||||||
|
`}
|
||||||
|
/>
|
||||||
|
<label
|
||||||
|
htmlFor={id}
|
||||||
|
className={`
|
||||||
|
absolute left-3
|
||||||
|
-top-5
|
||||||
|
text-gray-400 text-sm
|
||||||
|
transition-all
|
||||||
|
peer-placeholder-shown:top-2
|
||||||
|
peer-placeholder-shown:text-base
|
||||||
|
peer-placeholder-shown:text-gray-500
|
||||||
|
peer-focus:-top-5
|
||||||
|
peer-focus:text-gray-200
|
||||||
|
peer-focus:text-sm
|
||||||
|
`}
|
||||||
|
>
|
||||||
|
{label}
|
||||||
|
</label>
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
};
|
||||||
|
|
||||||
export default function SoapCalculator() {
|
export default function SoapCalculator() {
|
||||||
// 1) Поля ввода как строки (по умолчанию пустые)
|
|
||||||
const [soapName, setSoapName] = useState('');
|
const [soapName, setSoapName] = useState('');
|
||||||
const [weight, setWeight] = useState(''); // г
|
const [weight, setWeight] = useState('');
|
||||||
const [basePrice, setBasePrice] = useState(''); // руб/кг
|
const [basePrice, setBasePrice] = useState('');
|
||||||
const [aromaPrice, setAromaPrice] = useState(''); // руб/фасовка
|
const [aromaPrice, setAromaPrice] = useState('');
|
||||||
const [aromaWeight, setAromaWeight] = useState(''); // г фасовка
|
const [aromaWeight, setAromaWeight] = useState('');
|
||||||
const [pigmentPrice, setPigmentPrice] = useState(''); // руб/фасовка
|
const [pigmentPrice, setPigmentPrice] = useState('');
|
||||||
const [pigmentWeight, setPigmentWeight] = useState(''); // г фасовка
|
const [pigmentWeight, setPigmentWeight] = useState('');
|
||||||
const [moldPrice, setMoldPrice] = useState(''); // руб за форму
|
const [moldPrice, setMoldPrice] = useState('');
|
||||||
const [box, setBox] = useState(''); // руб
|
const [box, setBox] = useState('');
|
||||||
const [filler, setFiller] = useState(''); // руб
|
const [filler, setFiller] = useState('');
|
||||||
const [ribbon, setRibbon] = useState(''); // руб
|
const [ribbon, setRibbon] = useState('');
|
||||||
const [labelValue, setLabelValue] = useState(''); // руб наклейка
|
const [labelValue, setLabelValue] = useState('');
|
||||||
const [markup, setMarkup] = useState(''); // %
|
const [markup, setMarkup] = useState('');
|
||||||
|
|
||||||
// Файл фотографии и chat_id
|
|
||||||
const [photoFile, setPhotoFile] = useState<File | null>(null);
|
const [photoFile, setPhotoFile] = useState<File | null>(null);
|
||||||
const [chatId, setChatId] = useState<string | null>(null);
|
const [chatId, setChatId] = useState<string | null>(null);
|
||||||
|
|
||||||
// 2) Извлекаем chat_id из URL при монтировании
|
// При монтировании достаём chat_id из URL
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
const params = new URLSearchParams(window.location.search);
|
const params = new URLSearchParams(window.location.search);
|
||||||
const id = params.get('chat_id');
|
const id = params.get('chat_id');
|
||||||
@ -69,25 +84,25 @@ export default function SoapCalculator() {
|
|||||||
}
|
}
|
||||||
}, []);
|
}, []);
|
||||||
|
|
||||||
// 3) Преобразуем строковые поля в числа (или 0, если не число)
|
// Конвертация строковых значений в числа
|
||||||
const toNum = (str: string) => {
|
const toNum = (str: string) => {
|
||||||
const n = parseFloat(str.replace(',', '.'));
|
const n = parseFloat(str.replace(',', '.'));
|
||||||
return isNaN(n) ? 0 : n;
|
return isNaN(n) ? 0 : n;
|
||||||
};
|
};
|
||||||
const weightNum = toNum(weight);
|
const weightNum = toNum(weight);
|
||||||
const basePriceNum = toNum(basePrice);
|
const basePriceNum = toNum(basePrice);
|
||||||
const aromaPriceNum = toNum(aromaPrice);
|
const aromaPriceNum = toNum(aromaPrice);
|
||||||
const aromaWeightNum = toNum(aromaWeight);
|
const aromaWeightNum = toNum(aromaWeight);
|
||||||
const pigmentPriceNum = toNum(pigmentPrice);
|
const pigmentPriceNum = toNum(pigmentPrice);
|
||||||
const pigmentWeightNum = toNum(pigmentWeight);
|
const pigmentWeightNum = toNum(pigmentWeight);
|
||||||
const moldPriceNum = toNum(moldPrice);
|
const moldPriceNum = toNum(moldPrice);
|
||||||
const boxNum = toNum(box);
|
const boxNum = toNum(box);
|
||||||
const fillerNum = toNum(filler);
|
const fillerNum = toNum(filler);
|
||||||
const ribbonNum = toNum(ribbon);
|
const ribbonNum = toNum(ribbon);
|
||||||
const labelNum = toNum(labelValue);
|
const labelNum = toNum(labelValue);
|
||||||
const markupNum = toNum(markup);
|
const markupNum = toNum(markup);
|
||||||
|
|
||||||
// 4) Считаем все базовые значения через calculateTotal
|
// Считаем все базовые значения через calculateTotal
|
||||||
const result = calculateTotal({
|
const result = calculateTotal({
|
||||||
weight: weightNum,
|
weight: weightNum,
|
||||||
basePrice: basePriceNum,
|
basePrice: basePriceNum,
|
||||||
@ -104,11 +119,9 @@ export default function SoapCalculator() {
|
|||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
// 5) Итоговые значения
|
|
||||||
const finalPrice = result.total * (1 + markupNum / 100);
|
const finalPrice = result.total * (1 + markupNum / 100);
|
||||||
const pricePer100g = weightNum > 0 ? (finalPrice / weightNum) * 100 : 0;
|
const pricePer100g = weightNum > 0 ? (finalPrice / weightNum) * 100 : 0;
|
||||||
|
|
||||||
// 6) Обработчик изменения фото
|
|
||||||
const handlePhotoChange = (e: ChangeEvent<HTMLInputElement>) => {
|
const handlePhotoChange = (e: ChangeEvent<HTMLInputElement>) => {
|
||||||
if (e.target.files && e.target.files[0]) {
|
if (e.target.files && e.target.files[0]) {
|
||||||
setPhotoFile(e.target.files[0]);
|
setPhotoFile(e.target.files[0]);
|
||||||
@ -117,14 +130,13 @@ export default function SoapCalculator() {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
// 7) Обработчик отправки формы на backend
|
const handleSubmit = async (e: FormEvent) => {
|
||||||
const handleSubmit = async () => {
|
e.preventDefault();
|
||||||
if (!chatId) {
|
if (!chatId) {
|
||||||
alert('❗ Не найден chat_id. Откройте калькулятор через Telegram-бота.');
|
alert('❗ Не найден chat_id. Откройте калькулятор через Telegram-бота.');
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Собираем FormData
|
|
||||||
const formData = new FormData();
|
const formData = new FormData();
|
||||||
formData.append('chat_id', chatId);
|
formData.append('chat_id', chatId);
|
||||||
formData.append('soapName', soapName || '');
|
formData.append('soapName', soapName || '');
|
||||||
@ -149,8 +161,6 @@ export default function SoapCalculator() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
// Замените URL на публичный адрес вашего backend (Express/ngrok/другой хостинг)
|
|
||||||
// Например: 'https://abcd1234.ngrok.io/api/submit'
|
|
||||||
const res = await fetch('https://api-dosoap.duckdns.org/api/submit', {
|
const res = await fetch('https://api-dosoap.duckdns.org/api/submit', {
|
||||||
method: 'POST',
|
method: 'POST',
|
||||||
body: formData,
|
body: formData,
|
||||||
@ -158,8 +168,6 @@ export default function SoapCalculator() {
|
|||||||
|
|
||||||
if (res.ok) {
|
if (res.ok) {
|
||||||
alert('✅ Расчёт успешно отправлен в Telegram!');
|
alert('✅ Расчёт успешно отправлен в Telegram!');
|
||||||
|
|
||||||
// Сбрасываем все поля на пустые строки / null
|
|
||||||
setSoapName('');
|
setSoapName('');
|
||||||
setWeight('');
|
setWeight('');
|
||||||
setBasePrice('');
|
setBasePrice('');
|
||||||
@ -174,8 +182,6 @@ export default function SoapCalculator() {
|
|||||||
setLabelValue('');
|
setLabelValue('');
|
||||||
setMarkup('');
|
setMarkup('');
|
||||||
setPhotoFile(null);
|
setPhotoFile(null);
|
||||||
|
|
||||||
// Прокручиваем страницу вверх
|
|
||||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||||
} else {
|
} else {
|
||||||
const text = await res.text();
|
const text = await res.text();
|
||||||
@ -188,51 +194,102 @@ export default function SoapCalculator() {
|
|||||||
};
|
};
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div className="max-w-xl mx-auto p-4 space-y-6 text-sm">
|
<form
|
||||||
|
onSubmit={handleSubmit}
|
||||||
|
className="
|
||||||
|
max-w-xl mx-auto p-6 space-y-6
|
||||||
|
bg-gray-800 text-gray-200
|
||||||
|
rounded-lg shadow-lg
|
||||||
|
"
|
||||||
|
>
|
||||||
{chatId === null && (
|
{chatId === null && (
|
||||||
<div className="bg-yellow-100 p-2 text-yellow-800 font-semibold">
|
<div className="bg-yellow-800 p-2 text-yellow-200 font-semibold rounded">
|
||||||
❗ Не найден chat_id. Откройте калькулятор через Telegram-бота.
|
❗ Не найден chat_id. Откройте калькулятор через Telegram-бота.
|
||||||
</div>
|
</div>
|
||||||
)}
|
)}
|
||||||
|
|
||||||
|
<div className="flex justify-center">
|
||||||
|
<Image
|
||||||
|
src="/logo.svg"
|
||||||
|
alt="Logo"
|
||||||
|
width={250}
|
||||||
|
height={100}
|
||||||
|
className="mx-auto w-64 md:w-96 lg:w-112 h-auto"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
|
||||||
{/* Название мыла */}
|
{/* Название мыла */}
|
||||||
<label className="flex flex-col gap-1">
|
<div className="relative mt-6">
|
||||||
<span>Название мыла</span>
|
|
||||||
<input
|
<input
|
||||||
|
id="soap-name"
|
||||||
type="text"
|
type="text"
|
||||||
className="border px-2 py-1 rounded text-black"
|
|
||||||
value={soapName}
|
value={soapName}
|
||||||
onChange={(e) => setSoapName(e.target.value)}
|
onChange={(e) => setSoapName(e.target.value)}
|
||||||
placeholder="Например: Лавандовое"
|
placeholder=" "
|
||||||
|
className={`
|
||||||
|
peer
|
||||||
|
h-10 w-full
|
||||||
|
bg-gray-700
|
||||||
|
border-2 border-gray-600
|
||||||
|
rounded-md
|
||||||
|
text-gray-200
|
||||||
|
placeholder-transparent
|
||||||
|
pl-3
|
||||||
|
focus:outline-none focus:border-sky-500
|
||||||
|
appearance-none
|
||||||
|
`}
|
||||||
/>
|
/>
|
||||||
</label>
|
<label
|
||||||
|
htmlFor="soap-name"
|
||||||
|
className={`
|
||||||
|
absolute left-3
|
||||||
|
-top-5
|
||||||
|
text-gray-400 text-sm
|
||||||
|
transition-all
|
||||||
|
peer-placeholder-shown:top-2
|
||||||
|
peer-placeholder-shown:text-base
|
||||||
|
peer-placeholder-shown:text-gray-500
|
||||||
|
peer-focus:-top-5
|
||||||
|
peer-focus:text-gray-200
|
||||||
|
peer-focus:text-sm
|
||||||
|
`}
|
||||||
|
>
|
||||||
|
Название мыла
|
||||||
|
</label>
|
||||||
|
</div>
|
||||||
|
|
||||||
{/* Фото мыла */}
|
{/* Фото мыла */}
|
||||||
<label className="flex flex-col gap-1">
|
<label className="flex flex-col gap-1">
|
||||||
<span>Фото мыла (необязательно)</span>
|
<span className="text-gray-300">Фото мыла (необязательно)</span>
|
||||||
<input type="file" accept="image/*" onChange={handlePhotoChange} />
|
<input
|
||||||
|
type="file"
|
||||||
|
accept="image/*"
|
||||||
|
onChange={handlePhotoChange}
|
||||||
|
className="
|
||||||
|
bg-gray-700
|
||||||
|
text-gray-200
|
||||||
|
rounded-md
|
||||||
|
border border-gray-600
|
||||||
|
p-2
|
||||||
|
focus:outline-none focus:border-sky-500
|
||||||
|
"
|
||||||
|
/>
|
||||||
</label>
|
</label>
|
||||||
{photoFile && (
|
{photoFile && (
|
||||||
<img
|
<img
|
||||||
src={URL.createObjectURL(photoFile)}
|
src={URL.createObjectURL(photoFile)}
|
||||||
alt="Предпросмотр мыла"
|
alt="Предпросмотр мыла"
|
||||||
className="w-32 h-32 object-cover rounded"
|
className="w-32 h-32 object-cover rounded-lg border border-sky-400"
|
||||||
/>
|
/>
|
||||||
)}
|
)}
|
||||||
|
|
||||||
{/* Блок «Основа» */}
|
{/* Блок «Основа» */}
|
||||||
<div className="grid grid-cols-2 gap-4">
|
<div className="grid grid-cols-2 gap-4">
|
||||||
<InputNumber
|
<InputNumber label="Вес мыла, г" value={weight} onChange={setWeight} />
|
||||||
label="Вес мыла, г"
|
|
||||||
value={weight}
|
|
||||||
onChange={setWeight}
|
|
||||||
placeholder="Введите, например 60"
|
|
||||||
/>
|
|
||||||
<InputNumber
|
<InputNumber
|
||||||
label="Цена за 1 кг основы, руб"
|
label="Цена за 1 кг основы, руб"
|
||||||
value={basePrice}
|
value={basePrice}
|
||||||
onChange={setBasePrice}
|
onChange={setBasePrice}
|
||||||
placeholder="Введите, например 1000"
|
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
<CostBlock title="Себестоимость основы" value={result.base} />
|
<CostBlock title="Себестоимость основы" value={result.base} />
|
||||||
@ -243,13 +300,11 @@ export default function SoapCalculator() {
|
|||||||
label="Цена отдушки, руб"
|
label="Цена отдушки, руб"
|
||||||
value={aromaPrice}
|
value={aromaPrice}
|
||||||
onChange={setAromaPrice}
|
onChange={setAromaPrice}
|
||||||
placeholder="Введите, например 300"
|
|
||||||
/>
|
/>
|
||||||
<InputNumber
|
<InputNumber
|
||||||
label="Фасовка отдушки, г"
|
label="Фасовка отдушки, г"
|
||||||
value={aromaWeight}
|
value={aromaWeight}
|
||||||
onChange={setAromaWeight}
|
onChange={setAromaWeight}
|
||||||
placeholder="Введите, например 50"
|
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
<CostBlock title="Себестоимость отдушки (1 %)" value={result.aroma} />
|
<CostBlock title="Себестоимость отдушки (1 %)" value={result.aroma} />
|
||||||
@ -260,13 +315,11 @@ export default function SoapCalculator() {
|
|||||||
label="Цена пигмента, руб"
|
label="Цена пигмента, руб"
|
||||||
value={pigmentPrice}
|
value={pigmentPrice}
|
||||||
onChange={setPigmentPrice}
|
onChange={setPigmentPrice}
|
||||||
placeholder="Введите, например 20"
|
|
||||||
/>
|
/>
|
||||||
<InputNumber
|
<InputNumber
|
||||||
label="Фасовка пигмента, г"
|
label="Фасовка пигмента, г"
|
||||||
value={pigmentWeight}
|
value={pigmentWeight}
|
||||||
onChange={setPigmentWeight}
|
onChange={setPigmentWeight}
|
||||||
placeholder="Введите, например 10"
|
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
<CostBlock title="Себестоимость пигмента (0.5 %)" value={result.pigment} />
|
<CostBlock title="Себестоимость пигмента (0.5 %)" value={result.pigment} />
|
||||||
@ -276,61 +329,64 @@ export default function SoapCalculator() {
|
|||||||
label="Цена формы, руб"
|
label="Цена формы, руб"
|
||||||
value={moldPrice}
|
value={moldPrice}
|
||||||
onChange={setMoldPrice}
|
onChange={setMoldPrice}
|
||||||
placeholder="Введите, например 500"
|
|
||||||
/>
|
/>
|
||||||
<CostBlock title="Себестоимость формы" value={result.mold} />
|
<CostBlock title="Себестоимость формы" value={result.mold} />
|
||||||
|
|
||||||
{/* Блок «Упаковка» */}
|
{/* Блок «Упаковка» */}
|
||||||
<div className="grid grid-cols-2 gap-4">
|
<div className="grid grid-cols-2 gap-4">
|
||||||
<InputNumber
|
<InputNumber label="Пакет/коробка, руб" value={box} onChange={setBox} />
|
||||||
label="Пакет/коробка, руб"
|
<InputNumber label="Наполнитель, руб" value={filler} onChange={setFiller} />
|
||||||
value={box}
|
<InputNumber label="Лента, руб" value={ribbon} onChange={setRibbon} />
|
||||||
onChange={setBox}
|
|
||||||
placeholder="Введите, например 20"
|
|
||||||
/>
|
|
||||||
<InputNumber
|
|
||||||
label="Наполнитель, руб"
|
|
||||||
value={filler}
|
|
||||||
onChange={setFiller}
|
|
||||||
placeholder="Введите, например 5"
|
|
||||||
/>
|
|
||||||
<InputNumber
|
|
||||||
label="Лента, руб"
|
|
||||||
value={ribbon}
|
|
||||||
onChange={setRibbon}
|
|
||||||
placeholder="Введите, например 1"
|
|
||||||
/>
|
|
||||||
<InputNumber
|
<InputNumber
|
||||||
label="Наклейка, руб"
|
label="Наклейка, руб"
|
||||||
value={labelValue}
|
value={labelValue}
|
||||||
onChange={setLabelValue}
|
onChange={setLabelValue}
|
||||||
placeholder="Введите, например 1"
|
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
<CostBlock title="Стоимость упаковки" value={result.packaging} />
|
<CostBlock title="Стоимость упаковки" value={result.packaging} />
|
||||||
|
|
||||||
<CostBlock title="Операционные расходы (5 %)" value={result.operational} />
|
<CostBlock title="Операционные расходы (5 %)" value={result.operational} />
|
||||||
<CostBlock title="Итого себестоимость" value={result.total} highlight />
|
<CostBlock title="Итого себестоимость" value={result.total} highlight />
|
||||||
|
|
||||||
{/* Блок «Наценка и цена 100 г» */}
|
{/* Блок «Наценка и цена 100 г» */}
|
||||||
<div className="grid grid-cols-2 gap-4">
|
<div className="grid grid-cols-1 gap-4">
|
||||||
<InputNumber
|
<InputNumber label="Наценка, %" value={markup} onChange={setMarkup} />
|
||||||
label="Наценка, %"
|
|
||||||
value={markup}
|
|
||||||
onChange={setMarkup}
|
|
||||||
placeholder="Введите, например 30"
|
|
||||||
/>
|
|
||||||
</div>
|
</div>
|
||||||
<CostBlock title="Итоговая цена с наценкой" value={finalPrice} />
|
<CostBlock title="Итоговая цена с наценкой" value={finalPrice} />
|
||||||
<CostBlock title="Цена за 100 г" value={pricePer100g} />
|
<CostBlock title="Цена за 100 г" value={pricePer100g} />
|
||||||
|
|
||||||
{/* Кнопка «Отправить расчёт» */}
|
{/* Кнопка «Отправить расчёт» */}
|
||||||
<button
|
<button
|
||||||
className="bg-blue-500 hover:bg-blue-600 text-white font-bold py-2 px-4 rounded"
|
type="submit"
|
||||||
onClick={handleSubmit}
|
className="
|
||||||
|
w-full
|
||||||
|
py-2
|
||||||
|
rounded-md
|
||||||
|
bg-sky-500 hover:bg-sky-600
|
||||||
|
text-gray-100 font-semibold
|
||||||
|
focus:outline-none focus:ring focus:ring-offset-2 focus:ring-sky-500 focus:ring-opacity-60
|
||||||
|
"
|
||||||
>
|
>
|
||||||
Отправить расчёт в Telegram
|
Отправить расчёт в Telegram
|
||||||
</button>
|
</button>
|
||||||
</div>
|
</form>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type CostBlockProps = {
|
||||||
|
title: string;
|
||||||
|
value: number;
|
||||||
|
highlight?: boolean;
|
||||||
|
};
|
||||||
|
|
||||||
|
const CostBlock = ({ title, value, highlight = false }: CostBlockProps) => (
|
||||||
|
<div
|
||||||
|
className={`
|
||||||
|
p-2
|
||||||
|
${highlight ? 'bg-gray-600 font-semibold' : 'bg-gray-700'}
|
||||||
|
text-gray-200
|
||||||
|
rounded
|
||||||
|
`}
|
||||||
|
>
|
||||||
|
{title}: {value.toFixed(1)} руб
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
|||||||
141
frontend/public/logo.svg
Normal file
141
frontend/public/logo.svg
Normal file
@ -0,0 +1,141 @@
|
|||||||
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
|
<svg id="_Слой_2" xmlns="http://www.w3.org/2000/svg" version="1.1" viewBox="0 0 1892.5 609.5">
|
||||||
|
<!-- Generator: Adobe Illustrator 29.0.0, SVG Export Plug-In . SVG Version: 2.1.0 Build 186) -->
|
||||||
|
<defs>
|
||||||
|
<style>
|
||||||
|
.st0, .st1 {
|
||||||
|
fill: #9c5099;
|
||||||
|
}
|
||||||
|
|
||||||
|
.st2, .st3 {
|
||||||
|
fill: #e52722;
|
||||||
|
}
|
||||||
|
|
||||||
|
.st4, .st5 {
|
||||||
|
fill: #6bb42e;
|
||||||
|
}
|
||||||
|
|
||||||
|
.st6, .st7 {
|
||||||
|
fill: #fff;
|
||||||
|
}
|
||||||
|
|
||||||
|
.st8, .st9 {
|
||||||
|
fill: #f18918;
|
||||||
|
}
|
||||||
|
|
||||||
|
.st10, .st11, .st12 {
|
||||||
|
fill: none;
|
||||||
|
stroke: #fff;
|
||||||
|
stroke-miterlimit: 10;
|
||||||
|
}
|
||||||
|
|
||||||
|
.st13, .st7, .st14, .st15, .st16, .st17, .st18, .st19, .st9, .st1, .st3, .st5 {
|
||||||
|
isolation: isolate;
|
||||||
|
}
|
||||||
|
|
||||||
|
.st7 {
|
||||||
|
opacity: .5;
|
||||||
|
}
|
||||||
|
|
||||||
|
.st14 {
|
||||||
|
fill: #294d9d;
|
||||||
|
}
|
||||||
|
|
||||||
|
.st14, .st15, .st16, .st17, .st19, .st9, .st1, .st3, .st5 {
|
||||||
|
opacity: .8;
|
||||||
|
}
|
||||||
|
|
||||||
|
.st11 {
|
||||||
|
stroke-width: 3px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.st15 {
|
||||||
|
fill: #e52421;
|
||||||
|
}
|
||||||
|
|
||||||
|
.st16 {
|
||||||
|
fill: #6cc5d4;
|
||||||
|
}
|
||||||
|
|
||||||
|
.st17 {
|
||||||
|
fill: #2a4e9c;
|
||||||
|
}
|
||||||
|
|
||||||
|
.st18 {
|
||||||
|
opacity: .2;
|
||||||
|
}
|
||||||
|
|
||||||
|
.st19 {
|
||||||
|
fill: #6bb42d;
|
||||||
|
}
|
||||||
|
|
||||||
|
.st12 {
|
||||||
|
stroke-width: 2px;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
|
</defs>
|
||||||
|
<g id="_Монтажная_область_6">
|
||||||
|
<g id="_Логотип">
|
||||||
|
<g id="_Текст">
|
||||||
|
<g class="st13">
|
||||||
|
<g class="st13">
|
||||||
|
<path class="st6" d="M755.4,185.1h-.1c39.1,0,70.5,12.9,94.1,38.6,23.7,25.8,35.6,58.5,35.6,98s-11.7,70.4-35,95c-23.3,24.7-53,37.1-88.9,37.1h-91.7v-10.1c5.6,0,10.3-2.8,14.3-8.5,4.1-5.8,6.1-13.6,6.1-23.5v-184.5c0-10.6-2.4-18.4-7.3-23.4-5-5.1-13-7.6-24.1-7.6s-22.6,3.6-31.4,10.7c-8.7,7.1-13.1,17.2-13.1,30.2h1.2c0-7.8,2.7-13.9,8-18.3,5.5-4.4,11.8-6.6,18.9-6.6s14,2.6,20.1,7.7c6.2,5.3,9.2,12,9.2,20.1s-3.1,16.9-9.4,22.5c-6.2,5.5-13.8,8.2-23.1,8.2s-17.2-2.8-23.2-8.5c-6.1-5.7-9.1-14-9.1-25,0-16.7,5.7-29.5,17-38.6,11.2-9,26.6-13.6,46-13.6h85.9ZM761.1,443.6h-.3c22.7-.1,40.7-11.3,53.8-33.5,13.1-22.1,19.7-51.6,19.7-88.5s-1.2-32.7-3.7-46.9c-2.6-14.5-6.5-27.7-11.6-39.8-5.2-12-12.5-21.5-21.9-28.6-9.3-6.9-20.2-10.4-32.6-10.4l-29.3.3v215.3c0,10.9,2,19,6,24.1,4.1,5.3,10.8,7.9,20.1,7.9Z"/>
|
||||||
|
</g>
|
||||||
|
</g>
|
||||||
|
<g class="st13">
|
||||||
|
<g class="st13">
|
||||||
|
<path class="st6" d="M987,455.8v.2c-14.7,0-28.3-4.3-40.8-13-12.3-8.6-22.1-20.5-29.5-35.5-7.3-15-10.9-31.5-10.9-49.4,0-27,7.9-50,23.8-69.1,15.8-19.1,35-28.7,57.4-28.7s41.5,9.5,57.2,28.6c15.8,19.1,23.7,42.1,23.7,69.1s-7.9,50.4-23.7,69.4c-15.8,19-34.9,28.5-57.2,28.5ZM987.1,447.6h0c12.8-.1,23.6-8.6,32.3-25.6,8.8-17,13.1-38.4,13.1-64s-4.4-46.5-13.1-63.4c-8.8-16.9-19.5-25.3-32.3-25.3s-24,8.4-32.7,25.3c-8.8,16.9-13.1,38-13.1,63.5s4.4,47,13.1,64c8.8,17,19.7,25.5,32.7,25.5Z"/>
|
||||||
|
</g>
|
||||||
|
</g>
|
||||||
|
<g class="st13">
|
||||||
|
<g class="st13">
|
||||||
|
<path class="st6" d="M1124,226.8h-.4c0,7,2.8,13.5,8.3,19.7,5.5,6,12.6,11.5,21.4,16.7,8.1,4.8,17.8,9.9,29,15.3,11.1,5.5,21.7,11.2,31.7,17.1,10.8,6.4,20.5,13.1,29,20.3,8.8,7.3,16,16.2,21.4,26.5,5.6,10.5,8.3,21.9,8.3,34.1,0,22.1-10.1,41.5-30.4,58.2s-44.8,25-73.6,25h-2.5c-23.6,0-43.5-7.7-59.6-23.2-16.1-15.5-24.1-34.2-24.1-56.3s3.9-24.4,11.6-31.6c7.7-7.1,17.6-10.7,29.5-10.7s21.2,3.5,29.2,10.4c8,7,12.1,16.6,12.1,28.7s-3.8,18.6-11.5,25.2c-7.5,6.6-16,9.8-25.5,9.8s-17.3-2.8-24.3-8.3c-6.8-5.6-10.3-13.5-10.3-23.7h-1.3c0,19.2,7.4,34.5,22.3,46.2,14.9,11.6,32.2,17.4,51.8,17.4s33.2-5,45.9-15c12.7-10,19.1-22.5,19.1-37.4s-4.8-24.1-14.3-34.5c-9.5-10.4-21-19.3-34.5-26.5l-40.7-21.9c-13.5-7.2-25-15.9-34.5-26.1s-14.3-21.4-14.3-33.8c0-23.1,6.9-40.8,20.8-53,13.8-12.2,32-18.3,54.5-18.3s22.4,1.3,31.3,3.9c8.4,2.5,15.5,5,21.3,7.4,5.6,2.4,10.6,3.6,15,3.6s6.1-.9,8.3-2.7c2.3-1.9,3.7-3.7,4.3-5.4l.6-2.8h13.1v107.1h-13.1c0-27.5-8.2-50.7-24.7-69.7-16.5-19.1-34.9-28.6-55.4-28.6s-22.8,3.7-31.7,11.2-13.4,16-13.4,25.8Z"/>
|
||||||
|
</g>
|
||||||
|
</g>
|
||||||
|
<g class="st13">
|
||||||
|
<g class="st13">
|
||||||
|
<path class="st6" d="M1374.8,455.8v.2c-14.7,0-28.3-4.3-40.8-13-12.3-8.6-22.1-20.5-29.5-35.5-7.3-15-10.9-31.5-10.9-49.4,0-27,7.9-50,23.8-69.1,15.8-19.1,35-28.7,57.4-28.7s41.5,9.5,57.2,28.6c15.8,19.1,23.7,42.1,23.7,69.1s-7.9,50.4-23.7,69.4c-15.8,19-34.9,28.5-57.2,28.5ZM1374.9,447.6h0c12.8-.1,23.6-8.6,32.3-25.6,8.8-17,13.1-38.4,13.1-64s-4.4-46.5-13.1-63.4c-8.8-16.9-19.5-25.3-32.3-25.3s-24,8.4-32.7,25.3c-8.8,16.9-13.1,38-13.1,63.5s4.4,47,13.1,64c8.8,17,19.7,25.5,32.7,25.5Z"/>
|
||||||
|
<path class="st6" d="M1662.1,419.8h-.1c5.1,16.7,12.2,25.1,21.2,25.1v8.8h-46.9l-19.7-68.1c-9.7,9.1-19.7,13.7-30,13.7s-8.8-.7-14.8-2.2c-6.1-1.5-10.6-2-13.6-1.8,0,.3-.3,1.2-.8,2.9-.5,1.6-.9,3-1.2,4.1-.8,2.8-1.4,4.8-1.9,6-4.2,13.9-7.9,25.4-10.9,34.4-3.2,9.6-6.6,18.8-10.1,27.5-3.8,9.4-7.4,16.8-10.6,22.4-3.3,5.5-7,10.6-11.3,15.4-4.2,4.7-8.5,8-13.1,10-4.5,1.9-9.5,2.9-15,2.9s-10.7-.9-14.7-2.8c-4-1.9-6.9-4.2-8.8-7.1-1.9-2.9-3.3-5.7-4.3-8.4-1.1-2.9-1.7-5.3-1.8-7.2v-2.7c0-7.8,2.1-13.7,6.3-17.8,4.2-4.1,9.7-6.2,16.4-6.2s11.6,2,15.9,5.9,6.6,9.3,6.6,15.9-2.1,10.3-6.3,13.9c-4.2,3.5-8.9,5.3-14.2,5.3s-9.5-1.4-13.3-4.3c-3.8-2.8-5.6-7-5.6-12.5h-.6v1.9c0,.8.3,2.3.9,4.4.6,2.2,1.6,4,2.8,5.5,1.3,1.5,3.3,3,6.2,4.4,2.7,1.3,6.2,2,10.3,2,15.7,0,29.8-16.6,42.2-49.9,3.1-6.5,22.8-67,59.1-181.5-25.4-9.2-44.3-13.9-56.6-13.9-26,0-38.9,9.6-38.8,28.8h.8c0-5.5,1.8-9.8,5.5-12.8,3.7-3.1,8.1-4.6,13.1-4.6s9.8,1.8,14.1,5.4c4.3,3.7,6.5,8.4,6.5,14.1s-2.2,11.9-6.6,15.7c-4.3,3.8-9.7,5.7-16.2,5.7s-12-2-16.3-5.9c-4.3-4-6.5-9.8-6.5-17.5,0-11.7,4-20.7,12-27,8-6.3,18.7-9.5,32.2-9.5s24.8,2,47.6,5.9c22.9,4,38.7,5.9,47.5,5.9l43.3,149.6ZM1598.6,388.3h0c4.6.1,9.8-3.6,15.6-10.9l-23-79.4h-1.8c-5.2,16.6-14.7,46.1-28.5,88.4,5.8-2.2,10.5-3.2,14.3-3.2s6.6.9,11.2,2.6c4.5,1.7,8.6,2.6,12.2,2.6ZM1618.9,445h-.1c4.4-.1,7.2-2.4,8.4-7,1.2-4.6.7-11.4-1.6-20.3l10.5,36.1h-17.3v-8.8ZM1661.2,417.6c0,.3,0,.4.2.4l-.2-.4Z"/>
|
||||||
|
<path class="st6" d="M1801.5,409.1l-.4.5c-2.6,0-4.9,0-6.7.2v13.9c0,7.1,1.5,12.7,4.4,16.9,2.9,4.2,6.5,6.3,10.6,6.3v7.3h-59.6v-7.3c4,0,7.4-2.1,10.2-6.3,2.8-4.2,4.3-9.9,4.3-17v-88.4c0-5.6-1.4-10.5-4.3-14.5-2.8-4-6.2-6.7-10.2-8.1v-7.9h44.6v94.6c1.7.3,3.2.4,4.3.4,18.5,0,32.7-5.8,42.7-17.3,10-11.5,15-28.1,15-49.7s-6.4-42.1-19.2-56c-12.8-13.8-32-20.7-57.5-20.7s-40.6,7.3-56.4,21.8c-15.7,14.5-23.6,31.2-23.6,50.2s1.9,17.4,5.8,22.4c3.9,5,9.7,7.4,17.5,7.3v-1c-6.4,0-11.4-2.1-14.9-6.3-3.5-4.2-5.3-9.2-5.3-15.2s2.1-11.2,6.3-15.9,9.6-7.2,16.2-7.2,13.8,2.5,18.1,7.5,6.6,11.2,6.6,18.4-2.3,13.9-6.9,18.9c-4.6,4.9-11.3,7.3-20.1,7.2-10.1,0-18-3.6-23.5-10.9-5.5-7.2-8.2-16.5-8.2-27.7s2.3-19.9,6.8-29.6c4.5-9.7,10.7-18.2,18.6-25.6,7.9-7.5,17.8-13.6,29.7-18.1s24.7-6.9,38.6-6.9,23.3,2,35.3,5.9c12,4,23.2,9.6,33.5,16.9,10.3,7.3,18.7,16.9,25.3,28.7,6.5,11.7,9.8,24.7,9.8,38.8s-1.8,18.6-5.5,26.9c-3.7,8.3-8.5,15.2-14.4,20.8-6,5.7-12.8,10.5-20.4,14.4-7.7,4-15.5,6.9-23.5,8.8-7.9,1.9-15.7,2.8-23.5,2.8Z"/>
|
||||||
|
</g>
|
||||||
|
</g>
|
||||||
|
<path class="st4" d="M793.2,408.5c-22.4,18.8-46.1,21.4-45.2,26.3.7,3.8,15.2,7,28.5,3.2,36.2-10.5,49-70.1,46.7-71.2-1.4-.7-6.6,22.2-29.9,41.7h0Z"/>
|
||||||
|
<path class="st8" d="M987.4,272.1c-.9-1.4-13,2.1-22.1,10.8-14.2,13.7-15.4,35-13.6,35.6,1.5.5,4.2-13.6,18-29.3,9.7-11.1,18.6-15.8,17.8-17.1h0Z"/>
|
||||||
|
<path class="st0" d="M1853.3,335.2c-2-.5-4.4,14.1-16.8,34.1-10.7,17.3-20.1,24.6-19,25.9,1.5,1.6,19.9-7.8,29.8-25.8,8.7-15.9,8.1-33.6,6-34.2h0Z"/>
|
||||||
|
<path class="st2" d="M1347.6,291.2c-11.1,15.7-12.5,34.4-10.6,35,1.6.5,5-12.2,18-31.5,10.2-15.1,17.8-21.7,16.8-22.8-1.2-1.3-14.9,6.1-24.2,19.3Z"/>
|
||||||
|
</g>
|
||||||
|
<g id="_Лого">
|
||||||
|
<circle class="st14" cx="272.1" cy="362.7" r="158.3"/>
|
||||||
|
<circle class="st1" cx="370.7" cy="390.1" r="86.9"/>
|
||||||
|
<circle class="st17" cx="337.3" cy="90.2" r="30.4"/>
|
||||||
|
<circle class="st16" cx="203.9" cy="325.8" r="166.9"/>
|
||||||
|
<circle class="st16" cx="480.7" cy="320.8" r="13.7"/>
|
||||||
|
<circle class="st1" cx="25.5" cy="188.2" r="20.5"/>
|
||||||
|
<circle class="st15" cx="342.3" cy="250.1" r="108"/>
|
||||||
|
<circle class="st19" cx="136.4" cy="307.1" r="79"/>
|
||||||
|
<circle class="st5" cx="512.7" cy="228.1" r="22.4" transform="translate(205.4 697.7) rotate(-80.8)"/>
|
||||||
|
<circle class="st3" cx="122.4" cy="521" r="19"/>
|
||||||
|
<circle class="st9" cx="211.1" cy="199.8" r="94.7"/>
|
||||||
|
<circle class="st9" cx="398" cy="495.8" r="10.1"/>
|
||||||
|
<circle class="st18" cx="260.4" cy="303.2" r="137.8"/>
|
||||||
|
<circle cx="260.2" cy="326" r="137.8"/>
|
||||||
|
<circle class="st11" cx="234.3" cy="291.2" r="37.7"/>
|
||||||
|
<circle class="st12" cx="308.8" cy="325.8" r="28.5"/>
|
||||||
|
<circle class="st10" cx="257.8" cy="358.1" r="16.7"/>
|
||||||
|
<path class="st12" d="M209.5,272.3c-2.4,3.1-3.9,5.9-4.8,8-.3.7-.7,1.6-.3,2.4.8,1.4,3.9.6,7.4.9,4.1.3,4.8,2.2,6.2,1.5,2.2-1.1.2-4.8,2.7-11.2.9-2.2,1.7-3.4,3.1-7.2,1-2.9,1.5-4.4,1-4.8-1.6-1.6-11.4,5.5-15.3,10.5h0Z"/>
|
||||||
|
<path class="st12" d="M211.8,288.8c2.9.9,5,2.6,6.2,3.9.6.6.7,1.6.3,2.3-.6,1.1-1.2,2.6-1.2,4.6,0,1.8.3,3.2.7,4.2.3.8,0,1.6-.5,2.2l-.8.7c-.4.3-.9.5-1.4.5l-5.7-.4c-.3,0-.8-.2-1.3-.5-1.9-1.1-2.6-3.2-3.5-8.1-.9-5.3-1.4-7.9-.5-8.9,2-2.1,6.5-.8,7.8-.4h0Z"/>
|
||||||
|
<path class="st7" d="M146.6,146.6c-.8-.7,6.9-15.1,22.2-23.3,17.2-9.3,35.9-6.4,36-5.4,0,.9-15-.2-32.4,8.6-16.9,8.5-25,20.8-25.7,20.1h0Z"/>
|
||||||
|
<path class="st7" d="M69.7,281.1c-.9-.5,3.2-16.3,16.1-27.9,14.5-13.1,33.4-14.6,33.7-13.7.3.9-14.6,3.4-29.5,16-14.4,12.2-19.4,26-20.3,25.6h0Z"/>
|
||||||
|
<path class="st7" d="M62.4,249c-.9-.6,5.7-14.4,16.1-27.9,14.8-19,32.1-30.6,33-29.7.7.8-10.9,10.4-28.8,32-13.1,15.9-19.5,26.1-20.3,25.6h0Z"/>
|
||||||
|
<path class="st7" d="M6.9,189.5c-.4,0-.8-7.9,4-13.7,5-5.9,13-6.8,13.1-6.4.1.3-6.5,1.4-11.5,7.2-5.1,5.9-5.2,13-5.6,12.9Z"/>
|
||||||
|
<path class="st7" d="M105.3,525.1c-.4,0-.8-7.9,4-13.7,5-5.9,13-6.8,13.1-6.4.1.3-6.5,1.5-11.5,7.2-5.1,5.9-5.2,13-5.6,12.9Z"/>
|
||||||
|
<path class="st7" d="M310.8,87.3c-.4,0-.8-7.9,4-13.7,5-5.9,13-6.8,13.1-6.4.1.3-6.5,1.4-11.5,7.2-5.1,5.9-5.2,13-5.6,12.9Z"/>
|
||||||
|
<path class="st7" d="M492.7,228.1c-.4,0-.8-7.9,4-13.7,5-5.9,13-6.8,13.1-6.4.1.3-6.5,1.4-11.5,7.2-5.1,5.9-5.2,13-5.6,12.9Z"/>
|
||||||
|
<path class="st7" d="M468.6,325.2c-.3,0-.7-6.6,3.4-11.6,4.2-5,11-5.7,11.1-5.4.1.3-5.5,1.2-9.7,6.1-4.3,5-4.4,11-4.7,10.9Z"/>
|
||||||
|
<path class="st7" d="M388.8,498.7c-.2,0-.5-4.9,2.5-8.5,3.1-3.7,8-4.2,8.1-4,0,.2-4,.9-7.1,4.5-3.2,3.7-3.2,8-3.5,8h0Z"/>
|
||||||
|
<path class="st7" d="M299.6,155.5c-.2-1,14.3-5.9,31.2-7.8,24-2.6,44.3,1.9,44.2,3.1,0,1-15.1-.7-43,1.5-20.6,1.6-32.3,4-32.5,3.1h0Z"/>
|
||||||
|
<path class="st7" d="M170.4,231.4c-.6-.8,10.4-11.4,25-20.3,20.6-12.5,40.9-17.1,41.4-16,.4,1-13.9,5.8-38.3,19.6-17.9,10.2-27.5,17.4-28.1,16.6h0Z"/>
|
||||||
|
</g>
|
||||||
|
</g>
|
||||||
|
</g>
|
||||||
|
</svg>
|
||||||
|
After Width: | Height: | Size: 10 KiB |
Loading…
Reference in New Issue
Block a user