initial commit, lesson 1

This commit is contained in:
andres
2023-06-23 17:50:25 +02:00
parent e20bdb8eef
commit e190c8c698
44 changed files with 3424 additions and 498 deletions

10
pages/_meta.en.json Normal file
View File

@@ -0,0 +1,10 @@
{
"index": "Introduction",
"figma": {
"title": "Figma ↗",
"type": "page",
"href": "https://www.figma.com/file/PwHkQjA62wyw8BSEyW4gIk/%D0%9E%D0%B1%D1%83%D1%87%D0%B5%D0%BD%D0%B8%D0%B5-%D0%BF%D0%BE-%D0%BA%D0%B0%D1%80%D1%82%D0%BE%D1%87%D0%BA%D0%B0%D0%BC?node-id=0%3A1&mode=dev",
"newWindow": true
},
"lesson-1": "Lesson 1: Hello World!"
}

View File

@@ -1,15 +0,0 @@
{
"index": "Introduction",
"another": "Another Page",
"advanced": "Advanced (A Folder)",
"about": {
"title": "About",
"type": "page"
},
"contact": {
"title": "Contact ↗",
"type": "page",
"href": "https://twitter.com/shuding_",
"newWindow": true
}
}

10
pages/_meta.ru.json Normal file
View File

@@ -0,0 +1,10 @@
{
"index": "Введение",
"figma": {
"title": "Figma ↗",
"type": "page",
"href": "https://www.figma.com/file/PwHkQjA62wyw8BSEyW4gIk/%D0%9E%D0%B1%D1%83%D1%87%D0%B5%D0%BD%D0%B8%D0%B5-%D0%BF%D0%BE-%D0%BA%D0%B0%D1%80%D1%82%D0%BE%D1%87%D0%BA%D0%B0%D0%BC?node-id=0%3A1&mode=dev",
"newWindow": true
},
"lesson-1": "Урок 1"
}

View File

@@ -1,3 +0,0 @@
# About
This is the about page! This page is shown on the navbar.

View File

@@ -1,3 +0,0 @@
# Advanced
This is the index page for the Advanced folder!

View File

@@ -1,3 +0,0 @@
# Satori
Satori (悟り) is a Japanese Buddhist term for awakening, "comprehension; understanding".

View File

@@ -1,31 +0,0 @@
# Another Page
```js filename="demo.js" {3} copy
let a = 1;
console.log(a);
```
## Component
import { useState } from 'react'
{/* Import CSS modules */}
import styles from '../components/counters.module.css'
export const Counter = () => {
const [count, setCount] = useState(0);
return (
<div>
<button onClick={() => setCount(count + 1)} className={styles.counter}>Clicked {count} times</button>
</div>
);
};
<Counter/>
## External Component
import Counters from '../components/counters'
<Counters />

5
pages/index.en.mdx Normal file
View File

@@ -0,0 +1,5 @@
import { Callout } from 'nextra/components'
# Introduction
<Callout type="warning">This page is under construction. Check back later!</Callout>

View File

