React.js – Тема 4 – Результат – Courses WebSkill

Слідкуйте за нами:

Тема 4. React.js Product Catalog

Створення Каталогу товарів з кошиком покупок

Створення Product Catalog React.js додатку, введення команд в консоль
D: або C: - переключення між дисками
cd - переходимо в необхідну вам папку
npx create-react-app product-catalog - створення нового React.js проєкту
npx create-react-app - сама команда створення
product-catalog - назва папки в якій буде додаток
cd product-catalog - переходимо в створену папку

Видаляємо непотрібні файли, чистимо index.js та App.js від непотрібних команд
Видаляємо файли: setupTests.js,repor,WebVitals.js,logo.svg,index.css,App.test.js
З файлу index.js видаляємо такі рядки
import './index.css'; import reportWebVitals from './reportWebVitals'; reportWebVitals();
Та коментарі: // If you want...
З файлу App.js видаляємо import logo from './logo.svg';
Тег <div className="app"> і все що всередині нього

В папці src залишаємо лише такі файли:
App.js, App.css, index.js

Скопіюйте стилізацію нижче та замініть її в файлі App.css

Стилізація App.css
/* styles.css */

body {
  font-family: Arial, sans-serif;
  background-color: #f0f0f0;
  margin: 0;
  padding: 0;
}

.container {
  max-width: 1200px;
  margin: 0 auto;
  padding: 20px;
}

h1 {
  font-size: 24px;
  margin-bottom: 20px;
}

.product-list {
  display: flex;
  flex-wrap: wrap;
}

.product {
  background-color: #fff;
  border: 1px solid #ddd;
  padding: 20px;
  margin: 10px;
  flex: 0 0 calc(33.33% - 20px);
}

.product h2 {
  font-size: 18px;
  margin: 0;
}

.product p {
  font-size: 16px;
  margin: 10px 0;
}

.product button {
  background-color: #007bff;
  color: #fff;
  border: none;
  padding: 10px 15px;
  cursor: pointer;
  font-size: 14px;
  transition: background-color 0.3s ease;
}

.product button:hover {
  background-color: #0056b3;
}

.cart {
  background-color: #fff;
  border: 1px solid #ddd;
  padding: 20px;
  margin-top: 20px;
}

.cart h2 {
  font-size: 20px;
}

.cart-item {
  border-bottom: 1px solid #ddd;
  padding: 10px 0;
  display: flex;
  justify-content: space-between;
  align-items: center;
}

.cart-item h3 {
  font-size: 18px;
  margin: 0;
}

.cart-item p {
  font-size: 16px;
  margin: 0;
}

.cart-item button {
  background-color: #dc3545;
  color: #fff;
  border: none;
  padding: 5px 10px;
  cursor: pointer;
  font-size: 12px;
  transition: background-color 0.3s ease;
}

.cart-item button:hover {
  background-color: #c82333;
}

Робимо заміну всієї стилізації в файлі App.css на свою, яку копіювали вище

Заготовки файлів для додатку

import React from 'react';
import ReactDOM from 'react-dom/client';
import App from './App';

const root = ReactDOM.createRoot(document.getElementById('root'));
root.render(
  <React.StrictMode>
    <App />
  </React.StrictMode>
);
import React, { useState } from "react";
import './App.css';
 
function App() {
  return (
 
  );
}
export default App;

Початок роботи із App.js

1. Визначити початковий стан компонента, який містить масив товарів (products) і пустий кошик (cart).

2. Створити метод addToCart, який додає обраний товар до кошика. Метод створює копію поточного кошика та додає до неї новий товар.

3. Створити метод removeFromCart, який видаляє товар з кошика на основі його id. Метод фільтрує поточний кошик та видаляє товар з вказаним id.

Рендеринг компонентів

  • Реалізувати метод render, який відображає ваш інтерфейс. У цьому методі ви відображаєте список товарів, кнопки "Додати до кошика" та кошик з можливістю видалення товарів.

