Add image stickers and fix desktop chat composer
9
apps/web/public/stickers/anon-miner.svg
Normal file
@@ -0,0 +1,9 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 256 256">
|
||||
<rect width="256" height="256" fill="#0a0d17"/>
|
||||
<path d="M46 54h164v128H46z" fill="#151b2b" stroke="#29ffe6" stroke-width="4"/>
|
||||
<circle cx="99" cy="105" r="26" fill="#e8edff"/>
|
||||
<circle cx="157" cy="105" r="26" fill="#e8edff"/>
|
||||
<path d="M77 159c25 20 77 20 102 0" fill="none" stroke="#ff3df0" stroke-width="8"/>
|
||||
<path d="M65 62l126 126M191 62L65 188" stroke="#1f2a4a" stroke-width="5"/>
|
||||
<text x="128" y="222" text-anchor="middle" fill="#ffd84a" font-family="monospace" font-size="18" font-weight="700">ANON FOUND HASHES</text>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 610 B |
8
apps/web/public/stickers/block-denied.svg
Normal file
@@ -0,0 +1,8 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 256 256">
|
||||
<rect width="256" height="256" fill="#07090f"/>
|
||||
<rect x="54" y="42" width="148" height="148" fill="#131a2e" stroke="#29ffe6" stroke-width="5"/>
|
||||
<path d="M76 76l104 104M180 76L76 180" stroke="#ff4f78" stroke-width="15"/>
|
||||
<text x="128" y="118" text-anchor="middle" fill="#ffd84a" font-family="monospace" font-size="18" font-weight="700">BLOCK</text>
|
||||
<text x="128" y="142" text-anchor="middle" fill="#ffd84a" font-family="monospace" font-size="18" font-weight="700">DENIED</text>
|
||||
<text x="128" y="224" text-anchor="middle" fill="#b6c3e0" font-family="monospace" font-size="13">TRY ANOTHER 2 BILLION TIMES</text>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 691 B |
10
apps/web/public/stickers/block-hopium.svg
Normal file
@@ -0,0 +1,10 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 256 256">
|
||||
<rect width="256" height="256" fill="#07090f"/>
|
||||
<g>
|
||||
<animateTransform attributeName="transform" type="translate" values="0 0;0 -10;0 0" dur=".8s" repeatCount="indefinite"/>
|
||||
<rect x="74" y="52" width="108" height="108" fill="#131a2e" stroke="#29ffe6" stroke-width="5"/>
|
||||
<text x="128" y="113" text-anchor="middle" fill="#ffd84a" font-family="monospace" font-size="24" font-weight="700">?</text>
|
||||
</g>
|
||||
<path d="M82 185c24 13 68 13 92 0" fill="none" stroke="#ff3df0" stroke-width="8"/>
|
||||
<text x="128" y="224" text-anchor="middle" fill="#b6c3e0" font-family="monospace" font-size="14">THIS ONE IS OURS</text>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 694 B |
7
apps/web/public/stickers/boomer-unit.svg
Normal file
@@ -0,0 +1,7 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 256 256">
|
||||
<rect width="256" height="256" fill="#0a0d17"/>
|
||||
<rect x="65" y="48" width="126" height="145" rx="8" fill="#1b1f2b" stroke="#ff4f78" stroke-width="5"/>
|
||||
<path d="M89 74h78M89 98h78M89 122h78M89 146h78" stroke="#6a7aa0" stroke-width="7"/>
|
||||
<path d="M83 181h90" stroke="#ffd84a" stroke-width="8"/>
|
||||
<text x="128" y="222" text-anchor="middle" fill="#ff4f78" font-family="monospace" font-size="18" font-weight="700">0 H/s AND PROUD</text>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 511 B |
8
apps/web/public/stickers/chad-hash.svg
Normal file
@@ -0,0 +1,8 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 256 256">
|
||||
<rect width="256" height="256" fill="#07090f"/>
|
||||
<path d="M83 72l28-30h50l24 35-12 75-45 36-45-36z" fill="#d9d3c7" stroke="#29ffe6" stroke-width="5"/>
|
||||
<path d="M86 76h87l-16-30h-45z" fill="#ff3df0"/>
|
||||
<path d="M93 108h28M143 108h28" stroke="#07090f" stroke-width="7"/>
|
||||
<path d="M101 145c23 13 49 13 72 0" fill="none" stroke="#07090f" stroke-width="7"/>
|
||||
<text x="128" y="220" text-anchor="middle" fill="#6cff8c" font-family="monospace" font-size="18" font-weight="700">HASHING. UNBOTHERED.</text>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 576 B |
8
apps/web/public/stickers/chart-crime.svg
Normal file
@@ -0,0 +1,8 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 256 256">
|
||||
<rect width="256" height="256" fill="#07090f"/>
|
||||
<rect x="34" y="47" width="188" height="139" fill="#101624" stroke="#2c3a66" stroke-width="4"/>
|
||||
<path d="M52 164h154M52 127h154M52 90h154" stroke="#1f2a4a" stroke-width="3"/>
|
||||
<path d="M55 156l32-2 22-47 31 42 18-9 17-60 31 3" fill="none" stroke="#29ffe6" stroke-width="7"/>
|
||||
<circle cx="175" cy="80" r="9" fill="#ff4f78"/>
|
||||
<text x="128" y="222" text-anchor="middle" fill="#ffd84a" font-family="monospace" font-size="18" font-weight="700">CHART CRIME</text>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 586 B |
10
apps/web/public/stickers/fan-panic.svg
Normal file
@@ -0,0 +1,10 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 256 256">
|
||||
<rect width="256" height="256" fill="#07090f"/>
|
||||
<circle cx="128" cy="112" r="68" fill="#101624" stroke="#29ffe6" stroke-width="5"/>
|
||||
<g transform-origin="128 112">
|
||||
<animateTransform attributeName="transform" type="rotate" from="0 128 112" to="360 128 112" dur=".45s" repeatCount="indefinite"/>
|
||||
<path d="M128 112c38-44 75-21 45 11-16 17-38 7-45-11zM128 112c-38 44-75 21-45-11 16-17 38-7 45 11zM128 112c44 38 21 75-11 45-17-16-7-38 11-45zM128 112c-44-38-21-75 11-45 17 16 7 38-11 45z" fill="#ff3df0"/>
|
||||
</g>
|
||||
<circle cx="128" cy="112" r="13" fill="#ffd84a"/>
|
||||
<text x="128" y="221" text-anchor="middle" fill="#ffd84a" font-family="monospace" font-size="18" font-weight="700">FAN PANIC</text>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 776 B |
10
apps/web/public/stickers/fiat-npc.svg
Normal file
@@ -0,0 +1,10 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 256 256">
|
||||
<rect width="256" height="256" fill="#080a10"/>
|
||||
<circle cx="128" cy="93" r="58" fill="#8ea0c4" stroke="#2c3a66" stroke-width="5"/>
|
||||
<circle cx="105" cy="86" r="9" fill="#0a0d17"/>
|
||||
<circle cx="151" cy="86" r="9" fill="#0a0d17"/>
|
||||
<path d="M103 123h50" stroke="#0a0d17" stroke-width="7"/>
|
||||
<rect x="45" y="160" width="166" height="42" fill="#131a2e" stroke="#ff4f78" stroke-width="4"/>
|
||||
<text x="128" y="187" text-anchor="middle" fill="#ff4f78" font-family="monospace" font-size="17" font-weight="700">I TRUST BANKS</text>
|
||||
<text x="128" y="225" text-anchor="middle" fill="#ffd84a" font-family="monospace" font-size="14">NORMAL HEATER USER</text>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 726 B |
9
apps/web/public/stickers/heat-death.svg
Normal file
@@ -0,0 +1,9 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 256 256">
|
||||
<rect width="256" height="256" fill="#080a10"/>
|
||||
<g>
|
||||
<animateTransform attributeName="transform" type="scale" values="1;1.06;1" dur=".7s" repeatCount="indefinite" additive="sum"/>
|
||||
<path d="M128 35c38 43 59 75 59 111 0 37-26 68-59 68s-59-31-59-68c0-36 21-68 59-111z" fill="#ff4f78" stroke="#ffd84a" stroke-width="5"/>
|
||||
</g>
|
||||
<path d="M106 144h44M105 166h46" stroke="#0a0d17" stroke-width="7"/>
|
||||
<text x="128" y="232" text-anchor="middle" fill="#ffd84a" font-family="monospace" font-size="15" font-weight="700">PROOF OF WARMTH</text>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 616 B |
8
apps/web/public/stickers/money-printer.svg
Normal file
@@ -0,0 +1,8 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 256 256">
|
||||
<rect width="256" height="256" fill="#0c1120"/>
|
||||
<rect x="45" y="56" width="166" height="82" fill="#151b2b" stroke="#ff4f78" stroke-width="5"/>
|
||||
<rect x="64" y="118" width="128" height="62" fill="#101624" stroke="#29ffe6" stroke-width="4"/>
|
||||
<path d="M79 151h98" stroke="#ffd84a" stroke-width="7" stroke-dasharray="10 8"/>
|
||||
<text x="128" y="103" text-anchor="middle" fill="#ffd84a" font-family="monospace" font-size="26" font-weight="700">BRRR</text>
|
||||
<text x="128" y="218" text-anchor="middle" fill="#ff3df0" font-family="monospace" font-size="17" font-weight="700">FIAT PATCH NOTES</text>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 668 B |
9
apps/web/public/stickers/odds-wizard.svg
Normal file
@@ -0,0 +1,9 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 256 256">
|
||||
<rect width="256" height="256" fill="#080a10"/>
|
||||
<path d="M128 31l53 82H75z" fill="#131a2e" stroke="#ff3df0" stroke-width="5"/>
|
||||
<circle cx="128" cy="134" r="52" fill="#151b2b" stroke="#29ffe6" stroke-width="5"/>
|
||||
<circle cx="108" cy="126" r="7" fill="#ffd84a"/>
|
||||
<circle cx="148" cy="126" r="7" fill="#ffd84a"/>
|
||||
<path d="M102 157h52" stroke="#ff4f78" stroke-width="6"/>
|
||||
<text x="128" y="220" text-anchor="middle" fill="#ffd84a" font-family="monospace" font-size="16" font-weight="700">THE ODDS SAID LOL</text>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 591 B |
11
apps/web/public/stickers/printer-loop.svg
Normal file
@@ -0,0 +1,11 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 256 256">
|
||||
<rect width="256" height="256" fill="#0c1120"/>
|
||||
<rect x="48" y="54" width="160" height="72" fill="#151b2b" stroke="#ff4f78" stroke-width="5"/>
|
||||
<g>
|
||||
<animateTransform attributeName="transform" type="translate" values="0 -22;0 28;0 -22" dur="1s" repeatCount="indefinite"/>
|
||||
<rect x="76" y="126" width="104" height="42" fill="#6cff8c" stroke="#0a0d17" stroke-width="4"/>
|
||||
<text x="128" y="153" text-anchor="middle" fill="#0a0d17" font-family="monospace" font-size="19" font-weight="700">FIAT</text>
|
||||
</g>
|
||||
<text x="128" y="101" text-anchor="middle" fill="#ffd84a" font-family="monospace" font-size="24" font-weight="700">BRRR</text>
|
||||
<text x="128" y="222" text-anchor="middle" fill="#ff3df0" font-family="monospace" font-size="15" font-weight="700">INFINITE PATCH</text>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 856 B |
@@ -2,10 +2,12 @@ export type ChatSticker = {
|
||||
label: string;
|
||||
text: string;
|
||||
kind?: "sticker" | "gif";
|
||||
image?: string;
|
||||
};
|
||||
|
||||
export const STICKER_PREFIX = "[gashboard sticker]";
|
||||
const GIF_MARKER = "[gif]";
|
||||
const IMAGE_MARKER = "[img:";
|
||||
|
||||
export const CHAT_STICKERS: ChatSticker[] = [
|
||||
{ label: "fiat heater", text: "FIAT HEATER DETECTED: warm room, cold wallet." },
|
||||
@@ -48,17 +50,94 @@ export const CHAT_STICKERS: ChatSticker[] = [
|
||||
{ label: "main character", text: "MAIN CHARACTER ENERGY, BACKGROUND HASHRATE." },
|
||||
{ label: "block soon", text: "BLOCK SOON. SOURCE: THE SAME PART OF MY BRAIN THAT BUYS TOPS." },
|
||||
{ label: "heater max", text: "HEATER ON MAX. HASHES ON VACATION." },
|
||||
{
|
||||
label: "anon miner",
|
||||
text: "ANON DISCOVERS SOLO MINING AND IMMEDIATELY BECOMES A PROBLEM.",
|
||||
image: "/stickers/anon-miner.svg",
|
||||
},
|
||||
{
|
||||
label: "fiat npc",
|
||||
text: "I JUST USE A NORMAL HEATER BECAUSE THE BANK SAID IT WAS FINE.",
|
||||
image: "/stickers/fiat-npc.svg",
|
||||
},
|
||||
{
|
||||
label: "chad hash",
|
||||
text: "LOUD, WARM, WRONG, AND STILL MORE SOVEREIGN THAN YOUR SAVINGS ACCOUNT.",
|
||||
image: "/stickers/chad-hash.svg",
|
||||
},
|
||||
{
|
||||
label: "money printer",
|
||||
text: "CENTRAL BANK MONETARY POLICY, ARTIST'S IMPRESSION.",
|
||||
image: "/stickers/money-printer.svg",
|
||||
},
|
||||
{
|
||||
label: "block denied",
|
||||
text: "THE NETWORK REVIEWED YOUR NONCE AND CHOSE VIOLENCE.",
|
||||
image: "/stickers/block-denied.svg",
|
||||
},
|
||||
{
|
||||
label: "boomer unit",
|
||||
text: "LEGACY HEATER ACHIEVES ZERO HASHES PER RETIREMENT.",
|
||||
image: "/stickers/boomer-unit.svg",
|
||||
},
|
||||
{
|
||||
label: "chart crime",
|
||||
text: "TECHNICAL ANALYSIS CONDUCTED BY A FAN WITH A WALLET.",
|
||||
image: "/stickers/chart-crime.svg",
|
||||
},
|
||||
{
|
||||
label: "odds wizard",
|
||||
text: "I HAVE CONSULTED THE ODDS AND THEY SAID LOL.",
|
||||
image: "/stickers/odds-wizard.svg",
|
||||
},
|
||||
{
|
||||
label: "gif fan panic",
|
||||
kind: "gif",
|
||||
text: "LIVE FAN FOOTAGE AFTER HASHRATE MOVES BY A DECIMAL.",
|
||||
image: "/stickers/fan-panic.svg",
|
||||
},
|
||||
{
|
||||
label: "gif printer",
|
||||
kind: "gif",
|
||||
text: "FIAT POLICY IN ONE LOOP.",
|
||||
image: "/stickers/printer-loop.svg",
|
||||
},
|
||||
{
|
||||
label: "gif block hopium",
|
||||
kind: "gif",
|
||||
text: "SOLO MINER WATCHING EVERY NEW BLOCK LIKE IT OWES HIM MONEY.",
|
||||
image: "/stickers/block-hopium.svg",
|
||||
},
|
||||
{
|
||||
label: "gif heat death",
|
||||
kind: "gif",
|
||||
text: "THE ROOM IS WARMER THAN THE INVESTMENT THESIS.",
|
||||
image: "/stickers/heat-death.svg",
|
||||
},
|
||||
];
|
||||
|
||||
export function stickerContent(sticker: ChatSticker): string {
|
||||
return `${STICKER_PREFIX} ${sticker.kind === "gif" ? `${GIF_MARKER} ` : ""}${sticker.text}`;
|
||||
const image = sticker.image ? `${IMAGE_MARKER}${sticker.image}] ` : "";
|
||||
return `${STICKER_PREFIX} ${image}${sticker.kind === "gif" ? `${GIF_MARKER} ` : ""}${sticker.text}`;
|
||||
}
|
||||
|
||||
export function unsticker(content: string): { text: string; kind: "sticker" | "gif" } | null {
|
||||
export function unsticker(
|
||||
content: string,
|
||||
): { text: string; kind: "sticker" | "gif"; image?: string } | null {
|
||||
if (!content.startsWith(`${STICKER_PREFIX} `)) return null;
|
||||
const body = content.slice(STICKER_PREFIX.length + 1);
|
||||
if (body.startsWith(`${GIF_MARKER} `)) {
|
||||
return { text: body.slice(GIF_MARKER.length + 1), kind: "gif" };
|
||||
let body = content.slice(STICKER_PREFIX.length + 1);
|
||||
let image: string | undefined;
|
||||
if (body.startsWith(IMAGE_MARKER)) {
|
||||
const end = body.indexOf("] ");
|
||||
if (end > IMAGE_MARKER.length) {
|
||||
image = body.slice(IMAGE_MARKER.length, end);
|
||||
body = body.slice(end + 2);
|
||||
}
|
||||
}
|
||||
return { text: body, kind: "sticker" };
|
||||
if (body.startsWith(`${GIF_MARKER} `)) {
|
||||
const parsed = { text: body.slice(GIF_MARKER.length + 1), kind: "gif" as const };
|
||||
return image ? { ...parsed, image } : parsed;
|
||||
}
|
||||
const parsed = { text: body, kind: "sticker" as const };
|
||||
return image ? { ...parsed, image } : parsed;
|
||||
}
|
||||
|
||||
@@ -126,6 +126,10 @@ function stickerKind(content: string): "sticker" | "gif" | null {
|
||||
return unsticker(content)?.kind ?? null;
|
||||
}
|
||||
|
||||
function stickerImage(content: string): string | null {
|
||||
return unsticker(content)?.image ?? null;
|
||||
}
|
||||
|
||||
async function scrollBottom(): Promise<void> {
|
||||
await nextTick();
|
||||
if (listEl.value) listEl.value.scrollTop = listEl.value.scrollHeight;
|
||||
@@ -169,7 +173,10 @@ async function scrollBottom(): Promise<void> {
|
||||
<span>{{ timeLabel(message.createdAt) }}</span>
|
||||
</div>
|
||||
<p v-if="!stickerText(message.content)">{{ message.content }}</p>
|
||||
<p v-else :class="['sticker', stickerKind(message.content)]">{{ stickerText(message.content) }}</p>
|
||||
<div v-else :class="['sticker', stickerKind(message.content)]">
|
||||
<img v-if="stickerImage(message.content)" :src="stickerImage(message.content) || ''" alt="" />
|
||||
<span>{{ stickerText(message.content) }}</span>
|
||||
</div>
|
||||
</div>
|
||||
</article>
|
||||
</div>
|
||||
@@ -191,6 +198,7 @@ async function scrollBottom(): Promise<void> {
|
||||
:disabled="!canSend"
|
||||
@click="sendSticker(sticker)"
|
||||
>
|
||||
<img v-if="sticker.image" :src="sticker.image" alt="" />
|
||||
<span>{{ sticker.label }}</span>
|
||||
<small>{{ sticker.text }}</small>
|
||||
</button>
|
||||
@@ -235,10 +243,13 @@ async function scrollBottom(): Promise<void> {
|
||||
z-index: 20;
|
||||
width: min(430px, 92vw);
|
||||
height: 100dvh;
|
||||
--chat-pad: 16px;
|
||||
--composer-bottom: 24px;
|
||||
--composer-height: 70px;
|
||||
display: grid;
|
||||
grid-template-rows: auto auto minmax(0, 1fr) auto;
|
||||
grid-template-rows: auto auto minmax(0, 1fr);
|
||||
gap: 12px;
|
||||
padding: 16px 16px 28px;
|
||||
padding: var(--chat-pad);
|
||||
background: rgba(7, 9, 15, 0.97);
|
||||
border-left: 1px solid var(--line-bright);
|
||||
box-shadow: -16px 0 40px rgba(0, 0, 0, 0.45);
|
||||
@@ -289,6 +300,7 @@ h2 {
|
||||
flex-direction: column;
|
||||
gap: 14px;
|
||||
padding-right: 4px;
|
||||
padding-bottom: calc(var(--composer-height) + var(--composer-bottom) + 18px);
|
||||
}
|
||||
.empty {
|
||||
padding: 24px 0;
|
||||
@@ -355,7 +367,7 @@ p {
|
||||
overflow-wrap: anywhere;
|
||||
font-size: 12px;
|
||||
}
|
||||
p.sticker {
|
||||
.sticker {
|
||||
border: 1px solid var(--neon-magenta);
|
||||
color: var(--neon-amber);
|
||||
padding: 10px;
|
||||
@@ -364,19 +376,39 @@ p.sticker {
|
||||
text-transform: uppercase;
|
||||
box-shadow: inset 0 0 18px rgba(255, 61, 240, 0.08);
|
||||
}
|
||||
p.sticker.gif {
|
||||
.sticker img {
|
||||
display: block;
|
||||
width: min(220px, 100%);
|
||||
aspect-ratio: 1 / 1;
|
||||
height: auto;
|
||||
margin-bottom: 8px;
|
||||
border: 1px solid var(--line-bright);
|
||||
object-fit: contain;
|
||||
background: var(--bg-0);
|
||||
}
|
||||
.sticker span {
|
||||
display: block;
|
||||
white-space: pre-wrap;
|
||||
overflow-wrap: anywhere;
|
||||
}
|
||||
.sticker.gif {
|
||||
animation: sticker-bounce 1.4s steps(2, end) infinite;
|
||||
background:
|
||||
linear-gradient(90deg, rgba(255, 61, 240, 0.12), rgba(41, 255, 230, 0.08)),
|
||||
rgba(255, 255, 255, 0.025);
|
||||
}
|
||||
.composer {
|
||||
position: fixed;
|
||||
right: var(--chat-pad);
|
||||
bottom: var(--composer-bottom);
|
||||
z-index: 4;
|
||||
width: calc(min(430px, 92vw) - (var(--chat-pad) * 2));
|
||||
min-height: var(--composer-height);
|
||||
display: grid;
|
||||
grid-template-columns: 78px minmax(0, 1fr) 64px;
|
||||
gap: 8px;
|
||||
align-items: start;
|
||||
padding-top: 10px;
|
||||
padding-bottom: 2px;
|
||||
border-top: 1px solid var(--line);
|
||||
background: rgba(7, 9, 15, 0.97);
|
||||
}
|
||||
@@ -424,7 +456,7 @@ p.sticker.gif {
|
||||
}
|
||||
.sticker-tray button {
|
||||
min-width: 0;
|
||||
min-height: 74px;
|
||||
min-height: 138px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 5px;
|
||||
@@ -437,6 +469,14 @@ p.sticker.gif {
|
||||
text-align: left;
|
||||
overflow-wrap: anywhere;
|
||||
}
|
||||
.sticker-tray button img {
|
||||
width: 100%;
|
||||
aspect-ratio: 1 / 1;
|
||||
max-height: 118px;
|
||||
object-fit: contain;
|
||||
border: 1px solid var(--line);
|
||||
background: var(--bg-0);
|
||||
}
|
||||
.sticker-tray button span {
|
||||
color: var(--neon-cyan);
|
||||
}
|
||||
@@ -488,6 +528,8 @@ textarea {
|
||||
width: 100vw;
|
||||
height: 100svh;
|
||||
max-height: none;
|
||||
--chat-pad: 14px;
|
||||
grid-template-rows: auto auto minmax(0, 1fr) auto;
|
||||
padding: 14px 14px calc(72px + env(safe-area-inset-bottom));
|
||||
transform: translateY(105%);
|
||||
border-left: 0;
|
||||
@@ -498,8 +540,11 @@ textarea {
|
||||
}
|
||||
.messages {
|
||||
gap: 10px;
|
||||
padding-bottom: 0;
|
||||
}
|
||||
.composer {
|
||||
position: static;
|
||||
width: auto;
|
||||
grid-template-columns: 72px minmax(0, 1fr) 58px;
|
||||
gap: 6px;
|
||||
}
|
||||
|
||||