Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Module2-lesson3-ZOD #98

Open
wants to merge 15 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
60 changes: 19 additions & 41 deletions examples/module1/lesson1/solver/App.tsx
Original file line number Diff line number Diff line change
@@ -1,58 +1,36 @@
import React, { useState } from 'react';
import { f1, f2, f3, f4 } from './functions';
import { useState } from 'react';
import { sum, sub, multiply, divide } from './functions';
import Button from './components/Button';
import Input from './components/Input';

const App = () => {
const [numA, setNumA] = useState<number>(0);
const [numB, setNumB] = useState<number>(0);
const [numC, setNumC] = useState<number | string>(0);
const [firstDigit, setFirstDigit] = useState<number>(0);
const [secondDigit, setSecondDigit] = useState<number>(0);
const [result, setResult] = useState<number | string>(0);

const doWork = (func: (a: number, b: number) => number) => {
setNumC(func(numA, numB));
setResult(func(firstDigit, secondDigit));
};

return (
<div>
<div className="grid grid-cols-2 gap-x-4">
<input
type="number"
className="rounded-md shadow-md p-4"
value={numA}
onChange={(e) => setNumA(parseFloat(e.target.value))}
<Input
value={firstDigit}
onChange={(e) => setFirstDigit(parseFloat(e.target.value))}
/>
<input
type="number"
className="rounded-md shadow-md p-4"
value={numB}
onChange={(e) => setNumB(parseFloat(e.target.value))}
<Input
value={secondDigit}
onChange={(e) => setSecondDigit(parseFloat(e.target.value))}
/>
</div>
<div className="grid grid-cols-4 gap-x-4 my-4">
<button
className="bg-blue-200 px-2 py-4 text-lg hover:bg-blue-500 hover:text-white rounded-md"
onClick={() => doWork(f1)}
>
+
</button>
<button
className="bg-blue-200 px-2 py-4 text-lg hover:bg-blue-500 hover:text-white rounded-md"
onClick={() => doWork(f2)}
>
-
</button>
<button
className="bg-blue-200 px-2 py-4 text-lg hover:bg-blue-500 hover:text-white rounded-md"
onClick={() => doWork(f3)}
>
*
</button>
<button
className="bg-blue-200 px-2 py-4 text-lg hover:bg-blue-500 hover:text-white rounded-md"
onClick={() => doWork(f4)}
>
/
</button>
<Button onClick={() => doWork(sum)}> + </Button>
<Button onClick={() => doWork(sub)}> - </Button>
<Button onClick={() => doWork(multiply)}> * </Button>
<Button onClick={() => doWork(divide)}> / </Button>
</div>
<div>Result: {numC}</div>
<div>Result: {result}</div>
</div>
);
};
Expand Down
20 changes: 20 additions & 0 deletions examples/module1/lesson1/solver/components/Button.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
import React from 'react';

const Button = ({
children,
onClick,
}: {
children: React.ReactNode;
onClick: () => void;
}) => {
return (
<button
onClick={onClick}
className="bg-blue-200 px-2 py-4 text-lg hover:bg-blue-500 hover:text-white rounded-md"
>
{children}
</button>
);
};

export default Button;
14 changes: 14 additions & 0 deletions examples/module1/lesson1/solver/components/Input.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
import React from 'react';

const Input = ({ value, onChange }: { value: any; onChange: any }) => {
return (
<input
type="number"
className="rounded-md shadow-md p-4"
value={value}
onChange={onChange}
/>
);
};