Скріншоти усіх файлів в нашому додатку

Завдання 1

Ви можете створити окремий файл для функції "Підсумок покупок" та імпортувати його в компонент App. В цьому файлі ми створимо функцію calculateTotal, яка обчислить загальну вартість товарів у кошику.

Додавання можливості фільтрації товарів за категорією або ціновим діапазоном може бути досить обширним завданням, і воно потребує додаткової логіки та структури даних. Давайте спроектуємо цю логіку та створимо окремий файл для фільтрації.
Спочатку створіть новий файл, наприклад filterProducts.js
У цьому файлі ми створили функцію filterProducts, яка приймає список товарів, категорію та ціновий діапазон, і повертає список товарів, які відповідають вказаним критеріям.
Відредагуйте компонент App.js для використання фільтрації.
Імпортуйте функцію filterProducts і додайте два контроли введення для фільтрації за категорією та ціновим діапазоном. Ці значення фільтрації зберігаються у стані додатка та передаються функції filterProducts, яка фільтрує список товарів згідно зазначених критеріїв.
Добавте CSS до App.css(або створіть окремий файл - не забудьте його підключити) -  приклад стилізації нижче

Завдання 2

/* filter.css */

/* filter.css */

.filter-container {
background-color: #fff;
border: 1px solid #ddd;
padding: 20px;
margin-top: 20px;
}

.filter-container h2 {
font-size: 20px;
margin-bottom: 10px;
}

.filter-label {
font-size: 16px;
margin-right: 10px;
}

.filter-select,
.filter-input {
font-size: 14px;
padding: 5px;
border: 1px solid #ddd;
border-radius: 4px;
margin-right: 10px;
}

.filter-button {
background-color: #007bff;
color: #fff;
border: none;
padding: 10px 15px;
cursor: pointer;
font-size: 14px;
border-radius: 4px;
transition: background-color 0.3s ease;
}

.filter-button:hover {
background-color: #0056b3;
}

Додавання форми для введення адреси доставки та інших даних покупця та можливості здійснювати замовлення потребує розширення функціональності вашого додатку.

Спочатку створіть новий файл, наприклад OrderForm.js, в якому буде розміщено компонент форми замовлення.

Тепер ви можете імпортувати компонент OrderForm в App.js і використовувати його в шаблоні. Для відображення форми замовлення при добавленні товару в кошик і приховування її, коли кошик пустий, вам потрібно налаштувати умовний рендерінг в компоненті App.

Завдання 3

/* order-form.css */

/* order-form.css */

.order-form {
max-width: 400px;
margin: 0 auto;
padding: 20px;
background-color: #f5f5f5;
border: 1px solid #ddd;
border-radius: 5px;
}

.order-form h2 {
font-size: 20px;
margin-bottom: 10px;
}

.order-form label {
display: block;
font-size: 16px;
margin-bottom: 5px;
}

.order-form input[type="text"],
.order-form input[type="email"] {
width: 100%;
padding: 10px;
font-size: 14px;
margin-bottom: 10px;
border: 1px solid #ccc;
border-radius: 4px;
}

.order-form button[type="submit"] {
background-color: #007bff;
color: #fff;
border: none;
padding: 10px 15px;
cursor: pointer;
font-size: 14px;
border-radius: 4px;
transition: background-color 0.3s ease;
}

.order-form button[type="submit"]:hover {
background-color: #0056b3;
}

Завдання 4

Після успішного виконання попередніх завдань, доведіть Каталог товарів до хорошої якості, добавляючи в блоки товарів різні картинки, простилізуйте їх.
Добавте більше фільтрів по категоріях.
Доповніть форму для оформлення замовлення.

Скріншоти початкових файлів в нашому додатку

Посилання на Тему 9. Введення в React.js з попереднього курсу

Посилання на Тему 1. Створення React.js, проєкт ToDoList

Посилання на Тему 2. Створення React.js Quiz, Temperature App's

Завдання 1. Підсумок покупок

