tabor web
This commit is contained in:
parent
3bf72345fc
commit
773d65d95a
19 changed files with 8577 additions and 9 deletions
19
index.html
19
index.html
|
@ -1,11 +1,12 @@
|
||||||
<!DOCTYPE html>
|
<!DOCTYPE html>
|
||||||
<html>
|
<html lang="en">
|
||||||
<body>
|
<head>
|
||||||
|
<meta charset="UTF-8" />
|
||||||
<h1>My First Heading</h1>
|
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||||
|
<title>Dětský stanový tábor ve Střílkách</title>
|
||||||
<p>My first paragraph.</p>
|
</head>
|
||||||
|
<body>
|
||||||
</body>
|
<div id="root"></div>
|
||||||
|
<script type="module" src="/src/main.tsx"></script>
|
||||||
|
</body>
|
||||||
</html>
|
</html>
|
||||||
|
|
||||||
|
|
8222
package-lock.json
generated
Normal file
8222
package-lock.json
generated
Normal file
File diff suppressed because it is too large
Load diff
38
package.json
Normal file
38
package.json
Normal file
|
@ -0,0 +1,38 @@
|
||||||
|
{
|
||||||
|
"name": "frontend",
|
||||||
|
"private": true,
|
||||||
|
"version": "0.0.0",
|
||||||
|
"type": "module",
|
||||||
|
"scripts": {
|
||||||
|
"dev": "vite",
|
||||||
|
"build": "tsc && vite build",
|
||||||
|
"lint": "eslint src --ext ts,tsx --report-unused-disable-directives --max-warnings 0",
|
||||||
|
"preview": "vite preview",
|
||||||
|
"setup": "node ./contentful/setup.cjs"
|
||||||
|
},
|
||||||
|
"dependencies": {
|
||||||
|
"@contentful/rich-text-react-renderer": "^15.17.0",
|
||||||
|
"@emotion/react": "^11.11.1",
|
||||||
|
"@emotion/styled": "^11.11.0",
|
||||||
|
"@fontsource/roboto": "^5.0.3",
|
||||||
|
"@mui/material": "^5.13.5",
|
||||||
|
"contentful": "^10.2.4",
|
||||||
|
"contentful-import": "^8.5.57",
|
||||||
|
"dotenv": "^16.1.4",
|
||||||
|
"react": "^18.2.0",
|
||||||
|
"react-dom": "^18.2.0",
|
||||||
|
"react-router-dom": "^6.12.1"
|
||||||
|
},
|
||||||
|
"devDependencies": {
|
||||||
|
"@types/react": "^18.0.37",
|
||||||
|
"@types/react-dom": "^18.0.11",
|
||||||
|
"@typescript-eslint/eslint-plugin": "^5.59.0",
|
||||||
|
"@typescript-eslint/parser": "^5.59.0",
|
||||||
|
"@vitejs/plugin-react": "^4.0.0",
|
||||||
|
"eslint": "^8.38.0",
|
||||||
|
"eslint-plugin-react-hooks": "^4.6.0",
|
||||||
|
"eslint-plugin-react-refresh": "^0.3.4",
|
||||||
|
"typescript": "^5.0.2",
|
||||||
|
"vite": "^4.3.9"
|
||||||
|
}
|
||||||
|
}
|
0
public/.gitkeep
Normal file
0
public/.gitkeep
Normal file
1
public/_redirects
Normal file
1
public/_redirects
Normal file
|
@ -0,0 +1 @@
|
||||||
|
/* /index.html 200
|
42
src/App.css
Normal file
42
src/App.css
Normal file
|
@ -0,0 +1,42 @@
|
||||||
|
#root {
|
||||||
|
max-width: 1280px;
|
||||||
|
margin: 0 auto;
|
||||||
|
padding: 2rem;
|
||||||
|
text-align: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
.logo {
|
||||||
|
height: 6em;
|
||||||
|
padding: 1.5em;
|
||||||
|
will-change: filter;
|
||||||
|
transition: filter 300ms;
|
||||||
|
}
|
||||||
|
.logo:hover {
|
||||||
|
filter: drop-shadow(0 0 2em #646cffaa);
|
||||||
|
}
|
||||||
|
.logo.react:hover {
|
||||||
|
filter: drop-shadow(0 0 2em #61dafbaa);
|
||||||
|
}
|
||||||
|
|
||||||
|
@keyframes logo-spin {
|
||||||
|
from {
|
||||||
|
transform: rotate(0deg);
|
||||||
|
}
|
||||||
|
to {
|
||||||
|
transform: rotate(360deg);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@media (prefers-reduced-motion: no-preference) {
|
||||||
|
a:nth-of-type(2) .logo {
|
||||||
|
animation: logo-spin infinite 20s linear;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.card {
|
||||||
|
padding: 2em;
|
||||||
|
}
|
||||||
|
|
||||||
|
.read-the-docs {
|
||||||
|
color: #888;
|
||||||
|
}
|
89
src/App.tsx
Normal file
89
src/App.tsx
Normal file
|
@ -0,0 +1,89 @@
|
||||||
|
import "./App.css";
|
||||||
|
import Page from "./containers/Page/Page";
|
||||||
|
import { LandingPageSkeleton } from "../types/contentful";
|
||||||
|
import { Entry, createClient } from "contentful";
|
||||||
|
import MainNav from "./containers/MainNav/MainNav";
|
||||||
|
import { useEffect, useState } from "react";
|
||||||
|
import { createBrowserRouter, RouterProvider } from "react-router-dom";
|
||||||
|
|
||||||
|
function App() {
|
||||||
|
const [contentfuldata, setData] =
|
||||||
|
useState<Entry<LandingPageSkeleton, undefined, string>[]>();
|
||||||
|
|
||||||
|
const client = createClient({
|
||||||
|
space: import.meta.env.VITE_CONTENTFUL_SPACE_ID,
|
||||||
|
accessToken: import.meta.env.VITE_CONTENTFUL_DELIVERY_TOKEN,
|
||||||
|
});
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
const ass = async () => {
|
||||||
|
const response = await client.getEntries<LandingPageSkeleton>({
|
||||||
|
content_type: "landing-page",
|
||||||
|
});
|
||||||
|
console.log(response.items);
|
||||||
|
return setData(response.items);
|
||||||
|
};
|
||||||
|
|
||||||
|
ass();
|
||||||
|
}, []);
|
||||||
|
|
||||||
|
if (contentfuldata === null || contentfuldata === undefined) {
|
||||||
|
return <></>;
|
||||||
|
}
|
||||||
|
|
||||||
|
const current = contentfuldata.filter(
|
||||||
|
(n) => n.sys.id !== "7IShhDv8NE55WfsQf4RKuW"
|
||||||
|
)[0];
|
||||||
|
const prihlaska = contentfuldata.filter(
|
||||||
|
(n) => n.sys.id === "7IShhDv8NE55WfsQf4RKuW"
|
||||||
|
)[0];
|
||||||
|
|
||||||
|
const router = createBrowserRouter(
|
||||||
|
[
|
||||||
|
{
|
||||||
|
path: "/",
|
||||||
|
element: (
|
||||||
|
<Page title={current.fields.title} content={current.fields.content} />
|
||||||
|
),
|
||||||
|
},
|
||||||
|
{
|
||||||
|
path: "/prihlaska",
|
||||||
|
element: (
|
||||||
|
<Page
|
||||||
|
title={prihlaska.fields.title}
|
||||||
|
content={prihlaska.fields.content}
|
||||||
|
/>
|
||||||
|
),
|
||||||
|
},
|
||||||
|
{
|
||||||
|
element: <h1>Stránka nenalezena.</h1>,
|
||||||
|
path: "*",
|
||||||
|
},
|
||||||
|
],
|
||||||
|
{
|
||||||
|
basename: import.meta.env.VITE_BASENAME,
|
||||||
|
}
|
||||||
|
);
|
||||||
|
|
||||||
|
return (
|
||||||
|
<>
|
||||||
|
<MainNav />
|
||||||
|
<div
|
||||||
|
style={{
|
||||||
|
backgroundColor: "#ffe6b8",
|
||||||
|
padding: "1rem",
|
||||||
|
marginBlockStart: "2rem",
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
Naše webové stránky jsou v rekonstrukci, děkujeme za trpělivost. V
|
||||||
|
případě dotazů prosím kontaktuje hlavního vedoucího <b>Karla Košnara</b>{" "}
|
||||||
|
na emailové adrese <b>karel.kosnar (zavináč) gmail.com</b> nebo na
|
||||||
|
telefonu <b>608 906 987</b>.
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<RouterProvider router={router} />
|
||||||
|
</>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
export default App;
|
4
src/components/LinkButton/LinkButton.module.css
Normal file
4
src/components/LinkButton/LinkButton.module.css
Normal file
|
@ -0,0 +1,4 @@
|
||||||
|
.link {
|
||||||
|
padding: 1rem;
|
||||||
|
display: inline-block;
|
||||||
|
}
|
19
src/components/LinkButton/LinkButton.tsx
Normal file
19
src/components/LinkButton/LinkButton.tsx
Normal file
|
@ -0,0 +1,19 @@
|
||||||
|
import styles from "./LinkButton.module.css";
|
||||||
|
|
||||||
|
interface LinkButtonInterface {
|
||||||
|
text: string;
|
||||||
|
link: string;
|
||||||
|
type?: string;
|
||||||
|
}
|
||||||
|
|
||||||
|
const LinkButton = ({ text, link, type }: LinkButtonInterface) => {
|
||||||
|
return (
|
||||||
|
<div className={styles.link}>
|
||||||
|
<a className={type} href={link}>
|
||||||
|
{text}
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
};
|
||||||
|
|
||||||
|
export default LinkButton;
|
5
src/containers/MainNav/MainNav.module.css
Normal file
5
src/containers/MainNav/MainNav.module.css
Normal file
|
@ -0,0 +1,5 @@
|
||||||
|
.title {
|
||||||
|
font-size: 1.5rem;
|
||||||
|
font-weight: bold;
|
||||||
|
color: darkgreen;
|
||||||
|
}
|
19
src/containers/MainNav/MainNav.tsx
Normal file
19
src/containers/MainNav/MainNav.tsx
Normal file
|
@ -0,0 +1,19 @@
|
||||||
|
import styles from "./MainNav.module.css";
|
||||||
|
|
||||||
|
const MainNav = () => {
|
||||||
|
return (
|
||||||
|
<>
|
||||||
|
<div className={styles.title}>Dětský stanový tábor ve Střílkách</div>
|
||||||
|
|
||||||
|
<nav>
|
||||||
|
{/* <LinkButton text="Přihláška" link="" />
|
||||||
|
<LinkButton text="Filozofie" link="" />
|
||||||
|
<LinkButton text="Tým" link="" />
|
||||||
|
<LinkButton text="Minulé tábory" link="" />
|
||||||
|
<LinkButton text="Kontakt" link="" /> */}
|
||||||
|
</nav>
|
||||||
|
</>
|
||||||
|
);
|
||||||
|
};
|
||||||
|
|
||||||
|
export default MainNav;
|
18
src/containers/Page/Page.module.css
Normal file
18
src/containers/Page/Page.module.css
Normal file
|
@ -0,0 +1,18 @@
|
||||||
|
.poster {
|
||||||
|
max-width: min(100%, 30rem);
|
||||||
|
margin: 0 auto;
|
||||||
|
}
|
||||||
|
|
||||||
|
.content {
|
||||||
|
max-width: 50rem;
|
||||||
|
margin-left: auto;
|
||||||
|
margin-right: auto;
|
||||||
|
}
|
||||||
|
|
||||||
|
.content * {
|
||||||
|
text-align: left;
|
||||||
|
}
|
||||||
|
|
||||||
|
.content image {
|
||||||
|
text-align: center;
|
||||||
|
}
|
41
src/containers/Page/Page.tsx
Normal file
41
src/containers/Page/Page.tsx
Normal file
|
@ -0,0 +1,41 @@
|
||||||
|
import styles from "./Page.module.css";
|
||||||
|
import { documentToReactComponents } from "@contentful/rich-text-react-renderer";
|
||||||
|
|
||||||
|
import { BLOCKS } from "@contentful/rich-text-types";
|
||||||
|
|
||||||
|
interface InvitationBlockInterface {
|
||||||
|
title: string;
|
||||||
|
content: any;
|
||||||
|
}
|
||||||
|
|
||||||
|
const InvitationBlock = ({ title, content }: InvitationBlockInterface) => {
|
||||||
|
return (
|
||||||
|
<>
|
||||||
|
<div>
|
||||||
|
<h1>{title}</h1>
|
||||||
|
<div className={styles.content}>
|
||||||
|
{documentToReactComponents(content, {
|
||||||
|
renderText: (text) => {
|
||||||
|
return text.split("\n").reduce((lines, textSegment, index) => {
|
||||||
|
return [...lines, index > 0 && <br key={index} />, textSegment];
|
||||||
|
}, new Array()); // eslint-disable-line @typescript-eslint/no-array-constructor
|
||||||
|
},
|
||||||
|
renderNode: {
|
||||||
|
[BLOCKS.EMBEDDED_ASSET]: (node) => {
|
||||||
|
return (
|
||||||
|
<img
|
||||||
|
src={`https://${node.data.target.fields.file.url}`}
|
||||||
|
alt={node.data.target.fields.description}
|
||||||
|
className={styles.poster}
|
||||||
|
/>
|
||||||
|
);
|
||||||
|
},
|
||||||
|
},
|
||||||
|
})}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</>
|
||||||
|
);
|
||||||
|
};
|
||||||
|
|
||||||
|
export default InvitationBlock;
|
17
src/main.tsx
Normal file
17
src/main.tsx
Normal file
|
@ -0,0 +1,17 @@
|
||||||
|
import React from "react";
|
||||||
|
import ReactDOM from "react-dom/client";
|
||||||
|
import App from "./App.tsx";
|
||||||
|
|
||||||
|
import "@fontsource/roboto/300.css";
|
||||||
|
import "@fontsource/roboto/400.css";
|
||||||
|
import "@fontsource/roboto/500.css";
|
||||||
|
import "@fontsource/roboto/700.css";
|
||||||
|
|
||||||
|
import CssBaseline from "@mui/material/CssBaseline";
|
||||||
|
|
||||||
|
ReactDOM.createRoot(document.getElementById("root") as HTMLElement).render(
|
||||||
|
<React.StrictMode>
|
||||||
|
<CssBaseline />
|
||||||
|
<App />
|
||||||
|
</React.StrictMode>
|
||||||
|
);
|
1
src/vite-env.d.ts
vendored
Normal file
1
src/vite-env.d.ts
vendored
Normal file
|
@ -0,0 +1 @@
|
||||||
|
/// <reference types="vite/client" />
|
25
tsconfig.json
Normal file
25
tsconfig.json
Normal file
|
@ -0,0 +1,25 @@
|
||||||
|
{
|
||||||
|
"compilerOptions": {
|
||||||
|
"target": "ES2020",
|
||||||
|
"useDefineForClassFields": true,
|
||||||
|
"lib": ["ES2020", "DOM", "DOM.Iterable"],
|
||||||
|
"module": "ESNext",
|
||||||
|
"skipLibCheck": true,
|
||||||
|
|
||||||
|
/* Bundler mode */
|
||||||
|
"moduleResolution": "bundler",
|
||||||
|
"allowImportingTsExtensions": true,
|
||||||
|
"resolveJsonModule": true,
|
||||||
|
"isolatedModules": true,
|
||||||
|
"noEmit": true,
|
||||||
|
"jsx": "react-jsx",
|
||||||
|
|
||||||
|
/* Linting */
|
||||||
|
"strict": true,
|
||||||
|
"noUnusedLocals": true,
|
||||||
|
"noUnusedParameters": true,
|
||||||
|
"noFallthroughCasesInSwitch": true
|
||||||
|
},
|
||||||
|
"include": ["src"],
|
||||||
|
"references": [{ "path": "./tsconfig.node.json" }]
|
||||||
|
}
|
10
tsconfig.node.json
Normal file
10
tsconfig.node.json
Normal file
|
@ -0,0 +1,10 @@
|
||||||
|
{
|
||||||
|
"compilerOptions": {
|
||||||
|
"composite": true,
|
||||||
|
"skipLibCheck": true,
|
||||||
|
"module": "ESNext",
|
||||||
|
"moduleResolution": "bundler",
|
||||||
|
"allowSyntheticDefaultImports": true
|
||||||
|
},
|
||||||
|
"include": ["vite.config.ts"]
|
||||||
|
}
|
9
types/contentful.tsx
Normal file
9
types/contentful.tsx
Normal file
|
@ -0,0 +1,9 @@
|
||||||
|
import contentful from "contentful";
|
||||||
|
|
||||||
|
export type LandingPageSkeleton = {
|
||||||
|
contentTypeId: "landing-page";
|
||||||
|
fields: {
|
||||||
|
title: contentful.EntryFieldTypes.Symbol;
|
||||||
|
content: contentful.EntryFieldTypes.RichText;
|
||||||
|
};
|
||||||
|
};
|
7
vite.config.ts
Normal file
7
vite.config.ts
Normal file
|
@ -0,0 +1,7 @@
|
||||||
|
import { defineConfig } from 'vite'
|
||||||
|
import react from '@vitejs/plugin-react'
|
||||||
|
|
||||||
|
// https://vitejs.dev/config/
|
||||||
|
export default defineConfig({
|
||||||
|
plugins: [react()],
|
||||||
|
})
|
Loading…
Reference in a new issue