diff --git a/code/01-starting-setup/package.json b/code/01-starting-setup/package.json new file mode 100644 index 0000000000..b16a8faa39 --- /dev/null +++ b/code/01-starting-setup/package.json @@ -0,0 +1,38 @@ +{ + "name": "react-complete-guide", + "version": "0.1.0", + "private": true, + "dependencies": { + "@testing-library/jest-dom": "^5.11.6", + "@testing-library/react": "^11.2.2", + "@testing-library/user-event": "^12.5.0", + "react": "^18.0.0", + "react-dom": "^18.0.0", + "react-scripts": "4.0.1", + "web-vitals": "^0.2.4" + }, + "scripts": { + "start": "react-scripts start", + "build": "react-scripts build", + "test": "react-scripts test", + "eject": "react-scripts eject" + }, + "eslintConfig": { + "extends": [ + "react-app", + "react-app/jest" + ] + }, + "browserslist": { + "production": [ + ">0.2%", + "not dead", + "not op_mini all" + ], + "development": [ + "last 1 chrome version", + "last 1 firefox version", + "last 1 safari version" + ] + } +} diff --git a/code/01-starting-setup/public/favicon.ico b/code/01-starting-setup/public/favicon.ico new file mode 100644 index 0000000000..a11777cc47 Binary files /dev/null and b/code/01-starting-setup/public/favicon.ico differ diff --git a/code/01-starting-setup/public/index.html b/code/01-starting-setup/public/index.html new file mode 100644 index 0000000000..aa069f27cb --- /dev/null +++ b/code/01-starting-setup/public/index.html @@ -0,0 +1,43 @@ + + + + + + + + + + + + + React App + + + +
+ + + diff --git a/code/01-starting-setup/public/logo192.png b/code/01-starting-setup/public/logo192.png new file mode 100644 index 0000000000..fc44b0a379 Binary files /dev/null and b/code/01-starting-setup/public/logo192.png differ diff --git a/code/01-starting-setup/public/logo512.png b/code/01-starting-setup/public/logo512.png new file mode 100644 index 0000000000..a4e47a6545 Binary files /dev/null and b/code/01-starting-setup/public/logo512.png differ diff --git a/code/01-starting-setup/public/manifest.json b/code/01-starting-setup/public/manifest.json new file mode 100644 index 0000000000..080d6c77ac --- /dev/null +++ b/code/01-starting-setup/public/manifest.json @@ -0,0 +1,25 @@ +{ + "short_name": "React App", + "name": "Create React App Sample", + "icons": [ + { + "src": "favicon.ico", + "sizes": "64x64 32x32 24x24 16x16", + "type": "image/x-icon" + }, + { + "src": "logo192.png", + "type": "image/png", + "sizes": "192x192" + }, + { + "src": "logo512.png", + "type": "image/png", + "sizes": "512x512" + } + ], + "start_url": ".", + "display": "standalone", + "theme_color": "#000000", + "background_color": "#ffffff" +} diff --git a/code/01-starting-setup/public/robots.txt b/code/01-starting-setup/public/robots.txt new file mode 100644 index 0000000000..e9e57dc4d4 --- /dev/null +++ b/code/01-starting-setup/public/robots.txt @@ -0,0 +1,3 @@ +# https://www.robotstxt.org/robotstxt.html +User-agent: * +Disallow: diff --git a/code/01-starting-setup/src/App.js b/code/01-starting-setup/src/App.js new file mode 100644 index 0000000000..4a194e6079 --- /dev/null +++ b/code/01-starting-setup/src/App.js @@ -0,0 +1,9 @@ +function App() { + return ( +
+

Let's get started!