calculateTotal.js
// calculateTotal.js

export function calculateTotal(cart) {
    // Функція приймає масив товарів у кошику та обчислює загальну вартість
    const total = cart.reduce((acc, product) => acc + product.price, 0);
    return total;
  }
 
App.js
import React, { Component } from 'react';
import './App.css';
import { calculateTotal } from './components/calculateTotal'; // NEW Імпортуємо функцію

class App extends Component {
  state = {
    products: [
      { id: 1, name: 'Товар 1', price: 10 },
      { id: 2, name: 'Товар 2', price: 15 },
      { id: 3, name: 'Товар 3', price: 20 },
    ],
    cart: [],
  };

  addToCart = (product) => {
    const updatedCart = [...this.state.cart, product];
    this.setState({ cart: updatedCart });
  };

  removeFromCart = (productId) => {
    const updatedCart = this.state.cart.filter((product) => product.id !== productId);
    this.setState({ cart: updatedCart });
  };

  render() {
    const total = calculateTotal(this.state.cart); // NEW Обчислюємо загальну вартість
    return (
      <div>
        <h1>Каталог товарів</h1>
        <div className="product-list">
          {this.state.products.map((product) => (
            <div key={product.id} className="product">
              <h2>{product.name}</h2>
              <p>Ціна: ${product.price}</p>
              <button onClick={() => this.addToCart(product)}>Додати до кошика</button>
            </div>
          ))}
        </div>
        <h2>Кошик покупок</h2>
        <div className="cart">
          {this.state.cart.map((product) => (
            <div key={product.id} className="cart-item">
              <h3>{product.name}</h3>
              <p>Ціна: ${product.price}</p>
              <button onClick={() => this.removeFromCart(product.id)}>Видалити з кошика</button>
            </div>
          ))}
        </div>
        <h2>Підсумок покупок</h2>
        <p>Загальна вартість: ${total}</p>
      </div>
    );
  }
}

export default App;

Створіть папку components, в ній створіть новий файл calculateTotal.js у вашому проекті
Потім ви можете імпортувати calculateTotal у компонент App і використовувати її для відображення підсумку покупок.

Завдання 2. Фільтрувати товари за категорією або ціновим діапазоном

filterProducts.js
// filterProducts.js

export function filterProducts(products, category, priceRange) {
    // Функція для фільтрації товарів за категорією та ціновим діапазоном
    let filteredProducts = [...products];
 
    if (category) {
      filteredProducts = filteredProducts.filter(product => product.category === category);
    }
 
    if (priceRange) {
      filteredProducts = filteredProducts.filter(product => {
        const { min, max } = priceRange;
        return product.price >= min && product.price <= max;
      });
    }
 
    return filteredProducts;
  }
 
App.js
ПОМИЛКА
App.css

/* filter.css добавити вкінці App.css */

.filter-container {
background-color: #fff;
border: 1px solid #ddd;
padding: 20px;
margin-top: 20px;
}

.filter-container h2 {
font-size: 20px;
margin-bottom: 10px;
}

.filter-label {
font-size: 16px;
margin-right: 10px;
}

.filter-select,
.filter-input {
font-size: 14px;
padding: 5px;
border: 1px solid #ddd;
border-radius: 4px;
margin-right: 10px;
}

.filter-button {
background-color: #007bff;
color: #fff;
border: none;
padding: 10px 15px;
cursor: pointer;
font-size: 14px;
border-radius: 4px;
transition: background-color 0.3s ease;
}

.filter-button:hover {
background-color: #0056b3;
}

Спочатку створіть новий файл, наприклад filterProducts.js, у вашому проекті в папці components, не забудьте підключити його в App.js
Створіть метод applyFilters, який буде викликаний при натисканні кнопки “Застосувати фільтр”. У цьому методі ви можете оновити стан застосовуючи фільтри
Додайте кнопку “Застосувати фільтр” до компонента App.js при застосуванні фільтру показуються товари

Завдання 3. Форма замовлення