export default Input;
9 changes: 5 additions & 4 deletions examples/module1/lesson1/solver/functions.ts
Original file line number Diff line number Diff line change
@@ -1,13 +1,14 @@
export function f1(a, b) {
export function sum(a: number, b: number): number {
return a + b;
}
export function f2(a, b) {
export function sub(a: number, b: number): number {
return a - b;
}
export function f3(a, b) {
export function multiply(a: number, b: number): number {
return a * b;
}

export function f4(a, b) {
export function divide(a: number, b: number): number | string {
if (b === 0) return 'Cannot divide by zero';
return a / b;
}
59 changes: 26 additions & 33 deletions examples/module1/lesson1/validate-it/index.html
Original file line number Diff line number Diff line change
@@ -1,37 +1,30 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Validation - Demo App</title>
<script src="https://cdn.tailwindcss.com"></script>
</head>
<body class="bg-gray-100 p-4">
<div class="max-w-4xl mx-auto">
<div class="flex flex-col">
<input
class="rounded-md p-4 shadow-lg"
type="text"
id="input"
placeholder="Enter a number between 0 and 100"
/>
<div class="grid grid-cols-2 gap-x-2">
<button
class="rounded-md text-lg bg-blue-200 hover:bg-blue-800 hover:text-white p-4 mt-4"
id="button"
>
Validate It!
</button>
<button
class="rounded-md text-lg bg-red-200 hover:bg-red-800 hover:text-white p-4 mt-4"
id="button2"
>
Clear!
</button>
</div>
<div class="text-lg mt-4" id="result"></div>

<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Validation - Demo App</title>
<script src="https://cdn.tailwindcss.com"></script>
</head>

<body class="bg-gray-100 p-4">
<div class="max-w-4xl mx-auto">
<div class="flex flex-col">
<input class="rounded-md p-4 shadow-lg" type="text" id="input" placeholder="Enter a number between 0 and 100" />
<div class="grid grid-cols-2 gap-x-2">
<button class="rounded-md text-lg bg-blue-200 hover:bg-blue-800 hover:text-white p-4 mt-4"
id="onValidateButton">
Validate It!
</button>
<button class="rounded-md text-lg bg-red-200 hover:bg-red-800 hover:text-white p-4 mt-4" id="onCancelButton">
Clear!
</button>
</div>
<div class="text-lg mt-4" id="result"></div>
</div>
<script type="module" src="./index.js"></script>
</body>
</html>
</div>
<script type="module" src="./index.ts"></script>
</body>

</html>
34 changes: 0 additions & 34 deletions examples/module1/lesson1/validate-it/index.js

This file was deleted.

21 changes: 21 additions & 0 deletions examples/module1/lesson1/validate-it/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
import { NUMBER_VALIDATORS } from './validator/validation_rule';
import { validate } from './validator/validator';

function main() {
const input: HTMLInputElement = document.getElementById('input')!;
const onValidate: HTMLElement = document.getElementById('onValidateButton')!;
const onCancel: HTMLElement = document.getElementById('onCancelButton')!;
const result: HTMLElement = document.getElementById('result')!;

onValidate.addEventListener('click', () => {
const validationMessage = validate(input.value, NUMBER_VALIDATORS);
result.innerHTML = validationMessage;
});

onCancel.addEventListener('click', () => {
input.value = '';
result.innerHTML = '';
});
}

main();
15 changes: 15 additions & 0 deletions examples/module1/lesson1/validate-it/validator/validation_rule.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
export type ValidationRule = (input: number) => boolean;

const isEven: ValidationRule = (input: number) => input % 2 === 0;
const isGreaterThan = (boundary: number): ValidationRule => {
return (input: number) => input > boundary;
};
const isLessThan = (boundary: number): ValidationRule => {
return (input: number) => input < boundary;
};

export const NUMBER_VALIDATORS: ValidationRule[] = [
isEven,
isGreaterThan(0),
isLessThan(100),
];
7 changes: 7 additions & 0 deletions examples/module1/lesson1/validate-it/validator/validator.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
import { ValidationRule } from './validation_rule';

export function validate(value: string, validators: ValidationRule[]) {
const isValid = validators.every((validates) => validates(Number(value)));
if (!isValid) return 'Invalid';
return 'Valid';
}
Original file line number Diff line number Diff line change
Expand Up @@ -97,5 +97,8 @@
}
}
}
},
"cli": {
"analytics": false
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
import test, { expect } from '@playwright/test';

test('search for Ricks', async ({ page }) => {
await page.goto('/');

await page.getByRole('textbox', { name: /Name/i }).fill('Rick');

await expect(page.getByRole('listitem')).toHaveCount(20);
});
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
import { Character } from '../types/Character';

const CharacterItem = ({ character }: { character: Character }) => {
return (
<li key={character.id} className="flex flex-col items-center">
<h3>{character.name}</h3>
<img src={character.image} alt={character.name} />
</li>
);
};

export default CharacterItem;
Original file line number Diff line number Diff line change
@@ -1,13 +1,11 @@
import { Character } from '../types/Character';
import CharacterItem from './CharacterItem';

function CharacterList({ characters }: { characters: Character[] }) {
return (
<ol className="grid grid-cols-1 gap-4 list-none md:grid-cols-2 lg:grid-cols-3 xl:grid-cols-4">
{characters.map((character) => (
<li key={character.id} className="flex flex-col items-center">
<h3>{character.name}</h3>
<img src={character.image} alt={character.name} />
</li>
<CharacterItem character={character} key={character.id} />
))}
</ol>
);
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
type GenderSelectProps = {
onChange: (event: React.ChangeEvent<HTMLSelectElement>) => void;
gender: string;
};

const GenderSelect = ({ onChange, gender }: GenderSelectProps) => {
return (
<label className="flex flex-col">
Gender
<select value={gender} onChange={onChange} className="border h-7 mt-1">
<option value="">Any Gender</option>
<option value="female">Female</option>
<option value="male">Male</option>
<option value="genderless">Genderless</option>
<option value="unknown">Unknown</option>
</select>
</label>
);
};

export default GenderSelect;
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
type NameFieldProps = {
onChange: (event: React.ChangeEvent<HTMLInputElement>) => void;
name: string;
};

const NameField = ({ onChange, name }: NameFieldProps) => {
return (
<label className="flex flex-col">
Name
<input
className="border h-7 mt-1 indent-2"
type="text"
placeholder="Rick Sanchez..."
value={name}
onChange={onChange}
/>
</label>
);
};

export default NameField;
Loading