init
25
.deploy/deploy-dev.yaml
Normal file
@ -0,0 +1,25 @@
|
||||
version: "3.4"
|
||||
|
||||
|
||||
services:
|
||||
certupdater:
|
||||
image: mathwave/sprint-repo:setka
|
||||
networks:
|
||||
- common-infra-nginx-dev
|
||||
deploy:
|
||||
mode: replicated
|
||||
restart_policy:
|
||||
condition: any
|
||||
update_config:
|
||||
parallelism: 1
|
||||
order: start-first
|
||||
|
||||
networks:
|
||||
common-infra-nginx-development:
|
||||
external: true
|
||||
queues-development:
|
||||
external: true
|
||||
minio-development:
|
||||
external: true
|
||||
mongo-development:
|
||||
external: true
|
21
.deploy/deploy-prod.yaml
Normal file
@ -0,0 +1,21 @@
|
||||
version: "3.4"
|
||||
|
||||
|
||||
services:
|
||||
setka:
|
||||
image: mathwave/sprint-repo:setka
|
||||
networks:
|
||||
- common-infra-nginx
|
||||
deploy:
|
||||
mode: replicated
|
||||
restart_policy:
|
||||
condition: any
|
||||
placement:
|
||||
constraints: [node.labels.stage == production]
|
||||
update_config:
|
||||
parallelism: 1
|
||||
order: start-first
|
||||
|
||||
networks:
|
||||
common-infra-nginx:
|
||||
external: true
|
38
.dockerignore
Normal file
@ -0,0 +1,38 @@
|
||||
node_modules
|
||||
npm-debug.log*
|
||||
|
||||
dist
|
||||
build
|
||||
|
||||
.git
|
||||
.gitignore
|
||||
|
||||
Dockerfile
|
||||
.dockerignore
|
||||
|
||||
.vscode
|
||||
.idea
|
||||
*.swp
|
||||
*.swo
|
||||
*~
|
||||
|
||||
.DS_Store
|
||||
Thumbs.db
|
||||
|
||||
logs
|
||||
*.log
|
||||
|
||||
.tmp
|
||||
.temp
|
||||
|
||||
.env
|
||||
.env.local
|
||||
.env.production
|
||||
.env.staging
|
||||
|
||||
coverage
|
||||
|
||||
.eslintcache
|
||||
|
||||
README.md
|
||||
docs
|
41
.gitea/workflows/deploy-dev.yaml
Normal file
@ -0,0 +1,41 @@
|
||||
name: Deploy Dev
|
||||
|
||||
on:
|
||||
pull_request:
|
||||
branches:
|
||||
- dev
|
||||
types: [closed]
|
||||
|
||||
jobs:
|
||||
build:
|
||||
name: Build
|
||||
runs-on: [ dev ]
|
||||
steps:
|
||||
- name: login
|
||||
run: docker login -u mathwave -p ${{ secrets.DOCKERHUB_PASSWORD }}
|
||||
- name: checkout
|
||||
uses: actions/checkout@v4
|
||||
with:
|
||||
ref: dev
|
||||
- name: build
|
||||
run: docker build -t mathwave/sprint-repo:setka .
|
||||
push:
|
||||
name: Push
|
||||
runs-on: [ dev ]
|
||||
needs: build
|
||||
steps:
|
||||
- name: push
|
||||
run: docker push mathwave/sprint-repo:setka
|
||||
deploy-dev:
|
||||
name: Deploy dev
|
||||
runs-on: [prod]
|
||||
needs: push
|
||||
steps:
|
||||
- name: login
|
||||
run: docker login -u mathwave -p ${{ secrets.DOCKERHUB_PASSWORD }}
|
||||
- name: checkout
|
||||
uses: actions/checkout@v4
|
||||
with:
|
||||
ref: dev
|
||||
- name: deploy
|
||||
run: docker stack deploy --with-registry-auth -c ./.deploy/deploy-dev.yaml setka-development
|
41
.gitea/workflows/deploy-prod.yaml
Normal file
@ -0,0 +1,41 @@
|
||||
name: Deploy Prod
|
||||
|
||||
on:
|
||||
pull_request:
|
||||
branches:
|
||||
- prod
|
||||
types: [closed]
|
||||
|
||||
jobs:
|
||||
build:
|
||||
name: Build
|
||||
runs-on: [ dev ]
|
||||
steps:
|
||||
- name: login
|
||||
run: docker login -u mathwave -p ${{ secrets.DOCKERHUB_PASSWORD }}
|
||||
- name: checkout
|
||||
uses: actions/checkout@v4
|
||||
with:
|
||||
ref: prod
|
||||
- name: build
|
||||
run: docker build -t mathwave/sprint-repo:setka .
|
||||
push:
|
||||
name: Push
|
||||
runs-on: [ dev ]
|
||||
needs: build
|
||||
steps:
|
||||
- name: push
|
||||
run: docker push mathwave/sprint-repo:setka
|
||||
deploy-prod:
|
||||
name: Deploy prod
|
||||
runs-on: [prod]
|
||||
needs: push
|
||||
steps:
|
||||
- name: login
|
||||
run: docker login -u mathwave -p ${{ secrets.DOCKERHUB_PASSWORD }}
|
||||
- name: checkout
|
||||
uses: actions/checkout@v4
|
||||
with:
|
||||
ref: prod
|
||||
- name: deploy
|
||||
run: docker stack deploy --with-registry-auth -c ./.deploy/deploy-prod.yaml setka
|
24
.gitignore
vendored
Normal file
@ -0,0 +1,24 @@
|
||||
# Logs
|
||||
logs
|
||||
*.log
|
||||
npm-debug.log*
|
||||
yarn-debug.log*
|
||||
yarn-error.log*
|
||||
pnpm-debug.log*
|
||||
lerna-debug.log*
|
||||
|
||||
node_modules
|
||||
dist
|
||||
dist-ssr
|
||||
*.local
|
||||
|
||||
# Editor directories and files
|
||||
.vscode/*
|
||||
!.vscode/extensions.json
|
||||
.idea
|
||||
.DS_Store
|
||||
*.suo
|
||||
*.ntvs*
|
||||
*.njsproj
|
||||
*.sln
|
||||
*.sw?
|
21
Dockerfile
Normal file
@ -0,0 +1,21 @@
|
||||
FROM node:20-alpine AS builder
|
||||
|
||||
WORKDIR /app
|
||||
|
||||
COPY package*.json ./
|
||||
|
||||
RUN npm ci --only=production=false
|
||||
|
||||
COPY . .
|
||||
|
||||
RUN npm run build
|
||||
|
||||
FROM nginxinc/nginx-unprivileged:1.29-alpine-slim AS production
|
||||
|
||||
COPY --from=builder /app/dist /usr/share/nginx/html
|
||||
|
||||
COPY nginx.conf /etc/nginx/conf.d/default.conf
|
||||
|
||||
EXPOSE 8080
|
||||
|
||||
ENTRYPOINT ["nginx", "-g", "daemon off;"]
|
5
README.md
Normal file
@ -0,0 +1,5 @@
|
||||
# Запуск
|
||||
`docker-compose up --build -d`
|
||||
|
||||
# Остановка
|
||||
`docker-compose down`
|
6
docker-compose.yml
Normal file
@ -0,0 +1,6 @@
|
||||
services:
|
||||
frontend:
|
||||
build: .
|
||||
ports:
|
||||
- "3000:80"
|
||||
restart: unless-stopped
|
29
eslint.config.js
Normal file
@ -0,0 +1,29 @@
|
||||
import js from '@eslint/js'
|
||||
import globals from 'globals'
|
||||
import reactHooks from 'eslint-plugin-react-hooks'
|
||||
import reactRefresh from 'eslint-plugin-react-refresh'
|
||||
import { defineConfig, globalIgnores } from 'eslint/config'
|
||||
|
||||
export default defineConfig([
|
||||
globalIgnores(['dist']),
|
||||
{
|
||||
files: ['**/*.{js,jsx}'],
|
||||
extends: [
|
||||
js.configs.recommended,
|
||||
reactHooks.configs['recommended-latest'],
|
||||
reactRefresh.configs.vite,
|
||||
],
|
||||
languageOptions: {
|
||||
ecmaVersion: 2020,
|
||||
globals: globals.browser,
|
||||
parserOptions: {
|
||||
ecmaVersion: 'latest',
|
||||
ecmaFeatures: { jsx: true },
|
||||
sourceType: 'module',
|
||||
},
|
||||
},
|
||||
rules: {
|
||||
'no-unused-vars': ['error', { varsIgnorePattern: '^[A-Z_]' }],
|
||||
},
|
||||
},
|
||||
])
|
29
index.html
Normal file
@ -0,0 +1,29 @@
|
||||
<!doctype html>
|
||||
<html lang="ru">
|
||||
|
||||
<head>
|
||||
<meta charset="UTF-8" />
|
||||
<!-- <link rel="icon" type="image/svg+xml" href="/vite.svg" /> -->
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<title>Setka x Surf</title>
|
||||
</head>
|
||||
|
||||
<body>
|
||||
<div id="root"></div>
|
||||
<script type="module" src="/src/main.jsx"></script>
|
||||
</body>
|
||||
<!-- Yandex.Metrika counter -->
|
||||
<script type="text/javascript">
|
||||
(function(m,e,t,r,i,k,a){
|
||||
m[i]=m[i]||function(){(m[i].a=m[i].a||[]).push(arguments)};
|
||||
m[i].l=1*new Date();
|
||||
for (var j = 0; j < document.scripts.length; j++) {if (document.scripts[j].src === r) { return; }}
|
||||
k=e.createElement(t),a=e.getElementsByTagName(t)[0],k.async=1,k.src=r,a.parentNode.insertBefore(k,a)
|
||||
})(window, document,'script','https://mc.yandex.ru/metrika/tag.js', 'ym');
|
||||
|
||||
ym(97676450, 'init', {webvisor:true, clickmap:true, accurateTrackBounce:true, trackLinks:true});
|
||||
</script>
|
||||
<noscript><div><img src="https://mc.yandex.ru/watch/97676450" style="position:absolute; left:-9999px;" alt="" /></div></noscript>
|
||||
<!-- /Yandex.Metrika counter -->
|
||||
|
||||
</html>
|
28
nginx.conf
Normal file
@ -0,0 +1,28 @@
|
||||
server {
|
||||
listen 8080;
|
||||
server_name localhost;
|
||||
root /usr/share/nginx/html;
|
||||
index index.html;
|
||||
|
||||
location ~* ^/surfing/.*\.(js|css|png|jpg|jpeg|gif|ico|svg|woff|woff2|ttf|eot)$ {
|
||||
expires 1y;
|
||||
add_header Cache-Control "public, immutable";
|
||||
try_files $uri =404;
|
||||
}
|
||||
|
||||
location /surfing {
|
||||
try_files $uri /surfing/index.html;
|
||||
}
|
||||
|
||||
location = / {
|
||||
return 301 /surfing/;
|
||||
}
|
||||
|
||||
error_page 404 /surfing/index.html;
|
||||
|
||||
location /health {
|
||||
access_log off;
|
||||
return 200 "healthy\n";
|
||||
add_header Content-Type text/plain;
|
||||
}
|
||||
}
|
3317
package-lock.json
generated
Normal file
29
package.json
Normal file
@ -0,0 +1,29 @@
|
||||
{
|
||||
"name": "surf-x-setka",
|
||||
"private": true,
|
||||
"version": "0.0.0",
|
||||
"type": "module",
|
||||
"scripts": {
|
||||
"dev": "vite",
|
||||
"build": "vite build",
|
||||
"lint": "eslint .",
|
||||
"preview": "vite preview"
|
||||
},
|
||||
"dependencies": {
|
||||
"react": "^19.1.1",
|
||||
"react-dom": "^19.1.1",
|
||||
"typograf": "^7.4.4"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@eslint/js": "^9.33.0",
|
||||
"@types/react": "^19.1.10",
|
||||
"@types/react-dom": "^19.1.7",
|
||||
"@vitejs/plugin-react-swc": "^4.0.0",
|
||||
"eslint": "^9.33.0",
|
||||
"eslint-plugin-react-hooks": "^5.2.0",
|
||||
"eslint-plugin-react-refresh": "^0.4.20",
|
||||
"globals": "^16.3.0",
|
||||
"vite": "^7.1.2",
|
||||
"vite-plugin-svgr": "^4.5.0"
|
||||
}
|
||||
}
|
93
public/app_logo.svg
Normal file
After Width: | Height: | Size: 35 KiB |
BIN
public/avatar.png
Normal file
After Width: | Height: | Size: 12 KiB |
32
public/dark_setkaxsurf.svg
Normal file
After Width: | Height: | Size: 202 KiB |
BIN
public/fonts/TT_Travels_Next_Bold.woff
Normal file
BIN
public/fonts/TT_Travels_Next_Bold.woff2
Normal file
19681
public/rules.pdf
Normal file
32
public/setkaxsurf.svg
Normal file
After Width: | Height: | Size: 202 KiB |
30
public/tag.svg
Normal file
After Width: | Height: | Size: 12 KiB |
23
public/tags/sc_akademik.svg
Normal file
After Width: | Height: | Size: 11 KiB |
23
public/tags/sc_arts.svg
Normal file
After Width: | Height: | Size: 7.4 KiB |
23
public/tags/sc_belka.svg
Normal file
After Width: | Height: | Size: 8.8 KiB |
23
public/tags/sc_cave.svg
Normal file
After Width: | Height: | Size: 8.5 KiB |
23
public/tags/sc_erudit.svg
Normal file
After Width: | Height: | Size: 8.6 KiB |
23
public/tags/sc_flacon.svg
Normal file
After Width: | Height: | Size: 9.3 KiB |
23
public/tags/sc_lilo.svg
Normal file
@ -0,0 +1,23 @@
|
||||
<svg width="187" height="59" viewBox="0 0 187 59" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<rect x="3.828" y="-0.000732422" width="32.1319" height="29.219" rx="7.54788" transform="rotate(5.20225 3.828 -0.000732422)" fill="white"/>
|
||||
<path d="M26.2344 12.5845L26.0286 14.8449L23.1681 14.5844L21.9601 18.105L24.5005 18.3363L24.2947 20.5967L21.2142 20.3162L20.2263 23.1912L17.7459 22.9653L18.7337 20.0904L14.1729 19.6751L13.185 22.5501L10.7046 22.3242L11.6924 19.4493L9.372 19.238L9.57781 16.9776L12.4383 17.238L13.6463 13.7175L11.1059 13.4862L11.3117 11.2258L14.3922 11.5063L15.3801 8.63129L17.8605 8.85713L16.8727 11.7321L21.4335 12.1474L22.4214 9.27238L24.9018 9.49821L23.914 12.3732L26.2344 12.5845ZM14.9188 17.4639L19.4796 17.8791L20.6876 14.3586L16.1268 13.9433L14.9188 17.4639Z" fill="#262626"/>
|
||||
<mask id="mask0_2592_1904" style="mask-type:alpha" maskUnits="userSpaceOnUse" x="24" y="12" width="124" height="43">
|
||||
<path d="M27.8184 12.2249L147.667 23.1367L145.672 45.0461L135.873 44.1539L134.967 54.1127L24.9169 44.093L27.8184 12.2249Z" fill="#D9D9D9"/>
|
||||
</mask>
|
||||
<g mask="url(#mask0_2592_1904)">
|
||||
<path d="M27.134 19.7416C27.512 15.5902 31.1837 12.5313 35.3351 12.9092L140.134 22.4508C144.285 22.8288 147.344 26.5006 146.966 30.652L145.475 47.0363C145.074 51.4364 141.182 54.6786 136.782 54.278L32.4336 44.7774C28.2822 44.3994 25.2233 40.7277 25.6012 36.5763L27.134 19.7416Z" fill="white"/>
|
||||
<path d="M60.5788 35.9485C58.864 35.7923 57.6353 35.3963 56.8927 34.7603C56.1508 34.1164 55.824 33.3102 55.9122 32.3417L55.9263 32.1869L58.0817 32.3831L58.072 32.4903C57.9751 33.5541 58.8595 34.1709 60.7252 34.3408C61.7811 34.4369 62.5162 34.4078 62.9305 34.2534C63.3527 34.0997 63.5786 33.8602 63.6083 33.5347C63.635 33.2409 63.5239 33.0107 63.2749 32.8439C63.0267 32.6692 62.7023 32.5396 62.3017 32.4551C61.9012 32.3706 61.353 32.2807 60.6573 32.1853C59.6772 32.0481 58.8862 31.9 58.2843 31.7411C57.6824 31.5823 57.1743 31.3159 56.7601 30.942C56.3538 30.5688 56.181 30.0487 56.2417 29.3819C56.3111 28.6197 56.7439 28.0428 57.54 27.651C58.3361 27.2592 59.6075 27.1428 61.354 27.3018C63.0371 27.455 64.2463 27.8453 64.9817 28.4726C65.725 29.1006 66.0551 29.8711 65.972 30.7841L65.9633 30.8794L63.8078 30.6831L63.8165 30.5878C63.8548 30.1671 63.6676 29.8058 63.2548 29.5041C62.8507 29.1951 62.1683 28.9969 61.2077 28.9094C60.1835 28.8162 59.4643 28.8468 59.05 29.0012C58.6365 29.1476 58.4159 29.3717 58.3885 29.6734C58.3661 29.9195 58.4721 30.1173 58.7067 30.2667C58.9412 30.4161 59.2393 30.5273 59.6009 30.6003C59.9704 30.6739 60.4915 30.7534 61.1641 30.8386C62.1608 30.9694 62.976 31.1157 63.6097 31.2774C64.244 31.4312 64.7756 31.7038 65.2042 32.095C65.6408 32.487 65.8273 33.0323 65.7637 33.7309C65.69 34.5407 65.246 35.1527 64.4318 35.5668C63.6177 35.981 62.3333 36.1082 60.5788 35.9485ZM72.1947 37.006C71.0356 36.9005 70.0642 36.624 69.2804 36.1764C68.4967 35.7288 67.9241 35.1603 67.5626 34.471C67.2018 33.7738 67.059 33.0123 67.1342 32.1867C67.2094 31.361 67.487 30.6419 67.967 30.0292C68.4478 29.4085 69.114 28.9489 69.9657 28.6502C70.8174 28.3515 71.8228 28.2549 72.9819 28.3605C74.0695 28.4595 74.9882 28.6992 75.7381 29.0797C76.4966 29.4529 77.0703 29.9214 77.4592 30.4852C77.8561 31.0496 78.0797 31.6703 78.1302 32.3473L76.0105 32.1543C75.9362 31.6513 75.6367 31.2038 75.1121 30.8118C74.5874 30.4198 73.825 30.1783 72.8246 30.0872C72.1181 30.0229 71.5003 30.0827 70.9712 30.2667C70.4508 30.4434 70.0455 30.7187 69.7553 31.0925C69.4659 31.4584 69.2987 31.8875 69.2539 32.3797C69.2091 32.8719 69.2956 33.328 69.5135 33.7481C69.7322 34.1603 70.0811 34.5042 70.5603 34.78C71.0481 35.0485 71.6453 35.215 72.3519 35.2793C73.3522 35.3704 74.1458 35.2705 74.7326 34.9798C75.3194 34.689 75.6948 34.3029 75.8587 33.8215L77.9784 34.0145C77.8058 34.6792 77.4773 35.2537 76.993 35.7379C76.5086 36.2221 75.8597 36.5793 75.0463 36.8094C74.2408 37.0402 73.2903 37.1058 72.1947 37.006ZM84.2092 40.0691L77.9573 39.4999L78.0895 38.047L84.3415 38.6163L84.2092 40.0691ZM93.1585 38.7586L85.3585 38.0485L86.1174 29.7125L88.2371 29.9055L87.6386 36.479L93.319 36.9962L93.1585 38.7586ZM97.8485 37.6247L99.7301 37.796L99.5891 39.3441L93.7182 38.8096L93.8592 37.2615L96.0503 37.461L96.2596 35.1626C96.2834 34.9007 96.2445 34.713 96.1428 34.5997C96.0497 34.4791 95.8721 34.4069 95.6101 34.3831C95.3799 34.3621 95.1417 34.3845 94.8956 34.4501L95.0366 32.902C95.4234 32.7851 95.8709 32.7498 96.379 32.7961C97.0697 32.859 97.546 33.0344 97.808 33.3224C98.0699 33.6104 98.1742 34.0482 98.1207 34.6357L97.8485 37.6247ZM97.1867 32.1012C96.8453 32.0701 96.5837 31.9542 96.4019 31.7535C96.22 31.5529 96.1418 31.3136 96.1671 31.0357C96.1924 30.7579 96.3126 30.5367 96.5277 30.3722C96.7428 30.2076 97.021 30.1409 97.3624 30.172C97.6958 30.2024 97.9534 30.3179 98.1353 30.5185C98.3171 30.7192 98.3954 30.9585 98.3701 31.2363C98.3448 31.5142 98.2246 31.7354 98.0095 31.8999C97.7944 32.0644 97.5202 32.1315 97.1867 32.1012ZM104.576 38.2373L106.708 38.4313L106.567 39.9794L100.125 39.3929L100.266 37.8448L102.695 38.066L103.113 33.4693C103.137 33.2073 103.094 33.0193 102.985 32.9052C102.884 32.784 102.686 32.7099 102.393 32.6832C102.123 32.6586 101.855 32.6983 101.589 32.8022L101.73 31.2541C102.12 31.1055 102.613 31.0582 103.208 31.1125C103.946 31.1797 104.451 31.3537 104.721 31.6345C105 31.916 105.112 32.3545 105.058 32.9499L104.576 38.2373ZM110.982 40.5375C110.077 40.4551 109.32 40.2461 108.71 39.9104C108.101 39.5667 107.655 39.1419 107.373 38.636C107.099 38.1228 106.99 37.5685 107.044 36.973C107.098 36.3776 107.306 35.8562 107.667 35.4088C108.036 34.9541 108.551 34.6168 109.212 34.3967C109.873 34.1688 110.656 34.096 111.561 34.1784C112.458 34.26 113.211 34.4727 113.82 34.8163C114.43 35.152 114.872 35.5765 115.145 36.0896C115.427 36.5956 115.541 37.1463 115.487 37.7417C115.433 38.3372 115.221 38.8622 114.851 39.3168C114.491 39.7643 113.979 40.102 113.318 40.33C112.658 40.55 111.879 40.6192 110.982 40.5375ZM111.116 39.0608C111.871 39.1295 112.465 39.0235 112.899 38.7428C113.333 38.4542 113.573 38.0637 113.618 37.5715C113.662 37.0872 113.496 36.6679 113.12 36.3135C112.744 35.9511 112.18 35.7356 111.425 35.6669C110.671 35.5983 110.073 35.7079 109.63 35.9958C109.197 36.2765 108.958 36.659 108.914 37.1433C108.869 37.6355 109.034 38.0628 109.409 38.4251C109.793 38.7803 110.362 38.9922 111.116 39.0608Z" fill="#262626"/>
|
||||
</g>
|
||||
<path d="M135.742 44.217L134.835 54.1758L145.601 45.1146L135.742 44.217Z" fill="url(#paint0_linear_2592_1904)"/>
|
||||
<path d="M135.742 44.217L134.835 54.1758L145.601 45.1146L135.742 44.217Z" fill="url(#paint1_radial_2592_1904)" fill-opacity="0.8"/>
|
||||
<defs>
|
||||
<linearGradient id="paint0_linear_2592_1904" x1="138.321" y1="59.0003" x2="149.287" y2="48.0692" gradientUnits="userSpaceOnUse">
|
||||
<stop offset="0.0001" stop-color="#DB00FF"/>
|
||||
<stop offset="1" stop-color="#1400FF"/>
|
||||
</linearGradient>
|
||||
<radialGradient id="paint1_radial_2592_1904" cx="0" cy="0" r="1" gradientTransform="matrix(-6.07414 4.5848 -1.99392 -10.7303 144.922 44.5507)" gradientUnits="userSpaceOnUse">
|
||||
<stop stop-color="#EB00FF"/>
|
||||
<stop offset="1" stop-color="#EB00FF" stop-opacity="0"/>
|
||||
</radialGradient>
|
||||
</defs>
|
||||
</svg>
|
After Width: | Height: | Size: 6.9 KiB |
23
public/tags/sc_lovely.svg
Normal file
After Width: | Height: | Size: 8.0 KiB |
23
public/tags/sc_lucky.svg
Normal file
After Width: | Height: | Size: 7.1 KiB |
23
public/tags/sc_nazare.svg
Normal file
After Width: | Height: | Size: 9.9 KiB |
23
public/tags/sc_neglinka.svg
Normal file
After Width: | Height: | Size: 12 KiB |
23
public/tags/sc_nikola.svg
Normal file
After Width: | Height: | Size: 9.0 KiB |
23
public/tags/sc_oasis.svg
Normal file
After Width: | Height: | Size: 10 KiB |
23
public/tags/sc_pipe.svg
Normal file
After Width: | Height: | Size: 8.1 KiB |
23
public/tags/sc_sport.svg
Normal file
After Width: | Height: | Size: 9.4 KiB |
23
public/tags/sc_sretenka.svg
Normal file
After Width: | Height: | Size: 12 KiB |
23
public/tags/sc_supernova.svg
Normal file
After Width: | Height: | Size: 12 KiB |
23
public/tags/sc_umka.svg
Normal file
After Width: | Height: | Size: 7.7 KiB |
23
public/tags/sc_vdnx.svg
Normal file
After Width: | Height: | Size: 7.1 KiB |
23
public/tags/sc_yakimanka.svg
Normal file
After Width: | Height: | Size: 12 KiB |
BIN
public/users/0.png
Normal file
After Width: | Height: | Size: 170 KiB |
BIN
public/users/1.png
Normal file
After Width: | Height: | Size: 270 KiB |
BIN
public/users/2.png
Normal file
After Width: | Height: | Size: 585 KiB |
BIN
public/users/3.png
Normal file
After Width: | Height: | Size: 477 KiB |
BIN
public/users/4.png
Normal file
After Width: | Height: | Size: 84 KiB |
BIN
public/users/5.png
Normal file
After Width: | Height: | Size: 442 KiB |
BIN
public/users/6.png
Normal file
After Width: | Height: | Size: 141 KiB |
BIN
public/users/7.png
Normal file
After Width: | Height: | Size: 825 KiB |
BIN
public/users/8.png
Normal file
After Width: | Height: | Size: 459 KiB |
BIN
public/users/9.png
Normal file
After Width: | Height: | Size: 347 KiB |
0
src/App.css
Normal file
37
src/App.jsx
Normal file
@ -0,0 +1,37 @@
|
||||
|
||||
import { useState, useEffect } from 'react'
|
||||
import './App.css'
|
||||
import { HomePage } from './pages/HomePage/HomePage'
|
||||
import { RulesPage } from './pages/RulesPage/RulesPage'
|
||||
|
||||
function App() {
|
||||
const [currentPath, setCurrentPath] = useState(window.location.pathname)
|
||||
|
||||
useEffect(() => {
|
||||
const handlePopState = () => {
|
||||
setCurrentPath(window.location.pathname)
|
||||
}
|
||||
|
||||
window.addEventListener('popstate', handlePopState)
|
||||
return () => window.removeEventListener('popstate', handlePopState)
|
||||
}, [])
|
||||
|
||||
const getCurrentPage = () => {
|
||||
if (currentPath === '/surfing/rules') {
|
||||
return <RulesPage />
|
||||
} else if (currentPath === '/surfing' || currentPath === '/surfing/') {
|
||||
return <HomePage />
|
||||
} else {
|
||||
window.history.replaceState(null, '', '/surfing')
|
||||
return <HomePage />
|
||||
}
|
||||
}
|
||||
|
||||
return (
|
||||
<>
|
||||
{getCurrentPage()}
|
||||
</>
|
||||
)
|
||||
}
|
||||
|
||||
export default App
|
4
src/assets/divider-d.svg
Normal file
@ -0,0 +1,4 @@
|
||||
<svg width="25" height="24" viewBox="0 0 25 24" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<path d="M1.61633 22.5034L22.7679 1.35182" stroke="black" stroke-width="2.58985" stroke-linecap="round"/>
|
||||
<path d="M1.61633 1.35181L22.7679 22.5034" stroke="black" stroke-width="2.58985" stroke-linecap="round"/>
|
||||
</svg>
|
After Width: | Height: | Size: 315 B |
4
src/assets/divider.svg
Normal file
@ -0,0 +1,4 @@
|
||||
<svg width="20" height="21" viewBox="0 0 20 21" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<path d="M1.30713 19.2076L18.5138 2.00099" stroke="white" stroke-width="2.10682" stroke-linecap="round"/>
|
||||
<path d="M1.30695 2.00095L18.5136 19.2076" stroke="white" stroke-width="2.10682" stroke-linecap="round"/>
|
||||
</svg>
|
After Width: | Height: | Size: 315 B |
18
src/assets/setka-d.svg
Normal file
After Width: | Height: | Size: 191 KiB |
18
src/assets/setka.svg
Normal file
After Width: | Height: | Size: 191 KiB |
14
src/assets/surf-d.svg
Normal file
After Width: | Height: | Size: 10 KiB |
14
src/assets/surf.svg
Normal file
After Width: | Height: | Size: 11 KiB |
30
src/components/Logo/Logo.jsx
Normal file
@ -0,0 +1,30 @@
|
||||
import styles from "./Logo.module.css";
|
||||
import SurfLogo from "../../assets/surf.svg?react";
|
||||
import SetkaLogo from "../../assets/setka.svg?react";
|
||||
import Divider from "../../assets/divider.svg?react";
|
||||
import DividerD from "../../assets/divider-d.svg?react";
|
||||
import SurfLogoD from "../../assets/surf-d.svg?react";
|
||||
import SetkaLogoD from "../../assets/setka-d.svg?react";
|
||||
export const Logo = ({ isDark }) => {
|
||||
return !isDark ? (
|
||||
<div className={`${styles.wrapper}`}>
|
||||
<a href='https://www.surfcoffee.ru' target='_blank'>
|
||||
<SurfLogo />
|
||||
</a>
|
||||
<Divider />
|
||||
<a href='https://setka.onelink.me/tQlI/k82d3mhf' target='_blank'>
|
||||
<SetkaLogo />
|
||||
</a>
|
||||
</div>
|
||||
) : (
|
||||
<div className={`${styles.wrapper} ${styles.dark}`}>
|
||||
<a href='https://www.surfcoffee.ru' target='_blank'>
|
||||
<SurfLogoD />
|
||||
</a>
|
||||
<DividerD />
|
||||
<a href='https://setka.onelink.me/tQlI/k82d3mhf' target='_blank'>
|
||||
<SetkaLogoD />
|
||||
</a>
|
||||
</div>
|
||||
);
|
||||
};
|
66
src/components/Logo/Logo.module.css
Normal file
@ -0,0 +1,66 @@
|
||||
.logo {
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
.wrapper {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 30px;
|
||||
}
|
||||
|
||||
.wrapper a {
|
||||
opacity: 1;
|
||||
transition: opacity 0.3s ease;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.wrapper a:hover {
|
||||
opacity: 0.7;
|
||||
}
|
||||
|
||||
.wrapper a svg {
|
||||
max-width: 100%;
|
||||
height: auto;
|
||||
width: auto;
|
||||
}
|
||||
|
||||
.dark {
|
||||
margin-top: 75px;
|
||||
}
|
||||
|
||||
@media (max-width: 1000px) {
|
||||
.dark {
|
||||
margin-top: 57px;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 768px) {
|
||||
.wrapper {
|
||||
gap: 20px;
|
||||
}
|
||||
|
||||
.wrapper a svg {
|
||||
max-height: 40px;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 480px) {
|
||||
.wrapper {
|
||||
gap: 15px;
|
||||
}
|
||||
|
||||
.wrapper a svg {
|
||||
max-height: 32px;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 320px) {
|
||||
.wrapper {
|
||||
gap: 10px;
|
||||
}
|
||||
|
||||
.wrapper a svg {
|
||||
max-height: 28px;
|
||||
}
|
||||
}
|
42
src/components/Popup/Popup.jsx
Normal file
@ -0,0 +1,42 @@
|
||||
|
||||
import { useEffect, useRef } from 'react';
|
||||
import { Row } from './components/Row/Row';
|
||||
import styles from './Popup.module.css';
|
||||
import { TAG_ADDR } from './constants';
|
||||
|
||||
export const Popup = ( {isOpen = false, setIsOpen} ) => {
|
||||
|
||||
useEffect(() => {
|
||||
if (isOpen === true) {
|
||||
document.body.style.overflow = "hidden";
|
||||
} else {
|
||||
document.body.style.overflow = "";
|
||||
}
|
||||
},[isOpen]);
|
||||
|
||||
|
||||
function onClickHandle(event) {
|
||||
if (event.target !== event.currentTarget)
|
||||
return;
|
||||
setIsOpen(false);
|
||||
}
|
||||
|
||||
return (
|
||||
<div
|
||||
className={styles.container}
|
||||
onClick={onClickHandle}
|
||||
style={{ display: isOpen ? "flex" : "none" }}
|
||||
>
|
||||
<div className={styles.column}>
|
||||
{TAG_ADDR.map(({tag, addr}, index) => (
|
||||
<Row
|
||||
key={index}
|
||||
onClickTag={() => {setIsOpen(false)}}
|
||||
tag={tag}
|
||||
addr={addr}
|
||||
/>
|
||||
))}
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
}
|
75
src/components/Popup/Popup.module.css
Normal file
@ -0,0 +1,75 @@
|
||||
|
||||
.container {
|
||||
display: flex;
|
||||
position: fixed;
|
||||
top:0;
|
||||
left:0;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
background-color: rgba(0, 0, 0, 0.8);
|
||||
padding: 0 20px;
|
||||
|
||||
z-index: 10;
|
||||
}
|
||||
|
||||
.column {
|
||||
overflow: auto;
|
||||
background-color: #19191A;
|
||||
|
||||
padding-left: 40px;
|
||||
padding-right: 100px;
|
||||
|
||||
padding-top: 32px;
|
||||
padding-bottom: 32px;
|
||||
|
||||
max-width: 806px;
|
||||
max-height: 468px;
|
||||
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
}
|
||||
|
||||
@media screen and (max-width: 870px) {
|
||||
.column {
|
||||
padding-left: 5px;
|
||||
padding-right: 15px;
|
||||
padding-top: 20px;
|
||||
padding-bottom: 20px;
|
||||
}
|
||||
}
|
||||
|
||||
@media screen and (max-width: 580px) {
|
||||
.column {
|
||||
padding-top: 10px;
|
||||
padding-bottom: 10px;
|
||||
}
|
||||
}
|
||||
|
||||
.container::-webkit-scrollbar {
|
||||
width: 12px;
|
||||
height: 12px;
|
||||
}
|
||||
|
||||
.container::-webkit-scrollbar-track {
|
||||
background: #19191a;
|
||||
border-radius: 147px;
|
||||
}
|
||||
|
||||
.container::-webkit-scrollbar-thumb {
|
||||
background: #484848;
|
||||
border-radius: 135px;
|
||||
border: 2px solid #19191a;
|
||||
}
|
||||
|
||||
.container::-webkit-scrollbar-thumb:hover {
|
||||
background: #5c5c5c;
|
||||
}
|
||||
|
||||
.container {
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: #484848 #19191a;
|
||||
}
|
||||
|
25
src/components/Popup/components/Row/Row.jsx
Normal file
@ -0,0 +1,25 @@
|
||||
|
||||
import { useEffect } from 'react';
|
||||
import { sendGoal } from '@utils';
|
||||
import styles from './Row.module.css';
|
||||
|
||||
export const Row = ({
|
||||
tag = "#SC_Sretenka",
|
||||
addr = "Сретенка, 27, стр. 1, Москва"
|
||||
}) => {
|
||||
|
||||
function tagToName(tag) {
|
||||
const name = tag.slice(4);
|
||||
if (name === name.toUpperCase()) {
|
||||
return name.charAt(0).toUpperCase() + name.slice(1).toLowerCase();
|
||||
}
|
||||
return name;
|
||||
}
|
||||
|
||||
return (
|
||||
<div className={styles.row}>
|
||||
<span className={styles.tag}>{`Surf Coffee® х ${tagToName(tag)} — #SC_${tagToName(tag)}`}</span>
|
||||
<span className={styles.addr}>{addr}</span>
|
||||
</div>
|
||||
)
|
||||
}
|
77
src/components/Popup/components/Row/Row.module.css
Normal file
@ -0,0 +1,77 @@
|
||||
.row {
|
||||
display: flex;
|
||||
flex-direction: row;
|
||||
gap: 10px;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.tag {
|
||||
font-family: 'Inter';
|
||||
font-style: normal;
|
||||
font-weight: 600;
|
||||
font-size: 16px;
|
||||
line-height: 120%;
|
||||
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
|
||||
color: #EEEADD;
|
||||
flex-grow: 0;
|
||||
|
||||
width: 610px;
|
||||
height: 48px;
|
||||
|
||||
background: #000000;
|
||||
border: 1px solid #000000;
|
||||
border-radius: 12px;
|
||||
}
|
||||
|
||||
.addr {
|
||||
font-family: 'Inter';
|
||||
font-style: normal;
|
||||
font-weight: 600;
|
||||
font-size: 16px;
|
||||
line-height: 120%;
|
||||
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
|
||||
color: #EEEADD;
|
||||
|
||||
flex-grow: 0;
|
||||
|
||||
width: 438px;
|
||||
height: 48px;
|
||||
|
||||
background: #262626;
|
||||
border-radius: 12px;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
@media screen and (max-width: 880px) {
|
||||
.tag {
|
||||
font-size: 13px;
|
||||
width: 400px;
|
||||
}
|
||||
.addr {
|
||||
font-size: 13px;
|
||||
width: 372px;
|
||||
}
|
||||
}
|
||||
|
||||
@media screen and (max-width: 690px) {
|
||||
.row {
|
||||
flex-direction: column;
|
||||
align-items: normal;
|
||||
}
|
||||
.tag {
|
||||
width: 100%;
|
||||
padding: 0 20px;
|
||||
}
|
||||
.addr {
|
||||
width: 100%;
|
||||
padding: 0 20px;
|
||||
}
|
||||
}
|
22
src/components/Popup/constants.jsx
Normal file
@ -0,0 +1,22 @@
|
||||
export const TAG_ADDR = [
|
||||
{tag: "#SC_Sretenka", addr: "Сретенка, 27, стр. 1, Москва"},
|
||||
{tag: "#SC_Pipe", addr: "Трубная, 26, корп. 1, Москва"},
|
||||
{tag: "#SC_Cave", addr: "Новокузнецкая, 6, Москва"},
|
||||
{tag: "#SC_Flacon", addr: "Большая Новодмитровская, 36, стр. 8, Москва"},
|
||||
{tag: "#SC_Yakimanka", addr: "Большая Якиманка, 50, Москва"},
|
||||
{tag: "#SC_Sport", addr: "Усачёва, 62, Москва"},
|
||||
{tag: "#SC_Belka", addr: "Бутырский Вал, 4, Москва"},
|
||||
{tag: "#SC_NAZARE", addr: "Тверская, 18, корп. 1, Москва"},
|
||||
{tag: "#SC_Lucky", addr: "Бауманская, 33/2, стр. 1, Москва"},
|
||||
{tag: "#SC_SuperNova", addr: "Новинский бул., 7, Москва"},
|
||||
{tag: "#SC_Neglinka", addr: "Неглинная, 14, стр. 1А, Москва"},
|
||||
{tag: "#SC_VDNX", addr: "2-я Останкинская ул., 3, Москва"},
|
||||
{tag: "#SC_ERUDIT", addr: "Ломоносовский просп., 25, корп. 5, Москва"},
|
||||
{tag: "#SC_AKADEMIK", addr: "Ломоносовский просп., 25, корп. 5, Москва"},
|
||||
{tag: "#SC_OASIS", addr: "Орликов пер., 8, Москва"},
|
||||
{tag: "#SC_NIKOLA", addr: "Большой Черкасский пер., 2/10, Москва"},
|
||||
{tag: "#SC_LOVELY", addr: "просп. Мира, 40, Москва"},
|
||||
{tag: "#SC_LILO", addr: "Ленинская Слобода, 26, Москва"},
|
||||
{tag: "#SC_UMKA", addr: "Холодильный пер., 3, подъезд 2, Москва"},
|
||||
{tag: "#SC_ARTS", addr: "Архитектора Щусева, 2, корп. 1, Москва"},
|
||||
];
|
39
src/index.css
Normal file
@ -0,0 +1,39 @@
|
||||
@import url('https://fonts.googleapis.com/css2?family=Inter:ital,opsz,wght@0,14..32,100..900;1,14..32,100..900&display=swap');
|
||||
|
||||
@font-face {
|
||||
font-family: "TT Travels Next";
|
||||
font-weight: 600;
|
||||
src: url("/fonts/TT_Travels_Next_Bold.woff2") format("woff2"),
|
||||
url("/fonts/TT_Travels_Next_Bold.woff") format("woff");
|
||||
}
|
||||
|
||||
|
||||
|
||||
:root {
|
||||
font-family: "Inter", system-ui, -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, Oxygen, Ubuntu, Cantarell, 'Open Sans', 'Helvetica Neue', sans-serif, system-ui;
|
||||
line-height: 1.5;
|
||||
font-weight: 400;
|
||||
|
||||
color-scheme: light dark;
|
||||
color: rgba(255, 255, 255, 0.87);
|
||||
background-color: #242424;
|
||||
|
||||
font-synthesis: none;
|
||||
text-rendering: optimizeLegibility;
|
||||
-webkit-font-smoothing: antialiased;
|
||||
-moz-osx-font-smoothing: grayscale;
|
||||
|
||||
--transition: all 0.3s ease;
|
||||
--padding-mobile-horizontal: 20px;
|
||||
--padding-desktop-horizontal: 100px;
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
a {
|
||||
text-decoration: inherit;
|
||||
}
|
10
src/main.jsx
Normal file
@ -0,0 +1,10 @@
|
||||
import { StrictMode } from 'react'
|
||||
import { createRoot } from 'react-dom/client'
|
||||
import './index.css'
|
||||
import App from './App.jsx'
|
||||
|
||||
createRoot(document.getElementById('root')).render(
|
||||
<StrictMode>
|
||||
<App />
|
||||
</StrictMode>,
|
||||
)
|
17
src/pages/HomePage/HomePage.jsx
Normal file
@ -0,0 +1,17 @@
|
||||
|
||||
import { CommunityBlock } from './components/CommunityBlock/CommunityBlock';
|
||||
import { FooterBlock } from './components/FooterBlock/FooterBlock';
|
||||
import { MainBlock } from './components/MainBlock/MainBlock';
|
||||
import { StepsBlock } from './components/StepsBlock/StepsBlock';
|
||||
import styles from './HomePage.module.css';
|
||||
|
||||
export const HomePage = () => {
|
||||
return (
|
||||
<div className={styles.root}>
|
||||
<MainBlock/>
|
||||
<StepsBlock/>
|
||||
<CommunityBlock/>
|
||||
<FooterBlock/>
|
||||
</div>
|
||||
)
|
||||
}
|
0
src/pages/HomePage/HomePage.module.css
Normal file
@ -0,0 +1,25 @@
|
||||
|
||||
import styles from './CommunityBlock.module.css';
|
||||
import { Button } from './components/Button/Button';
|
||||
import { CardList } from './components/CardList/CardList';
|
||||
import { Header } from './components/Header/Header';
|
||||
import { MobileIcon } from './components/MobileIcon/MobileIcon';
|
||||
|
||||
export const CommunityBlock = () => {
|
||||
return (
|
||||
<div className={styles.column}>
|
||||
<Header/>
|
||||
|
||||
<div className={styles.list}>
|
||||
<CardList/>
|
||||
</div>
|
||||
|
||||
<MobileIcon/>
|
||||
|
||||
<div className={styles.button}>
|
||||
<Button/>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
)
|
||||
}
|
@ -0,0 +1,89 @@
|
||||
|
||||
.column {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
padding-top: 90px;
|
||||
padding-bottom: 90px;
|
||||
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
|
||||
color: white;
|
||||
|
||||
background-color: black;
|
||||
background-image: url('./background.png');
|
||||
background-repeat: no-repeat;
|
||||
background-size: contain;
|
||||
background-position: top;
|
||||
|
||||
padding-left: var(--padding-desktop-horizontal);
|
||||
padding-right: var(--padding-desktop-horizontal);
|
||||
|
||||
}
|
||||
|
||||
@media screen and (max-width: 1100px) {
|
||||
.column {
|
||||
padding-left: var(--padding-mobile-horizontal);
|
||||
padding-right: var(--padding-mobile-horizontal);
|
||||
}
|
||||
}
|
||||
|
||||
.list {
|
||||
padding-top: 70px;
|
||||
|
||||
max-width: 1440px;
|
||||
z-index: 2;
|
||||
}
|
||||
|
||||
.button {
|
||||
width: 100%;
|
||||
padding-top: 75px;
|
||||
max-width: 384px;
|
||||
|
||||
z-index: 2;
|
||||
}
|
||||
|
||||
@media screen and (max-width: 880px) {
|
||||
.column {
|
||||
padding-top: 22px;
|
||||
padding-bottom: 44px;
|
||||
}
|
||||
.button {
|
||||
padding-top: 44px;
|
||||
}
|
||||
}
|
||||
|
||||
@media screen and (max-width: 1350px) {
|
||||
.column {
|
||||
background-size: 120%;
|
||||
background-position: top left;
|
||||
}
|
||||
}
|
||||
|
||||
@media screen and (max-width: 1100px) {
|
||||
.column {
|
||||
background-image: url("./background_blur_up.png");
|
||||
|
||||
background-size: 100%;
|
||||
background-position: top;
|
||||
background-position-y: 70px;
|
||||
background-repeat: no-repeat;
|
||||
position: relative;
|
||||
}
|
||||
.column::after {
|
||||
position: absolute;
|
||||
content: "";
|
||||
background-image: url("./background_blur.png");
|
||||
background-size: contain;
|
||||
background-repeat: no-repeat;
|
||||
background-position: bottom;
|
||||
z-index: 1;
|
||||
bottom:0;
|
||||
left:0;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
|
||||
pointer-events: none;
|
||||
|
||||
}
|
||||
}
|
BIN
src/pages/HomePage/components/CommunityBlock/background.png
Normal file
After Width: | Height: | Size: 220 KiB |
BIN
src/pages/HomePage/components/CommunityBlock/background_blur.png
Normal file
After Width: | Height: | Size: 594 KiB |
After Width: | Height: | Size: 354 KiB |
After Width: | Height: | Size: 513 KiB |
@ -0,0 +1,13 @@
|
||||
import { sendGoal } from '@utils';
|
||||
import styles from './Button.module.css';
|
||||
|
||||
export const Button = () => {
|
||||
|
||||
const handleMorePosts = () => {
|
||||
sendGoal('more_posts_clicked');
|
||||
};
|
||||
|
||||
return (
|
||||
<a href='https://setka.onelink.me/tQlI/k82d3mhf' target='_blank' className={styles.button} onClick={handleMorePosts}>больше постов — в сетке</a>
|
||||
)
|
||||
}
|
@ -0,0 +1,43 @@
|
||||
|
||||
.button {
|
||||
background-color: #FFFFFF;
|
||||
border-radius: 4px;
|
||||
|
||||
display: flex;
|
||||
flex-direction: row;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
|
||||
width: 100%;
|
||||
height: 48px;
|
||||
|
||||
font-family: 'TT Travels Next';
|
||||
font-style: normal;
|
||||
font-weight: 700;
|
||||
font-size: 20px;
|
||||
line-height: 120%;
|
||||
color: #000000;
|
||||
|
||||
flex-grow: 0;
|
||||
|
||||
border: 1px solid #FFFFFF;
|
||||
transition: var(--transition);
|
||||
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
@media screen and (max-width: 680px) {
|
||||
.button {
|
||||
font-family: 'TT Travels Next';
|
||||
font-style: normal;
|
||||
font-weight: 700;
|
||||
font-size: 16px;
|
||||
line-height: 120%;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
.button:hover {
|
||||
background-color: transparent;
|
||||
color: white;
|
||||
}
|
@ -0,0 +1,42 @@
|
||||
|
||||
import styles from './Card.module.css';
|
||||
import { Button } from './components/Button/Button';
|
||||
import { HashTag } from './components/HashTag/HashTag';
|
||||
|
||||
import { typo } from '@utils/typo';
|
||||
|
||||
export const Card = ({
|
||||
fullname = "Марат Юсупов",
|
||||
image_url = "/avatar.png",
|
||||
about = "Продуктовый маркетолог в VK",
|
||||
date = "09.06",
|
||||
title = "Исследования внутри компаний",
|
||||
text = "В маркетинге есть большая проблема, о которой мало кто говорит — экспертность специалистов",
|
||||
tag = "SC_Sretenka",
|
||||
cardId
|
||||
}) => {
|
||||
return (
|
||||
<div className={styles.card}>
|
||||
<div className={styles.tag}>
|
||||
<img src={`/surfing/tags/${tag.toLowerCase()}.svg`}/>
|
||||
</div>
|
||||
<div className={styles.head}>
|
||||
<div
|
||||
className={styles.avatar}
|
||||
style={{backgroundImage: `url(${image_url})`}}
|
||||
/>
|
||||
<div className={styles.left}>
|
||||
<h2 className={styles.name}>{fullname}</h2>
|
||||
<h3 className={styles.about}>{about}</h3>
|
||||
</div>
|
||||
</div>
|
||||
<h1 className={styles.h1}>{typo(title)}</h1>
|
||||
<p className={styles.text}>
|
||||
{typo(text)}
|
||||
</p>
|
||||
<div className={styles.spacer} />
|
||||
|
||||
<Button cardId={cardId} link="https://set.ki/chan_inv/CrvvTgv"/>
|
||||
</div>
|
||||
)
|
||||
}
|
@ -0,0 +1,124 @@
|
||||
|
||||
.card {
|
||||
padding: 12px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 12px;
|
||||
|
||||
/* max-width: 338px; */
|
||||
|
||||
background: #19191A;
|
||||
border-radius: 20px;
|
||||
|
||||
position: relative;
|
||||
}
|
||||
|
||||
.tag {
|
||||
position: absolute;
|
||||
left: 53%;
|
||||
top: -25px;
|
||||
overflow: hidden;
|
||||
width: 155px;
|
||||
z-index: 3;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
@media screen and (max-width: 370px) {
|
||||
.tag {
|
||||
width: 127px;
|
||||
}
|
||||
.tag img {
|
||||
width: 47vw;
|
||||
}
|
||||
}
|
||||
|
||||
.head {
|
||||
display: flex;
|
||||
flex-direction: row;
|
||||
gap: 8px;
|
||||
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.avatar {
|
||||
height: 40px;
|
||||
width: 40px;
|
||||
border-radius: 50%;
|
||||
background-color: #343436;
|
||||
background-position: center;
|
||||
background-size: cover;
|
||||
background-repeat: no-repeat;
|
||||
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.name {
|
||||
/* SF Semibold */
|
||||
font-family: 'SF Pro', "Inter";
|
||||
font-style: normal;
|
||||
font-weight: 590;
|
||||
font-size: 15px;
|
||||
line-height: 140%;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
letter-spacing: -0.02em;
|
||||
|
||||
color: #E1E3E6;
|
||||
|
||||
flex-grow: 0;
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.about {
|
||||
/* SF Regular */
|
||||
font-family: 'SF Pro', "Inter";
|
||||
font-style: normal;
|
||||
font-weight: 400;
|
||||
font-size: 13px;
|
||||
line-height: 140%;
|
||||
|
||||
letter-spacing: -0.02em;
|
||||
|
||||
|
||||
color: rgba(255, 255, 255, 0.4);
|
||||
|
||||
flex-grow: 0;
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.h1 {
|
||||
/* SF Semibold */
|
||||
font-family: 'SF Pro', "Inter";
|
||||
font-style: normal;
|
||||
font-weight: 590;
|
||||
font-size: 18px;
|
||||
line-height: 140%;
|
||||
|
||||
letter-spacing: -0.02em;
|
||||
|
||||
color: #E1E3E6;
|
||||
|
||||
flex-grow: 0;
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.text {
|
||||
/* SF Regular */
|
||||
font-family: 'SF Pro', "Inter";
|
||||
font-style: normal;
|
||||
font-weight: 400;
|
||||
font-size: 15px;
|
||||
line-height: 140%;
|
||||
letter-spacing: -0.02em;
|
||||
|
||||
color: #E1E3E6;
|
||||
|
||||
|
||||
flex-grow: 0;
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
|
||||
.spacer {
|
||||
flex: 1;
|
||||
}
|
@ -0,0 +1,14 @@
|
||||
|
||||
import { sendGoal } from '@utils';
|
||||
import styles from './Button.module.css';
|
||||
|
||||
export const Button = ( {link = "#", cardId} ) => {
|
||||
|
||||
const handleWriteInSetka = () => {
|
||||
sendGoal('write_in_setka_clicked', { card_id: cardId });
|
||||
};
|
||||
|
||||
return (
|
||||
<a href={link} target='_blank' className={styles.button} onClick={handleWriteInSetka}>написать в сетке</a>
|
||||
)
|
||||
}
|
@ -0,0 +1,27 @@
|
||||
|
||||
.button {
|
||||
font-family: 'TT Travels Next';
|
||||
font-style: normal;
|
||||
font-weight: 700;
|
||||
font-size: 20px;
|
||||
line-height: 100%;
|
||||
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
|
||||
color: #E1E3E6;
|
||||
|
||||
background:
|
||||
radial-gradient(56.91% 105.05% at 7.34% 105%, rgba(235, 0, 255, 0.8) 0%, rgba(235, 0, 255, 0) 100%),
|
||||
linear-gradient(188.61deg, #DB00FF -6.68%, #1400FF 103.74%);
|
||||
border-radius: 12px;
|
||||
|
||||
align-self: stretch;
|
||||
flex-grow: 0;
|
||||
|
||||
height: 48px;
|
||||
width: 100%;
|
||||
|
||||
transition: var(--transition);
|
||||
}
|
@ -0,0 +1,8 @@
|
||||
|
||||
import styles from './HashTag.module.css';
|
||||
|
||||
export const HashTag = ({tag = "SC_Sretenka"}) => {
|
||||
return (
|
||||
<div className={styles.tag}><span className={styles.text}>{tag}</span></div>
|
||||
)
|
||||
}
|
@ -0,0 +1,34 @@
|
||||
|
||||
.tag {
|
||||
font-family: 'TT Travels Next';
|
||||
font-style: normal;
|
||||
font-weight: 700;
|
||||
font-size: 11px;
|
||||
line-height: 140%;
|
||||
|
||||
color: #262626;
|
||||
position: relative;
|
||||
|
||||
transform: rotate(5.2deg);
|
||||
}
|
||||
|
||||
/* transform: rotate(5.2deg); */
|
||||
|
||||
.tag::after {
|
||||
position: absolute;
|
||||
content: "";
|
||||
background-image: url("/tag.svg");
|
||||
background-repeat: no-repeat;
|
||||
top:-16px;
|
||||
left:-32px;
|
||||
z-index: 3;
|
||||
width: 150px;
|
||||
height: 100px;
|
||||
}
|
||||
|
||||
.text {
|
||||
z-index: 4;
|
||||
position: absolute;
|
||||
left: 0;
|
||||
top: 0;
|
||||
}
|
@ -0,0 +1,33 @@
|
||||
|
||||
import { Card } from '../Card/Card';
|
||||
import styles from './CardList.module.css';
|
||||
import { CARDS } from './constants';
|
||||
|
||||
export const CardList = () => {
|
||||
|
||||
let cards = [];
|
||||
|
||||
for(let i = 0; i < 9; i += 1) {
|
||||
cards.push( 0 );
|
||||
}
|
||||
|
||||
return (
|
||||
<div className={styles.container}>
|
||||
{/* todo: determine cardId */}
|
||||
{CARDS.map((el, index) =>
|
||||
(<Card
|
||||
fullname={el.fullname}
|
||||
image_url={el.image_url || `/surfing/users/${el.cardId}.png`}
|
||||
about={el.about}
|
||||
date={el.date}
|
||||
title={el.title}
|
||||
text={el.text}
|
||||
tag={el.tag}
|
||||
key={index}
|
||||
cardId={index}
|
||||
/>))
|
||||
}
|
||||
|
||||
</div>
|
||||
)
|
||||
}
|
@ -0,0 +1,20 @@
|
||||
|
||||
.container {
|
||||
display: grid;
|
||||
grid-template-columns: 1fr 1fr 1fr;
|
||||
row-gap: 21px;
|
||||
column-gap: 20px;
|
||||
z-index: 2;
|
||||
}
|
||||
|
||||
@media screen and (max-width: 1100px) {
|
||||
.container {
|
||||
grid-template-columns: 1fr 1fr;
|
||||
}
|
||||
}
|
||||
|
||||
@media screen and (max-width: 680px) {
|
||||
.container {
|
||||
grid-template-columns: 1fr;
|
||||
}
|
||||
}
|
@ -0,0 +1,112 @@
|
||||
|
||||
export const CARDS = [
|
||||
{
|
||||
fullname : "Даниил Холопцев",
|
||||
image_url : "",
|
||||
about : "Product owner в Россельхозбанк",
|
||||
date : "13.09",
|
||||
title : "Вам сообщение от чайного ценителя",
|
||||
text :
|
||||
"Привет! Меня зовут Даниил Холопцев, основатель сообщества Немного продакт. Приюта для продактов, ищущих полезный контент. Объединил более 30 сильных авторов в закрытом сообществе и вместе пишем контент о продукте, выступаем и тусим вместе 🫂",
|
||||
tag: "SC_Lucky",
|
||||
cardId: 0,
|
||||
},
|
||||
{
|
||||
fullname: "Никита Крисанов",
|
||||
image_url: "",
|
||||
about: "Технический менеджер",
|
||||
date: "12.09",
|
||||
title: "Привет! Я Никита, мне 30 годиков",
|
||||
text:
|
||||
"Горю идеей сделать цифровое пространство добрее и комфортнее для людей. Сейчас работаю техническим менеджером проектов в Российском обществе «Знание». Мы запускаем и развиваем сервисы для просветителей и лекторов. Один из последних кейсов — конкурс «Родная игрушка».",
|
||||
tag: "SC_Yakimanka",
|
||||
cardId: 1,
|
||||
},
|
||||
{
|
||||
fullname: "Елена Васильева",
|
||||
image_url: "",
|
||||
about: "Редактор в VK",
|
||||
date: "12.09",
|
||||
title: "Профессионально делаю что хочу",
|
||||
text:
|
||||
"Привет! Я Лена, амбассадор работы по любви. Дважды меняла профессию, чтобы заниматься тем, что драйвит.",
|
||||
tag: "SC_NAZARE",
|
||||
cardId: 2,
|
||||
},
|
||||
{
|
||||
fullname: "Анастасия См",
|
||||
image_url: "",
|
||||
about: "Brand дизайнер в Сетка",
|
||||
date: "12.09",
|
||||
title: "Есть тут любители кофе и дизайна?)",
|
||||
text: "Я с вами))) отвечаю за бренд дизайн Сетки (все что вы видите в онлайн и оффлайн коммуникации)",
|
||||
tag: "SC_CAVE",
|
||||
cardId: 3,
|
||||
},
|
||||
{
|
||||
fullname: "Алексей Смагин",
|
||||
image_url: "",
|
||||
about: "Аналитик в Яндекс",
|
||||
date: "12.09",
|
||||
title: "Нахожу в данных прекрасное",
|
||||
text:
|
||||
"Привет, меня зовут Лёша. Я люблю творить. И исследовать мир. В своей работе я самовыражаюсь через данные: работаю с большим количеством текстов и цифр, превращая их в познавательные, развлекательные или социальные истории; делаю инфографику и спецпроекты, основанные на данных.",
|
||||
tag: "SC_CAVE",
|
||||
cardId: 4,
|
||||
},
|
||||
{
|
||||
fullname: "Виктор Жаров",
|
||||
image_url: "",
|
||||
about: "Руководитель аналитики в Сетка",
|
||||
date: "12.09",
|
||||
title: "Привет! Я Витя и я аналитик",
|
||||
text: "Помогаю ребятам делать аналитику Сетки лучше. Мы с командой строим дашборды, анализируем поведение пользователей, делаем А/Б тесты. Все для того, чтобы лучше понимать, зачем пользователи приходят в Сетку и как сделать ее лучше.",
|
||||
tag: "SC_VDNX",
|
||||
cardId: 5,
|
||||
},
|
||||
{
|
||||
fullname: "Ярослав Вершинин",
|
||||
image_url: "",
|
||||
about: "Контент-лид",
|
||||
date: "12.09",
|
||||
title: "Я не люблю кофе... но обожаю различные чаи и какао 😏",
|
||||
text:
|
||||
"Всем привети, я Ярослав, успел целую неделю отработать на позиции руководителя пользовательского контента в Сетке. \
|
||||
Вместе с моей замечательно командой ищем...",
|
||||
tag: "SC_CAVE",
|
||||
cardId: 6,
|
||||
},
|
||||
{
|
||||
fullname: "Екатерина Савоськина",
|
||||
image_url: "",
|
||||
about: "Бренд-менеджер",
|
||||
date: "12.09",
|
||||
title: "бренд-менеджер vs амбассадор",
|
||||
text:
|
||||
"Всем привет! Я Катя, и я работаю в Сетке. Хотя многие мои знакомые, которые следят за моими другими соцсетями, думают, что я просто амбассадор. Но думаю, что базовая настройка профессии бренд-менеджера — выбирать и работать в продуктах, в которые искренне веришь, и быть главным фанатом.",
|
||||
tag: "SC_Belka",
|
||||
cardId: 7,
|
||||
},
|
||||
{
|
||||
fullname: "Кирилл Бургов",
|
||||
image_url: "",
|
||||
about: "Marketing",
|
||||
date: "12.09",
|
||||
title: "Спишь?",
|
||||
text:
|
||||
"Всем привет! Я Кирилл, маркетолог, который верит, что реклама – это не про «купите срочно», а про эмоции, истории и связи между людьми.",
|
||||
tag: "SC_Yakimanka",
|
||||
cardId: 8,
|
||||
},
|
||||
{
|
||||
fullname: "Валерия Рыбакова",
|
||||
image_url: "",
|
||||
about: "Бренд-менеджер",
|
||||
date: "12.09",
|
||||
title: "Зумеры массово отменяют кофейни...",
|
||||
text:
|
||||
"Если в мире и есть люди, которых не удивляют такие новостные заголовки, то это маркетологи, которые работают с молодой аудиторией, потому что изучать (и часто опровергать) подобные новости — наша работа :) Меня зовут Лера, a.k.a. зумер-патруль в команде маркетинга hh.ru . Именно наша команда делает так, чтобы молодежь точно знала, где искать ту самую работу.",
|
||||
tag: "SC_Flacon",
|
||||
cardId: 9,
|
||||
},
|
||||
];
|
@ -0,0 +1,14 @@
|
||||
|
||||
import { sendGoal } from '@utils';
|
||||
import styles from './Button.module.css';
|
||||
|
||||
export const Button = ({text}) => {
|
||||
|
||||
const handleContestRules = () => {
|
||||
sendGoal('contest_rules_clicked');
|
||||
};
|
||||
|
||||
return (
|
||||
<a href='/surfing/rules' className={styles.button} onClick={handleContestRules}>{text}</a>
|
||||
)
|
||||
}
|
@ -0,0 +1,36 @@
|
||||
.button {
|
||||
width: 100%;
|
||||
height: 58px;
|
||||
|
||||
font-family: 'TT Travels Next';
|
||||
font-style: normal;
|
||||
font-weight: 700;
|
||||
font-size: 20px;
|
||||
line-height: 120%;
|
||||
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
|
||||
border: 1px solid #FFFFFF;
|
||||
border-radius: 4px;
|
||||
|
||||
transition: var(--transition);
|
||||
color: inherit;
|
||||
background-color: black;
|
||||
}
|
||||
|
||||
.button:hover {
|
||||
background-color: white;
|
||||
color: black;
|
||||
}
|
||||
|
||||
@media screen and (max-width: 1100px) {
|
||||
.button {
|
||||
font-family: 'TT Travels Next';
|
||||
font-style: normal;
|
||||
font-weight: 700;
|
||||
font-size: 16px;
|
||||
line-height: 120%;
|
||||
}
|
||||
}
|
@ -0,0 +1,37 @@
|
||||
import { Button } from "./Button/Button";
|
||||
import styles from "./Header.module.css";
|
||||
|
||||
export const Header = () => {
|
||||
return (
|
||||
<div className={styles.container}>
|
||||
<h1 className={styles.h1}>
|
||||
попади в закрытое комьюнити для сёрфинга по локациям
|
||||
</h1>
|
||||
<p className={styles.text}>
|
||||
Смотри по хештегу, кто уже сёрфит в удобной для тебя локации.
|
||||
<br />
|
||||
<br />А также публикуй{" "}
|
||||
<a href='https://set.ki/chan_inv/CrvvTgv' target='_blank'>
|
||||
в закрытом сообществе
|
||||
</a>{" "}
|
||||
Сетка х Surf Coffee® в Сетке свои посты с фото
|
||||
и хештегами локаций, чтобы тебя заметили нужные люди. Каждую неделю
|
||||
мы выбираем 3 поста, авторы которых получают набор классного мерча
|
||||
Сетки и коробку дрип-пакетов от Surf Coffee®.
|
||||
<br />
|
||||
<br />
|
||||
Конкурс действует до его отмены.
|
||||
</p>
|
||||
<a
|
||||
className={styles.link}
|
||||
href='https://setka.onelink.me/tQlI/k82d3mhf'
|
||||
target='_blank'
|
||||
>
|
||||
<img src='/surfing/app_logo.svg' className={styles.logo_app} />
|
||||
</a>
|
||||
<div className={styles.button}>
|
||||
<Button text='условия конкурса' />
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
};
|
@ -0,0 +1,118 @@
|
||||
.link {
|
||||
width: min-content;
|
||||
}
|
||||
|
||||
.container a {
|
||||
color: inherit;
|
||||
}
|
||||
|
||||
.h1 {
|
||||
font-family: 'TT Travels Next';
|
||||
font-style: normal;
|
||||
font-weight: 700;
|
||||
font-size: 55px;
|
||||
line-height: 100%;
|
||||
|
||||
max-width: 671px;
|
||||
|
||||
}
|
||||
|
||||
.text {
|
||||
font-family: 'Inter';
|
||||
font-style: normal;
|
||||
font-weight: 500;
|
||||
font-size: 20px;
|
||||
line-height: 130%;
|
||||
|
||||
max-width: 539px;
|
||||
}
|
||||
|
||||
.text a {
|
||||
text-decoration-line: underline;
|
||||
}
|
||||
|
||||
.container {
|
||||
display: grid;
|
||||
column-gap: 30px;
|
||||
row-gap: 60px;
|
||||
align-items: center;
|
||||
|
||||
max-width: 1440px;
|
||||
}
|
||||
|
||||
@media screen and (max-width: 880px) {
|
||||
.container {
|
||||
row-gap: 20px;
|
||||
}
|
||||
}
|
||||
|
||||
.h1 {
|
||||
grid-column: 1;
|
||||
align-self: normal;
|
||||
}
|
||||
|
||||
.text {
|
||||
grid-column: 2;
|
||||
align-self: normal;
|
||||
}
|
||||
|
||||
@media screen and (max-width: 1100px) {
|
||||
.logo_app {
|
||||
display: none;
|
||||
}
|
||||
.container {
|
||||
grid-template-columns: 1fr;
|
||||
width: 100%;
|
||||
}
|
||||
.text {
|
||||
grid-column: 1;
|
||||
max-width: 700px;
|
||||
|
||||
font-size: 16px;
|
||||
align-self: normal;
|
||||
}
|
||||
.h1 {
|
||||
max-width: 80vw;
|
||||
|
||||
font-size: 40px;
|
||||
}
|
||||
}
|
||||
|
||||
@media screen and (max-width: 650px) {
|
||||
.h1 {
|
||||
font-family: 'TT Travels Next';
|
||||
font-style: normal;
|
||||
font-weight: 700;
|
||||
font-size: 28px;
|
||||
line-height: 100%;
|
||||
|
||||
max-width: 100%;
|
||||
}
|
||||
|
||||
.text {
|
||||
font-family: 'Inter';
|
||||
font-style: normal;
|
||||
font-weight: 500;
|
||||
font-size: 13px;
|
||||
line-height: 130%;
|
||||
|
||||
max-width: 100%;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
.button {
|
||||
max-width: 309px;
|
||||
}
|
||||
|
||||
@media screen and (max-width:680) {
|
||||
.button {
|
||||
max-width: 335px;
|
||||
}
|
||||
}
|
||||
|
||||
@media screen and (max-width: 500px) {
|
||||
.button {
|
||||
max-width: 100%;
|
||||
}
|
||||
}
|
@ -0,0 +1,10 @@
|
||||
|
||||
import styles from './MobileIcon.module.css';
|
||||
|
||||
export const MobileIcon = () => {
|
||||
return (
|
||||
<a href="https://setka.onelink.me/tQlI/k82d3mhf" target='_blank' className={styles.container}>
|
||||
<img src="/surfing/app_logo.svg" className={styles.app_logo}/>
|
||||
</a>
|
||||
)
|
||||
}
|
@ -0,0 +1,28 @@
|
||||
|
||||
|
||||
.container {
|
||||
padding-top: 60px;
|
||||
|
||||
width: 100%;
|
||||
display: none;
|
||||
justify-content: center;
|
||||
position: relative;
|
||||
z-index: 2;
|
||||
max-width: min-content;
|
||||
}
|
||||
|
||||
.app_logo {
|
||||
width: 122px;
|
||||
}
|
||||
|
||||
@media screen and (max-width: 1100px) {
|
||||
.container {
|
||||
display: flex;
|
||||
}
|
||||
}
|
||||
|
||||
@media screen and (max-width: 680px) {
|
||||
.container {
|
||||
padding-top: 22px;
|
||||
}
|
||||
}
|
After Width: | Height: | Size: 169 KiB |
40
src/pages/HomePage/components/FooterBlock/FooterBlock.jsx
Normal file
@ -0,0 +1,40 @@
|
||||
import styles from "./FooterBlock.module.css";
|
||||
|
||||
import head_image from "./waves.svg";
|
||||
|
||||
import image_1 from "./sc_setka-1.png";
|
||||
import image_2 from "./sc_setka-2.png";
|
||||
import image_3 from "./sc_setka-3.png";
|
||||
import { Logo } from "../../../../components/Logo/Logo";
|
||||
import { ButtonGroupFooter } from "../MainBlock/components/ButtonGroupFooter/ButtonGroupFooter";
|
||||
|
||||
export const FooterBlock = () => {
|
||||
return (
|
||||
<div className={styles.footer}>
|
||||
<div className={styles.row}>
|
||||
<img src={head_image} className={styles.head_image} />
|
||||
<div className={styles.right}>
|
||||
<div className={styles.right_image}>
|
||||
<img src={image_1} />
|
||||
<img src={image_2} />
|
||||
<img src={image_3} />
|
||||
</div>
|
||||
<h1 className={styles.h1}>
|
||||
нетворкинг
|
||||
<br />
|
||||
от Сетки
|
||||
<br />и Surf Coffee®
|
||||
</h1>
|
||||
<h2 className={styles.h2}>16 октября, следите за обновлениями</h2>
|
||||
</div>
|
||||
</div>
|
||||
<Logo isDark={true} />
|
||||
<ButtonGroupFooter />
|
||||
<p className={styles.copyright}>
|
||||
(c) HeadHunter {new Date().getFullYear()}. Информация на данном сайте
|
||||
<br />
|
||||
не является публичной офертой.
|
||||
</p>
|
||||
</div>
|
||||
);
|
||||
};
|
247
src/pages/HomePage/components/FooterBlock/FooterBlock.module.css
Normal file
@ -0,0 +1,247 @@
|
||||
|
||||
.footer {
|
||||
background-color: white;
|
||||
|
||||
color: black;
|
||||
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
|
||||
padding-top: 105px;
|
||||
|
||||
/* overflow: hidden; */
|
||||
}
|
||||
|
||||
/* текст-картинка и надпись с тремя картинками */
|
||||
.row {
|
||||
display: flex;
|
||||
flex-direction: row;
|
||||
gap: 81px;
|
||||
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
max-width: 1440px;
|
||||
/* padding-left: var(--padding-mobile-horizontal); */
|
||||
/* padding-right: var(--padding-mobile-horizontal); */
|
||||
}
|
||||
|
||||
.h1 {
|
||||
font-family: 'TT Travels Next';
|
||||
font-style: normal;
|
||||
font-weight: 700;
|
||||
font-size: 56px;
|
||||
line-height: 100%;
|
||||
}
|
||||
|
||||
.h1 {
|
||||
padding-top: 50px;
|
||||
}
|
||||
|
||||
.h2 {
|
||||
font-family: 'Inter';
|
||||
font-style: normal;
|
||||
font-weight: 400;
|
||||
font-size: 30px;
|
||||
line-height: 100%;
|
||||
|
||||
padding-top: 19px;
|
||||
}
|
||||
|
||||
/* Выше картинки ниже текст */
|
||||
.right {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
/* Начало трех картинки */
|
||||
.right_image {
|
||||
display: flex;
|
||||
flex-direction: row;
|
||||
gap: 38px;
|
||||
align-items: baseline;
|
||||
}
|
||||
|
||||
.right_image img {
|
||||
width: 100%;
|
||||
height: auto;
|
||||
position: relative;
|
||||
}
|
||||
|
||||
.right_image img:nth-child(1) {
|
||||
top: -44px;
|
||||
}
|
||||
|
||||
.right_image img:nth-child(3) {
|
||||
top: 150px;
|
||||
}
|
||||
|
||||
@media screen and (max-width: 1340px) {
|
||||
.h1 {
|
||||
font-size: 42px;
|
||||
|
||||
padding-top: 25px;
|
||||
}
|
||||
.h2 {
|
||||
font-size: 24px;
|
||||
}
|
||||
.h1 {
|
||||
width: fit-content;
|
||||
}
|
||||
.h2 {
|
||||
width: fit-content;
|
||||
}
|
||||
.right {
|
||||
width: 39vw;
|
||||
}
|
||||
.right_image {
|
||||
position: relative;
|
||||
left: -60px;
|
||||
scale: 0.80;
|
||||
}
|
||||
.row {
|
||||
gap: 40px;
|
||||
}
|
||||
.head_image {
|
||||
max-width: 40vw;
|
||||
}
|
||||
}
|
||||
|
||||
@media screen and (max-width: 680px) {
|
||||
.h1 {
|
||||
font-family: 'TT Travels Next';
|
||||
font-style: normal;
|
||||
font-weight: 700;
|
||||
font-size: 30px;
|
||||
line-height: 100%;
|
||||
}
|
||||
|
||||
.h2 {
|
||||
|
||||
font-family: 'Inter';
|
||||
font-style: normal;
|
||||
font-weight: 500;
|
||||
font-size: 13px;
|
||||
line-height: 130%;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* --- Конец трех картинок */
|
||||
|
||||
.logo {
|
||||
padding-top: 76px;
|
||||
padding-bottom: 90px;
|
||||
max-width: 465px;
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
.logo img {
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
@media screen and (max-width:1000px) {
|
||||
.head_image {
|
||||
max-width: 70vw;
|
||||
z-index: 1;
|
||||
}
|
||||
.right_image {
|
||||
display: none;
|
||||
z-index: 2;
|
||||
}
|
||||
.row {
|
||||
padding-top: 100px;
|
||||
flex-direction: column;
|
||||
align-items: baseline;
|
||||
position: relative;
|
||||
gap: 120px;
|
||||
}
|
||||
.right {
|
||||
width: 100%;
|
||||
}
|
||||
.footer {
|
||||
padding-top: 0;
|
||||
}
|
||||
.logo {
|
||||
padding-top: 58px;
|
||||
max-width: 45vw;
|
||||
padding-bottom: 67px;
|
||||
}
|
||||
|
||||
.row::after {
|
||||
margin-top: 20px;
|
||||
content: "";
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
background-image: url("./image_mobile_group.png");
|
||||
background-repeat: no-repeat;
|
||||
background-size: contain;
|
||||
position: absolute;
|
||||
top: 0;
|
||||
left: 0;
|
||||
}
|
||||
}
|
||||
|
||||
@media screen and (max-width: 680px) {
|
||||
.head_image {
|
||||
max-width: 300px;
|
||||
}
|
||||
.logo {
|
||||
padding-top: 58px;
|
||||
max-width: 250px;
|
||||
}
|
||||
|
||||
.row::after {
|
||||
top: 30px;
|
||||
}
|
||||
|
||||
.row {
|
||||
gap: 60px;
|
||||
}
|
||||
}
|
||||
|
||||
@media screen and (max-width: 370px) {
|
||||
.head_image {
|
||||
max-width: 80vw;
|
||||
}
|
||||
.h1 {
|
||||
font-size: 8vw;
|
||||
}
|
||||
.h2 {
|
||||
font-size: 4vw;
|
||||
}
|
||||
.logo {
|
||||
max-width: 70vw;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
.copyright {
|
||||
font-family: Inter;
|
||||
font-size: 16px;
|
||||
line-height: 130%;
|
||||
text-align: center;
|
||||
margin: 52px auto 82px;
|
||||
}
|
||||
|
||||
@media screen and (max-width: 800px) {
|
||||
.copyright {
|
||||
margin: 28px auto 44px;
|
||||
|
||||
font-family: 'Inter';
|
||||
font-style: normal;
|
||||
font-weight: 500;
|
||||
font-size: 13px;
|
||||
line-height: 130%;
|
||||
|
||||
text-align: start;
|
||||
padding: 0 var(--padding-mobile-horizontal);
|
||||
}
|
||||
}
|
||||
|
||||
@media screen and (max-width: 340px) {
|
||||
.copyright {
|
||||
font-size: 9px;
|
||||
}
|
||||
}
|
BIN
src/pages/HomePage/components/FooterBlock/image_mobile_group.png
Normal file
After Width: | Height: | Size: 276 KiB |
BIN
src/pages/HomePage/components/FooterBlock/sc_setka-1.png
Normal file
After Width: | Height: | Size: 59 KiB |
BIN
src/pages/HomePage/components/FooterBlock/sc_setka-2.png
Normal file
After Width: | Height: | Size: 67 KiB |