OrderForm.js
// OrderForm.js

import React, { Component } from 'react';
import './order-form.css'; // Імпортуємо файли стилів

class OrderForm extends Component {
  state = {
    name: '',
    address: '',
    email: '',
  };

  handleChange = (event) => {
    this.setState({ [event.target.name]: event.target.value });
  };

  handleSubmit = (event) => {
    event.preventDefault();
    const { name, address, email } = this.state;

    // Виконайте необхідну логіку для збереження даних та здійснення замовлення

    // Після здійснення замовлення можна очистити дані форми
    this.setState({ name: '', address: '', email: '' });
  };

  render() {
    return (
      <div className="order-form">
        <h2>Форма замовлення</h2>
        <form onSubmit={this.handleSubmit}>
          <div>
            <label htmlFor="name">Ім'я:</label>
            <input
              type="text"
              id="name"
              name="name"
              value={this.state.name}
              onChange={this.handleChange}
              required
            />
          </div>
          <div>
            <label htmlFor="address">Адреса доставки:</label>
            <input
              type="text"
              id="address"
              name="address"
              value={this.state.address}
              onChange={this.handleChange}
              required
            />
          </div>
          <div>
            <label htmlFor="email">Email:</label>
            <input
              type="email"
              id="email"
              name="email"
              value={this.state.email}
              onChange={this.handleChange}
              required
            />
          </div>
          <button type="submit">Замовити</button>
        </form>
      </div>
    );
  }
}

export default OrderForm;
App.js
import React, { Component } from 'react';
import './App.css';
import { calculateTotal } from './components/calculateTotal';
import { filterProducts } from './components/filterProducts';
import OrderForm from './components/OrderForm'; // Імпортуємо компонент форми

class App extends Component {
  state = {
    products: [
      { id: 1, name: 'Товар 1', category: 'Категорія 1', price: 10 },
      { id: 2, name: 'Товар 2', category: 'Категорія 2', price: 15 },
      { id: 3, name: 'Товар 3', category: 'Категорія 1', price: 20 },
    ],
    cart: [],
    categoryFilter: '', // Фільтр за категорією
    priceRangeFilter: { min: 0, max: Infinity }, // Фільтр за ціною
    filteredProducts: [], // Результати фільтрації
    showOrderForm: false, // Початково форма прихована
  };

  addToCart = (product) => {
    const updatedCart = [...this.state.cart, product];
    this.setState({ cart: updatedCart, showOrderForm: true });
  };
 clearCart = () => {
    this.setState({ cart: [], showOrderForm: false });
  };
  removeFromCart = (productId) => {
    const updatedCart = this.state.cart.filter((product) => product.id !== productId);
    this.setState({ cart: updatedCart });
  };

  handleCategoryFilterChange = (event) => {
    const category = event.target.value;
    this.setState({ categoryFilter: category });
  };

  handlePriceRangeFilterChange = (event) => {
    const min = parseFloat(event.target.value); // Отримуємо значення поля введення
    this.setState({ priceRangeFilter: { ...this.state.priceRangeFilter, min } });
  };

  handlePriceRangeMaxFilterChange = (event) => {
    const max = parseFloat(event.target.value); // Отримуємо значення поля введення
    this.setState({ priceRangeFilter: { ...this.state.priceRangeFilter, max } });
  };
  applyFilters = () => {
    const filteredProducts = filterProducts(
      this.state.products,
      this.state.categoryFilter,
      this.state.priceRangeFilter
    );
 
    this.setState({ filteredProducts });
  };