+
+ ); +} + +export default App; diff --git a/code/01-starting-setup/src/index.css b/code/01-starting-setup/src/index.css new file mode 100644 index 0000000000..72399cc5c6 --- /dev/null +++ b/code/01-starting-setup/src/index.css @@ -0,0 +1,15 @@ +@import url('https://fonts.googleapis.com/css2?family=Noto+Sans+JP:wght@400;700&display=swap'); + +* { + box-sizing: border-box; +} + +html { + font-family: 'Noto Sans JP', sans-serif; +} + +body { + margin: 0; + background-color: #3f3f3f; +} + diff --git a/code/01-starting-setup/src/index.js b/code/01-starting-setup/src/index.js new file mode 100644 index 0000000000..778ec1ba20 --- /dev/null +++ b/code/01-starting-setup/src/index.js @@ -0,0 +1,7 @@ +import ReactDOM from 'react-dom/client'; + +import './index.css'; +import App from './App'; + +const root = ReactDOM.createRoot(document.getElementById('root')); +root.render(); diff --git a/code/02-building-a-first-custom-component/package.json b/code/02-building-a-first-custom-component/package.json new file mode 100644 index 0000000000..b16a8faa39 --- /dev/null +++ b/code/02-building-a-first-custom-component/package.json @@ -0,0 +1,38 @@ +{ + "name": "react-complete-guide", + "version": "0.1.0", + "private": true, + "dependencies": { + "@testing-library/jest-dom": "^5.11.6", + "@testing-library/react": "^11.2.2", + "@testing-library/user-event": "^12.5.0", + "react": "^18.0.0", + "react-dom": "^18.0.0", + "react-scripts": "4.0.1", + "web-vitals": "^0.2.4" + }, + "scripts": { + "start": "react-scripts start", + "build": "react-scripts build", + "test": "react-scripts test", + "eject": "react-scripts eject" + }, + "eslintConfig": { + "extends": [ + "react-app", + "react-app/jest" + ] + }, + "browserslist": { + "production": [ + ">0.2%", + "not dead", + "not op_mini all" + ], + "development": [ + "last 1 chrome version", + "last 1 firefox version", + "last 1 safari version" + ] + } +} diff --git a/code/02-building-a-first-custom-component/public/favicon.ico b/code/02-building-a-first-custom-component/public/favicon.ico new file mode 100644 index 0000000000..a11777cc47 Binary files /dev/null and b/code/02-building-a-first-custom-component/public/favicon.ico differ diff --git a/code/02-building-a-first-custom-component/public/index.html b/code/02-building-a-first-custom-component/public/index.html new file mode 100644 index 0000000000..aa069f27cb --- /dev/null +++ b/code/02-building-a-first-custom-component/public/index.html @@ -0,0 +1,43 @@ + + + + + + + + + + + + + React App + + + +
+ + + diff --git a/code/02-building-a-first-custom-component/public/logo192.png b/code/02-building-a-first-custom-component/public/logo192.png new file mode 100644 index 0000000000..fc44b0a379 Binary files /dev/null and b/code/02-building-a-first-custom-component/public/logo192.png differ diff --git a/code/02-building-a-first-custom-component/public/logo512.png b/code/02-building-a-first-custom-component/public/logo512.png new file mode 100644 index 0000000000..a4e47a6545 Binary files /dev/null and b/code/02-building-a-first-custom-component/public/logo512.png differ diff --git a/code/02-building-a-first-custom-component/public/manifest.json b/code/02-building-a-first-custom-component/public/manifest.json new file mode 100644 index 0000000000..080d6c77ac --- /dev/null +++ b/code/02-building-a-first-custom-component/public/manifest.json @@ -0,0 +1,25 @@ +{ + "short_name": "React App", + "name": "Create React App Sample", + "icons": [ + { + "src": "favicon.ico", + "sizes": "64x64 32x32 24x24 16x16", + "type": "image/x-icon" + }, + { + "src": "logo192.png", + "type": "image/png", + "sizes": "192x192" + }, + { + "src": "logo512.png", + "type": "image/png", + "sizes": "512x512" + } + ], + "start_url": ".", + "display": "standalone", + "theme_color": "#000000", + "background_color": "#ffffff" +} diff --git a/code/02-building-a-first-custom-component/public/robots.txt b/code/02-building-a-first-custom-component/public/robots.txt new file mode 100644 index 0000000000..e9e57dc4d4 --- /dev/null +++ b/code/02-building-a-first-custom-component/public/robots.txt @@ -0,0 +1,3 @@ +# https://www.robotstxt.org/robotstxt.html +User-agent: * +Disallow: diff --git a/code/02-building-a-first-custom-component/src/App.js b/code/02-building-a-first-custom-component/src/App.js new file mode 100644 index 0000000000..264e51e726 --- /dev/null +++ b/code/02-building-a-first-custom-component/src/App.js @@ -0,0 +1,12 @@ +import ExpenseItem from './components/ExpenseItem'; + +function App() { + return ( +
+

Let's get started!

+ +
+ ); +} + +export default App; diff --git a/code/02-building-a-first-custom-component/src/components/ExpenseItem.js b/code/02-building-a-first-custom-component/src/components/ExpenseItem.js new file mode 100644 index 0000000000..790588b878 --- /dev/null +++ b/code/02-building-a-first-custom-component/src/components/ExpenseItem.js @@ -0,0 +1,5 @@ +function ExpenseItem() { + return

Expense item!

; +} + +export default ExpenseItem; diff --git a/code/02-building-a-first-custom-component/src/index.css b/code/02-building-a-first-custom-component/src/index.css new file mode 100644 index 0000000000..72399cc5c6 --- /dev/null +++ b/code/02-building-a-first-custom-component/src/index.css @@ -0,0 +1,15 @@ +@import url('https://fonts.googleapis.com/css2?family=Noto+Sans+JP:wght@400;700&display=swap'); + +* { + box-sizing: border-box; +} + +html { + font-family: 'Noto Sans JP', sans-serif; +} + +body { + margin: 0; + background-color: #3f3f3f; +} + diff --git a/code/02-building-a-first-custom-component/src/index.js b/code/02-building-a-first-custom-component/src/index.js new file mode 100644 index 0000000000..778ec1ba20 --- /dev/null +++ b/code/02-building-a-first-custom-component/src/index.js @@ -0,0 +1,7 @@ +import ReactDOM from 'react-dom/client'; + +import './index.css'; +import App from './App'; + +const root = ReactDOM.createRoot(document.getElementById('root')); +root.render(); diff --git a/code/03-writing-more-complex-jsx-code/package.json b/code/03-writing-more-complex-jsx-code/package.json new file mode 100644 index 0000000000..b16a8faa39 --- /dev/null +++ b/code/03-writing-more-complex-jsx-code/package.json @@ -0,0 +1,38 @@ +{ + "name": "react-complete-guide", + "version": "0.1.0", + "private": true, + "dependencies": { + "@testing-library/jest-dom": "^5.11.6", + "@testing-library/react": "^11.2.2", + "@testing-library/user-event": "^12.5.0", + "react": "^18.0.0", + "react-dom": "^18.0.0", + "react-scripts": "4.0.1", + "web-vitals": "^0.2.4" + }, + "scripts": { + "start": "react-scripts start", + "build": "react-scripts build", + "test": "react-scripts test", + "eject": "react-scripts eject" + }, + "eslintConfig": { + "extends": [ + "react-app", + "react-app/jest" + ] + }, + "browserslist": { + "production": [ + ">0.2%", + "not dead", + "not op_mini all" + ], + "development": [ + "last 1 chrome version", + "last 1 firefox version", + "last 1 safari version" + ] + } +} diff --git a/code/03-writing-more-complex-jsx-code/public/favicon.ico b/code/03-writing-more-complex-jsx-code/public/favicon.ico new file mode 100644 index 0000000000..a11777cc47 Binary files /dev/null and b/code/03-writing-more-complex-jsx-code/public/favicon.ico differ diff --git a/code/03-writing-more-complex-jsx-code/public/index.html b/code/03-writing-more-complex-jsx-code/public/index.html new file mode 100644 index 0000000000..aa069f27cb --- /dev/null +++ b/code/03-writing-more-complex-jsx-code/public/index.html @@ -0,0 +1,43 @@ + + + + + + + + + + + + + React App + + + +
+ + + diff --git a/code/03-writing-more-complex-jsx-code/public/logo192.png b/code/03-writing-more-complex-jsx-code/public/logo192.png new file mode 100644 index 0000000000..fc44b0a379 Binary files /dev/null and b/code/03-writing-more-complex-jsx-code/public/logo192.png differ diff --git a/code/03-writing-more-complex-jsx-code/public/logo512.png b/code/03-writing-more-complex-jsx-code/public/logo512.png new file mode 100644 index 0000000000..a4e47a6545 Binary files /dev/null and b/code/03-writing-more-complex-jsx-code/public/logo512.png differ diff --git a/code/03-writing-more-complex-jsx-code/public/manifest.json b/code/03-writing-more-complex-jsx-code/public/manifest.json new file mode 100644 index 0000000000..080d6c77ac --- /dev/null +++ b/code/03-writing-more-complex-jsx-code/public/manifest.json @@ -0,0 +1,25 @@ +{ + "short_name": "React App", + "name": "Create React App Sample", + "icons": [ + { + "src": "favicon.ico", + "sizes": "64x64 32x32 24x24 16x16", + "type": "image/x-icon" + }, + { + "src": "logo192.png", + "type": "image/png", + "sizes": "192x192" + }, + { + "src": "logo512.png", + "type": "image/png", + "sizes": "512x512" + } + ], + "start_url": ".", + "display": "standalone", + "theme_color": "#000000", + "background_color": "#ffffff" +} diff --git a/code/03-writing-more-complex-jsx-code/public/robots.txt b/code/03-writing-more-complex-jsx-code/public/robots.txt new file mode 100644 index 0000000000..e9e57dc4d4 --- /dev/null +++ b/code/03-writing-more-complex-jsx-code/public/robots.txt @@ -0,0 +1,3 @@ +# https://www.robotstxt.org/robotstxt.html +User-agent: * +Disallow: diff --git a/code/03-writing-more-complex-jsx-code/src/App.js b/code/03-writing-more-complex-jsx-code/src/App.js new file mode 100644 index 0000000000..264e51e726 --- /dev/null +++ b/code/03-writing-more-complex-jsx-code/src/App.js @@ -0,0 +1,12 @@ +import ExpenseItem from './components/ExpenseItem'; + +function App() { + return ( +
+

Let's get started!

+ +
+ ); +} + +export default App; diff --git a/code/03-writing-more-complex-jsx-code/src/components/ExpenseItem.js b/code/03-writing-more-complex-jsx-code/src/components/ExpenseItem.js new file mode 100644 index 0000000000..1b178e39c5 --- /dev/null +++ b/code/03-writing-more-complex-jsx-code/src/components/ExpenseItem.js @@ -0,0 +1,13 @@ +function ExpenseItem() { + return ( +
+
March 28th 2021
+
+

Car Insurance

+
$294.67
+
+
+ ); +} + +export default ExpenseItem; diff --git a/code/03-writing-more-complex-jsx-code/src/index.css b/code/03-writing-more-complex-jsx-code/src/index.css new file mode 100644 index 0000000000..72399cc5c6 --- /dev/null +++ b/code/03-writing-more-complex-jsx-code/src/index.css @@ -0,0 +1,15 @@ +@import url('https://fonts.googleapis.com/css2?family=Noto+Sans+JP:wght@400;700&display=swap'); + +* { + box-sizing: border-box; +} + +html { + font-family: 'Noto Sans JP', sans-serif; +} + +body { + margin: 0; + background-color: #3f3f3f; +} + diff --git a/code/03-writing-more-complex-jsx-code/src/index.js b/code/03-writing-more-complex-jsx-code/src/index.js new file mode 100644 index 0000000000..778ec1ba20 --- /dev/null +++ b/code/03-writing-more-complex-jsx-code/src/index.js @@ -0,0 +1,7 @@ +import ReactDOM from 'react-dom/client'; + +import './index.css'; +import App from './App'; + +const root = ReactDOM.createRoot(document.getElementById('root')); +root.render(); diff --git a/code/04-adding-basic-css-styling/package.json b/code/04-adding-basic-css-styling/package.json new file mode 100644 index 0000000000..b16a8faa39 --- /dev/null +++ b/code/04-adding-basic-css-styling/package.json @@ -0,0 +1,38 @@ +{ + "name": "react-complete-guide", + "version": "0.1.0", + "private": true, + "dependencies": { + "@testing-library/jest-dom": "^5.11.6", + "@testing-library/react": "^11.2.2", + "@testing-library/user-event": "^12.5.0", + "react": "^18.0.0", + "react-dom": "^18.0.0", + "react-scripts": "4.0.1", + "web-vitals": "^0.2.4" + }, + "scripts": { + "start": "react-scripts start", + "build": "react-scripts build", + "test": "react-scripts test", + "eject": "react-scripts eject" + }, + "eslintConfig": { + "extends": [ + "react-app", + "react-app/jest" + ] + }, + "browserslist": { + "production": [ + ">0.2%", + "not dead", + "not op_mini all" + ], + "development": [ + "last 1 chrome version", + "last 1 firefox version", + "last 1 safari version" + ] + } +} diff --git a/code/04-adding-basic-css-styling/public/favicon.ico b/code/04-adding-basic-css-styling/public/favicon.ico new file mode 100644 index 0000000000..a11777cc47 Binary files /dev/null and b/code/04-adding-basic-css-styling/public/favicon.ico differ diff --git a/code/04-adding-basic-css-styling/public/index.html b/code/04-adding-basic-css-styling/public/index.html new file mode 100644 index 0000000000..aa069f27cb --- /dev/null +++ b/code/04-adding-basic-css-styling/public/index.html @@ -0,0 +1,43 @@ + + + + + + + + + + + + + React App + + + +
+ + + diff --git a/code/04-adding-basic-css-styling/public/logo192.png b/code/04-adding-basic-css-styling/public/logo192.png new file mode 100644 index 0000000000..fc44b0a379 Binary files /dev/null and b/code/04-adding-basic-css-styling/public/logo192.png differ diff --git a/code/04-adding-basic-css-styling/public/logo512.png b/code/04-adding-basic-css-styling/public/logo512.png new file mode 100644 index 0000000000..a4e47a6545 Binary files /dev/null and b/code/04-adding-basic-css-styling/public/logo512.png differ diff --git a/code/04-adding-basic-css-styling/public/manifest.json b/code/04-adding-basic-css-styling/public/manifest.json new file mode 100644 index 0000000000..080d6c77ac --- /dev/null +++ b/code/04-adding-basic-css-styling/public/manifest.json @@ -0,0 +1,25 @@ +{ + "short_name": "React App", + "name": "Create React App Sample", + "icons": [ + { + "src": "favicon.ico", + "sizes": "64x64 32x32 24x24 16x16", + "type": "image/x-icon" + }, + { + "src": "logo192.png", + "type": "image/png", + "sizes": "192x192" + }, + { + "src": "logo512.png", + "type": "image/png", + "sizes": "512x512" + } + ], + "start_url": ".", + "display": "standalone", + "theme_color": "#000000", + "background_color": "#ffffff" +} diff --git a/code/04-adding-basic-css-styling/public/robots.txt b/code/04-adding-basic-css-styling/public/robots.txt new file mode 100644 index 0000000000..e9e57dc4d4 --- /dev/null +++ b/code/04-adding-basic-css-styling/public/robots.txt @@ -0,0 +1,3 @@ +# https://www.robotstxt.org/robotstxt.html +User-agent: * +Disallow: diff --git a/code/04-adding-basic-css-styling/src/App.js b/code/04-adding-basic-css-styling/src/App.js new file mode 100644 index 0000000000..264e51e726 --- /dev/null +++ b/code/04-adding-basic-css-styling/src/App.js @@ -0,0 +1,12 @@ +import ExpenseItem from './components/ExpenseItem'; + +function App() { + return ( +
+

Let's get started!

+ +
+ ); +} + +export default App; diff --git a/code/04-adding-basic-css-styling/src/components/ExpenseItem.css b/code/04-adding-basic-css-styling/src/components/ExpenseItem.css new file mode 100644 index 0000000000..22eabe9e80 --- /dev/null +++ b/code/04-adding-basic-css-styling/src/components/ExpenseItem.css @@ -0,0 +1,56 @@ +.expense-item { + display: flex; + justify-content: space-between; + align-items: center; + box-shadow: 0 2px 8px rgba(0, 0, 0, 0.25); + padding: 0.5rem; + margin: 1rem 0; + border-radius: 12px; + background-color: #4b4b4b; +} + +.expense-item__description { + display: flex; + flex-direction: column; + gap: 1rem; + align-items: flex-end; + flex-flow: column-reverse; + justify-content: flex-start; + flex: 1; +} + +.expense-item h2 { + color: #3a3a3a; + font-size: 1rem; + flex: 1; + margin: 0 1rem; + color: white; +} + +.expense-item__price { + font-size: 1rem; + font-weight: bold; + color: white; + background-color: #40005d; + border: 1px solid white; + padding: 0.5rem; + border-radius: 12px; +} + +@media (min-width: 580px) { + .expense-item__description { + flex-direction: row; + align-items: center; + justify-content: flex-start; + flex: 1; + } + + .expense-item__description h2 { + font-size: 1.25rem; + } + + .expense-item__price { + font-size: 1.25rem; + padding: 0.5rem 1.5rem; + } +} \ No newline at end of file diff --git a/code/04-adding-basic-css-styling/src/components/ExpenseItem.js b/code/04-adding-basic-css-styling/src/components/ExpenseItem.js new file mode 100644 index 0000000000..4ed06c3ff8 --- /dev/null +++ b/code/04-adding-basic-css-styling/src/components/ExpenseItem.js @@ -0,0 +1,15 @@ +import './ExpenseItem.css'; + +function ExpenseItem() { + return ( +
+
March 28th 2021
+
+

Car Insurance

+
$294.67
+
+
+ ); +} + +export default ExpenseItem; diff --git a/code/04-adding-basic-css-styling/src/index.css b/code/04-adding-basic-css-styling/src/index.css new file mode 100644 index 0000000000..72399cc5c6 --- /dev/null +++ b/code/04-adding-basic-css-styling/src/index.css @@ -0,0 +1,15 @@ +@import url('https://fonts.googleapis.com/css2?family=Noto+Sans+JP:wght@400;700&display=swap'); + +* { + box-sizing: border-box; +} + +html { + font-family: 'Noto Sans JP', sans-serif; +} + +body { + margin: 0; + background-color: #3f3f3f; +} + diff --git a/code/04-adding-basic-css-styling/src/index.js b/code/04-adding-basic-css-styling/src/index.js new file mode 100644 index 0000000000..778ec1ba20 --- /dev/null +++ b/code/04-adding-basic-css-styling/src/index.js @@ -0,0 +1,7 @@ +import ReactDOM from 'react-dom/client'; + +import './index.css'; +import App from './App'; + +const root = ReactDOM.createRoot(document.getElementById('root')); +root.render(); diff --git a/code/05-outputting-dynamic-data/package.json b/code/05-outputting-dynamic-data/package.json new file mode 100644 index 0000000000..b16a8faa39 --- /dev/null +++ b/code/05-outputting-dynamic-data/package.json @@ -0,0 +1,38 @@ +{ + "name": "react-complete-guide", + "version": "0.1.0", + "private": true, + "dependencies": { + "@testing-library/jest-dom": "^5.11.6", + "@testing-library/react": "^11.2.2", + "@testing-library/user-event": "^12.5.0", + "react": "^18.0.0", + "react-dom": "^18.0.0", + "react-scripts": "4.0.1", + "web-vitals": "^0.2.4" + }, + "scripts": { + "start": "react-scripts start", + "build": "react-scripts build", + "test": "react-scripts test", + "eject": "react-scripts eject" + }, + "eslintConfig": { + "extends": [ + "react-app", + "react-app/jest" + ] + }, + "browserslist": { + "production": [ + ">0.2%", + "not dead", + "not op_mini all" + ], + "development": [ + "last 1 chrome version", + "last 1 firefox version", + "last 1 safari version" + ] + } +} diff --git a/code/05-outputting-dynamic-data/public/favicon.ico b/code/05-outputting-dynamic-data/public/favicon.ico new file mode 100644 index 0000000000..a11777cc47 Binary files /dev/null and b/code/05-outputting-dynamic-data/public/favicon.ico differ diff --git a/code/05-outputting-dynamic-data/public/index.html b/code/05-outputting-dynamic-data/public/index.html new file mode 100644 index 0000000000..aa069f27cb --- /dev/null +++ b/code/05-outputting-dynamic-data/public/index.html @@ -0,0 +1,43 @@ + + + + + + + + + + + + + React App + + + +
+ + + diff --git a/code/05-outputting-dynamic-data/public/logo192.png b/code/05-outputting-dynamic-data/public/logo192.png new file mode 100644 index 0000000000..fc44b0a379 Binary files /dev/null and b/code/05-outputting-dynamic-data/public/logo192.png differ diff --git a/code/05-outputting-dynamic-data/public/logo512.png b/code/05-outputting-dynamic-data/public/logo512.png new file mode 100644 index 0000000000..a4e47a6545 Binary files /dev/null and b/code/05-outputting-dynamic-data/public/logo512.png differ diff --git a/code/05-outputting-dynamic-data/public/manifest.json b/code/05-outputting-dynamic-data/public/manifest.json new file mode 100644 index 0000000000..080d6c77ac --- /dev/null +++ b/code/05-outputting-dynamic-data/public/manifest.json @@ -0,0 +1,25 @@ +{ + "short_name": "React App", + "name": "Create React App Sample", + "icons": [ + { + "src": "favicon.ico", + "sizes": "64x64 32x32 24x24 16x16", + "type": "image/x-icon" + }, + { + "src": "logo192.png", + "type": "image/png", + "sizes": "192x192" + }, + { + "src": "logo512.png", + "type": "image/png", + "sizes": "512x512" + } + ], + "start_url": ".", + "display": "standalone", + "theme_color": "#000000", + "background_color": "#ffffff" +} diff --git a/code/05-outputting-dynamic-data/public/robots.txt b/code/05-outputting-dynamic-data/public/robots.txt new file mode 100644 index 0000000000..e9e57dc4d4 --- /dev/null +++ b/code/05-outputting-dynamic-data/public/robots.txt @@ -0,0 +1,3 @@ +# https://www.robotstxt.org/robotstxt.html +User-agent: * +Disallow: diff --git a/code/05-outputting-dynamic-data/src/App.js b/code/05-outputting-dynamic-data/src/App.js new file mode 100644 index 0000000000..264e51e726 --- /dev/null +++ b/code/05-outputting-dynamic-data/src/App.js @@ -0,0 +1,12 @@ +import ExpenseItem from './components/ExpenseItem'; + +function App() { + return ( +
+

Let's get started!

+ +
+ ); +} + +export default App; diff --git a/code/05-outputting-dynamic-data/src/components/ExpenseItem.css b/code/05-outputting-dynamic-data/src/components/ExpenseItem.css new file mode 100644 index 0000000000..22eabe9e80 --- /dev/null +++ b/code/05-outputting-dynamic-data/src/components/ExpenseItem.css @@ -0,0 +1,56 @@ +.expense-item { + display: flex; + justify-content: space-between; + align-items: center; + box-shadow: 0 2px 8px rgba(0, 0, 0, 0.25); + padding: 0.5rem; + margin: 1rem 0; + border-radius: 12px; + background-color: #4b4b4b; +} + +.expense-item__description { + display: flex; + flex-direction: column; + gap: 1rem; + align-items: flex-end; + flex-flow: column-reverse; + justify-content: flex-start; + flex: 1; +} + +.expense-item h2 { + color: #3a3a3a; + font-size: 1rem; + flex: 1; + margin: 0 1rem; + color: white; +} + +.expense-item__price { + font-size: 1rem; + font-weight: bold; + color: white; + background-color: #40005d; + border: 1px solid white; + padding: 0.5rem; + border-radius: 12px; +} + +@media (min-width: 580px) { + .expense-item__description { + flex-direction: row; + align-items: center; + justify-content: flex-start; + flex: 1; + } + + .expense-item__description h2 { + font-size: 1.25rem; + } + + .expense-item__price { + font-size: 1.25rem; + padding: 0.5rem 1.5rem; + } +} \ No newline at end of file diff --git a/code/05-outputting-dynamic-data/src/components/ExpenseItem.js b/code/05-outputting-dynamic-data/src/components/ExpenseItem.js new file mode 100644 index 0000000000..362371a920 --- /dev/null +++ b/code/05-outputting-dynamic-data/src/components/ExpenseItem.js @@ -0,0 +1,19 @@ +import './ExpenseItem.css'; + +function ExpenseItem() { + const expenseDate = new Date(2021, 2, 28); + const expenseTitle = 'Car Insurance'; + const expenseAmount = 294.67; + + return ( +
+
{expenseDate.toISOString()}
+
+

{expenseTitle}

+
${expenseAmount}
+
+
+ ); +} + +export default ExpenseItem; diff --git a/code/05-outputting-dynamic-data/src/index.css b/code/05-outputting-dynamic-data/src/index.css new file mode 100644 index 0000000000..72399cc5c6 --- /dev/null +++ b/code/05-outputting-dynamic-data/src/index.css @@ -0,0 +1,15 @@ +@import url('https://fonts.googleapis.com/css2?family=Noto+Sans+JP:wght@400;700&display=swap'); + +* { + box-sizing: border-box; +} + +html { + font-family: 'Noto Sans JP', sans-serif; +} + +body { + margin: 0; + background-color: #3f3f3f; +} + diff --git a/code/05-outputting-dynamic-data/src/index.js b/code/05-outputting-dynamic-data/src/index.js new file mode 100644 index 0000000000..778ec1ba20 --- /dev/null +++ b/code/05-outputting-dynamic-data/src/index.js @@ -0,0 +1,7 @@ +import ReactDOM from 'react-dom/client'; + +import './index.css'; +import App from './App'; + +const root = ReactDOM.createRoot(document.getElementById('root')); +root.render(); diff --git a/code/06-passing-data-via-props/package.json b/code/06-passing-data-via-props/package.json new file mode 100644 index 0000000000..b16a8faa39 --- /dev/null +++ b/code/06-passing-data-via-props/package.json @@ -0,0 +1,38 @@ +{ + "name": "react-complete-guide", + "version": "0.1.0", + "private": true, + "dependencies": { + "@testing-library/jest-dom": "^5.11.6", + "@testing-library/react": "^11.2.2", + "@testing-library/user-event": "^12.5.0", + "react": "^18.0.0", + "react-dom": "^18.0.0", + "react-scripts": "4.0.1", + "web-vitals": "^0.2.4" + }, + "scripts": { + "start": "react-scripts start", + "build": "react-scripts build", + "test": "react-scripts test", + "eject": "react-scripts eject" + }, + "eslintConfig": { + "extends": [ + "react-app", + "react-app/jest" + ] + }, + "browserslist": { + "production": [ + ">0.2%", + "not dead", + "not op_mini all" + ], + "development": [ + "last 1 chrome version", + "last 1 firefox version", + "last 1 safari version" + ] + } +} diff --git a/code/06-passing-data-via-props/public/favicon.ico b/code/06-passing-data-via-props/public/favicon.ico new file mode 100644 index 0000000000..a11777cc47 Binary files /dev/null and b/code/06-passing-data-via-props/public/favicon.ico differ diff --git a/code/06-passing-data-via-props/public/index.html b/code/06-passing-data-via-props/public/index.html new file mode 100644 index 0000000000..aa069f27cb --- /dev/null +++ b/code/06-passing-data-via-props/public/index.html @@ -0,0 +1,43 @@ + + + + + + + + + + + + + React App + + + +
+ + + diff --git a/code/06-passing-data-via-props/public/logo192.png b/code/06-passing-data-via-props/public/logo192.png new file mode 100644 index 0000000000..fc44b0a379 Binary files /dev/null and b/code/06-passing-data-via-props/public/logo192.png differ diff --git a/code/06-passing-data-via-props/public/logo512.png b/code/06-passing-data-via-props/public/logo512.png new file mode 100644 index 0000000000..a4e47a6545 Binary files /dev/null and b/code/06-passing-data-via-props/public/logo512.png differ diff --git a/code/06-passing-data-via-props/public/manifest.json b/code/06-passing-data-via-props/public/manifest.json new file mode 100644 index 0000000000..080d6c77ac --- /dev/null +++ b/code/06-passing-data-via-props/public/manifest.json @@ -0,0 +1,25 @@ +{ + "short_name": "React App", + "name": "Create React App Sample", + "icons": [ + { + "src": "favicon.ico", + "sizes": "64x64 32x32 24x24 16x16", + "type": "image/x-icon" + }, + { + "src": "logo192.png", + "type": "image/png", + "sizes": "192x192" + }, + { + "src": "logo512.png", + "type": "image/png", + "sizes": "512x512" + } + ], + "start_url": ".", + "display": "standalone", + "theme_color": "#000000", + "background_color": "#ffffff" +} diff --git a/code/06-passing-data-via-props/public/robots.txt b/code/06-passing-data-via-props/public/robots.txt new file mode 100644 index 0000000000..e9e57dc4d4 --- /dev/null +++ b/code/06-passing-data-via-props/public/robots.txt @@ -0,0 +1,3 @@ +# https://www.robotstxt.org/robotstxt.html +User-agent: * +Disallow: diff --git a/code/06-passing-data-via-props/src/App.js b/code/06-passing-data-via-props/src/App.js new file mode 100644 index 0000000000..878e1cd3a3 --- /dev/null +++ b/code/06-passing-data-via-props/src/App.js @@ -0,0 +1,53 @@ +import ExpenseItem from './components/ExpenseItem'; + +function App() { + const expenses = [ + { + id: 'e1', + title: 'Toilet Paper', + amount: 94.12, + date: new Date(2020, 7, 14), + }, + { id: 'e2', title: 'New TV', amount: 799.49, date: new Date(2021, 2, 12) }, + { + id: 'e3', + title: 'Car Insurance', + amount: 294.67, + date: new Date(2021, 2, 28), + }, + { + id: 'e4', + title: 'New Desk (Wooden)', + amount: 450, + date: new Date(2021, 5, 12), + }, + ]; + + return ( +
+

Let's get started!

+ + + + +
+ ); +} + +export default App; diff --git a/code/06-passing-data-via-props/src/components/ExpenseItem.css b/code/06-passing-data-via-props/src/components/ExpenseItem.css new file mode 100644 index 0000000000..22eabe9e80 --- /dev/null +++ b/code/06-passing-data-via-props/src/components/ExpenseItem.css @@ -0,0 +1,56 @@ +.expense-item { + display: flex; + justify-content: space-between; + align-items: center; + box-shadow: 0 2px 8px rgba(0, 0, 0, 0.25); + padding: 0.5rem; + margin: 1rem 0; + border-radius: 12px; + background-color: #4b4b4b; +} + +.expense-item__description { + display: flex; + flex-direction: column; + gap: 1rem; + align-items: flex-end; + flex-flow: column-reverse; + justify-content: flex-start; + flex: 1; +} + +.expense-item h2 { + color: #3a3a3a; + font-size: 1rem; + flex: 1; + margin: 0 1rem; + color: white; +} + +.expense-item__price { + font-size: 1rem; + font-weight: bold; + color: white; + background-color: #40005d; + border: 1px solid white; + padding: 0.5rem; + border-radius: 12px; +} + +@media (min-width: 580px) { + .expense-item__description { + flex-direction: row; + align-items: center; + justify-content: flex-start; + flex: 1; + } + + .expense-item__description h2 { + font-size: 1.25rem; + } + + .expense-item__price { + font-size: 1.25rem; + padding: 0.5rem 1.5rem; + } +} \ No newline at end of file diff --git a/code/06-passing-data-via-props/src/components/ExpenseItem.js b/code/06-passing-data-via-props/src/components/ExpenseItem.js new file mode 100644 index 0000000000..9de60d6b21 --- /dev/null +++ b/code/06-passing-data-via-props/src/components/ExpenseItem.js @@ -0,0 +1,15 @@ +import './ExpenseItem.css'; + +function ExpenseItem(props) { + return ( +
+
{props.date.toISOString()}
+
+

{props.title}

+
${props.amount}
+
+
+ ); +} + +export default ExpenseItem; diff --git a/code/06-passing-data-via-props/src/index.css b/code/06-passing-data-via-props/src/index.css new file mode 100644 index 0000000000..72399cc5c6 --- /dev/null +++ b/code/06-passing-data-via-props/src/index.css @@ -0,0 +1,15 @@ +@import url('https://fonts.googleapis.com/css2?family=Noto+Sans+JP:wght@400;700&display=swap'); + +* { + box-sizing: border-box; +} + +html { + font-family: 'Noto Sans JP', sans-serif; +} + +body { + margin: 0; + background-color: #3f3f3f; +} + diff --git a/code/06-passing-data-via-props/src/index.js b/code/06-passing-data-via-props/src/index.js new file mode 100644 index 0000000000..778ec1ba20 --- /dev/null +++ b/code/06-passing-data-via-props/src/index.js @@ -0,0 +1,7 @@ +import ReactDOM from 'react-dom/client'; + +import './index.css'; +import App from './App'; + +const root = ReactDOM.createRoot(document.getElementById('root')); +root.render(); diff --git a/code/07-adding-normal-javascript-logic/package.json b/code/07-adding-normal-javascript-logic/package.json new file mode 100644 index 0000000000..b16a8faa39 --- /dev/null +++ b/code/07-adding-normal-javascript-logic/package.json @@ -0,0 +1,38 @@ +{ + "name": "react-complete-guide", + "version": "0.1.0", + "private": true, + "dependencies": { + "@testing-library/jest-dom": "^5.11.6", + "@testing-library/react": "^11.2.2", + "@testing-library/user-event": "^12.5.0", + "react": "^18.0.0", + "react-dom": "^18.0.0", + "react-scripts": "4.0.1", + "web-vitals": "^0.2.4" + }, + "scripts": { + "start": "react-scripts start", + "build": "react-scripts build", + "test": "react-scripts test", + "eject": "react-scripts eject" + }, + "eslintConfig": { + "extends": [ + "react-app", + "react-app/jest" + ] + }, + "browserslist": { + "production": [ + ">0.2%", + "not dead", + "not op_mini all" + ], + "development": [ + "last 1 chrome version", + "last 1 firefox version", + "last 1 safari version" + ] + } +} diff --git a/code/07-adding-normal-javascript-logic/public/favicon.ico b/code/07-adding-normal-javascript-logic/public/favicon.ico new file mode 100644 index 0000000000..a11777cc47 Binary files /dev/null and b/code/07-adding-normal-javascript-logic/public/favicon.ico differ diff --git a/code/07-adding-normal-javascript-logic/public/index.html b/code/07-adding-normal-javascript-logic/public/index.html new file mode 100644 index 0000000000..aa069f27cb --- /dev/null +++ b/code/07-adding-normal-javascript-logic/public/index.html @@ -0,0 +1,43 @@ + + + + + + + + + + + + + React App + + + +
+ + + diff --git a/code/07-adding-normal-javascript-logic/public/logo192.png b/code/07-adding-normal-javascript-logic/public/logo192.png new file mode 100644 index 0000000000..fc44b0a379 Binary files /dev/null and b/code/07-adding-normal-javascript-logic/public/logo192.png differ diff --git a/code/07-adding-normal-javascript-logic/public/logo512.png b/code/07-adding-normal-javascript-logic/public/logo512.png new file mode 100644 index 0000000000..a4e47a6545 Binary files /dev/null and b/code/07-adding-normal-javascript-logic/public/logo512.png differ diff --git a/code/07-adding-normal-javascript-logic/public/manifest.json b/code/07-adding-normal-javascript-logic/public/manifest.json new file mode 100644 index 0000000000..080d6c77ac --- /dev/null +++ b/code/07-adding-normal-javascript-logic/public/manifest.json @@ -0,0 +1,25 @@ +{ + "short_name": "React App", + "name": "Create React App Sample", + "icons": [ + { + "src": "favicon.ico", + "sizes": "64x64 32x32 24x24 16x16", + "type": "image/x-icon" + }, + { + "src": "logo192.png", + "type": "image/png", + "sizes": "192x192" + }, + { + "src": "logo512.png", + "type": "image/png", + "sizes": "512x512" + } + ], + "start_url": ".", + "display": "standalone", + "theme_color": "#000000", + "background_color": "#ffffff" +} diff --git a/code/07-adding-normal-javascript-logic/public/robots.txt b/code/07-adding-normal-javascript-logic/public/robots.txt new file mode 100644 index 0000000000..e9e57dc4d4 --- /dev/null +++ b/code/07-adding-normal-javascript-logic/public/robots.txt @@ -0,0 +1,3 @@ +# https://www.robotstxt.org/robotstxt.html +User-agent: * +Disallow: diff --git a/code/07-adding-normal-javascript-logic/src/App.js b/code/07-adding-normal-javascript-logic/src/App.js new file mode 100644 index 0000000000..878e1cd3a3 --- /dev/null +++ b/code/07-adding-normal-javascript-logic/src/App.js @@ -0,0 +1,53 @@ +import ExpenseItem from './components/ExpenseItem'; + +function App() { + const expenses = [ + { + id: 'e1', + title: 'Toilet Paper', + amount: 94.12, + date: new Date(2020, 7, 14), + }, + { id: 'e2', title: 'New TV', amount: 799.49, date: new Date(2021, 2, 12) }, + { + id: 'e3', + title: 'Car Insurance', + amount: 294.67, + date: new Date(2021, 2, 28), + }, + { + id: 'e4', + title: 'New Desk (Wooden)', + amount: 450, + date: new Date(2021, 5, 12), + }, + ]; + + return ( +
+

Let's get started!

+ + + + +
+ ); +} + +export default App; diff --git a/code/07-adding-normal-javascript-logic/src/components/ExpenseItem.css b/code/07-adding-normal-javascript-logic/src/components/ExpenseItem.css new file mode 100644 index 0000000000..22eabe9e80 --- /dev/null +++ b/code/07-adding-normal-javascript-logic/src/components/ExpenseItem.css @@ -0,0 +1,56 @@ +.expense-item { + display: flex; + justify-content: space-between; + align-items: center; + box-shadow: 0 2px 8px rgba(0, 0, 0, 0.25); + padding: 0.5rem; + margin: 1rem 0; + border-radius: 12px; + background-color: #4b4b4b; +} + +.expense-item__description { + display: flex; + flex-direction: column; + gap: 1rem; + align-items: flex-end; + flex-flow: column-reverse; + justify-content: flex-start; + flex: 1; +} + +.expense-item h2 { + color: #3a3a3a; + font-size: 1rem; + flex: 1; + margin: 0 1rem; + color: white; +} + +.expense-item__price { + font-size: 1rem; + font-weight: bold; + color: white; + background-color: #40005d; + border: 1px solid white; + padding: 0.5rem; + border-radius: 12px; +} + +@media (min-width: 580px) { + .expense-item__description { + flex-direction: row; + align-items: center; + justify-content: flex-start; + flex: 1; + } + + .expense-item__description h2 { + font-size: 1.25rem; + } + + .expense-item__price { + font-size: 1.25rem; + padding: 0.5rem 1.5rem; + } +} \ No newline at end of file diff --git a/code/07-adding-normal-javascript-logic/src/components/ExpenseItem.js b/code/07-adding-normal-javascript-logic/src/components/ExpenseItem.js new file mode 100644 index 0000000000..6821b40063 --- /dev/null +++ b/code/07-adding-normal-javascript-logic/src/components/ExpenseItem.js @@ -0,0 +1,23 @@ +import './ExpenseItem.css'; + +function ExpenseItem(props) { + const month = props.date.toLocaleString('en-US', { month: 'long' }); + const day = props.date.toLocaleString('en-US', { day: '2-digit' }); + const year = props.date.getFullYear(); + + return ( +
+
+
{month}
+
{year}
+
{day}
+
+
+

{props.title}

+
${props.amount}
+
+
+ ); +} + +export default ExpenseItem; diff --git a/code/07-adding-normal-javascript-logic/src/index.css b/code/07-adding-normal-javascript-logic/src/index.css new file mode 100644 index 0000000000..72399cc5c6 --- /dev/null +++ b/code/07-adding-normal-javascript-logic/src/index.css @@ -0,0 +1,15 @@ +@import url('https://fonts.googleapis.com/css2?family=Noto+Sans+JP:wght@400;700&display=swap'); + +* { + box-sizing: border-box; +} + +html { + font-family: 'Noto Sans JP', sans-serif; +} + +body { + margin: 0; + background-color: #3f3f3f; +} + diff --git a/code/07-adding-normal-javascript-logic/src/index.js b/code/07-adding-normal-javascript-logic/src/index.js new file mode 100644 index 0000000000..778ec1ba20 --- /dev/null +++ b/code/07-adding-normal-javascript-logic/src/index.js @@ -0,0 +1,7 @@ +import ReactDOM from 'react-dom/client'; + +import './index.css'; +import App from './App'; + +const root = ReactDOM.createRoot(document.getElementById('root')); +root.render(); diff --git a/code/08-splitting-components-into-multiple-components/package.json b/code/08-splitting-components-into-multiple-components/package.json new file mode 100644 index 0000000000..b16a8faa39 --- /dev/null +++ b/code/08-splitting-components-into-multiple-components/package.json @@ -0,0 +1,38 @@ +{ + "name": "react-complete-guide", + "version": "0.1.0", + "private": true, + "dependencies": { + "@testing-library/jest-dom": "^5.11.6", + "@testing-library/react": "^11.2.2", + "@testing-library/user-event": "^12.5.0", + "react": "^18.0.0", + "react-dom": "^18.0.0", + "react-scripts": "4.0.1", + "web-vitals": "^0.2.4" + }, + "scripts": { + "start": "react-scripts start", + "build": "react-scripts build", + "test": "react-scripts test", + "eject": "react-scripts eject" + }, + "eslintConfig": { + "extends": [ + "react-app", + "react-app/jest" + ] + }, + "browserslist": { + "production": [ + ">0.2%", + "not dead", + "not op_mini all" + ], + "development": [ + "last 1 chrome version", + "last 1 firefox version", + "last 1 safari version" + ] + } +} diff --git a/code/08-splitting-components-into-multiple-components/public/favicon.ico b/code/08-splitting-components-into-multiple-components/public/favicon.ico new file mode 100644 index 0000000000..a11777cc47 Binary files /dev/null and b/code/08-splitting-components-into-multiple-components/public/favicon.ico differ diff --git a/code/08-splitting-components-into-multiple-components/public/index.html b/code/08-splitting-components-into-multiple-components/public/index.html new file mode 100644 index 0000000000..aa069f27cb --- /dev/null +++ b/code/08-splitting-components-into-multiple-components/public/index.html @@ -0,0 +1,43 @@ + + + + + + + + + + + + + React App + + + +
+ + + diff --git a/code/08-splitting-components-into-multiple-components/public/logo192.png b/code/08-splitting-components-into-multiple-components/public/logo192.png new file mode 100644 index 0000000000..fc44b0a379 Binary files /dev/null and b/code/08-splitting-components-into-multiple-components/public/logo192.png differ diff --git a/code/08-splitting-components-into-multiple-components/public/logo512.png b/code/08-splitting-components-into-multiple-components/public/logo512.png new file mode 100644 index 0000000000..a4e47a6545 Binary files /dev/null and b/code/08-splitting-components-into-multiple-components/public/logo512.png differ diff --git a/code/08-splitting-components-into-multiple-components/public/manifest.json b/code/08-splitting-components-into-multiple-components/public/manifest.json new file mode 100644 index 0000000000..080d6c77ac --- /dev/null +++ b/code/08-splitting-components-into-multiple-components/public/manifest.json @@ -0,0 +1,25 @@ +{ + "short_name": "React App", + "name": "Create React App Sample", + "icons": [ + { + "src": "favicon.ico", + "sizes": "64x64 32x32 24x24 16x16", + "type": "image/x-icon" + }, + { + "src": "logo192.png", + "type": "image/png", + "sizes": "192x192" + }, + { + "src": "logo512.png", + "type": "image/png", + "sizes": "512x512" + } + ], + "start_url": ".", + "display": "standalone", + "theme_color": "#000000", + "background_color": "#ffffff" +} diff --git a/code/08-splitting-components-into-multiple-components/public/robots.txt b/code/08-splitting-components-into-multiple-components/public/robots.txt new file mode 100644 index 0000000000..e9e57dc4d4 --- /dev/null +++ b/code/08-splitting-components-into-multiple-components/public/robots.txt @@ -0,0 +1,3 @@ +# https://www.robotstxt.org/robotstxt.html +User-agent: * +Disallow: diff --git a/code/08-splitting-components-into-multiple-components/src/App.js b/code/08-splitting-components-into-multiple-components/src/App.js new file mode 100644 index 0000000000..f88ab5fa92 --- /dev/null +++ b/code/08-splitting-components-into-multiple-components/src/App.js @@ -0,0 +1,53 @@ +import ExpenseItem from './components/ExpenseItem'; + +function App() { + const expenses = [ + { + id: 'e1', + title: 'Toilet Paper', + amount: 94.12, + date: new Date(2020, 7, 14), + }, + { id: 'e2', title: 'New TV', amount: 799.49, date: new Date(2021, 2, 12) }, + { + id: 'e3', + title: 'Car Insurance', + amount: 294.67, + date: new Date(2021, 2, 28), + }, + { + id: 'e4', + title: 'New Desk (Wooden)', + amount: 450, + date: new Date(2021, 5, 12), + }, + ]; + + return ( +
+

Let's get started!

+ + + + +
+ ); +} + +export default App; diff --git a/code/08-splitting-components-into-multiple-components/src/components/ExpenseDate.css b/code/08-splitting-components-into-multiple-components/src/components/ExpenseDate.css new file mode 100644 index 0000000000..d69691de84 --- /dev/null +++ b/code/08-splitting-components-into-multiple-components/src/components/ExpenseDate.css @@ -0,0 +1,26 @@ +.expense-date { + display: flex; + flex-direction: column; + width: 5.5rem; + height: 5.5rem; + border: 1px solid #ececec; + background-color: #2a2a2a; + color: white; + border-radius: 12px; + align-items: center; + justify-content: center; +} + +.expense-date__month { + font-size: 0.75rem; + font-weight: bold; +} + +.expense-date__year { + font-size: 0.75rem; +} + +.expense-date__day { + font-size: 1.5rem; + font-weight: bold; +} diff --git a/code/08-splitting-components-into-multiple-components/src/components/ExpenseDate.js b/code/08-splitting-components-into-multiple-components/src/components/ExpenseDate.js new file mode 100644 index 0000000000..ba5698cf0d --- /dev/null +++ b/code/08-splitting-components-into-multiple-components/src/components/ExpenseDate.js @@ -0,0 +1,17 @@ +import './ExpenseDate.css'; + +function ExpenseDate(props) { + const month = props.date.toLocaleString('en-US', { month: 'long' }); + const day = props.date.toLocaleString('en-US', { day: '2-digit' }); + const year = props.date.getFullYear(); + + return ( +
+
{month}
+
{year}
+
{day}
+
+ ); +} + +export default ExpenseDate; diff --git a/code/08-splitting-components-into-multiple-components/src/components/ExpenseItem.css b/code/08-splitting-components-into-multiple-components/src/components/ExpenseItem.css new file mode 100644 index 0000000000..22eabe9e80 --- /dev/null +++ b/code/08-splitting-components-into-multiple-components/src/components/ExpenseItem.css @@ -0,0 +1,56 @@ +.expense-item { + display: flex; + justify-content: space-between; + align-items: center; + box-shadow: 0 2px 8px rgba(0, 0, 0, 0.25); + padding: 0.5rem; + margin: 1rem 0; + border-radius: 12px; + background-color: #4b4b4b; +} + +.expense-item__description { + display: flex; + flex-direction: column; + gap: 1rem; + align-items: flex-end; + flex-flow: column-reverse; + justify-content: flex-start; + flex: 1; +} + +.expense-item h2 { + color: #3a3a3a; + font-size: 1rem; + flex: 1; + margin: 0 1rem; + color: white; +} + +.expense-item__price { + font-size: 1rem; + font-weight: bold; + color: white; + background-color: #40005d; + border: 1px solid white; + padding: 0.5rem; + border-radius: 12px; +} + +@media (min-width: 580px) { + .expense-item__description { + flex-direction: row; + align-items: center; + justify-content: flex-start; + flex: 1; + } + + .expense-item__description h2 { + font-size: 1.25rem; + } + + .expense-item__price { + font-size: 1.25rem; + padding: 0.5rem 1.5rem; + } +} \ No newline at end of file diff --git a/code/08-splitting-components-into-multiple-components/src/components/ExpenseItem.js b/code/08-splitting-components-into-multiple-components/src/components/ExpenseItem.js new file mode 100644 index 0000000000..07e4e0f98a --- /dev/null +++ b/code/08-splitting-components-into-multiple-components/src/components/ExpenseItem.js @@ -0,0 +1,16 @@ +import ExpenseDate from './ExpenseDate'; +import './ExpenseItem.css'; + +function ExpenseItem(props) { + return ( +
+ +
+

{props.title}

+
${props.amount}
+
+
+ ); +} + +export default ExpenseItem; diff --git a/code/08-splitting-components-into-multiple-components/src/index.css b/code/08-splitting-components-into-multiple-components/src/index.css new file mode 100644 index 0000000000..72399cc5c6 --- /dev/null +++ b/code/08-splitting-components-into-multiple-components/src/index.css @@ -0,0 +1,15 @@ +@import url('https://fonts.googleapis.com/css2?family=Noto+Sans+JP:wght@400;700&display=swap'); + +* { + box-sizing: border-box; +} + +html { + font-family: 'Noto Sans JP', sans-serif; +} + +body { + margin: 0; + background-color: #3f3f3f; +} + diff --git a/code/08-splitting-components-into-multiple-components/src/index.js b/code/08-splitting-components-into-multiple-components/src/index.js new file mode 100644 index 0000000000..778ec1ba20 --- /dev/null +++ b/code/08-splitting-components-into-multiple-components/src/index.js @@ -0,0 +1,7 @@ +import ReactDOM from 'react-dom/client'; + +import './index.css'; +import App from './App'; + +const root = ReactDOM.createRoot(document.getElementById('root')); +root.render(); diff --git a/code/09-assignment-1-solution/package.json b/code/09-assignment-1-solution/package.json new file mode 100644 index 0000000000..b16a8faa39 --- /dev/null +++ b/code/09-assignment-1-solution/package.json @@ -0,0 +1,38 @@ +{ + "name": "react-complete-guide", + "version": "0.1.0", + "private": true, + "dependencies": { + "@testing-library/jest-dom": "^5.11.6", + "@testing-library/react": "^11.2.2", + "@testing-library/user-event": "^12.5.0", + "react": "^18.0.0", + "react-dom": "^18.0.0", + "react-scripts": "4.0.1", + "web-vitals": "^0.2.4" + }, + "scripts": { + "start": "react-scripts start", + "build": "react-scripts build", + "test": "react-scripts test", + "eject": "react-scripts eject" + }, + "eslintConfig": { + "extends": [ + "react-app", + "react-app/jest" + ] + }, + "browserslist": { + "production": [ + ">0.2%", + "not dead", + "not op_mini all" + ], + "development": [ + "last 1 chrome version", + "last 1 firefox version", + "last 1 safari version" + ] + } +} diff --git a/code/09-assignment-1-solution/public/favicon.ico b/code/09-assignment-1-solution/public/favicon.ico new file mode 100644 index 0000000000..a11777cc47 Binary files /dev/null and b/code/09-assignment-1-solution/public/favicon.ico differ diff --git a/code/09-assignment-1-solution/public/index.html b/code/09-assignment-1-solution/public/index.html new file mode 100644 index 0000000000..aa069f27cb --- /dev/null +++ b/code/09-assignment-1-solution/public/index.html @@ -0,0 +1,43 @@ + + + + + + + + + + + + + React App + + + +
+ + + diff --git a/code/09-assignment-1-solution/public/logo192.png b/code/09-assignment-1-solution/public/logo192.png new file mode 100644 index 0000000000..fc44b0a379 Binary files /dev/null and b/code/09-assignment-1-solution/public/logo192.png differ diff --git a/code/09-assignment-1-solution/public/logo512.png b/code/09-assignment-1-solution/public/logo512.png new file mode 100644 index 0000000000..a4e47a6545 Binary files /dev/null and b/code/09-assignment-1-solution/public/logo512.png differ diff --git a/code/09-assignment-1-solution/public/manifest.json b/code/09-assignment-1-solution/public/manifest.json new file mode 100644 index 0000000000..080d6c77ac --- /dev/null +++ b/code/09-assignment-1-solution/public/manifest.json @@ -0,0 +1,25 @@ +{ + "short_name": "React App", + "name": "Create React App Sample", + "icons": [ + { + "src": "favicon.ico", + "sizes": "64x64 32x32 24x24 16x16", + "type": "image/x-icon" + }, + { + "src": "logo192.png", + "type": "image/png", + "sizes": "192x192" + }, + { + "src": "logo512.png", + "type": "image/png", + "sizes": "512x512" + } + ], + "start_url": ".", + "display": "standalone", + "theme_color": "#000000", + "background_color": "#ffffff" +} diff --git a/code/09-assignment-1-solution/public/robots.txt b/code/09-assignment-1-solution/public/robots.txt new file mode 100644 index 0000000000..e9e57dc4d4 --- /dev/null +++ b/code/09-assignment-1-solution/public/robots.txt @@ -0,0 +1,3 @@ +# https://www.robotstxt.org/robotstxt.html +User-agent: * +Disallow: diff --git a/code/09-assignment-1-solution/src/App.js b/code/09-assignment-1-solution/src/App.js new file mode 100644 index 0000000000..21dfc576bc --- /dev/null +++ b/code/09-assignment-1-solution/src/App.js @@ -0,0 +1,34 @@ +import Expenses from './components/Expenses'; + +function App() { + const expenses = [ + { + id: 'e1', + title: 'Toilet Paper', + amount: 94.12, + date: new Date(2020, 7, 14), + }, + { id: 'e2', title: 'New TV', amount: 799.49, date: new Date(2021, 2, 12) }, + { + id: 'e3', + title: 'Car Insurance', + amount: 294.67, + date: new Date(2021, 2, 28), + }, + { + id: 'e4', + title: 'New Desk (Wooden)', + amount: 450, + date: new Date(2021, 5, 12), + }, + ]; + + return ( +
+

Let's get started!

+ +
+ ); +} + +export default App; diff --git a/code/09-assignment-1-solution/src/components/ExpenseDate.css b/code/09-assignment-1-solution/src/components/ExpenseDate.css new file mode 100644 index 0000000000..d69691de84 --- /dev/null +++ b/code/09-assignment-1-solution/src/components/ExpenseDate.css @@ -0,0 +1,26 @@ +.expense-date { + display: flex; + flex-direction: column; + width: 5.5rem; + height: 5.5rem; + border: 1px solid #ececec; + background-color: #2a2a2a; + color: white; + border-radius: 12px; + align-items: center; + justify-content: center; +} + +.expense-date__month { + font-size: 0.75rem; + font-weight: bold; +} + +.expense-date__year { + font-size: 0.75rem; +} + +.expense-date__day { + font-size: 1.5rem; + font-weight: bold; +} diff --git a/code/09-assignment-1-solution/src/components/ExpenseDate.js b/code/09-assignment-1-solution/src/components/ExpenseDate.js new file mode 100644 index 0000000000..ba5698cf0d --- /dev/null +++ b/code/09-assignment-1-solution/src/components/ExpenseDate.js @@ -0,0 +1,17 @@ +import './ExpenseDate.css'; + +function ExpenseDate(props) { + const month = props.date.toLocaleString('en-US', { month: 'long' }); + const day = props.date.toLocaleString('en-US', { day: '2-digit' }); + const year = props.date.getFullYear(); + + return ( +
+
{month}
+
{year}
+
{day}
+
+ ); +} + +export default ExpenseDate; diff --git a/code/09-assignment-1-solution/src/components/ExpenseItem.css b/code/09-assignment-1-solution/src/components/ExpenseItem.css new file mode 100644 index 0000000000..22eabe9e80 --- /dev/null +++ b/code/09-assignment-1-solution/src/components/ExpenseItem.css @@ -0,0 +1,56 @@ +.expense-item { + display: flex; + justify-content: space-between; + align-items: center; + box-shadow: 0 2px 8px rgba(0, 0, 0, 0.25); + padding: 0.5rem; + margin: 1rem 0; + border-radius: 12px; + background-color: #4b4b4b; +} + +.expense-item__description { + display: flex; + flex-direction: column; + gap: 1rem; + align-items: flex-end; + flex-flow: column-reverse; + justify-content: flex-start; + flex: 1; +} + +.expense-item h2 { + color: #3a3a3a; + font-size: 1rem; + flex: 1; + margin: 0 1rem; + color: white; +} + +.expense-item__price { + font-size: 1rem; + font-weight: bold; + color: white; + background-color: #40005d; + border: 1px solid white; + padding: 0.5rem; + border-radius: 12px; +} + +@media (min-width: 580px) { + .expense-item__description { + flex-direction: row; + align-items: center; + justify-content: flex-start; + flex: 1; + } + + .expense-item__description h2 { + font-size: 1.25rem; + } + + .expense-item__price { + font-size: 1.25rem; + padding: 0.5rem 1.5rem; + } +} \ No newline at end of file diff --git a/code/09-assignment-1-solution/src/components/ExpenseItem.js b/code/09-assignment-1-solution/src/components/ExpenseItem.js new file mode 100644 index 0000000000..07e4e0f98a --- /dev/null +++ b/code/09-assignment-1-solution/src/components/ExpenseItem.js @@ -0,0 +1,16 @@ +import ExpenseDate from './ExpenseDate'; +import './ExpenseItem.css'; + +function ExpenseItem(props) { + return ( +
+ +
+

{props.title}

+
${props.amount}
+
+
+ ); +} + +export default ExpenseItem; diff --git a/code/09-assignment-1-solution/src/components/Expenses.css b/code/09-assignment-1-solution/src/components/Expenses.css new file mode 100644 index 0000000000..2a3c9d0fbd --- /dev/null +++ b/code/09-assignment-1-solution/src/components/Expenses.css @@ -0,0 +1,9 @@ +.expenses { + padding: 1rem; + background-color: rgb(31, 31, 31); + margin: 2rem auto; + width: 50rem; + max-width: 95%; + border-radius: 12px; + box-shadow: 0 1px 8px rgba(0, 0, 0, 0.25); +} diff --git a/code/09-assignment-1-solution/src/components/Expenses.js b/code/09-assignment-1-solution/src/components/Expenses.js new file mode 100644 index 0000000000..6bd58d5710 --- /dev/null +++ b/code/09-assignment-1-solution/src/components/Expenses.js @@ -0,0 +1,31 @@ +import ExpenseItem from './ExpenseItem'; +import './Expenses.css'; + +function Expenses(props) { + return ( +
+ + + + +
+ ); +} + +export default Expenses; diff --git a/code/09-assignment-1-solution/src/index.css b/code/09-assignment-1-solution/src/index.css new file mode 100644 index 0000000000..72399cc5c6 --- /dev/null +++ b/code/09-assignment-1-solution/src/index.css @@ -0,0 +1,15 @@ +@import url('https://fonts.googleapis.com/css2?family=Noto+Sans+JP:wght@400;700&display=swap'); + +* { + box-sizing: border-box; +} + +html { + font-family: 'Noto Sans JP', sans-serif; +} + +body { + margin: 0; + background-color: #3f3f3f; +} + diff --git a/code/09-assignment-1-solution/src/index.js b/code/09-assignment-1-solution/src/index.js new file mode 100644 index 0000000000..778ec1ba20 --- /dev/null +++ b/code/09-assignment-1-solution/src/index.js @@ -0,0 +1,7 @@ +import ReactDOM from 'react-dom/client'; + +import './index.css'; +import App from './App'; + +const root = ReactDOM.createRoot(document.getElementById('root')); +root.render(); diff --git a/code/10-the-concept-of-composition/package.json b/code/10-the-concept-of-composition/package.json new file mode 100644 index 0000000000..b16a8faa39 --- /dev/null +++ b/code/10-the-concept-of-composition/package.json @@ -0,0 +1,38 @@ +{ + "name": "react-complete-guide", + "version": "0.1.0", + "private": true, + "dependencies": { + "@testing-library/jest-dom": "^5.11.6", + "@testing-library/react": "^11.2.2", + "@testing-library/user-event": "^12.5.0", + "react": "^18.0.0", + "react-dom": "^18.0.0", + "react-scripts": "4.0.1", + "web-vitals": "^0.2.4" + }, + "scripts": { + "start": "react-scripts start", + "build": "react-scripts build", + "test": "react-scripts test", + "eject": "react-scripts eject" + }, + "eslintConfig": { + "extends": [ + "react-app", + "react-app/jest" + ] + }, + "browserslist": { + "production": [ + ">0.2%", + "not dead", + "not op_mini all" + ], + "development": [ + "last 1 chrome version", + "last 1 firefox version", + "last 1 safari version" + ] + } +} diff --git a/code/10-the-concept-of-composition/public/favicon.ico b/code/10-the-concept-of-composition/public/favicon.ico new file mode 100644 index 0000000000..a11777cc47 Binary files /dev/null and b/code/10-the-concept-of-composition/public/favicon.ico differ diff --git a/code/10-the-concept-of-composition/public/index.html b/code/10-the-concept-of-composition/public/index.html new file mode 100644 index 0000000000..aa069f27cb --- /dev/null +++ b/code/10-the-concept-of-composition/public/index.html @@ -0,0 +1,43 @@ + + + + + + + + + + + + + React App + + + +
+ + + diff --git a/code/10-the-concept-of-composition/public/logo192.png b/code/10-the-concept-of-composition/public/logo192.png new file mode 100644 index 0000000000..fc44b0a379 Binary files /dev/null and b/code/10-the-concept-of-composition/public/logo192.png differ diff --git a/code/10-the-concept-of-composition/public/logo512.png b/code/10-the-concept-of-composition/public/logo512.png new file mode 100644 index 0000000000..a4e47a6545 Binary files /dev/null and b/code/10-the-concept-of-composition/public/logo512.png differ diff --git a/code/10-the-concept-of-composition/public/manifest.json b/code/10-the-concept-of-composition/public/manifest.json new file mode 100644 index 0000000000..080d6c77ac --- /dev/null +++ b/code/10-the-concept-of-composition/public/manifest.json @@ -0,0 +1,25 @@ +{ + "short_name": "React App", + "name": "Create React App Sample", + "icons": [ + { + "src": "favicon.ico", + "sizes": "64x64 32x32 24x24 16x16", + "type": "image/x-icon" + }, + { + "src": "logo192.png", + "type": "image/png", + "sizes": "192x192" + }, + { + "src": "logo512.png", + "type": "image/png", + "sizes": "512x512" + } + ], + "start_url": ".", + "display": "standalone", + "theme_color": "#000000", + "background_color": "#ffffff" +} diff --git a/code/10-the-concept-of-composition/public/robots.txt b/code/10-the-concept-of-composition/public/robots.txt new file mode 100644 index 0000000000..e9e57dc4d4 --- /dev/null +++ b/code/10-the-concept-of-composition/public/robots.txt @@ -0,0 +1,3 @@ +# https://www.robotstxt.org/robotstxt.html +User-agent: * +Disallow: diff --git a/code/10-the-concept-of-composition/src/App.js b/code/10-the-concept-of-composition/src/App.js new file mode 100644 index 0000000000..21dfc576bc --- /dev/null +++ b/code/10-the-concept-of-composition/src/App.js @@ -0,0 +1,34 @@ +import Expenses from './components/Expenses'; + +function App() { + const expenses = [ + { + id: 'e1', + title: 'Toilet Paper', + amount: 94.12, + date: new Date(2020, 7, 14), + }, + { id: 'e2', title: 'New TV', amount: 799.49, date: new Date(2021, 2, 12) }, + { + id: 'e3', + title: 'Car Insurance', + amount: 294.67, + date: new Date(2021, 2, 28), + }, + { + id: 'e4', + title: 'New Desk (Wooden)', + amount: 450, + date: new Date(2021, 5, 12), + }, + ]; + + return ( +
+

Let's get started!

+ +
+ ); +} + +export default App; diff --git a/code/10-the-concept-of-composition/src/components/Card.css b/code/10-the-concept-of-composition/src/components/Card.css new file mode 100644 index 0000000000..166cffe458 --- /dev/null +++ b/code/10-the-concept-of-composition/src/components/Card.css @@ -0,0 +1,4 @@ +.card { + border-radius: 12px; + box-shadow: 0 1px 8px rgba(0, 0, 0, 0.25); +} diff --git a/code/10-the-concept-of-composition/src/components/Card.js b/code/10-the-concept-of-composition/src/components/Card.js new file mode 100644 index 0000000000..2615acdd3c --- /dev/null +++ b/code/10-the-concept-of-composition/src/components/Card.js @@ -0,0 +1,9 @@ +import './Card.css'; + +function Card(props) { + const classes = 'card ' + props.className; + + return
{props.children}
; +} + +export default Card; diff --git a/code/10-the-concept-of-composition/src/components/ExpenseDate.css b/code/10-the-concept-of-composition/src/components/ExpenseDate.css new file mode 100644 index 0000000000..d69691de84 --- /dev/null +++ b/code/10-the-concept-of-composition/src/components/ExpenseDate.css @@ -0,0 +1,26 @@ +.expense-date { + display: flex; + flex-direction: column; + width: 5.5rem; + height: 5.5rem; + border: 1px solid #ececec; + background-color: #2a2a2a; + color: white; + border-radius: 12px; + align-items: center; + justify-content: center; +} + +.expense-date__month { + font-size: 0.75rem; + font-weight: bold; +} + +.expense-date__year { + font-size: 0.75rem; +} + +.expense-date__day { + font-size: 1.5rem; + font-weight: bold; +} diff --git a/code/10-the-concept-of-composition/src/components/ExpenseDate.js b/code/10-the-concept-of-composition/src/components/ExpenseDate.js new file mode 100644 index 0000000000..ba5698cf0d --- /dev/null +++ b/code/10-the-concept-of-composition/src/components/ExpenseDate.js @@ -0,0 +1,17 @@ +import './ExpenseDate.css'; + +function ExpenseDate(props) { + const month = props.date.toLocaleString('en-US', { month: 'long' }); + const day = props.date.toLocaleString('en-US', { day: '2-digit' }); + const year = props.date.getFullYear(); + + return ( +
+
{month}
+
{year}
+
{day}
+
+ ); +} + +export default ExpenseDate; diff --git a/code/10-the-concept-of-composition/src/components/ExpenseItem.css b/code/10-the-concept-of-composition/src/components/ExpenseItem.css new file mode 100644 index 0000000000..aba2913253 --- /dev/null +++ b/code/10-the-concept-of-composition/src/components/ExpenseItem.css @@ -0,0 +1,54 @@ +.expense-item { + display: flex; + justify-content: space-between; + align-items: center; + padding: 0.5rem; + margin: 1rem 0; + background-color: #4b4b4b; +} + +.expense-item__description { + display: flex; + flex-direction: column; + gap: 1rem; + align-items: flex-end; + flex-flow: column-reverse; + justify-content: flex-start; + flex: 1; +} + +.expense-item h2 { + color: #3a3a3a; + font-size: 1rem; + flex: 1; + margin: 0 1rem; + color: white; +} + +.expense-item__price { + font-size: 1rem; + font-weight: bold; + color: white; + background-color: #40005d; + border: 1px solid white; + padding: 0.5rem; + border-radius: 12px; +} + +@media (min-width: 580px) { + .expense-item__description { + flex-direction: row; + align-items: center; + justify-content: flex-start; + flex: 1; + } + + .expense-item__description h2 { + font-size: 1.25rem; + } + + .expense-item__price { + font-size: 1.25rem; + padding: 0.5rem 1.5rem; + } +} \ No newline at end of file diff --git a/code/10-the-concept-of-composition/src/components/ExpenseItem.js b/code/10-the-concept-of-composition/src/components/ExpenseItem.js new file mode 100644 index 0000000000..cdc6cee206 --- /dev/null +++ b/code/10-the-concept-of-composition/src/components/ExpenseItem.js @@ -0,0 +1,17 @@ +import ExpenseDate from './ExpenseDate'; +import Card from './Card'; +import './ExpenseItem.css'; + +function ExpenseItem(props) { + return ( + + +
+

{props.title}

+
${props.amount}
+
+
+ ); +} + +export default ExpenseItem; diff --git a/code/10-the-concept-of-composition/src/components/Expenses.css b/code/10-the-concept-of-composition/src/components/Expenses.css new file mode 100644 index 0000000000..9b05ca92dc --- /dev/null +++ b/code/10-the-concept-of-composition/src/components/Expenses.css @@ -0,0 +1,7 @@ +.expenses { + padding: 1rem; + background-color: rgb(31, 31, 31); + margin: 2rem auto; + width: 50rem; + max-width: 95%; +} diff --git a/code/10-the-concept-of-composition/src/components/Expenses.js b/code/10-the-concept-of-composition/src/components/Expenses.js new file mode 100644 index 0000000000..c42f88321d --- /dev/null +++ b/code/10-the-concept-of-composition/src/components/Expenses.js @@ -0,0 +1,32 @@ +import ExpenseItem from './ExpenseItem'; +import Card from './Card'; +import './Expenses.css'; + +function Expenses(props) { + return ( + + + + + + + ); +} + +export default Expenses; diff --git a/code/10-the-concept-of-composition/src/index.css b/code/10-the-concept-of-composition/src/index.css new file mode 100644 index 0000000000..72399cc5c6 --- /dev/null +++ b/code/10-the-concept-of-composition/src/index.css @@ -0,0 +1,15 @@ +@import url('https://fonts.googleapis.com/css2?family=Noto+Sans+JP:wght@400;700&display=swap'); + +* { + box-sizing: border-box; +} + +html { + font-family: 'Noto Sans JP', sans-serif; +} + +body { + margin: 0; + background-color: #3f3f3f; +} + diff --git a/code/10-the-concept-of-composition/src/index.js b/code/10-the-concept-of-composition/src/index.js new file mode 100644 index 0000000000..778ec1ba20 --- /dev/null +++ b/code/10-the-concept-of-composition/src/index.js @@ -0,0 +1,7 @@ +import ReactDOM from 'react-dom/client'; + +import './index.css'; +import App from './App'; + +const root = ReactDOM.createRoot(document.getElementById('root')); +root.render(); diff --git a/code/11-finished/package.json b/code/11-finished/package.json new file mode 100644 index 0000000000..b16a8faa39 --- /dev/null +++ b/code/11-finished/package.json @@ -0,0 +1,38 @@ +{ + "name": "react-complete-guide", + "version": "0.1.0", + "private": true, + "dependencies": { + "@testing-library/jest-dom": "^5.11.6", + "@testing-library/react": "^11.2.2", + "@testing-library/user-event": "^12.5.0", + "react": "^18.0.0", + "react-dom": "^18.0.0", + "react-scripts": "4.0.1", + "web-vitals": "^0.2.4" + }, + "scripts": { + "start": "react-scripts start", + "build": "react-scripts build", + "test": "react-scripts test", + "eject": "react-scripts eject" + }, + "eslintConfig": { + "extends": [ + "react-app", + "react-app/jest" + ] + }, + "browserslist": { + "production": [ + ">0.2%", + "not dead", + "not op_mini all" + ], + "development": [ + "last 1 chrome version", + "last 1 firefox version", + "last 1 safari version" + ] + } +} diff --git a/code/11-finished/public/favicon.ico b/code/11-finished/public/favicon.ico new file mode 100644 index 0000000000..a11777cc47 Binary files /dev/null and b/code/11-finished/public/favicon.ico differ diff --git a/code/11-finished/public/index.html b/code/11-finished/public/index.html new file mode 100644 index 0000000000..aa069f27cb --- /dev/null +++ b/code/11-finished/public/index.html @@ -0,0 +1,43 @@ + + + + + + + + + + + + + React App + + + +
+ + + diff --git a/code/11-finished/public/logo192.png b/code/11-finished/public/logo192.png new file mode 100644 index 0000000000..fc44b0a379 Binary files /dev/null and b/code/11-finished/public/logo192.png differ diff --git a/code/11-finished/public/logo512.png b/code/11-finished/public/logo512.png new file mode 100644 index 0000000000..a4e47a6545 Binary files /dev/null and b/code/11-finished/public/logo512.png differ diff --git a/code/11-finished/public/manifest.json b/code/11-finished/public/manifest.json new file mode 100644 index 0000000000..080d6c77ac --- /dev/null +++ b/code/11-finished/public/manifest.json @@ -0,0 +1,25 @@ +{ + "short_name": "React App", + "name": "Create React App Sample", + "icons": [ + { + "src": "favicon.ico", + "sizes": "64x64 32x32 24x24 16x16", + "type": "image/x-icon" + }, + { + "src": "logo192.png", + "type": "image/png", + "sizes": "192x192" + }, + { + "src": "logo512.png", + "type": "image/png", + "sizes": "512x512" + } + ], + "start_url": ".", + "display": "standalone", + "theme_color": "#000000", + "background_color": "#ffffff" +} diff --git a/code/11-finished/public/robots.txt b/code/11-finished/public/robots.txt new file mode 100644 index 0000000000..e9e57dc4d4 --- /dev/null +++ b/code/11-finished/public/robots.txt @@ -0,0 +1,3 @@ +# https://www.robotstxt.org/robotstxt.html +User-agent: * +Disallow: diff --git a/code/11-finished/src/App.js b/code/11-finished/src/App.js new file mode 100644 index 0000000000..c7b17821a7 --- /dev/null +++ b/code/11-finished/src/App.js @@ -0,0 +1,43 @@ +import React from 'react'; + +import Expenses from './components/Expenses/Expenses'; + +const App = () => { + const expenses = [ + { + id: 'e1', + title: 'Toilet Paper', + amount: 94.12, + date: new Date(2020, 7, 14), + }, + { id: 'e2', title: 'New TV', amount: 799.49, date: new Date(2021, 2, 12) }, + { + id: 'e3', + title: 'Car Insurance', + amount: 294.67, + date: new Date(2021, 2, 28), + }, + { + id: 'e4', + title: 'New Desk (Wooden)', + amount: 450, + date: new Date(2021, 5, 12), + }, + ]; + + // return React.createElement( + // 'div', + // {}, + // React.createElement('h2', {}, "Let's get started!"), + // React.createElement(Expenses, { items: expenses }) + // ); + + return ( +
+

Let's get started!

+ +
+ ); +} + +export default App; diff --git a/code/11-finished/src/components/Expenses/ExpenseDate.css b/code/11-finished/src/components/Expenses/ExpenseDate.css new file mode 100644 index 0000000000..d69691de84 --- /dev/null +++ b/code/11-finished/src/components/Expenses/ExpenseDate.css @@ -0,0 +1,26 @@ +.expense-date { + display: flex; + flex-direction: column; + width: 5.5rem; + height: 5.5rem; + border: 1px solid #ececec; + background-color: #2a2a2a; + color: white; + border-radius: 12px; + align-items: center; + justify-content: center; +} + +.expense-date__month { + font-size: 0.75rem; + font-weight: bold; +} + +.expense-date__year { + font-size: 0.75rem; +} + +.expense-date__day { + font-size: 1.5rem; + font-weight: bold; +} diff --git a/code/11-finished/src/components/Expenses/ExpenseDate.js b/code/11-finished/src/components/Expenses/ExpenseDate.js new file mode 100644 index 0000000000..0b307c24ad --- /dev/null +++ b/code/11-finished/src/components/Expenses/ExpenseDate.js @@ -0,0 +1,19 @@ +import React from 'react'; + +import './ExpenseDate.css'; + +const ExpenseDate = (props) => { + const month = props.date.toLocaleString('en-US', { month: 'long' }); + const day = props.date.toLocaleString('en-US', { day: '2-digit' }); + const year = props.date.getFullYear(); + + return ( +
+
{month}
+
{year}
+
{day}
+
+ ); +}; + +export default ExpenseDate; diff --git a/code/11-finished/src/components/Expenses/ExpenseItem.css b/code/11-finished/src/components/Expenses/ExpenseItem.css new file mode 100644 index 0000000000..aba2913253 --- /dev/null +++ b/code/11-finished/src/components/Expenses/ExpenseItem.css @@ -0,0 +1,54 @@ +.expense-item { + display: flex; + justify-content: space-between; + align-items: center; + padding: 0.5rem; + margin: 1rem 0; + background-color: #4b4b4b; +} + +.expense-item__description { + display: flex; + flex-direction: column; + gap: 1rem; + align-items: flex-end; + flex-flow: column-reverse; + justify-content: flex-start; + flex: 1; +} + +.expense-item h2 { + color: #3a3a3a; + font-size: 1rem; + flex: 1; + margin: 0 1rem; + color: white; +} + +.expense-item__price { + font-size: 1rem; + font-weight: bold; + color: white; + background-color: #40005d; + border: 1px solid white; + padding: 0.5rem; + border-radius: 12px; +} + +@media (min-width: 580px) { + .expense-item__description { + flex-direction: row; + align-items: center; + justify-content: flex-start; + flex: 1; + } + + .expense-item__description h2 { + font-size: 1.25rem; + } + + .expense-item__price { + font-size: 1.25rem; + padding: 0.5rem 1.5rem; + } +} \ No newline at end of file diff --git a/code/11-finished/src/components/Expenses/ExpenseItem.js b/code/11-finished/src/components/Expenses/ExpenseItem.js new file mode 100644 index 0000000000..b180c46841 --- /dev/null +++ b/code/11-finished/src/components/Expenses/ExpenseItem.js @@ -0,0 +1,19 @@ +import React from 'react'; + +import ExpenseDate from './ExpenseDate'; +import Card from '../UI/Card'; +import './ExpenseItem.css'; + +const ExpenseItem = (props) => { + return ( + + +
+

{props.title}

+
${props.amount}
+
+
+ ); +} + +export default ExpenseItem; diff --git a/code/11-finished/src/components/Expenses/Expenses.css b/code/11-finished/src/components/Expenses/Expenses.css new file mode 100644 index 0000000000..9b05ca92dc --- /dev/null +++ b/code/11-finished/src/components/Expenses/Expenses.css @@ -0,0 +1,7 @@ +.expenses { + padding: 1rem; + background-color: rgb(31, 31, 31); + margin: 2rem auto; + width: 50rem; + max-width: 95%; +} diff --git a/code/11-finished/src/components/Expenses/Expenses.js b/code/11-finished/src/components/Expenses/Expenses.js new file mode 100644 index 0000000000..7128bcf77a --- /dev/null +++ b/code/11-finished/src/components/Expenses/Expenses.js @@ -0,0 +1,34 @@ +import React from 'react'; + +import ExpenseItem from './ExpenseItem'; +import Card from '../UI/Card'; +import './Expenses.css'; + +const Expenses = (props) => { + return ( + + + + + + + ); +} + +export default Expenses; diff --git a/code/11-finished/src/components/UI/Card.css b/code/11-finished/src/components/UI/Card.css new file mode 100644 index 0000000000..166cffe458 --- /dev/null +++ b/code/11-finished/src/components/UI/Card.css @@ -0,0 +1,4 @@ +.card { + border-radius: 12px; + box-shadow: 0 1px 8px rgba(0, 0, 0, 0.25); +} diff --git a/code/11-finished/src/components/UI/Card.js b/code/11-finished/src/components/UI/Card.js new file mode 100644 index 0000000000..841fb93fa3 --- /dev/null +++ b/code/11-finished/src/components/UI/Card.js @@ -0,0 +1,11 @@ +import React from 'react'; + +import './Card.css'; + +const Card = (props) => { + const classes = 'card ' + props.className; + + return
{props.children}
; +}; + +export default Card; diff --git a/code/11-finished/src/index.css b/code/11-finished/src/index.css new file mode 100644 index 0000000000..72399cc5c6 --- /dev/null +++ b/code/11-finished/src/index.css @@ -0,0 +1,15 @@ +@import url('https://fonts.googleapis.com/css2?family=Noto+Sans+JP:wght@400;700&display=swap'); + +* { + box-sizing: border-box; +} + +html { + font-family: 'Noto Sans JP', sans-serif; +} + +body { + margin: 0; + background-color: #3f3f3f; +} + diff --git a/code/11-finished/src/index.js b/code/11-finished/src/index.js new file mode 100644 index 0000000000..9065e05326 --- /dev/null +++ b/code/11-finished/src/index.js @@ -0,0 +1,8 @@ +import React from 'react'; +import ReactDOM from 'react-dom/client'; + +import './index.css'; +import App from './App'; + +const root = ReactDOM.createRoot(document.getElementById('root')); +root.render(); diff --git a/extra-files/ExpenseDate.css b/extra-files/ExpenseDate.css new file mode 100644 index 0000000000..d69691de84 --- /dev/null +++ b/extra-files/ExpenseDate.css @@ -0,0 +1,26 @@ +.expense-date { + display: flex; + flex-direction: column; + width: 5.5rem; + height: 5.5rem; + border: 1px solid #ececec; + background-color: #2a2a2a; + color: white; + border-radius: 12px; + align-items: center; + justify-content: center; +} + +.expense-date__month { + font-size: 0.75rem; + font-weight: bold; +} + +.expense-date__year { + font-size: 0.75rem; +} + +.expense-date__day { + font-size: 1.5rem; + font-weight: bold; +} diff --git a/extra-files/ExpenseItem.css b/extra-files/ExpenseItem.css new file mode 100644 index 0000000000..22eabe9e80 --- /dev/null +++ b/extra-files/ExpenseItem.css @@ -0,0 +1,56 @@ +.expense-item { + display: flex; + justify-content: space-between; + align-items: center; + box-shadow: 0 2px 8px rgba(0, 0, 0, 0.25); + padding: 0.5rem; + margin: 1rem 0; + border-radius: 12px; + background-color: #4b4b4b; +} + +.expense-item__description { + display: flex; + flex-direction: column; + gap: 1rem; + align-items: flex-end; + flex-flow: column-reverse; + justify-content: flex-start; + flex: 1; +} + +.expense-item h2 { + color: #3a3a3a; + font-size: 1rem; + flex: 1; + margin: 0 1rem; + color: white; +} + +.expense-item__price { + font-size: 1rem; + font-weight: bold; + color: white; + background-color: #40005d; + border: 1px solid white; + padding: 0.5rem; + border-radius: 12px; +} + +@media (min-width: 580px) { + .expense-item__description { + flex-direction: row; + align-items: center; + justify-content: flex-start; + flex: 1; + } + + .expense-item__description h2 { + font-size: 1.25rem; + } + + .expense-item__price { + font-size: 1.25rem; + padding: 0.5rem 1.5rem; + } +} \ No newline at end of file diff --git a/extra-files/Expenses.css b/extra-files/Expenses.css new file mode 100644 index 0000000000..2a3c9d0fbd --- /dev/null +++ b/extra-files/Expenses.css @@ -0,0 +1,9 @@ +.expenses { + padding: 1rem; + background-color: rgb(31, 31, 31); + margin: 2rem auto; + width: 50rem; + max-width: 95%; + border-radius: 12px; + box-shadow: 0 1px 8px rgba(0, 0, 0, 0.25); +} diff --git a/extra-files/expenses.txt b/extra-files/expenses.txt new file mode 100644 index 0000000000..ec90c0623f --- /dev/null +++ b/extra-files/expenses.txt @@ -0,0 +1,21 @@ +const expenses = [ + { + id: 'e1', + title: 'Toilet Paper', + amount: 94.12, + date: new Date(2020, 7, 14), + }, + { id: 'e2', title: 'New TV', amount: 799.49, date: new Date(2021, 2, 12) }, + { + id: 'e3', + title: 'Car Insurance', + amount: 294.67, + date: new Date(2021, 2, 28), + }, + { + id: 'e4', + title: 'New Desk (Wooden)', + amount: 450, + date: new Date(2021, 5, 12), + }, + ]; \ No newline at end of file diff --git a/slides/slides.pdf b/slides/slides.pdf new file mode 100644 index 0000000000..01c2ca8ae3 Binary files /dev/null and b/slides/slides.pdf differ