Compare commits
2 commits
e0fa242e69
...
e3ce3c90c7
Author | SHA1 | Date | |
---|---|---|---|
e3ce3c90c7 | |||
9f3351292b |
15 changed files with 296 additions and 262 deletions
|
@ -6,6 +6,19 @@ export const marquee_container = style({
|
||||||
height: 'max-content',
|
height: 'max-content',
|
||||||
overflow: 'hidden',
|
overflow: 'hidden',
|
||||||
backgroundColor: 'black',
|
backgroundColor: 'black',
|
||||||
|
fontSize: '0.75em',
|
||||||
|
'@media': {
|
||||||
|
'screen and (min-width: 768px)': {
|
||||||
|
fontSize: '1em',
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
export const marquee_sneaky = style({
|
||||||
|
position: 'absolute',
|
||||||
|
visibility: 'hidden',
|
||||||
|
whiteSpace: 'pre',
|
||||||
|
width: 'max-content',
|
||||||
});
|
});
|
||||||
|
|
||||||
const scroll_marquee = keyframes({
|
const scroll_marquee = keyframes({
|
||||||
|
@ -15,16 +28,11 @@ const scroll_marquee = keyframes({
|
||||||
|
|
||||||
export const marquee_content = style({
|
export const marquee_content = style({
|
||||||
position: 'relative',
|
position: 'relative',
|
||||||
fontSize: '0.75em',
|
|
||||||
color: 'magenta',
|
color: 'magenta',
|
||||||
whiteSpace: 'nowrap',
|
whiteSpace: 'pre',
|
||||||
|
width: 'max-content',
|
||||||
animationName: scroll_marquee,
|
animationName: scroll_marquee,
|
||||||
animationDuration: '8s',
|
animationDuration: '2s',
|
||||||
animationTimingFunction: 'linear',
|
animationTimingFunction: 'linear',
|
||||||
animationIterationCount: 'infinite',
|
animationIterationCount: 'infinite',
|
||||||
'@media': {
|
|
||||||
'screen and (min-width: 768px)': {
|
|
||||||
fontSize: '1em',
|
|
||||||
}
|
|
||||||
}
|
|
||||||
});
|
});
|
||||||
|
|
|
@ -1,13 +1,47 @@
|
||||||
import {
|
'use client'
|
||||||
marquee_container,
|
|
||||||
marquee_content,
|
import { useRef, useEffect, useLayoutEffect } from 'react';
|
||||||
} from './Marquee.css';
|
|
||||||
|
import * as style from './Marquee.css';
|
||||||
|
|
||||||
export default function Marquee({ children }: { children: React.ReactNode }) {
|
export default function Marquee({ children }: { children: React.ReactNode }) {
|
||||||
|
const target_ref = useRef<HTMLDivElement | null>(null);
|
||||||
|
const scroll_ref = useRef<HTMLDivElement | null>(null);
|
||||||
|
const sneaky_ref = useRef<HTMLParagraphElement | null>(null);
|
||||||
|
const not_so_sneaky_ref = useRef<HTMLParagraphElement | null>(null);
|
||||||
|
|
||||||
|
function expand_content() {
|
||||||
|
function strip_px(px: string) {
|
||||||
|
return Number(px.substring(0, px.length - 2));
|
||||||
|
}
|
||||||
|
const text = `${children}`;
|
||||||
|
let content = text;
|
||||||
|
const sneaky_width = strip_px(window.getComputedStyle(sneaky_ref.current!).getPropertyValue("width"));
|
||||||
|
let target_width = strip_px(window.getComputedStyle(target_ref.current!).getPropertyValue("width"));
|
||||||
|
while (target_width > 0) {
|
||||||
|
content += text;
|
||||||
|
target_width -= sneaky_width;
|
||||||
|
}
|
||||||
|
scroll_ref.current!.style.width = `${sneaky_width}px`;
|
||||||
|
not_so_sneaky_ref.current!.textContent = content;
|
||||||
|
}
|
||||||
|
|
||||||
|
useLayoutEffect(expand_content);
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
window.addEventListener("resize", expand_content);
|
||||||
|
|
||||||
|
return () => {
|
||||||
|
window.removeEventListener("resize", expand_content);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div className={marquee_container}>
|
<div ref={target_ref} className={style.marquee_container}>
|
||||||
<p className={marquee_content}>{children}</p>
|
<p ref={sneaky_ref} className={style.marquee_sneaky}>{children}</p>
|
||||||
<p className={marquee_content}>{children}</p>
|
<div ref={scroll_ref}>
|
||||||
|
<p ref={not_so_sneaky_ref} className={style.marquee_content}></p>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
17
src/app/airstrip_one/0/layout.css.ts
Normal file
17
src/app/airstrip_one/0/layout.css.ts
Normal file
|
@ -0,0 +1,17 @@
|
||||||
|
import { style } from '@vanilla-extract/css';
|
||||||
|
|
||||||
|
export const center_vertical = style({
|
||||||
|
position: 'relative',
|
||||||
|
display: 'flex',
|
||||||
|
flexDirection: 'column',
|
||||||
|
alignItems: 'center',
|
||||||
|
margin: 'auto',
|
||||||
|
width: '100%',
|
||||||
|
border: '0.3em solid purple',
|
||||||
|
'@media': {
|
||||||
|
'screen and (min-width: 768px)': {
|
||||||
|
width: '50%',
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
13
src/app/airstrip_one/0/layout.tsx
Normal file
13
src/app/airstrip_one/0/layout.tsx
Normal file
|
@ -0,0 +1,13 @@
|
||||||
|
import Marquee from './components/Marquee';
|
||||||
|
|
||||||
|
import * as style from './layout.css';
|
||||||
|
|
||||||
|
export default function ExcellentLayout({ children }: { children: React.ReactNode }) {
|
||||||
|
return (
|
||||||
|
<div className={style.center_vertical}>
|
||||||
|
<Marquee>THE SNACK IS WATCHING YOU </Marquee>
|
||||||
|
{children}
|
||||||
|
<Marquee>THE SNACK IS WATCHING YOU </Marquee>
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
}
|
|
@ -1,4 +1,4 @@
|
||||||
import { style } from "@vanilla-extract/css";
|
import { style } from '@vanilla-extract/css';
|
||||||
|
|
||||||
export const message_style = style({
|
export const message_style = style({
|
||||||
boxSizing: 'border-box',
|
boxSizing: 'border-box',
|
||||||
|
@ -8,10 +8,12 @@ export const message_style = style({
|
||||||
border: 'none',
|
border: 'none',
|
||||||
padding: '0.5em',
|
padding: '0.5em',
|
||||||
fontSize: '1em',
|
fontSize: '1em',
|
||||||
|
fontFamily: 'inherit',
|
||||||
color: 'magenta',
|
color: 'magenta',
|
||||||
backgroundColor: 'black',
|
backgroundColor: 'black',
|
||||||
overflowWrap: 'break-word',
|
overflowWrap: 'break-word',
|
||||||
textAlign: 'center',
|
textAlign: 'center',
|
||||||
|
resize: 'none',
|
||||||
':focus': {
|
':focus': {
|
||||||
outline: 'none',
|
outline: 'none',
|
||||||
},
|
},
|
||||||
|
|
|
@ -1,8 +1,9 @@
|
||||||
'use client'
|
'use client'
|
||||||
|
|
||||||
import { useEffect, useRef } from 'react';
|
import { useRef, useEffect, useLayoutEffect } from 'react';
|
||||||
import { useSearchParams } from 'next/navigation';
|
import { useSearchParams } from 'next/navigation';
|
||||||
|
|
||||||
|
import comic_sans from '../../../../comic.ts';
|
||||||
import { message_style } from '../components/Input.css';
|
import { message_style } from '../components/Input.css';
|
||||||
|
|
||||||
export default function Input() {
|
export default function Input() {
|
||||||
|
@ -13,6 +14,8 @@ export default function Input() {
|
||||||
const encoded = btoa(message);
|
const encoded = btoa(message);
|
||||||
const new_url = `${window.location.protocol}//${window.location.host}${window.location.pathname}?e=${encoded}`;
|
const new_url = `${window.location.protocol}//${window.location.host}${window.location.pathname}?e=${encoded}`;
|
||||||
window.history.replaceState(null, '', new_url);
|
window.history.replaceState(null, '', new_url);
|
||||||
|
input_ref.current!.style.height = "";
|
||||||
|
input_ref.current!.style.height = `${input_ref.current!.scrollHeight}px`;
|
||||||
}
|
}
|
||||||
|
|
||||||
const message = search_params.get('e') ?
|
const message = search_params.get('e') ?
|
||||||
|
@ -23,17 +26,30 @@ export default function Input() {
|
||||||
);
|
);
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
|
function resize_handler() {
|
||||||
|
input_ref.current!.style.height = "";
|
||||||
|
input_ref.current!.style.height = `${input_ref.current!.scrollHeight}px`;
|
||||||
|
}
|
||||||
|
|
||||||
|
window.addEventListener("resize", resize_handler);
|
||||||
|
|
||||||
|
return () => {
|
||||||
|
window.removeEventListener("resize", resize_handler);
|
||||||
|
};
|
||||||
|
});
|
||||||
|
|
||||||
|
useLayoutEffect(() => {
|
||||||
set_message(message);
|
set_message(message);
|
||||||
});
|
});
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<p
|
<textarea
|
||||||
ref={input_ref}
|
ref={input_ref}
|
||||||
className={message_style}
|
className={message_style}
|
||||||
|
type="text"
|
||||||
|
rows="1"
|
||||||
onInput={() => set_message(input_ref.current!.textContent ?? '')}
|
onInput={() => set_message(input_ref.current!.textContent ?? '')}
|
||||||
contentEditable
|
defaultValue={message}
|
||||||
>
|
/>
|
||||||
{message}
|
|
||||||
</p>
|
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,21 +1,5 @@
|
||||||
import { keyframes, style } from "@vanilla-extract/css";
|
import { keyframes, style } from "@vanilla-extract/css";
|
||||||
|
|
||||||
export const center_vertical = style({
|
|
||||||
boxSizing: 'border-box',
|
|
||||||
position: 'relative',
|
|
||||||
display: 'flex',
|
|
||||||
flexDirection: 'column',
|
|
||||||
alignItems: 'center',
|
|
||||||
margin: 'auto',
|
|
||||||
width: '100%',
|
|
||||||
border: '0.3em solid purple',
|
|
||||||
'@media': {
|
|
||||||
'screen and (min-width: 768px)': {
|
|
||||||
width: '50%',
|
|
||||||
}
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
export const border = style({
|
export const border = style({
|
||||||
width: '61%',
|
width: '61%',
|
||||||
marginBottom: '4em',
|
marginBottom: '4em',
|
||||||
|
|
|
@ -1,26 +1,17 @@
|
||||||
import React from 'react';
|
import React from 'react';
|
||||||
import Image from 'next/image';
|
import Image from 'next/image';
|
||||||
import BeegText from '../components/BeegText';
|
import BeegText from '../components/BeegText';
|
||||||
import Marquee from '../components/Marquee';
|
|
||||||
import Input from './components/Input';
|
import Input from './components/Input';
|
||||||
import {
|
import * as style from './page.css';
|
||||||
center_vertical,
|
|
||||||
border,
|
|
||||||
big_brother_style,
|
|
||||||
} from './page.css';
|
|
||||||
|
|
||||||
export default function Home() {
|
export default function Home() {
|
||||||
return (
|
return <>
|
||||||
<div className={center_vertical}>
|
|
||||||
<Marquee>THE SNACK IS WATCHING YOU THE SNACK IS WATCHING YOU THE SNACK IS WATCHING YOU THE SNACK IS WATCHING YOU THE SNACK IS WATCHING YOU THE SNACK IS WATCHING YOU THE SNACK IS WATCHING YOU THE SNACK IS WATCHING YOU </Marquee>
|
|
||||||
<BeegText>THE MINISTRY OF TRUTH</BeegText>
|
<BeegText>THE MINISTRY OF TRUTH</BeegText>
|
||||||
<div className={border}>
|
<div className={style.border}>
|
||||||
<Image className={big_brother_style} width={400} height={300} src='/big_brother_screen.gif' alt='Big Brother' />
|
<Image className={style.big_brother_style} width={400} height={300} src='/big_brother_screen.gif' alt='Big Brother' />
|
||||||
<React.Suspense>
|
<React.Suspense>
|
||||||
<Input />
|
<Input />
|
||||||
</React.Suspense>
|
</React.Suspense>
|
||||||
</div>
|
</div>
|
||||||
<Marquee>THE SNACK IS WATCHING YOU THE SNACK IS WATCHING YOU THE SNACK IS WATCHING YOU THE SNACK IS WATCHING YOU THE SNACK IS WATCHING YOU THE SNACK IS WATCHING YOU THE SNACK IS WATCHING YOU THE SNACK IS WATCHING YOU </Marquee>
|
</>;
|
||||||
</div>
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,20 +1,5 @@
|
||||||
import { keyframes, style } from "@vanilla-extract/css";
|
import { keyframes, style } from "@vanilla-extract/css";
|
||||||
|
|
||||||
export const center_vertical = style({
|
|
||||||
position: 'relative',
|
|
||||||
display: 'flex',
|
|
||||||
flexDirection: 'column',
|
|
||||||
alignItems: 'center',
|
|
||||||
margin: 'auto',
|
|
||||||
width: '100%',
|
|
||||||
border: '0.3em solid purple',
|
|
||||||
'@media': {
|
|
||||||
'screen and (min-width: 768px)': {
|
|
||||||
width: '50%',
|
|
||||||
}
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
export const big_brother_style = style({
|
export const big_brother_style = style({
|
||||||
width: '60%',
|
width: '60%',
|
||||||
height: 'auto',
|
height: 'auto',
|
||||||
|
|
|
@ -1,41 +1,29 @@
|
||||||
import { Metadata } from 'next'
|
import { Metadata } from 'next';
|
||||||
import Image from 'next/image'
|
import Image from 'next/image';
|
||||||
import Marquee from './components/Marquee'
|
import BeegText from './components/BeegText';
|
||||||
import BeegText from './components/BeegText'
|
import * as style from './page.css';
|
||||||
import {
|
|
||||||
center_vertical,
|
|
||||||
big_brother_style,
|
|
||||||
cats_div,
|
|
||||||
subcats_div,
|
|
||||||
reverse_subcats_div,
|
|
||||||
cat,
|
|
||||||
} from './page.css'
|
|
||||||
|
|
||||||
export const metadata: Metadata = {
|
export const metadata: Metadata = {
|
||||||
title: 'The Snack is Watching You',
|
title: 'The Snack is Watching You',
|
||||||
description: 'The Snack is Watching You',
|
description: 'The Snack is Watching You',
|
||||||
}
|
};
|
||||||
|
|
||||||
export default function Home() {
|
export default function Home() {
|
||||||
return (
|
return <>
|
||||||
<div className={center_vertical}>
|
|
||||||
<Marquee>THE SNACK IS WATCHING YOU THE SNACK IS WATCHING YOU THE SNACK IS WATCHING YOU THE SNACK IS WATCHING YOU THE SNACK IS WATCHING YOU THE SNACK IS WATCHING YOU THE SNACK IS WATCHING YOU THE SNACK IS WATCHING YOU </Marquee>
|
|
||||||
<BeegText>THE SNACK IS</BeegText>
|
<BeegText>THE SNACK IS</BeegText>
|
||||||
<Image className={big_brother_style} width={256} height={256} src='/big_brother.png' alt='Big Brother' />
|
<Image className={style.big_brother_style} width={256} height={256} src='/big_brother.png' alt='Big Brother' />
|
||||||
<BeegText>WATCHING YOU</BeegText>
|
<BeegText>WATCHING YOU</BeegText>
|
||||||
<div className={cats_div}>
|
<div className={style.cats_div}>
|
||||||
<div className={subcats_div}>
|
<div className={style.subcats_div}>
|
||||||
<Image className={cat} width={128} height={128} src='/praising_cat.gif' alt='Cat praising Big Brother' />
|
<Image className={style.cat} width={128} height={128} src='/praising_cat.gif' alt='Cat praising Big Brother' />
|
||||||
<Image className={cat} width={128} height={128} src='/praising_cat.gif' alt='Cat praising Big Brother' />
|
<Image className={style.cat} width={128} height={128} src='/praising_cat.gif' alt='Cat praising Big Brother' />
|
||||||
<Image className={cat} width={128} height={128} src='/praising_cat.gif' alt='Cat praising Big Brother' />
|
<Image className={style.cat} width={128} height={128} src='/praising_cat.gif' alt='Cat praising Big Brother' />
|
||||||
</div>
|
</div>
|
||||||
<div className={reverse_subcats_div}>
|
<div className={style.reverse_subcats_div}>
|
||||||
<Image className={cat} width={128} height={128} src='/praising_cat.gif' alt='Cat praising Big Brother' />
|
<Image className={style.cat} width={128} height={128} src='/praising_cat.gif' alt='Cat praising Big Brother' />
|
||||||
<Image className={cat} width={128} height={128} src='/praising_cat.gif' alt='Cat praising Big Brother' />
|
<Image className={style.cat} width={128} height={128} src='/praising_cat.gif' alt='Cat praising Big Brother' />
|
||||||
<Image className={cat} width={128} height={128} src='/praising_cat.gif' alt='Cat praising Big Brother' />
|
<Image className={style.cat} width={128} height={128} src='/praising_cat.gif' alt='Cat praising Big Brother' />
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<Marquee>THE SNACK IS WATCHING YOU THE SNACK IS WATCHING YOU THE SNACK IS WATCHING YOU THE SNACK IS WATCHING YOU THE SNACK IS WATCHING YOU THE SNACK IS WATCHING YOU THE SNACK IS WATCHING YOU THE SNACK IS WATCHING YOU </Marquee>
|
</>;
|
||||||
</div>
|
|
||||||
)
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -7,11 +7,7 @@ const comic_sans = localFont({
|
||||||
weight: '100',
|
weight: '100',
|
||||||
});
|
});
|
||||||
|
|
||||||
export default function RootLayout({
|
export default function RootLayout({ children }: { children: React.ReactNode }) {
|
||||||
children,
|
|
||||||
}: {
|
|
||||||
children: React.ReactNode
|
|
||||||
}) {
|
|
||||||
return (
|
return (
|
||||||
<html lang="en">
|
<html lang="en">
|
||||||
<body className={comic_sans.className}>{children}</body>
|
<body className={comic_sans.className}>{children}</body>
|
||||||
|
|
Loading…
Reference in a new issue