    // Метод для зміни стану та відображення/приховування форми замовлення
    toggleOrderForm = () => {
      this.setState((prevState) => ({
        showOrderForm: !prevState.showOrderForm,
      }));
    };
  render() {
    const total = calculateTotal(this.state.cart); // Обчислюємо загальну вартість
    return (
      <div>
      <div className="filter-container">
        <h2>Фільтрація</h2>
        <label className="filter-label" htmlFor="categoryFilter">Категорія:</label>
        <select
          className="filter-select"
          id="categoryFilter"
          onChange={(e) => this.setState({ categoryFilter: e.target.value })}
          value={this.state.categoryFilter}
        >
          <option value="">Всі</option>
          <option value="Категорія 1">Категорія 1</option>
          <option value="Категорія 2">Категорія 2</option>
        </select>
        <label className="filter-label" htmlFor="minPriceFilter">Мінімальна ціна:</label>
        <input
          className="filter-input"
          type="number"
          id="minPriceFilter"
          min="0"
          onChange={(e) => this.setState({ priceRangeFilter: { ...this.state.priceRangeFilter, min: parseFloat(e.target.value) } })}
          value={this.state.priceRangeFilter.min}
        />
        <label className="filter-label" htmlFor="maxPriceFilter">Максимальна ціна:</label>
        <input
          className="filter-input"
          type="number"
          id="maxPriceFilter"
          min="0"
          onChange={(e) => this.setState({ priceRangeFilter: { ...this.state.priceRangeFilter, max: parseFloat(e.target.value) } })}
          value={this.state.priceRangeFilter.max}
        />
        <button className="filter-button" onClick={this.applyFilters}>Застосувати фільтр</button>
      </div>
        <br />
        <h1>Каталог товарів</h1>
        <div className="product-list">
          {this.state.filteredProducts.map((product) => (
            <div key={product.id} className="product">
              <h2>{product.name}</h2>
              <p>Категорія: {product.category}</p>
              <p>Ціна: ${product.price}</p>
              <button onClick={() => this.addToCart(product)}>Додати до кошика</button>
            </div>
          ))}
        </div>
        <h2>Кошик покупок</h2>
        <div className="cart">
          {this.state.cart.map((product) => (
            <div key={product.id} className="cart-item">
              <h3>{product.name}</h3>
              <p>Ціна: ${product.price}</p>
              <button onClick={() => this.removeFromCart(product.id)}>Видалити з кошика</button>
            </div>
          ))}
        </div>
        <h2>Підсумок покупок</h2>
        <p>Загальна вартість: ${total}</p>
       
        {this.state.cart.length > 0 && (
          <button className="clear-cart-button" onClick={this.clearCart}>Очистити кошик</button>
        )}
        {this.state.showOrderForm && <OrderForm />}
      </div>
    );
  }
}

export default App;
order-form.css
/* order-form.css */

.order-form {
    max-width: 400px;
    margin: 0 auto;
    padding: 20px;
    background-color: #f5f5f5;
    border: 1px solid #ddd;
    border-radius: 5px;
  }
 
  .order-form h2 {
    font-size: 20px;
    margin-bottom: 10px;
  }
 
  .order-form label {
    display: block;
    font-size: 16px;
    margin-bottom: 5px;
  }
 
  .order-form input[type="text"],
  .order-form input[type="email"] {
    width: 100%;
    padding: 10px;
    font-size: 14px;
    margin-bottom: 10px;
    border: 1px solid #ccc;
    border-radius: 4px;
  }
 
  .order-form button[type="submit"] {
    background-color: #007bff;
    color: #fff;
    border: none;
    padding: 10px 15px;
    cursor: pointer;
    font-size: 14px;
    border-radius: 4px;
    transition: background-color 0.3s ease;
  }
 
  .order-form button[type="submit"]:hover {
    background-color: #0056b3;
  }
/* order-form.css */

.clear-cart-button {
  background-color: #dc3545; /* Червоний колір кнопки */
  color: #fff; /* Білий текст */
  border: none;
  padding: 10px 15px;
  cursor: pointer;
  font-size: 14px;
  border-radius: 4px;
  margin-top: 10px; /* Відступ зверху */
  transition: background-color 0.3s ease;
}

.clear-cart-button:hover {
  background-color: #c82333; /* Зміна кольору при наведенні */
}
 

