This commit is contained in:
Nalvazhuthi 2025-05-27 18:16:58 +05:30
commit 3944588cb0
9 changed files with 598 additions and 229 deletions

View File

@ -12,140 +12,198 @@ import Widget4InputCard3D from './Widget4InputCard3D'
import WarehouseThroughputInputComponent from './WarehouseThroughputInputComponent'
import { useWidgetStore } from '../../../../../store/useWidgetStore'
// const InputSelecterComponent = () => {
// const { selectedChartId } = useWidgetStore();
// if (selectedChartId && selectedChartId.type && selectedChartId.type === 'bar' ) {
// return (
// <>
// <div className="sideBarHeader">2D Widget Input</div>
// <BarChartInput />
// </>
// )
// }
// else if (selectedChartId && selectedChartId.type && selectedChartId.type === 'line' ) {
// return (
// <>
// <div className="sideBarHeader">2D Widget Input</div>
// <LineGrapInput />
// </>
// )
// }
// else if (selectedChartId && selectedChartId.type && selectedChartId.type === 'pie' ) {
// return (
// <>
// <div className="sideBarHeader">2D Widget Input</div>
// <PieChartInput />
// </>
// )
// }
// else if (selectedChartId && selectedChartId.type && selectedChartId.type === 'doughnut' ) {
// return (
// <>
// <div className="sideBarHeader">2D Widget Input</div>
// <PieChartInput />
// </>
// )
// }
// else if (selectedChartId && selectedChartId.type && selectedChartId.type === 'polarArea' ) {
// return (
// <>
// <div className="sideBarHeader">2D Widget Input</div>
// <PieChartInput />
// </>
// )
// }
// else if (selectedChartId && selectedChartId.type && selectedChartId.type === 'progress 1' ) {
// return (
// <>
// <div className="sideBarHeader">2D Widget Input</div>
// <Progress1Input />
// </>
// )
// }
// else if (selectedChartId && selectedChartId.type && selectedChartId.type === 'progress 2' ) {
// return (
// <>
// <div className="sideBarHeader">2D Widget Input</div>
// <Progress2Input />
// </>
// )
// }
// else if (selectedChartId && selectedChartId.className && selectedChartId.className === 'warehouseThroughput floating' ) {
// return (
// <>
// <div className="sideBarHeader">Floting Widget Input</div>
// <WarehouseThroughputInputComponent />
// </>
// )
// }
// else if (selectedChartId && selectedChartId.className && selectedChartId.className === 'fleetEfficiency floating' ) {
// return (
// <>
// <div className="sideBarHeader">Floting Widget Input</div>
// <FleetEfficiencyInputComponent />
// </>
// )
// }
// else if (selectedChartId && selectedChartId.className && selectedChartId.className === 'floating total-card' ) {
// return (
// <>
// <div className="sideBarHeader">Floting Widget Input</div>
// <FleetEfficiencyInputComponent />
// </>
// )
// }
// else if (selectedChartId && selectedChartId.type && selectedChartId.type === 'ui-Widget 1' ) {
// return (
// <>
// <div className="sideBarHeader">3D Widget Input</div>
// <Widget4InputCard3D />
// </>
// )
// }
// else if (selectedChartId && selectedChartId.type && selectedChartId.type === 'ui-Widget 2' ) {
// return (
// <>
// <div className="sideBarHeader">3D Widget Input</div>
// <Widget2InputCard3D />
// </>
// )
// }
// else if (selectedChartId && selectedChartId.type && selectedChartId.type === 'ui-Widget 3' ) {
// return (
// <>
// <div className="sideBarHeader">3D Widget Input</div>
// <Widget3InputCard3D />
// </>
// )
// }
// else if (selectedChartId && selectedChartId.type && selectedChartId.type === 'ui-Widget 4' ) {
// return (
// <>
// <div className="sideBarHeader">3D Widget Input</div>
// <Widget4InputCard3D />
// </>
// )
// }
// else {
// return (
// <div>No chart selected</div>
// )
// }
// }
const chartTypeMap: Record<| 'bar'| 'line'| 'pie' | 'doughnut' | 'polarArea'| 'progress 1' | 'progress 2'
| 'ui-Widget 1'| 'ui-Widget 2'| 'ui-Widget 3'| 'ui-Widget 4',JSX.Element> = {
bar: <BarChartInput />,
line: <LineGrapInput />,
pie: <PieChartInput />,
doughnut: <PieChartInput />,
polarArea: <PieChartInput />,
'progress 1': <Progress1Input />,
'progress 2': <Progress2Input />,
'ui-Widget 1': <Widget4InputCard3D />,
'ui-Widget 2': <Widget2InputCard3D />,
'ui-Widget 3': <Widget3InputCard3D />,
'ui-Widget 4': <Widget4InputCard3D />,
};
const classNameMap: Record<
| 'warehouseThroughput floating'
| 'fleetEfficiency floating'
| 'floating total-card',
JSX.Element
> = {
'warehouseThroughput floating': <WarehouseThroughputInputComponent />,
'fleetEfficiency floating': <FleetEfficiencyInputComponent />,
'floating total-card': <FleetEfficiencyInputComponent />,
};
const InputSelecterComponent = () => {
const { selectedChartId } = useWidgetStore();
const { selectedChartId } = useWidgetStore();
if (selectedChartId && selectedChartId.type && selectedChartId.type === 'bar' ) {
return (
if (selectedChartId) {
const { type, className } = selectedChartId;
if (type && chartTypeMap[type as keyof typeof chartTypeMap]) {
const label = ['ui-Widget 1', 'ui-Widget 2', 'ui-Widget 3', 'ui-Widget 4'].includes(type)
? '3D Widget Input'
: '2D Widget Input';
return (
<>
<div className="sideBarHeader">2D Widget Input</div>
<BarChartInput />
<div className="sideBarHeader">{label}</div>
{chartTypeMap[type as keyof typeof chartTypeMap]}
</>
)
}
);
}
else if (selectedChartId && selectedChartId.type && selectedChartId.type === 'line' ) {
return (
if (className && classNameMap[className as keyof typeof classNameMap]) {
return (
<>
<div className="sideBarHeader">2D Widget Input</div>
<LineGrapInput />
<div className="sideBarHeader">Floting Widget Input</div>
{classNameMap[className as keyof typeof classNameMap]}
</>
)
);
}
}
else if (selectedChartId && selectedChartId.type && selectedChartId.type === 'pie' ) {
return (
<>
<div className="sideBarHeader">2D Widget Input</div>
<PieChartInput />
</>
)
}
return <div>No chart selected</div>;
};
else if (selectedChartId && selectedChartId.type && selectedChartId.type === 'doughnut' ) {
return (
<>
<div className="sideBarHeader">2D Widget Input</div>
<PieChartInput />
</>
)
}
else if (selectedChartId && selectedChartId.type && selectedChartId.type === 'polarArea' ) {
return (
<>
<div className="sideBarHeader">2D Widget Input</div>
<PieChartInput />
</>
)
}
else if (selectedChartId && selectedChartId.type && selectedChartId.type === 'progress 1' ) {
return (
<>
<div className="sideBarHeader">2D Widget Input</div>
<Progress1Input />
</>
)
}
else if (selectedChartId && selectedChartId.type && selectedChartId.type === 'progress 2' ) {
return (
<>
<div className="sideBarHeader">2D Widget Input</div>
<Progress2Input />
</>
)
}
else if (selectedChartId && selectedChartId.className && selectedChartId.className === 'warehouseThroughput floating' ) {
return (
<>
<div className="sideBarHeader">Floting Widget Input</div>
<WarehouseThroughputInputComponent />
</>
)
}
else if (selectedChartId && selectedChartId.className && selectedChartId.className === 'fleetEfficiency floating' ) {
return (
<>
<div className="sideBarHeader">Floting Widget Input</div>
<FleetEfficiencyInputComponent />
</>
)
}
else if (selectedChartId && selectedChartId.className && selectedChartId.className === 'floating total-card' ) {
return (
<>
<div className="sideBarHeader">Floting Widget Input</div>
<FleetEfficiencyInputComponent />
</>
)
}
else if (selectedChartId && selectedChartId.type && selectedChartId.type === 'ui-Widget 1' ) {
return (
<>
<div className="sideBarHeader">3D Widget Input</div>
<Widget4InputCard3D />
</>
)
}
else if (selectedChartId && selectedChartId.type && selectedChartId.type === 'ui-Widget 2' ) {
return (
<>
<div className="sideBarHeader">3D Widget Input</div>
<Widget2InputCard3D />
</>
)
}
else if (selectedChartId && selectedChartId.type && selectedChartId.type === 'ui-Widget 3' ) {
return (
<>
<div className="sideBarHeader">3D Widget Input</div>
<Widget3InputCard3D />
</>
)
}
else if (selectedChartId && selectedChartId.type && selectedChartId.type === 'ui-Widget 4' ) {
return (
<>
<div className="sideBarHeader">3D Widget Input</div>
<Widget4InputCard3D />
</>
)
}
else {
return (
<div>No chart selected</div>
)
}
}
export default InputSelecterComponent
export default InputSelecterComponent;