@@ -1,11 +0,0 @@
# Introduction
Welcome to Nextra! This is a basic docs template. You can use it as a starting point for your own project :)
## What is Nextra?
A **simple**, **powerful** and **flexible** site generation framework with everything you love from Next.js.
## Documentation
The documentation is available at [https://nextra.site](https://nextra.site).

5
pages/index.ru.mdx Normal file
View File

@@ -0,0 +1,5 @@
import { Callout } from 'nextra/components'
# Introduction
<Callout type="warning">Страница в разработке, возвращайтесь попозже!</Callout>

View File

@@ -0,0 +1,4 @@
{
"chapter-1": "Chapter 1",
"chapter-2": "Chapter 2"
}

View File

@@ -0,0 +1,4 @@
{
"chapter-1": "1. Создание и настройка проекта",
"chapter-2": "Chapter 2"
}

View File

@@ -0,0 +1 @@
# Under construction

View File

@@ -0,0 +1,181 @@
import { Callout } from 'nextra/components'
import { DownloadLink } from '../../components'
# 1. Создание и настройка проекта
## Vite
Мы будем использовать [Vite](https://vitejs.dev/) в качестве сборщика.
```bash filename="Terminal"
pnpm create vite
```
- Выберите название для проекта на ваш вкус
- Фреймворк - React
- Тип приложения - TypeScript
<Callout type={'warning'}>
После создания проекта не забудьте установить зависимости, используя <code>pnpm i</code>
</Callout>
## Инициализация git
В отличие от create-react-app, vite не инициализирует git репозиторий автоматически, поэтому нам нужно сделать это вручную:
```bash filename="Terminal"
git init
```
## Установка зависимостей
### Linters
Мы будем использовать линтеры от команды IT-Incubator:
```bash filename="Terminal"
pnpm i @it-incubator/eslint-config @it-incubator/prettier-config @it-incubator/stylelint-config stylelint -D
```
### SASS
Мы будем использовать SASS в качестве препроцессора стилей:
```bash filename="Terminal"
pnpm i sass -D
```
## Конфигурация линтеров
### Prettier
Создайте файл .prettierrc.cjs в корне проекта и скопируйте туда следующее содержимое:
```js filename=".prettierrc.cjs"
module.exports = {
...require('@it-incubator/prettier-config'),
//override settings here
}
```
### ESLint
Замените содержимое файла .eslintrc.cjs на следующее:
```js filename=".eslintrc.cjs"
module.exports = {
extends: '@it-incubator/eslint-config',
rules: { 'no-console': ['warn', { allow: ['warn', 'error'] }] },
}
```
### Stylelint
Создайте файл .stylelintrc.cjs в корне проекта и скопируйте туда следующее содержимое:
```js filename=".stylelintrc.cjs"
module.exports = {
extends: '@it-incubator/stylelint-config',
}
```
## Конфигурация WebStorm
### Включить ESLint
![eslint-settings.png](./images/eslint-settings.png)
### Включить Prettier
```bash
{**/*,*}.{js,ts,jsx,tsx,vue,astro,cjs,mjs,css,scss}
```
![prettier-settings.png](./images/prettier-settings.png)
### Включить stylelint
![stylelint-settings.png](./images/stylelint-settings.png)
### Включить автоматическое исправление ошибок при сохранении .css/.scss файлов
<DownloadLink href="./watchers.xml" />
После импорта получим следующее: ![file-watchers-settings.png](./images/file-watchers-settings.png)
### Добавить скрипты в package.json, перезаписывая значения по умолчанию при необходимости
```json lines filename="package.json"
{
"scripts": {
"format": "prettier --write src",
"lint": "eslint --fix src/**/*.{tsx,ts,jsx,js} --no-error-on-unmatched-pattern && stylelint --fix src/{,*/}*.{scss,css} --allow-empty-input"
}
}
```
### Убрать boilerplate
- Удалить файл App.css
- Удалить папку assets
- Заменить содержимое файла App.tsx на следующее:
```tsx filename="App.tsx"
export function App() {
return <div>Hello</div>
}
```
### Запустить линтеры
- Prettier
```bash
pnpm run format
```
- Eslint и Stylelint
```bash
pnpm run lint
```
Некоторые ошибки eslint не исправляются автоматически, поэтому вам придется сделать это самостоятельно, например:
![eslint-error-main.png](./images/eslint-error-main.png)
Постарайтесь разобраться сами, если не получится - замените содержимое файла main.tsx на следующее:
```tsx filename="main.tsx"
import './index.css'
import { StrictMode } from 'react'
import { createRoot } from 'react-dom/client'
import { App } from './App.tsx'
createRoot(document.getElementById('root') as HTMLElement).render(
<StrictMode>
<App />
</StrictMode>
)
```
<Callout type={'warning'}>
Наш eslint конфиг использует плагин import\/order, который требует, чтобы ваши файлы **css/scss
были размещены либо первыми, либо последними в импортах** (см. пример выше), иначе вы получите
неразрешимые ошибки.
</Callout>
## Итоговая структура папок
Так должна выглядеть структура папок к концу этой главы:
![final-folder-structure.png](./images/final-folder-structure.png)
## Коммитим изменения
Не забудьте закоммитить изменения:
```bash filename="Terminal"
git add .
git commit -m "Initial commit"
```

207
pages/lesson-1/chapter-2.md Normal file
View File

@@ -0,0 +1,207 @@
# Chapter 2
## Deploy to Vercel
You should already know how to do it.
If you're using the Redux-vite template make sure to change the output directory to 'build' in project settings on
Vercel:
![vercel-output-directory.png](./images/vercel-output-directory.png)
Make sure it is deployed successfully.
## Storybook
- Install:
```bash
pnpm dlx storybook@latest init
```
> **Accept eslint config**
- Try it out:
```bash
pnpm run storybook
```
## Install fonts
[Fontsource/montserrat](https://fontsource.org/fonts/montserrat)
```bash
pnpm install @fontsource-variable/montserrat
```
```tsx
// main.tsx
import '@fontsource-variable/montserrat'
```
## Set up css variables
- Create an _src/styles_ directory in your project
containing the following files:
```markdown
src
└── styles
└── \_boilerplate.scss
└── \_colors.scss
└── \_typography.scss
└── index.scss
```
- Add the following to _index.scss_:
```scss
@forward 'colors';
@forward 'typography';
@forward 'boilerplate';
```
- Add the following to \__colors.scss_:
```scss
:root {
// text
--color-text-primary: #000;
--color-text-secondary: #fff;
// backgrounds
--color-bg-primary: #3d3d3d;
--color-bg-secondary: #fcfcfc;
--color-bg-tertiary: #efefef;
// palette
--color-primary: #366eff;
--color-secondary: #ffc700;
--color-danger: #ff3636;
}
```
> Add any extra colors you need yourself
- Add the following to \__typography.scss_:
```scss
:root {
--font-family-primary: 'Montserrat Variable', sans-serif;
// line heights
--line-height-xs: 0.991rem;
--line-height-s: 1.219rem;
--line-height-m: 1.5rem;
--line-height-l: 1.75rem;
}
```
> Add font sizes and font weights yourself
> Transform font sizes to rem: <https://nekocalc.com/px-to-rem-converter>
- Add the following to \__boilerplate.scss_:
```scss
html {
font-size: 100%;
-webkit-font-smoothing: antialiased;
-moz-osx-font-smoothing: grayscale;
}
*,
*::before,
*::after {
box-sizing: border-box;
}
input,
button,
select,
textarea,
optgroup,
option {
font-family: inherit;
font-size: inherit;
font-weight: inherit;
font-style: inherit;
color: inherit;
}
body {
margin: 0;
padding: 0;
font-family: var(--font-family-primary);
line-height: var(--line-height-m);
color: var(--color-text-primary);
background-color: var(--color-bg-primary);
}
```
- Import _index.scss_ in _main.tsx_:
```tsx
// main.tsx
import './styles/index.scss'
```
- Import fonts and styles in storybook:
```tsx
// .storybook/preview.tsx
import '@fontsource-variable/montserrat'
import '../src/styles/index.scss'
```
## Components
- Create an _src/components/ui_ directory in your project
### Button
- Create a _button_ directory in _src/components/ui_ with the following files:
```markdown
src
└── components
└── ui
└── button
└── button.tsx
└── button.module.scss
└── button.stories.ts
└── index.ts
```
> **Try to create the component yourself first**
Essentially, we are going to have 5 variants of our button:
- Primary (blue)
- Secondary (white)
- Danger (orange)
- Full width
- A link that looks like a button
What it means is that we are going to need these props:
<https://www.tints.dev>
```tsx
import { ComponentPropsWithoutRef } from 'react'
type ButtonProps = {
variant?: 'primary' | 'secondary' | 'danger'
fullWidth?: boolean
} & ComponentPropsWithoutRef<'button'>
```
The problem here is that we are getting button props, but we will also need it to be a link, and, potentially, a react-router-dom Link, so we want to make our component polymorphic:
```tsx
```

Binary file not shown.

After

Width:  |  Height:  |  Size: 78 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 569 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 563 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 51 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 554 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 633 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 149 KiB

View File

@@ -0,0 +1,42 @@
<TaskOptions>
<TaskOptions>
<option name="arguments" value="$FilePath$ --fix" />
<option name="checkSyntaxErrors" value="true" />
<option name="description" />
<option name="exitCodeBehavior" value="ERROR" />
<option name="fileExtension" value="css" />
<option name="immediateSync" value="false" />
<option name="name" value="Stylelint" />
<option name="output" value="$FilePath$" />
<option name="outputFilters">
<array />
</option>
<option name="outputFromStdout" value="false" />
<option name="program" value="$ProjectFileDir$/node_modules/.bin/stylelint" />
<option name="runOnExternalChanges" value="false" />
<option name="scopeName" value="Current File" />
<option name="trackOnlyRoot" value="false" />
<option name="workingDir" value="" />
<envs />
</TaskOptions>
<TaskOptions>
<option name="arguments" value="$FilePath$ --fix" />
<option name="checkSyntaxErrors" value="true" />
<option name="description" />
<option name="exitCodeBehavior" value="ERROR" />
<option name="fileExtension" value="scss" />
<option name="immediateSync" value="false" />
<option name="name" value="Stylelint scss" />
<option name="output" value="$FilePath$" />
<option name="outputFilters">
<array />
</option>
<option name="outputFromStdout" value="false" />
<option name="program" value="$ProjectFileDir$/node_modules/.bin/stylelint" />
<option name="runOnExternalChanges" value="false" />
<option name="scopeName" value="Current File" />
<option name="trackOnlyRoot" value="false" />
<option name="workingDir" value="" />
<envs />
</TaskOptions>
</TaskOptions>