Спочатку створіть новий файл, наприклад OrderForm.js, в якому буде розміщено компонент форми замовлення.
Тепер ви можете імпортувати компонент OrderForm в App.js і використовувати його в шаблоні. Для відображення форми замовлення при добавленні товару в кошик і приховування її, коли кошик пустий, вам потрібно налаштувати умовний рендерінг в компоненті App
Для умовного рендерінгу форми замовлення на основі стану можна використовувати умовний оператор (if). Ось як ви можете здійснити умовний рендерінг форми замовлення на основі значення стану showOrderForm

Вміст кожного із файлів готового додатку Product Catalog

App.js
import React, { Component } from 'react';
import './App.css';
import { calculateTotal } from './components/calculateTotal';
import { filterProducts } from './components/filterProducts';
import OrderForm from './components/OrderForm'; // Імпортуємо компонент форми

 

class App extends Component {
  state = {
    products: [
      { id: 1, name: 'Товар 1', category: 'Категорія 1', price: 10 },
      { id: 2, name: 'Товар 2', category: 'Категорія 2', price: 15 },
      { id: 3, name: 'Товар 3', category: 'Категорія 1', price: 20 },
    ],
    cart: [],
    categoryFilter: '', // Фільтр за категорією
    priceRangeFilter: { min: 0, max: Infinity }, // Фільтр за ціною
    filteredProducts: [], // Результати фільтрації
    showOrderForm: false, // Початково форма прихована
  };

 

  addToCart = (product) => {
    const updatedCart = [...this.state.cart, product];
    this.setState({ cart: updatedCart, showOrderForm: true });
  };
 clearCart = () => {
    this.setState({ cart: [], showOrderForm: false });
  };
  removeFromCart = (productId) => {
    const updatedCart = this.state.cart.filter((product) => product.id !== productId);
    this.setState({ cart: updatedCart });
  };

 

  handleCategoryFilterChange = (event) => {
    const category = event.target.value;
    this.setState({ categoryFilter: category });
  };

 

  handlePriceRangeFilterChange = (event) => {
    const min = parseFloat(event.target.value); // Отримуємо значення поля введення
    this.setState({ priceRangeFilter: { ...this.state.priceRangeFilter, min } });
  };

 

  handlePriceRangeMaxFilterChange = (event) => {
    const max = parseFloat(event.target.value); // Отримуємо значення поля введення
    this.setState({ priceRangeFilter: { ...this.state.priceRangeFilter, max } });
  };
  applyFilters = () => {
    const filteredProducts = filterProducts(
      this.state.products,
      this.state.categoryFilter,
      this.state.priceRangeFilter
    );
 
    this.setState({ filteredProducts });
  };

 