View File

@ -1,30 +1,75 @@
import React, { useState } from "react";
import React, { useEffect, useRef, useState } from "react";
import { getAvatarColor } from "../../../modules/collaboration/functions/getAvatarColor";
import { KebabIcon } from "../../icons/ExportCommonIcons";
import { adjustHeight } from "./function/textAreaHeightAdjust";
interface MessageProps {
val: Reply;
val: Reply | CommentSchema;
i: number;
}
const Messages: React.FC<MessageProps> = ({ val, i }) => {
const [isEditing, setIsEditing] = useState(false);
const [openOptions, setOpenOptions] = useState(false);
// input
const [value, setValue] = useState<string>(
"reply" in val ? val.reply : val.comment
);
const textareaRef = useRef<HTMLTextAreaElement>(null);
const currentUser = "1";
const UserName = "username";
useEffect(() => {
if (textareaRef.current) adjustHeight(textareaRef.current);
}, [value]);
function handleCancelAction() {
setIsEditing(false);
}
function handleSaveAction() {
setIsEditing(false);
}
function handleDeleteAction() {
setOpenOptions(false);
}
return (
<>
{isEditing ? (
<div className="edit-container">
<div className="input-container">
<textarea />
<textarea
placeholder="type here"
ref={textareaRef}
autoFocus
value={value}
onChange={(e) => setValue(e.target.value)}
style={{ resize: "none" }}
/>
</div>
<div className="actions-container">
<div className="options"></div>
<div className="actions">
<button className="cancel-button">Cancel</button>
<button className="save-button">Save</button>
<button
className="cancel-button"
onClick={() => {
handleCancelAction();
}}
>
Cancel
</button>
<button
className="save-button"
onClick={() => {
handleSaveAction();
}}
>
Save
</button>
</div>
</div>
</div>
@ -46,7 +91,7 @@ const Messages: React.FC<MessageProps> = ({ val, i }) => {
<button
className="more-options-button"
onClick={() => {
setOpenOptions(true);
setOpenOptions(!openOptions);
}}
>
<KebabIcon />
@ -56,17 +101,27 @@ const Messages: React.FC<MessageProps> = ({ val, i }) => {
<button
className="option"
onClick={() => {
setOpenOptions(false);
setIsEditing(true);
}}
>
Edit
</button>
<button className="option">Delete</button>
<button
className="option"
onClick={() => {
handleDeleteAction();
}}
>
Delete
</button>
</div>
)}
</div>
)}
<div className="message">{val.reply}</div>
<div className="message">
{"reply" in val ? val.reply : val.comment}
</div>
</div>
</div>
)}

