рефакторинг
This commit is contained in:
28
README.md
28
README.md
@@ -1,27 +1 @@
|
||||
# React + TypeScript + Vite
|
||||
|
||||
This template provides a minimal setup to get React working in Vite with HMR and some ESLint rules.
|
||||
|
||||
Currently, two official plugins are available:
|
||||
|
||||
- [@vitejs/plugin-react](https://github.com/vitejs/vite-plugin-react/blob/main/packages/plugin-react/README.md) uses [Babel](https://babeljs.io/) for Fast Refresh
|
||||
- [@vitejs/plugin-react-swc](https://github.com/vitejs/vite-plugin-react-swc) uses [SWC](https://swc.rs/) for Fast Refresh
|
||||
|
||||
## Expanding the ESLint configuration
|
||||
|
||||
If you are developing a production application, we recommend updating the configuration to enable type aware lint rules:
|
||||
|
||||
- Configure the top-level `parserOptions` property like this:
|
||||
|
||||
```js
|
||||
parserOptions: {
|
||||
ecmaVersion: 'latest',
|
||||
sourceType: 'module',
|
||||
project: ['./tsconfig.json', './tsconfig.node.json'],
|
||||
tsconfigRootDir: __dirname,
|
||||
},
|
||||
```
|
||||
|
||||
- Replace `plugin:@typescript-eslint/recommended` to `plugin:@typescript-eslint/recommended-type-checked` or `plugin:@typescript-eslint/strict-type-checked`
|
||||
- Optionally add `plugin:@typescript-eslint/stylistic-type-checked`
|
||||
- Install [eslint-plugin-react](https://github.com/jsx-eslint/eslint-plugin-react) and add `plugin:react/recommended` & `plugin:react/jsx-runtime` to the `extends` list
|
||||
Сайт с калькулятором на mathjs
|
||||
|
||||
@@ -6,7 +6,7 @@
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<link rel="icon" type="image/svg" href="./favicon.svg" />
|
||||
<link rel="manifest" href="./manifest.webmanifest" />
|
||||
<title>Calculator</title>
|
||||
<title>calculator</title>
|
||||
</head>
|
||||
<body>
|
||||
<div id="root"></div>
|
||||
|
||||
53
src/App.tsx
53
src/App.tsx
@@ -1,53 +0,0 @@
|
||||
import { noop } from 'lodash'
|
||||
import { Editor } from './Editor'
|
||||
|
||||
export const App = () => {
|
||||
return <Editor text={testText} onChange={noop} />
|
||||
}
|
||||
|
||||
const testText = `
|
||||
# Welcome to calculator (написать норм приветствие и описать принцип работы калькулятора)
|
||||
# Lines starting with # are ignored
|
||||
|
||||
# Basic math
|
||||
2 + 2
|
||||
6 - 3
|
||||
10 / 4
|
||||
5 * 1.5
|
||||
2 + 2 * 2
|
||||
(2 + 2) * 2
|
||||
0.1 + 0.2
|
||||
|
||||
# Units
|
||||
10 inch in cm
|
||||
2 feet to m
|
||||
15 degC to degF
|
||||
3 tbsp to tsp
|
||||
9 km/h to m/s
|
||||
|
||||
# Functions
|
||||
sqrt(3^2 + 4^2)
|
||||
cos(pi rad)
|
||||
sin(30 deg)
|
||||
|
||||
# Variables
|
||||
a = 25
|
||||
b = a * 2
|
||||
|
||||
2 * 2
|
||||
last + 1
|
||||
|
||||
# Function declaration
|
||||
pow2(x) = x ^ 2
|
||||
pow2(6)
|
||||
|
||||
f(x) = (sin(x) + cos(x/2)) * 5
|
||||
|
||||
# Matrices
|
||||
a = [1, 2, 3; 2+2, 5, 6]
|
||||
a[2, 3]
|
||||
a[1:2, 2]
|
||||
b = [1, 2; 3, 4]
|
||||
b * a
|
||||
a[3, 1:3] = [7, 8, 9]
|
||||
`
|
||||
@@ -1,33 +1,89 @@
|
||||
import { defaultKeymap, historyKeymap, history } from '@codemirror/commands'
|
||||
import { EditorView, drawSelection, dropCursor, keymap } from '@codemirror/view'
|
||||
import { EditorView, drawSelection, dropCursor, keymap, placeholder } from '@codemirror/view'
|
||||
import { defaultHighlightStyle, indentOnInput, syntaxHighlighting } from '@codemirror/language'
|
||||
import { Extension } from '@codemirror/state'
|
||||
import { closeBrackets, closeBracketsKeymap } from '@codemirror/autocomplete'
|
||||
import { searchKeymap } from '@codemirror/search'
|
||||
import { useEffect, useRef } from 'react'
|
||||
import { textObserverPlugin } from './textObserverPlugin'
|
||||
import { mathPlugin } from './mathPlugin'
|
||||
|
||||
type Props = {
|
||||
text: string
|
||||
onChange: (text: string) => void
|
||||
}
|
||||
const testText = `# Welcome to calculator
|
||||
# Lines starting with # are ignored
|
||||
|
||||
export const Editor = ({ text, onChange }: Props) => {
|
||||
# Basic math
|
||||
2 + 2
|
||||
6 - 3
|
||||
10 / 4
|
||||
5 * 1.5
|
||||
2 + 2 * 2
|
||||
(2 + 2) * 2
|
||||
0.1 + 0.2
|
||||
|
||||
# Units
|
||||
10 inch in cm
|
||||
2 feet to m
|
||||
15 degC to degF
|
||||
3 tbsp to tsp
|
||||
9 km/h to m/s
|
||||
|
||||
# Functions
|
||||
sqrt(3^2 + 4^2)
|
||||
cos(pi rad)
|
||||
sin(30 deg)
|
||||
|
||||
# Variables
|
||||
a = 25
|
||||
b = a * 2
|
||||
|
||||
2 * 2
|
||||
last + 1
|
||||
|
||||
# Function declaration
|
||||
pow2(x) = x ^ 2
|
||||
pow2(6)
|
||||
|
||||
f(x) = (sin(x) + cos(x/2)) * 5
|
||||
|
||||
# Matrices
|
||||
a = [1, 2, 3; 2+2, 5, 6]
|
||||
a[2, 3]
|
||||
a[1:2, 2]
|
||||
b = [1, 2; 3, 4]
|
||||
b * a
|
||||
a[3, 1:3] = [7, 8, 9]
|
||||
`
|
||||
|
||||
export const Editor = () => {
|
||||
const ref = useRef<HTMLDivElement>(null)
|
||||
const view = useRef<EditorView>()
|
||||
|
||||
useEffect(() => {
|
||||
view.current = new EditorView({
|
||||
doc: text,
|
||||
extensions: [basicSetup, textObserverPlugin(onChange)],
|
||||
doc: '',
|
||||
extensions: [basicSetup],
|
||||
parent: ref.current!,
|
||||
})
|
||||
|
||||
return () => view.current?.destroy()
|
||||
}, [])
|
||||
|
||||
return <div className="cm-editor-mount" ref={ref}></div>
|
||||
return (
|
||||
<div className="wrapper">
|
||||
<div className="header">
|
||||
<button
|
||||
className="example-button"
|
||||
onClick={() => {
|
||||
view.current?.dispatch({
|
||||
changes: { from: 0, to: view.current?.state.doc.length, insert: testText },
|
||||
})
|
||||
}}
|
||||
>
|
||||
tutorial
|
||||
</button>
|
||||
</div>
|
||||
<div className="cm-editor-mount" ref={ref}></div>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
||||
const basicSetup: Extension = [
|
||||
@@ -39,4 +95,5 @@ const basicSetup: Extension = [
|
||||
closeBrackets(),
|
||||
keymap.of([...closeBracketsKeymap, ...defaultKeymap, ...searchKeymap, ...historyKeymap]),
|
||||
mathPlugin(),
|
||||
placeholder('0.1 + 0.2 = 0.3'),
|
||||
]
|
||||
|
||||
@@ -22,6 +22,10 @@ body {
|
||||
outline: none;
|
||||
}
|
||||
|
||||
.cm-scroller {
|
||||
margin-right: -14px;
|
||||
}
|
||||
|
||||
.math-result {
|
||||
color: rgb(80, 80, 80);
|
||||
margin-left: 8px;
|
||||
@@ -52,3 +56,26 @@ body {
|
||||
border-left: 0;
|
||||
margin-left: 6px;
|
||||
}
|
||||
|
||||
.example-button {
|
||||
background-color: black;
|
||||
color: white;
|
||||
border: none;
|
||||
border-radius: 4px;
|
||||
padding: 8px 16px;
|
||||
font-family: monospace;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
margin: 8px 0;
|
||||
transition: all 0.2s ease;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
.example-button:hover {
|
||||
background-color: #333;
|
||||
transform: translateY(-3px);
|
||||
}
|
||||
|
||||
.example-button:active {
|
||||
transform: translateY(3px);
|
||||
}
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
import React from 'react'
|
||||
import ReactDOM from 'react-dom/client'
|
||||
import { App } from './App.tsx'
|
||||
import { Editor } from './Editor.tsx'
|
||||
import './index.css'
|
||||
|
||||
const root = document.getElementById('root')
|
||||
@@ -8,7 +8,7 @@ const root = document.getElementById('root')
|
||||
if (root) {
|
||||
ReactDOM.createRoot(root).render(
|
||||
<React.StrictMode>
|
||||
<App />
|
||||
<Editor />
|
||||
</React.StrictMode>,
|
||||
)
|
||||
}
|
||||
|
||||
@@ -1,3 +0,0 @@
|
||||
import { create, all } from 'mathjs'
|
||||
|
||||
export const math = create(all)
|
||||
@@ -1,5 +1,7 @@
|
||||
import { Decoration, DecorationSet, EditorView, ViewPlugin, ViewUpdate, WidgetType } from '@codemirror/view'
|
||||
import { math } from './math'
|
||||
import { create, all } from 'mathjs'
|
||||
|
||||
const math = create(all)
|
||||
|
||||
export const mathPlugin = () =>
|
||||
ViewPlugin.fromClass(
|
||||
|
||||
@@ -1,10 +0,0 @@
|
||||
import { ViewPlugin, ViewUpdate } from '@codemirror/view'
|
||||
|
||||
export const textObserverPlugin = (callback: (text: string) => void) =>
|
||||
ViewPlugin.define(() => ({
|
||||
update(update: ViewUpdate) {
|
||||
if (update.docChanged) {
|
||||
callback(update.state.doc.toString())
|
||||
}
|
||||
},
|
||||
}))
|
||||
Reference in New Issue
Block a user