    // Метод для зміни стану та відображення/приховування форми замовлення
    toggleOrderForm = () => {
      this.setState((prevState) => ({
        showOrderForm: !prevState.showOrderForm,
      }));
    };
  render() {
    const total = calculateTotal(this.state.cart); // Обчислюємо загальну вартість
    return (
      <div>
      <div className="filter-container">
        <h2>Фільтрація</h2>
        <label className="filter-label" htmlFor="categoryFilter">Категорія:</label>
        <select
          className="filter-select"
          id="categoryFilter"
          onChange={(e) => this.setState({ categoryFilter: e.target.value })}
          value={this.state.categoryFilter}
        >
          <option value="">Всі</option>
          <option value="Категорія 1">Категорія 1</option>
          <option value="Категорія 2">Категорія 2</option>
        </select>
        <label className="filter-label" htmlFor="minPriceFilter">Мінімальна ціна:</label>
        <input
          className="filter-input"
          type="number"
          id="minPriceFilter"
          min="0"
          onChange={(e) => this.setState({ priceRangeFilter: { ...this.state.priceRangeFilter, min: parseFloat(e.target.value) } })}
          value={this.state.priceRangeFilter.min}
        />
        <label className="filter-label" htmlFor="maxPriceFilter">Максимальна ціна:</label>
        <input
          className="filter-input"
          type="number"
          id="maxPriceFilter"
          min="0"
          onChange={(e) => this.setState({ priceRangeFilter: { ...this.state.priceRangeFilter, max: parseFloat(e.target.value) } })}
          value={this.state.priceRangeFilter.max}
        />
        <button className="filter-button" onClick={this.applyFilters}>Застосувати фільтр</button>
      </div>
        <br />
        <h1>Каталог товарів</h1>
        <div className="product-list">
          {this.state.filteredProducts.map((product) => (
            <div key={product.id} className="product">
              <h2>{product.name}</h2>
              <p>Категорія: {product.category}</p>
              <p>Ціна: ${product.price}</p>
              <button onClick={() => this.addToCart(product)}>Додати до кошика</button>
            </div>
          ))}
        </div>
        <h2>Кошик покупок</h2>
        <div className="cart">
          {this.state.cart.map((product) => (
            <div key={product.id} className="cart-item">
              <h3>{product.name}</h3>
              <p>Ціна: ${product.price}</p>
              <button onClick={() => this.removeFromCart(product.id)}>Видалити з кошика</button>
            </div>
          ))}
        </div>
        <h2>Підсумок покупок</h2>
        <p>Загальна вартість: ${total}</p>
       
        {this.state.cart.length > 0 && (
          <button className="clear-cart-button" onClick={this.clearCart}>Очистити кошик</button>
        )}
        {this.state.showOrderForm && <OrderForm />}
      </div>
    );
  }
}

 

export default App;
App.css
/* styles.css */

body {
  font-family: Arial, sans-serif;
  background-color: #f0f0f0;
  margin: 0;
  padding: 0;
}

.container {
  max-width: 1200px;
  margin: 0 auto;
  padding: 20px;
}

h1 {
  font-size: 24px;
  margin-bottom: 20px;
}

.product-list {
  display: flex;
  flex-wrap: wrap;
}

.product {
  background-color: #fff;
  border: 1px solid #ddd;
  padding: 20px;
  margin: 10px;
  flex: 0 0 calc(33.33% - 20px);
}

.product h2 {
  font-size: 18px;
  margin: 0;
}

.product p {
  font-size: 16px;
  margin: 10px 0;
}

.product button {
  background-color: #007bff;
  color: #fff;
  border: none;
  padding: 10px 15px;
  cursor: pointer;
  font-size: 14px;
  transition: background-color 0.3s ease;
}

.product button:hover {
  background-color: #0056b3;
}

.cart {
  background-color: #fff;
  border: 1px solid #ddd;
  padding: 20px;
  margin-top: 20px;
}

.cart h2 {
  font-size: 20px;
}

.cart-item {
  border-bottom: 1px solid #ddd;
  padding: 10px 0;
  display: flex;
  justify-content: space-between;
  align-items: center;
}

.cart-item h3 {
  font-size: 18px;
  margin: 0;
}

.cart-item p {
  font-size: 16px;
  margin: 0;
}

.cart-item button {
  background-color: #dc3545;
  color: #fff;
  border: none;
  padding: 5px 10px;
  cursor: pointer;
  font-size: 12px;
  transition: background-color 0.3s ease;
}

.cart-item button:hover {
  background-color: #c82333;
}
/* filter.css */

.filter-container {
  background-color: #fff;
  border: 1px solid #ddd;
  padding: 20px;
  margin-top: 20px;
}

.filter-container h2 {
  font-size: 20px;
  margin-bottom: 10px;
}

.filter-label {
  font-size: 16px;
  margin-right: 10px;
}

.filter-select,
.filter-input {
  font-size: 14px;
  padding: 5px;
  border: 1px solid #ddd;
  border-radius: 4px;
  margin-right: 10px;
}

.filter-button {
  background-color: #007bff;
  color: #fff;
  border: none;
  padding: 10px 15px;
  cursor: pointer;
  font-size: 14px;
  border-radius: 4px;
  transition: background-color 0.3s ease;
}