View File

@ -1,38 +1,115 @@
import React, { useState } from "react";
import React, { useEffect, useRef, useState } from "react";
import { CloseIcon, KebabIcon } from "../../icons/ExportCommonIcons";
import Messages from "./Messages";
import { ExpandIcon } from "../../icons/SimulationIcons";
import { adjustHeight } from "./function/textAreaHeightAdjust";
const ThreadChat: React.FC = () => {
const [openThreadOptions, setOpenThreadOptions] = useState(false);
const [inputActive, setInputActive] = useState(false);
const [value, setValue] = useState<string>("");
const textareaRef = useRef<HTMLTextAreaElement>(null);
const wrapperRef = useRef<HTMLDivElement>(null);
const [dragging, setDragging] = useState(false);
const [dragOffset, setDragOffset] = useState({ x: 0, y: 0 });
const [position, setPosition] = useState({ x: 100, y: 100 });
const messages = [
{
replyId: "user 1",
creatorId: "1",
createdAt: "hello, thread check",
createdAt: "2 hrs ago",
lastUpdatedAt: "2 hrs ago",
reply: "true",
reply:
"reply testing reply content 1, reply testing reply content 1reply testing reply content 1",
},
{
replyId: "user 2",
creatorId: "2",
createdAt: "hello, thread check",
createdAt: "2 hrs ago",
lastUpdatedAt: "2 hrs ago",
reply: "true",
reply: "reply 2",
},
];
useEffect(() => {
if (textareaRef.current) adjustHeight(textareaRef.current);
}, [value]);
const clamp = (val: number, min: number, max: number) => {
return Math.min(Math.max(val, min), max);
};
const handlePointerDown = (event: React.PointerEvent<HTMLDivElement>) => {
if (event.button !== 0) return;
const wrapper = wrapperRef.current;
if (!wrapper) return;
const rect = wrapper.getBoundingClientRect();
const offsetX = event.clientX - rect.left;
const offsetY = event.clientY - rect.top;
setDragging(true);
setDragOffset({ x: offsetX, y: offsetY });
wrapper.setPointerCapture(event.pointerId);
};
const handlePointerMove = (event: React.PointerEvent<HTMLDivElement>) => {
if (!dragging) return;
const container = document.getElementById("work-space-three-d-canvas");
const wrapper = wrapperRef.current;
if (!container || !wrapper) return;
const containerRect = container.getBoundingClientRect();
const wrapperRect = wrapper.getBoundingClientRect();
let newX = event.clientX - containerRect.left - dragOffset.x;
let newY = event.clientY - containerRect.top - dragOffset.y;
const maxX = containerRect.width - wrapper.offsetWidth;
const maxY = containerRect.height - wrapper.offsetHeight;
newX = clamp(newX, 0, maxX);
newY = clamp(newY, 0, maxY);
setPosition({ x: newX, y: newY });
};
const handlePointerUp = (event: React.PointerEvent<HTMLDivElement>) => {
if (!dragging) return;
setDragging(false);
const wrapper = wrapperRef.current;
if (wrapper) wrapper.releasePointerCapture(event.pointerId);
};
return (
<div className="thread-char-wrapper">
<div className="thread-char-container">
<div
ref={wrapperRef}
className="thread-chat-wrapper"
onPointerDown={handlePointerDown}
onPointerMove={handlePointerMove}
onPointerUp={handlePointerUp}
style={{
position: "absolute",
left: position.x,
top: position.y,
cursor: dragging ? "grabbing" : "grab",
userSelect: "none",
zIndex: 9999,
}}
>
<div className="thread-chat-container">
<div className="header-wrapper">
<div className="header">Comment</div>
<div className="header-options">
<button
className="options-button"
onClick={() => {
setOpenThreadOptions(true);
}}
onClick={() => setOpenThreadOptions(!openThreadOptions)}
>
<KebabIcon />
</button>
@ -40,7 +117,7 @@ const ThreadChat: React.FC = () => {
<div className="options-list">
<div className="options">Mark as Unread</div>
<div className="options">Mark as Resolved</div>
<div className="options">Delete Thread</div>
<div className="options delete">Delete Thread</div>
</div>
)}
<button className="close-button">
@ -48,15 +125,25 @@ const ThreadChat: React.FC = () => {
</button>
</div>
</div>
<div className="messages-wrapper">
{messages.map((val, i) => (
<Messages val={val as Reply} i={i} key={val.replyId} />
<Messages val={val as any} i={i} key={val.replyId} />
))}
</div>
<div className="send-message-wrapper">
<div className="input-container">
<input type="text" />
<div className="sent-button">
<div className={`input-container ${inputActive ? "active" : ""}`}>
<textarea
placeholder="type something"
ref={textareaRef}
value={value}
onChange={(e) => setValue(e.target.value)}
onFocus={() => setInputActive(true)}
onBlur={() => setInputActive(false)}
style={{ resize: "none" }}
/>
<div className={`sent-button ${value === "" ? "disable-send-btn" : ""}`}>
<ExpandIcon />
</div>
</div>

View File

@ -0,0 +1,17 @@
export const adjustHeight = (textareaRef: HTMLTextAreaElement) => {
const el = textareaRef;
if (el) {
el.style.height = "auto";
el.style.height = "38px";
// Clamp to max height for 6 lines
const lineHeight = 18; // px, adjust if needed
const maxHeight = lineHeight * 6;
if (el.scrollHeight > maxHeight) {
el.style.overflowY = "auto";
el.style.height = `${maxHeight}px`;
} else {
el.style.overflowY = "hidden";
}
}
};

View File

@ -5,7 +5,6 @@ import Controls from '../controls/controls';
import { Environment } from '@react-three/drei'
import background from "../../../assets/textures/hdr/mudroadpuresky2k.hdr";
import { MovingClouds } from '../clouds/clouds';
function Setup() {
return (
@ -18,7 +17,7 @@ function Setup() {
<PostProcessing />
<MovingClouds />
{/* <MovingClouds /> */}
<Environment files={background} environmentIntensity={1.5} />
</>

View File

@ -31,6 +31,7 @@ interface ProductionCapacityProps {
type: string;
position: [number, number, number];
rotation: [number, number, number];
scale?: [number, number, number];
Data?: any;
onContextMenu?: (event: React.MouseEvent) => void;
// onPointerDown:any
@ -41,7 +42,8 @@ const ProductionCapacity: React.FC<ProductionCapacityProps> = ({
type,
Data,
position,
rotation,
rotation = [0, 0, 0],
scale = [0.5, 0.5, 0.5],
onContextMenu,
}) => {
const { selectedChartId, setSelectedChartId } = useWidgetStore();
@ -198,74 +200,75 @@ const ProductionCapacity: React.FC<ProductionCapacityProps> = ({
useEffect(() => {}, [rotation]);
return (
<Html
// data
position={position}
scale={[0.5, 0.5, 0.5]}
rotation={rotation}
// class
wrapperClass="pointer-none"
// other
transform
zIndexRange={[1, 0]}
prepend
// sprite
distanceFactor={20}
// events
onDragOver={(e) => {
e.preventDefault();
e.stopPropagation();
}}
onDrop={(e) => {
e.preventDefault();
}}
>
<div
className={`productionCapacity-wrapper card ${
selectedChartId?.id === id ? "activeChart" : ""
}`}
onClick={() => setSelectedChartId({ id: id, type: type })}
onContextMenu={onContextMenu}
style={{
width: "300px", // Original width
height: "300px", // Original height
// transform: transformStyle.transform,
transformStyle: "preserve-3d",
position: "absolute",
transform: "translate(-50%, -50%)",
<>
{position && scale && rotation && <Html
// data
position={position}
scale={scale}
rotation={rotation}
// class
wrapperClass="pointer-none"
// other
transform
zIndexRange={[1, 0]}
prepend
// sprite
distanceFactor={20}
// events
onDragOver={(e) => {
e.preventDefault();
e.stopPropagation();
}}
onDrop={(e) => {
e.preventDefault();
}}
>
<div className="headeproductionCapacityr-wrapper">
<div className="header">Production Capacity</div>
<div className="production-capacity">
<div className="value">1,200</div>{" "}
<div className="value">units/hour</div>
</div>
<div className="production-capacity">
<div className="current">
<div className="key">Current</div>
<div className="value">1500</div>
<div
className={`productionCapacity-wrapper card ${selectedChartId?.id === id ? "activeChart" : ""
}`}
onClick={() => setSelectedChartId({ id: id, type: type })}
onContextMenu={onContextMenu}
style={{
width: "300px", // Original width
height: "300px", // Original height
// transform: transformStyle.transform,
transformStyle: "preserve-3d",
position: "absolute",
transform: "translate(-50%, -50%)",
}}
>
<div className="headeproductionCapacityr-wrapper">
<div className="header">Production Capacity</div>
<div className="production-capacity">
<div className="value">1,200</div>{" "}
<div className="value">units/hour</div>
</div>
<div className="target">
<div className="key">Target</div>
<div className="value">2.345</div>
<div className="production-capacity">
<div className="current">
<div className="key">Current</div>
<div className="value">1500</div>
</div>
<div className="target">
<div className="key">Target</div>
<div className="value">2.345</div>
</div>
{/* <div className="value">units/hour</div> */}
</div>
{/* <div className="value">units/hour</div> */}
</div>{" "}
<div className="bar-chart charts">
{/* Bar Chart */}
<Bar
data={
Object.keys(measurements).length > 0
? chartData
: defaultChartData
}
options={chartOptions}
/>
</div>
</div>{" "}
<div className="bar-chart charts">
{/* Bar Chart */}
<Bar
data={
Object.keys(measurements).length > 0
? chartData
: defaultChartData
}
options={chartOptions}
/>
</div>
</div>
</Html>
</Html>}
</>
);
};

View File

@ -185,7 +185,6 @@ const Project: React.FC = () => {
</>
)}
<VersionSaved />
{/* <ThreadChat /> */}
</div>
);
};

View File

@ -3,7 +3,8 @@
// global input style
input {
input,
textarea {
width: 100%;
padding: 4px 8px;
border-radius: #{$border-radius-large};

View File

@ -93,66 +93,216 @@
}
}
.thread-char-wrapper {
.thread-chat-wrapper {
position: absolute;
// remove later
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
// ----
z-index: 10000;
.thread-char-container {
z-index: #{$z-index-ui-highest};
.thread-chat-container {
background: var(--background-color);
backdrop-filter: blur(14px);
border-radius: #{$border-radius-extra-large};
width: 20rem;
.header-wrapper {
.header {
}
padding: 12px;
@include flex-space-between;
.header-options {
.options-button {
}
@include flex-center;
position: relative;
.options-list {
position: absolute;
bottom: 0;
right: 0;
transform: translate(-24px, 100%);
background: var(--background-color);
padding: 8px 4px;
border-radius: #{$border-radius-medium};
backdrop-filter: blur(10px);
z-index: 100;
.options {
text-wrap: nowrap;
padding: 2px 4px;
border-radius: #{$border-radius-medium};
cursor: pointer;
&:hover {
color: var(--text-button-color);
background: var(--background-color-accent);
}
&.delete {
&:hover {
color: var(--log-error-text-color);
background: var(--log-error-background-color);
}
}
}
}
.options-button,
.close-button {
@include flex-center;
height: 24px;
width: 24px;
border-radius: #{$border-radius-medium};
&:hover {
background: var(--background-color-solid);
}
}
.close-button {
svg {
scale: 1.4;
}
}
}
}
.messages-wrapper {
padding: 12px;
padding-top: 0;
.edit-container {
.input-container {
textarea{
background: var(--background-color);
&:focus{
outline-color: var(--border-color-accent);
}
}
}
.actions-container {
@include flex-space-between;
width: 100%;
margin: 8px 0;
.actions {
.cancel-button {
@include flex-center;
gap: 4px;
.cancel-button,
.save-button {
padding: 4px 10px;
border-radius: #{$border-radius-large};
background: var(--background-color-solid);
outline: 1px solid var(--border-color);
}
.save-button {
color: var(--text-button-color);
background: var(--background-color-accent);
outline: none;
}
}
}
}
.message-container {
position: relative;
@include flex-space-between;
align-items: flex-start;
gap: 12px;
margin-top: 8px;
&:first-child{
margin: 0;
}
.profile {
height: 28px;
width: 28px;
min-width: 28px;
text-transform: uppercase;
line-height: 28px;
text-align: center;
border-radius: #{$border-radius-circle};
}
.content {
width: 100%;
.user-details {
display: flex;
align-items: flex-end;
gap: 8px;
.user-name {
text-transform: capitalize;
}
.time {
font-size: var(--font-size-tiny);
color: var(--input-text-color);
}
}
}
.more-options {
position: absolute;
right: 0;
top: 0;
.more-options-button {
}
.options-list {
.option {
@include flex-center;
height: 18px;
width: 18px;
border-radius: #{$border-radius-small};
&:hover{
background: var(--background-color-solid);
}
}
.options-list {
position: absolute;
right: 0;
padding: 3px 6px;
background: var(--background-color);
backdrop-filter: blur(10px);
outline: 1px solid var(--border-color);
border-radius: #{$border-radius-medium};
z-index: 100;
.option {
width: 100%;
border-radius: #{$border-radius-medium};
padding: 2px 6px;
text-align: start;
&:hover{
background: var(--background-color-accent);
color: var(--text-button-color);
}
}
}
}
.message{
margin-top: 6px;
}
}
}
.send-message-wrapper {
padding: 12px;
padding-top: 8px;
.input-container {
position: relative;
@include flex-space-between;
background: var(--background-color);
border-radius: #{$border-radius-extra-large};
outline: 1px solid var(--border-color);
textarea {
background: transparent;
outline: none;
width: calc(100% - 36px);
overflow: hidden;
line-height: 28px;
max-height: 108px;
}
.sent-button {
position: absolute;
right: 2px;
bottom: 2px;
@include flex-center;
padding: 2px;
svg {
rotate: 45deg;
}
}
.disable-send-btn {
filter: saturate(0);
}
&.active {
background: var(--background-color-solid);
padding-top: 4px;
flex-direction: column;
align-items: end;
textarea {
width: 100%;
line-height: 18px;
}
.sent-button {
position: relative;
}
}
}
}