update demo-shop-app-ui,

This commit is contained in:
louiscklaw
2025-06-08 19:08:01 +08:00
parent 592a099f7b
commit 15f8d2e6aa
3 changed files with 97 additions and 60 deletions

View File

@@ -1,4 +1,22 @@
import { IonBackButton, IonBreadcrumb, IonBreadcrumbs, IonButtons, IonCol, IonContent, IonGrid, IonHeader, IonPage, IonRow, IonSearchbar, IonTitle, IonToolbar, useIonViewWillEnter, useIonViewWillLeave, IonRouterLink, useIonModal } from '@ionic/react';
import {
IonBackButton,
IonBreadcrumb,
IonBreadcrumbs,
IonButtons,
IonCol,
IonContent,
IonGrid,
IonHeader,
IonPage,
IonRow,
IonSearchbar,
IonTitle,
IonToolbar,
useIonViewWillEnter,
useIonViewWillLeave,
IonRouterLink,
useIonModal,
} from '@ionic/react';
import { useStoreState } from 'pullstate';
import { useRef } from 'react';
import { useState } from 'react';
@@ -9,49 +27,43 @@ import { ProductStore } from '../store';
import { getCategoryProducts } from '../store/Selectors';
import { capitalizeWords } from '../utils';
import styles from "./Category.module.scss";
import styles from './Category.module.scss';
const Category = () => {
const pageRef = useRef();
const pageRef = useRef(null);
const { name } = useParams();
const products = useStoreState(ProductStore, getCategoryProducts(name));
const [ selectedProduct, setSelectedProduct ] = useState(false);
const handleShowModal = product => {
const [selectedProduct, setSelectedProduct] = useState(false);
const handleShowModal = (product) => {
setSelectedProduct(product);
present({
cssClass: "product-modal",
presentingElement: pageRef.current
cssClass: 'product-modal',
presentingElement: pageRef.current,
});
}
const [ present, dismiss ] = useIonModal(ProductModal, {
};
const [present, dismiss] = useIonModal(ProductModal, {
dismiss: () => dismiss(),
product: selectedProduct
product: selectedProduct,
});
useIonViewWillEnter(() => {
document.querySelector("ion-tab-bar").style.display = "none";
document.querySelector('ion-tab-bar').style.display = 'none';
});
useIonViewWillLeave(() => {
document.querySelector("ion-tab-bar").style.display = "";
})
document.querySelector('ion-tab-bar').style.display = '';
});
return (
<IonPage ref={ pageRef }>
<IonPage ref={pageRef}>
<IonHeader>
<IonToolbar>
<IonButtons slot="start">
<IonBackButton />
</IonButtons>
<IonTitle>{ capitalizeWords(name) }</IonTitle>
<IonTitle>{capitalizeWords(name)}</IonTitle>
</IonToolbar>
</IonHeader>
<IonContent fullscreen>
@@ -60,25 +72,33 @@ const Category = () => {
{/* <IonTitle size="large">{ capitalizeWords(name) }</IonTitle> */}
<IonBreadcrumbs>
<IonBreadcrumb color="dark">
<IonRouterLink routerLink="/home" routerDirection="back" color="dark">Shop</IonRouterLink>
<IonRouterLink routerLink="/home" routerDirection="back" color="dark">
Shop
</IonRouterLink>
</IonBreadcrumb>
<IonBreadcrumb color="primary" active>
{capitalizeWords(name)}
</IonBreadcrumb>
<IonBreadcrumb color="primary" active>{ capitalizeWords(name) }</IonBreadcrumb>
</IonBreadcrumbs>
</IonToolbar>
</IonHeader>
<IonGrid className="ion-padding">
<IonRow className={ styles.searchContainer }>
<IonRow className={styles.searchContainer}>
<IonCol size="12">
<IonSearchbar animated placeholder="Search for a product" />
</IonCol>
</IonRow>
<IonRow>
{ products.map((product, index) => {
return <Product product={ product } key={ `product_${ index }` } click={ () => handleShowModal(product) } />;
{products.map((product, index) => {
return (
<Product
product={product}
key={`product_${index}`}
click={() => handleShowModal(product)}
/>
);
})}
</IonRow>
</IonGrid>

View File

@@ -25,7 +25,7 @@ import { chevronBackOutline, refreshOutline } from 'ionicons/icons';
const Home = () => {
const router = useIonRouter();
const pageRef = useRef();
const pageRef = useRef(null);
const [showModal, setShowModal] = useState(false);
const [selectedProduct, setSelectedProduct] = useState(false);

View File

@@ -1,38 +1,46 @@
import { IonBadge, IonButton, IonButtons, IonCard, IonCardContent, IonCol, IonContent, IonGrid, IonHeader, IonIcon, IonPage, IonRow, IonTitle, IonToolbar } from '@ionic/react';
import {
IonBadge,
IonButton,
IonButtons,
IonCard,
IonCardContent,
IonCol,
IonContent,
IonGrid,
IonHeader,
IonIcon,
IonPage,
IonRow,
IonTitle,
IonToolbar,
} from '@ionic/react';
import { cart, star } from 'ionicons/icons';
import { useRef } from 'react';
import { addToCart } from '../store/CartStore';
import { capitalizeWords } from '../utils';
import styles from "./ProductModal.module.scss";
import styles from './ProductModal.module.scss';
export const ProductModal = ({ dismiss, product }) => {
const cartRef = useRef();
const cartRef = useRef(null);
const handleAddToCart = () => {
cartRef.current.style.display = "inline";
cartRef.current.style.display = 'inline';
addToCart(product);
setTimeout(() => {
cartRef.current.style.display = "none";
cartRef.current.style.display = 'none';
}, 750);
}
};
return (
<IonPage>
<IonHeader>
<IonToolbar>
<IonTitle>View Product</IonTitle>
<IonButtons slot="end">
<IonButton onClick={ dismiss }>
Close
</IonButton>
<IonButton onClick={dismiss}>Close</IonButton>
</IonButtons>
</IonToolbar>
</IonHeader>
@@ -40,27 +48,29 @@ export const ProductModal = ({ dismiss, product }) => {
<IonGrid>
<IonRow className="animate__animated animate__faster animate__slideInUp">
<IonCol size="12">
<IonCard className={ styles.productCard }>
<IonCard className={styles.productCard}>
<IonCardContent>
<div className={ styles.productTopInfo }>
<img src={ product.image } alt="product" />
<div className={ styles.productDetails }>
<IonBadge color="primary">{ capitalizeWords(product.category) }</IonBadge>
<h3>{ product.title }</h3>
<div className={styles.productTopInfo}>
<img src={product.image} alt="product" />
<div className={styles.productDetails}>
<IonBadge color="primary">{capitalizeWords(product.category)}</IonBadge>
<h3>{product.title}</h3>
</div>
</div>
<div className={ styles.productDescription }>
<div className={styles.productDescription}>
<h3>Product Description</h3>
<p>{ product.description }</p>
<p>{product.description}</p>
</div>
<div className={ styles.productDescription }>
<div className={styles.productDescription}>
<h3>Product Rating</h3>
<div>
<p>{ product.rating.count} people have bought this item from the IonShop and have rated an average of { product.rating.rate }.</p>
<IonIcon icon={ star } color="primary" />
<p>
{product.rating.count} people have bought this item from the IonShop and
have rated an average of {product.rating.rate}.
</p>
<IonIcon icon={star} color="primary" />
</div>
</div>
</IonCardContent>
@@ -69,15 +79,22 @@ export const ProductModal = ({ dismiss, product }) => {
</IonRow>
</IonGrid>
<IonGrid className={ `${ styles.bottom } animate__animated animate__slideInUp` }>
<IonGrid className={`${styles.bottom} animate__animated animate__slideInUp`}>
<IonRow>
<IonCol size="12">
<div className={ styles.price }>
<div className={styles.price}>
Buy now for
<IonBadge color="dark" className="ion-padding-left">£{ product.price.toFixed(2) }</IonBadge>
<IonBadge color="dark" className="ion-padding-left">
£{product.price.toFixed(2)}
</IonBadge>
</div>
<IonIcon ref={ cartRef } className={ `${ styles.animatedCart } animate__animated animate__slideInUp` } icon={ cart } color="dark" />
<IonButton onClick={ handleAddToCart }>Add to Cart</IonButton>
<IonIcon
ref={cartRef}
className={`${styles.animatedCart} animate__animated animate__slideInUp`}
icon={cart}
color="dark"
/>
<IonButton onClick={handleAddToCart}>Add to Cart</IonButton>
</IonCol>
</IonRow>
</IonGrid>