.filter-button:hover {
  background-color: #0056b3;
}
calculateTotal.js
// calculateTotal.js

export function calculateTotal(cart) {
    // Функція приймає масив товарів у кошику та обчислює загальну вартість
    const total = cart.reduce((acc, product) => acc + product.price, 0);
    return total;
  }
 
filterProducts.js
// filterProducts.js

export function filterProducts(products, category, priceRange) {
    // Функція для фільтрації товарів за категорією та ціновим діапазоном
    let filteredProducts = [...products];
 
    if (category) {
      filteredProducts = filteredProducts.filter(product => product.category === category);
    }
 
    if (priceRange) {
      filteredProducts = filteredProducts.filter(product => {
        const { min, max } = priceRange;
        return product.price >= min && product.price <= max;
      });
    }
 
    return filteredProducts;
  }
 
OrderForm.js
// OrderForm.js

import React, { Component } from 'react';
import './order-form.css'; // Імпортуємо файли стилів

class OrderForm extends Component {
  state = {
    name: '',
    address: '',
    email: '',
  };

  handleChange = (event) => {
    this.setState({ [event.target.name]: event.target.value });
  };

  handleSubmit = (event) => {
    event.preventDefault();
    const { name, address, email } = this.state;

    // Виконайте необхідну логіку для збереження даних та здійснення замовлення

    // Після здійснення замовлення можна очистити дані форми
    this.setState({ name: '', address: '', email: '' });
  };

  render() {
    return (
      <div className="order-form">
        <h2>Форма замовлення</h2>
        <form onSubmit={this.handleSubmit}>
          <div>
            <label htmlFor="name">Ім'я:</label>
            <input
              type="text"
              id="name"
              name="name"
              value={this.state.name}
              onChange={this.handleChange}
              required
            />
          </div>
          <div>
            <label htmlFor="address">Адреса доставки:</label>
            <input
              type="text"
              id="address"
              name="address"
              value={this.state.address}
              onChange={this.handleChange}
              required
            />
          </div>
          <div>
            <label htmlFor="email">Email:</label>
            <input
              type="email"
              id="email"
              name="email"
              value={this.state.email}
              onChange={this.handleChange}
              required
            />
          </div>
          <button type="submit">Замовити</button>
        </form>
      </div>
    );
  }
}

export default OrderForm;
order-form.css
/* order-form.css */

.order-form {
    max-width: 400px;
    margin: 0 auto;
    padding: 20px;
    background-color: #f5f5f5;
    border: 1px solid #ddd;
    border-radius: 5px;
  }
 
  .order-form h2 {
    font-size: 20px;
    margin-bottom: 10px;
  }
 
  .order-form label {
    display: block;
    font-size: 16px;
    margin-bottom: 5px;
  }
 
  .order-form input[type="text"],
  .order-form input[type="email"] {
    width: 100%;
    padding: 10px;
    font-size: 14px;
    margin-bottom: 10px;
    border: 1px solid #ccc;
    border-radius: 4px;
  }
 
  .order-form button[type="submit"] {
    background-color: #007bff;
    color: #fff;
    border: none;
    padding: 10px 15px;
    cursor: pointer;
    font-size: 14px;
    border-radius: 4px;
    transition: background-color 0.3s ease;
  }
 
  .order-form button[type="submit"]:hover {
    background-color: #0056b3;
  }
/* order-form.css */

.clear-cart-button {
  background-color: #dc3545; /* Червоний колір кнопки */
  color: #fff; /* Білий текст */
  border: none;
  padding: 10px 15px;
  cursor: pointer;
  font-size: 14px;
  border-radius: 4px;
  margin-top: 10px; /* Відступ зверху */
  transition: background-color 0.3s ease;
}

.clear-cart-button:hover {
  background-color: #c82333; /* Зміна кольору при наведенні */
}
 
Copyright © 2023 Courses WebSkill | Powered by WebSkill
Scroll to Top