(feat): layout update

This commit is contained in:
Maksym Sadovnychyy 2022-05-20 20:46:05 +02:00
parent 138cd250dd
commit 2f65cd44b5
18 changed files with 817 additions and 38 deletions

View File

@ -9,6 +9,7 @@ import { actionCreators as settingsActionCreators } from './store/reducers/Setti
import { DynamicLayout } from './layouts'
import { DynamicPage } from './pages'
import { IReduxState, IRoute } from './interfaces'
interface IRouteProp {
path: string,
element?: JSX.Element

View File

@ -25,7 +25,7 @@ const NavMenu : FC<INavMenu> = (props: INavMenu) => {
}
return <header>
<Navbar className="navbar-expand-sm navbar-toggleable-sm fixed-top border-bottom box-shadow mb-3" light>
<Navbar className="navbar-expand-sm navbar-toggleable-sm fixed-top border-bottom box-shadow mb-3 bg-light">
<Button color="light" onClick={toggleSidebar}>
<FeatherIcon icon="align-left" />
</Button>

View File

@ -20,9 +20,9 @@ const AdminLayout: FC<ILayout> = ({ children = null }) => {
<div className={classNames(`${style.sidebar}`, sidebarIsOpen ? `${style.isopen}` : '')}>
<SideMenu />
</div>
<Container fluid className={classNames(`${style.content}`, sidebarIsOpen ? `${style.isopen}` : '') }>
<div className={classNames(`${style.content}`, sidebarIsOpen ? `${style.isopen}` : '') }>
{children}
</Container>
</div>
</div>
</>
}

View File

@ -0,0 +1,17 @@
import React from 'react'
import { useSelector } from 'react-redux'
import { Container } from 'reactstrap'
import { IReduxState } from '../../../interfaces'
const Footer = () => {
let { siteName } = useSelector((state: IReduxState) => state.settings)
return <footer className="py-5 bg-dark">
<Container fluid><p className="m-0 text-center text-white">Copyright &copy; {siteName} {(new Date).getFullYear()}</p></Container>
</footer>
}
export {
Footer
}

View File

@ -19,7 +19,7 @@ const NavMenu : FC = () => {
}
return <header>
<Navbar className="navbar-expand-sm navbar-toggleable-sm fixed-top border-bottom box-shadow mb-3" light>
<Navbar className="navbar-expand-sm navbar-toggleable-sm fixed-top border-bottom box-shadow mb-3 bg-light">
<NavbarBrand href="/">{siteName}</ NavbarBrand>
<NavbarToggler onClick={toggle} className="mr-2"/>
<Collapse className="d-sm-inline-flex flex-sm-row-reverse" isOpen={state.isOpen} navbar>
@ -34,6 +34,13 @@ const NavMenu : FC = () => {
})}
</ul>
</Collapse>
<form className="d-flex">
<button className="btn btn-outline-dark" type="submit">
<FeatherIcon icon='shopping-cart' className="me-1"/>Cart
<span className="badge bg-dark text-white ms-1 rounded-pill">0</span>
</button>
</form>
</Navbar>
</header>
}

View File

@ -1,7 +1,7 @@
import React, { FC } from 'react'
import { Container } from 'reactstrap'
import { NavMenu } from './NavMenu'
import { Footer } from './Footer'
import { ILayout } from '../interfaces'
import s from './scss/style.module.scss'
@ -10,10 +10,11 @@ const PublicLayout: FC<ILayout> = ({ children = null }) => {
return <>
<NavMenu />
<div className={s.wrapper}>
<Container fluid className={s.content}>
<div className={s.content}>
{children}
</Container>
</div>
</div>
<Footer />
</>
}

View File

@ -0,0 +1,137 @@
import React from 'react'
import { Link } from 'react-router-dom'
import { Card, CardBody, CardHeader, CardImg, Col, Container, Row } from 'reactstrap'
const BlogCatalog = () => {
const items = [
{
id: "1"
},
{
id: "2"
}
]
return <>
<header className="py-5 bg-light border-bottom mb-4">
<Container fluid>
<div className="text-center my-5">
<h1 className="fw-bolder">Welcome to Blog Home!</h1>
<p className="lead mb-0">A Bootstrap 5 starter layout for your next blog homepage</p>
</div>
</Container>
</header>
<Container fluid>
<Row>
<Col>
<Card className="mb-4">
<Link to={`blog/item/featured`}>
<CardImg top src="https://dummyimage.com/850x350/dee2e6/6c757d.jpg" alt="..." />
</Link>
<CardBody>
<div className="small text-muted">January 1, 2022</div>
<h2 className="card-title">Featured Post Title</h2>
<p className="card-text">Lorem ipsum dolor sit amet, consectetur adipisicing elit. Reiciendis aliquid atque, nulla? Quos cum ex quis soluta, a laboriosam. Dicta expedita corporis animi vero voluptate voluptatibus possimus, veniam magni quis!</p>
<a className="btn btn-primary" href="#!">Read more </a>
</CardBody>
</Card>
<Row>
{items.map((item, index) => <Col key={index} lg={6}>
<Card mb={4}>
<Link to={`blog/item/${item.id}`}>
<CardImg top src="https://dummyimage.com/850x350/dee2e6/6c757d.jpg" alt="..." />
</Link>
<CardBody>
<div className="small text-muted">January 1, 2022</div>
<h2 className="card-title h4">Post Title</h2>
<p className="card-text">Lorem ipsum dolor sit amet, consectetur adipisicing elit. Reiciendis aliquid atque, nulla.</p>
<a className="btn btn-primary" href="#!">Read more </a>
</CardBody>
</Card>
<Card className="mb-4">
<Link to={`blog/item/${item.id}`}>
<CardImg top src="https://dummyimage.com/850x350/dee2e6/6c757d.jpg" alt="..." />
</Link>
<CardBody>
<div className="small text-muted">January 1, 2022</div>
<h2 className="card-title h4">Post Title</h2>
<p className="card-text">Lorem ipsum dolor sit amet, consectetur adipisicing elit. Reiciendis aliquid atque, nulla.</p>
<a className="btn btn-primary" href="#!">Read more </a>
</CardBody>
</Card>
</Col>)}
<nav aria-label="Pagination">
<hr className="my-0" />
<ul className="pagination justify-content-center my-4">
<li className="page-item disabled"><a className="page-link" href="#" aria-disabled="true">Newer</a></li>
<li className="page-item active" aria-current="page"><a className="page-link" href="#!">1</a></li>
<li className="page-item"><a className="page-link" href="#!">2</a></li>
<li className="page-item"><a className="page-link" href="#!">3</a></li>
<li className="page-item disabled"><a className="page-link" href="#!">...</a></li>
<li className="page-item"><a className="page-link" href="#!">15</a></li>
<li className="page-item"><a className="page-link" href="#!">Older</a></li>
</ul>
</nav>
</Row>
</Col>
<Col className="lg-4">
<Card className="mb-4">
<CardHeader>Search</CardHeader>
<CardBody>
<div className="input-group">
<input className="form-control" type="text" placeholder="Enter search term..." aria-label="Enter search term..." aria-describedby="button-search" />
<button className="btn btn-primary" id="button-search" type="button">Go!</button>
</div>
</CardBody>
</Card>
<Card className="mb-4">
<CardHeader>Categories</CardHeader>
<CardBody>
<Row>
<Col className="sm-6">
<ul className="list-unstyled mb-0">
<li><a href="#!">Web Design</a></li>
<li><a href="#!">HTML</a></li>
<li><a href="#!">Freebies</a></li>
</ul>
</Col>
<Col sm={6}>
<ul className="list-unstyled mb-0">
<li><a href="#!">JavaScript</a></li>
<li><a href="#!">CSS</a></li>
<li><a href="#!">Tutorials</a></li>
</ul>
</Col>
</Row>
</CardBody>
</Card>
<Card className="mb-4">
<CardHeader>Side Widget</CardHeader>
<CardBody>You can put anything you want inside of these side widgets. They are easy to use, and feature the Bootstrap 5 card component!</CardBody>
</Card>
</Col>
</Row>
</Container>
</>
}
export {
BlogCatalog
}

View File

@ -0,0 +1,133 @@
import React from 'react'
import { Card, CardBody, CardHeader, Col, Container, Row } from 'reactstrap'
const BlogItem = () => {
const postItem = {
comments: []
}
return <Container fluid className="mt-5">
<Row>
<Col className="lg-8">
<article>
<header className="mb-4">
<h1 className="fw-bolder mb-1">Welcome to Blog Post!</h1>
<div className="text-muted fst-italic mb-2">Posted on January 1, 2022 by Start Bootstrap</div>
<a className="badge bg-secondary text-decoration-none link-light" href="#!">Web Design</a>
<a className="badge bg-secondary text-decoration-none link-light" href="#!">Freebies</a>
</header>
<figure className="mb-4"><img className="img-fluid rounded" src="https://dummyimage.com/900x400/ced4da/6c757d.jpg" alt="..." /></figure>
<section className="mb-5">
<p className="fs-5 mb-4">Science is an enterprise that should be cherished as an activity of the free human mind. Because it transforms who we are, how we live, and it gives us an understanding of our place in the universe.</p>
<p className="fs-5 mb-4">The universe is large and old, and the ingredients for life as we know it are everywhere, so there's no reason to think that Earth would be unique in that regard. Whether of not the life became intelligent is a different question, and we'll see if we find that.</p>
<p className="fs-5 mb-4">If you get asteroids about a kilometer in size, those are large enough and carry enough energy into our system to disrupt transportation, communication, the food chains, and that can be a really bad day on Earth.</p>
<h2 className="fw-bolder mb-4 mt-5">I have odd cosmic thoughts every day</h2>
<p className="fs-5 mb-4">For me, the most fascinating interface is Twitter. I have odd cosmic thoughts every day and I realized I could hold them to myself or share them with people who might be interested.</p>
<p className="fs-5 mb-4">Venus has a runaway greenhouse effect. I kind of want to know what happened there because we're twirling knobs here on Earth without knowing the consequences of it. Mars once had running water. It's bone dry today. Something bad happened there as well.</p>
</section>
</article>
<section className="mb-5">
<div className="card bg-light">
<div className="card-body">
<form className="mb-4">
{/*<textarea class="form-control" rows="3" placeholder="Join the discussion and leave a comment!"></textarea>*/}
</form>
<div className="d-flex mb-4">
<div className="flex-shrink-0"><img className="rounded-circle" src="https://dummyimage.com/50x50/ced4da/6c757d.jpg" alt="..." /></div>
<div className="ms-3">
<div className="fw-bold">Commenter Name</div>
If you're going to lead a space frontier, it has to be government; it'll never be private enterprise. Because the space frontier is dangerous, and it's expensive, and it has unquantified risks.
<div className="d-flex mt-4">
<div className="flex-shrink-0"><img className="rounded-circle" src="https://dummyimage.com/50x50/ced4da/6c757d.jpg" alt="..." /></div>
<div className="ms-3">
<div className="fw-bold">Commenter Name</div>
And under those conditions, you cannot establish a capital-market evaluation of that enterprise. You can't get investors.
</div>
</div>
<div className="d-flex mt-4">
<div className="flex-shrink-0"><img className="rounded-circle" src="https://dummyimage.com/50x50/ced4da/6c757d.jpg" alt="..." /></div>
<div className="ms-3">
<div className="fw-bold">Commenter Name</div>
When you put money directly to a problem, it makes a good headline.
</div>
</div>
</div>
</div>
<div className="d-flex">
<div className="flex-shrink-0"><img className="rounded-circle" src="https://dummyimage.com/50x50/ced4da/6c757d.jpg" alt="..." /></div>
<div className="ms-3">
<div className="fw-bold">Commenter Name</div>
When I look at the universe and all the ways the universe wants to kill us, I find it hard to reconcile that with statements of beneficence.
</div>
</div>
</div>
</div>
</section>
</Col>
<Col className="lg-4">
<Card className="mb-4">
<CardHeader>Search</CardHeader>
<CardBody>
<div className="input-group">
<input className="form-control" type="text" placeholder="Enter search term..." aria-label="Enter search term..." aria-describedby="button-search" />
<button className="btn btn-primary" id="button-search" type="button">Go!</button>
</div>
</CardBody>
</Card>
<Card className="mb-4">
<CardHeader>Categories</CardHeader>
<CardBody>
<Row>
<Col className="sm-6">
<ul className="list-unstyled mb-0">
<li><a href="#!">Web Design</a></li>
<li><a href="#!">HTML</a></li>
<li><a href="#!">Freebies</a></li>
</ul>
</Col>
<Col className="sm-6">
<ul className="list-unstyled mb-0">
<li><a href="#!">JavaScript</a></li>
<li><a href="#!">CSS</a></li>
<li><a href="#!">Tutorials</a></li>
</ul>
</Col>
</Row>
</CardBody>
</Card>
<Card className="mb-4">
<CardHeader>Side Widget</CardHeader>
<CardBody>
You can put anything you want inside of these side widgets. They are easy to use, and feature the Bootstrap 5 card component!
</CardBody>
</Card>
</Col>
</Row>
</Container>
}
export {
BlogItem
}

View File

@ -0,0 +1,7 @@
import { BlogCatalog } from './Catalog'
import { BlogItem } from './Item'
export {
BlogCatalog,
BlogItem
}

View File

@ -1,25 +0,0 @@
import * as React from 'react'
const Home = () => {
return <div>
<h1>Hello, world!</h1>
<p>Welcome to your new single-page application, built with:</p>
<ul>
<li><a href='https://get.asp.net/'>ASP.NET Core</a> and <a href='https://msdn.microsoft.com/en-us/library/67ef8sbd.aspx'>C#</a> for cross-platform server-side code</li>
<li><a href='https://facebook.github.io/react/'>React</a> and <a href='https://redux.js.org/'>Redux</a> for client-side code</li>
<li><a href='http://getbootstrap.com/'>Bootstrap</a> for layout and styling</li>
</ul>
<p>To help you get started, we have also set up:</p>
<ul>
<li><strong>Client-side navigation</strong>. For example, click <em>Counter</em> then <em>Back</em> to return here.</li>
<li><strong>Development server integration</strong>. In development mode, the development server from <code>create-react-app</code> runs in the background automatically, so your client-side resources are dynamically built on demand and the page refreshes when you modify any file.</li>
<li><strong>Efficient production builds</strong>. In production mode, development-time features are disabled, and your <code>dotnet publish</code> configuration produces minified, efficiently bundled JavaScript files.</li>
</ul>
<p>The <code>ClientApp</code> subdirectory is a standard React application based on the <code>create-react-app</code> template. If you open a command prompt in that directory, you can run <code>npm</code> commands such as <code>npm test</code> or <code>npm install</code>.</p>
</div>
}
export {
Home
}

View File

@ -0,0 +1,233 @@
import * as React from 'react'
import { Link } from 'react-router-dom'
import { Card, CardBody, CardFooter, CardImg, Col, Container, Row } from 'reactstrap'
import { FeatherIcon } from '../../components/FeatherIcons'
import style from './scss/style.module.scss'
const Home = () => {
const titleSection = {
title: "Hello, world!",
text: `
<p>Welcome to your new single-page application, built with:</p>
<ul>
<li><a href='https://get.asp.net/'>ASP.NET Core</a> and <a href='https://msdn.microsoft.com/en-us/library/67ef8sbd.aspx'>C#</a> for cross-platform server-side code</li>
<li><a href='https://facebook.github.io/react/'>React</a> and <a href='https://redux.js.org/'>Redux</a> for client-side code</li>
<li><a href='https://getbootstrap.com/'>Bootstrap</a> + <a href='https://reactstrap.github.io/?path=/story/home-installation--page'>Reactstrap</a> + <a href="https://feathericons.com/">Feather icons</a> for layout and styling</li>
</ul>
`
}
const featuresSecton = {
title: "To help you get started, we have also set up:",
items: [
{
icon: "navigation",
title: "Client-side navigation",
text: "For example, click <em>Counter</em> then <em>Back</em> to return here."
},
{
icon: "server",
title: "Development server integration",
text: "In development mode, the development server from <code>create-react-app</code> runs in the background automatically, so your client-side resources are dynamically built on demand and the page refreshes when you modify any file."
},
{
icon: "terminal",
title: "Efficient production builds",
text: "In production mode, development-time features are disabled, and your <code>dotnet publish</code> configuration produces minified, efficiently bundled JavaScript files."
}
]
}
const testimonialsSection = {
text: "The <code>ClientApp</code> subdirectory is a standard React application based on the <code>create-react-app</code> template. If you open a command prompt in that directory, you can run <code>npm</code> commands such as <code>npm test</code> or <code>npm install</code>.",
image: {
src: "https://dummyimage.com/40x40/ced4da/6c757d",
alt: "..."
}
}
const fromOurBlogSection = {
title: "From our blog",
text: "Lorem ipsum, dolor sit amet consectetur adipisicing elit. Eaque fugit ratione dicta mollitia. Officiis ad.",
items: [
{
badge: "News",
image: {
src: "https://dummyimage.com/600x350/ced4da/6c757d",
alt: "..."
},
title: "Blog post title",
text: "Some quick example text to build on the card title and make up the bulk of the card's content.",
author: {
image: {
src: "https://dummyimage.com/40x40/ced4da/6c757d",
alt: "..."
},
name: "Kelly Rowan"
},
date: "March 12, 2022",
readTime: "6 min read"
},
{
badge: "News",
image: {
src: "https://dummyimage.com/600x350/ced4da/6c757d",
alt: "..."
},
title: "Blog post title",
text: "Some quick example text to build on the card title and make up the bulk of the card's content.",
author: {
image: {
src: "https://dummyimage.com/40x40/ced4da/6c757d",
alt: "..."
},
name: "Kelly Rowan"
},
date: "March 12, 2022",
readTime: "6 min read"
},
{
badge: "News",
image: {
src: "https://dummyimage.com/600x350/ced4da/6c757d",
alt: "..."
},
title: "Blog post title",
text: "Some quick example text to build on the card title and make up the bulk of the card's content.",
author: {
image: {
src: "https://dummyimage.com/40x40/ced4da/6c757d",
alt: "..."
},
name: "Kelly Rowan"
},
date: "March 12, 2022",
readTime: "6 min read"
}
]
}
const callToActionSection = {
}
return <>
<header className="py-5 bg-dark">
<Container fluid className="px-5">
<Row className="gx-5 align-items-center justify-content-center">
<Col className="lg-8 xl-7 xxl-6">
<div className="my-5 text-center text-xl-start">
<h1 className="display-5 fw-bolder text-white mb-2">{titleSection.title}</h1>
<span className="lead fw-normal text-white-50 mb-4" dangerouslySetInnerHTML={{ __html: titleSection.text }}>
</span>
<div className="d-grid gap-3 d-sm-flex justify-content-sm-center justify-content-xl-start">
<a className="btn btn-primary btn-lg px-4 me-sm-3" href="#features">Get Started</a>
<a className="btn btn-outline-light btn-lg px-4" href="#!">Learn More</a>
</div>
</div>
</Col>
<div className="col-xl-5 col-xxl-6 d-none d-xl-block text-center"><img className="img-fluid rounded-3 my-5" src="https://dummyimage.com/600x400/343a40/6c757d" alt="..." /></div>
</Row>
</Container>
</header>
<section className="py-5" id="features">
<Container fluid className="px-5 my-5">
<Row className="gx-5">
<Col className="lg-4 mb-5 mb-lg-0">
<h2 className="fw-bolder mb-0">{featuresSecton.title}</h2>
</Col>
<Col className="lg-8">
<Row className="gx-5 cols-1 cols-md-2">
{featuresSecton.items.map((item, index) => <Col key={index} className="mb-5 h-100">
<div className={`${style.feature} bg-primary bg-gradient text-white rounded-3 mb-3`}>
<FeatherIcon icon={item.icon} />
</div>
<h2 className="h5">{item.title}</h2>
<p className="mb-0" dangerouslySetInnerHTML={{ __html: item.text }}></p>
</Col>)}
</Row>
</Col>
</Row>
</Container>
</section>
<div className="py-5 bg-light">
<Container fluid className="px-5 my-5">
<Row className="gx-5 justify-content-center">
<Col className="lg-10 xl-7">
<div className="text-center">
<div className="fs-4 mb-4 fst-italic" dangerouslySetInnerHTML={{ __html: testimonialsSection.text }}></div>
<div className="d-flex align-items-center justify-content-center">
<img className="rounded-circle me-3" {...testimonialsSection.image} />
<div className="fw-bold">Tom Ato<span className="fw-bold text-primary mx-1">/</span>CEO, Pomodoro
</div>
</div>
</div>
</Col>
</Row>
</Container>
</div>
<section className="py-5">
<Container fluid className="px-5 my-5">
<Row className="gx-5 justify-content-center">
<Col className="lg-8 xl-6">
<div className="text-center">
<h2 className="fw-bolder">{fromOurBlogSection.title}</h2>
<p className="lead fw-normal text-muted mb-5" dangerouslySetInnerHTML={{ __html: fromOurBlogSection.text }}></p>
</div>
</Col>
</Row>
<Row className="gx-5">
{fromOurBlogSection.items.map((item, index) => <Col key={index} className="lg-4 mb-5">
<Card className="h-100 shadow border-0">
<CardImg top {...item.image} />
<CardBody className="p-4">
<div className="badge bg-primary bg-gradient rounded-pill mb-2">{item.badge}</div>
<Link className="text-decoration-none link-dark stretched-link" to="#!">
<h5 className="card-title mb-3">{item.title}</h5>
</Link>
<p className="card-text mb-0" dangerouslySetInnerHTML={{ __html: item.text }}></p>
</CardBody>
<CardFooter className="p-4 pt-0 bg-transparent border-top-0">
<div className="d-flex align-items-end justify-content-between">
<div className="d-flex align-items-center">
<img className="rounded-circle me-3" {...item.author.image} />
<div className="small">
<div className="fw-bold">{item.author.name}</div>
<div className="text-muted">{item.date} &middot; {item.readTime}</div>
</div>
</div>
</div>
</CardFooter>
</Card>
</Col>)}
</Row>
<aside className="bg-primary bg-gradient rounded-3 p-4 p-sm-5 mt-5">
<div className="d-flex align-items-center justify-content-between flex-column flex-xl-row text-center text-xl-start">
<div className="mb-4 mb-xl-0">
<div className="fs-3 fw-bold text-white">New products, delivered to you.</div>
<div className="text-white-50">Sign up for our newsletter for the latest updates.</div>
</div>
<div className="ms-xl-4">
<div className="input-group mb-2">
<input className="form-control" type="text" placeholder="Email address..." aria-label="Email address..." aria-describedby="button-newsletter" />
<button className="btn btn-outline-light" id="button-newsletter" type="button">Sign up</button>
</div>
<div className="small text-white-50">We care about privacy, and will never share your data.</div>
</div>
</div>
</aside>
</Container>
</section>
</>
}
export {
Home
}

View File

@ -0,0 +1,19 @@
// Custom SCSS for feature component with Bootstrap icon
.feature {
display: inline-flex;
align-items: center;
justify-content: center;
height: 3rem;
width: 3rem;
font-size: 1.5rem;
}
// Background image for featured blog post
.bg-featured-blog {
height: 100%;
width: 100%;
background-size: cover;
background-position: center;
background-repeat: no-repeat;
min-height: 15rem;
}

View File

@ -0,0 +1,85 @@
import * as React from 'react'
import { Link } from 'react-router-dom'
import { Card, CardBody, CardFooter, CardImg, Col, Container, Row } from 'reactstrap'
const ShopCatalog = () => {
const items = [
{
id: "1"
},
{
id: "2"
},
{
id: "3"
},
{
id: "4"
},
{
id: "5"
},
{
id: "6"
},
{
id: "7"
},
{
id: "8"
}
]
return <>
<header className="bg-dark py-5">
<Container fluid className="px-4 px-lg-5 my-5">
<div className="text-center text-white">
<h1 className="display-4 fw-bolder">Shop in style</h1>
<p className="lead fw-normal text-white-50 mb-0">With this shop hompeage template</p>
</div>
</Container>
</header>
<section className="py-5">
<Container fluid className="px-4 px-lg-5 mt-5">
<Row className="gx-4 gx-lg-5 row-cols-2 row-cols-md-3 row-cols-xl-4 justify-content-center">
{items.map((item, index) => <Col key={index} className="mb-5">
<Card className="h-100">
<div className="badge bg-dark text-white position-absolute" style={{top: "0.5rem", right: "0.5rem"}}>Sale</div>
<Link to={`/shop/item/${item.id}`}><CardImg top src="https://dummyimage.com/450x300/dee2e6/6c757d.jpg" alt="..." /></Link>
<CardBody>
<div className="text-center">
<h5 className="fw-bolder">Fancy Product</h5>
<div className="d-flex justify-content-center small text-warning mb-2">
<div className="bi-star-fill"></div>
<div className="bi-star-fill"></div>
<div className="bi-star-fill"></div>
<div className="bi-star-fill"></div>
<div className="bi-star-fill"></div>
</div>
<span className="text-muted text-decoration-line-through">$20.00</span>
$10.00
</div>
</CardBody>
<CardFooter className="p-4 pt-0 border-top-0 bg-transparent">
<div className="text-center"><a className="btn btn-outline-dark mt-auto" href="#">Add to cart</a></div>
</CardFooter>
</Card>
</Col>
)}
</Row>
</Container>
</section>
</>
}
export {
ShopCatalog
}

View File

@ -0,0 +1,37 @@
import React, { FC } from 'react'
import { Container } from 'reactstrap'
import { FeatherIcon } from '../../../components/FeatherIcons'
import { RelatedProducts } from '../RelatedProducts'
const ShopItem = () => {
return <>
<section className="py-5">
<Container fluid className="px-4 px-lg-5 my-5">
<div className="row gx-4 gx-lg-5 align-items-center">
<div className="col-md-6"><img className="card-img-top mb-5 mb-md-0" src="https://dummyimage.com/600x700/dee2e6/6c757d.jpg" alt="..." /></div>
<div className="col-md-6">
<div className="small mb-1">SKU: BST-498</div>
<h1 className="display-5 fw-bolder">Shop item template</h1>
<div className="fs-5 mb-5">
<span className="text-decoration-line-through">$45.00</span>
<span>$40.00</span>
</div>
<p className="lead">Lorem ipsum dolor sit amet consectetur adipisicing elit. Praesentium at dolorem quidem modi. Nam sequi consequatur obcaecati excepturi alias magni, accusamus eius blanditiis delectus ipsam minima ea iste laborum vero?</p>
<div className="d-flex">
<input className="form-control text-center me-3" id="inputQuantity" type="num" value="1" style={{maxWidth: "3rem"}} />
<button className="btn btn-outline-dark flex-shrink-0" type="button">
<FeatherIcon icon='shopping-cart' className="me-1"/> Add to cart</button>
</div>
</div>
</div>
</Container>
</section>
<RelatedProducts />
</>
}
export {
ShopItem
}

View File

@ -0,0 +1,61 @@
import React from "react"
import { Card, CardBody, CardFooter, CardImg, Col, Container, Row } from "reactstrap"
const RelatedProducts = () => {
const items = [
{
},
{
},
{
},
{
}
]
return <section className="py-5 bg-light">
<Container fluid className="px-4 px-lg-5 my-5">
<h2 className="fw-bolder mb-4">Related products</h2>
<Row className="gx-4 gx-lg-5 row-cols-2 row-cols-md-3 row-cols-xl-4 justify-content-center">
{items.map((item, index) => <Col key={index} className="mb-5">
<Card className="h-100">
<div className="badge bg-dark text-white position-absolute" style={{top: "0.5rem", right: "0.5rem"}}>Sale</div>
<CardImg className="card-img-top" src="https://dummyimage.com/450x300/dee2e6/6c757d.jpg" alt="..." />
<CardBody className="p-4">
<div className="text-center">
<h5 className="fw-bolder">Special Item</h5>
<div className="d-flex justify-content-center small text-warning mb-2">
<div className="bi-star-fill"></div>
<div className="bi-star-fill"></div>
<div className="bi-star-fill"></div>
<div className="bi-star-fill"></div>
<div className="bi-star-fill"></div>
</div>
<span className="text-muted text-decoration-line-through">$20.00</span>
$18.00
</div>
</CardBody>
<CardFooter className="p-4 pt-0 border-top-0 bg-transparent">
<div className="text-center"><a className="btn btn-outline-dark mt-auto" href="#">Add to cart</a></div>
</CardFooter>
</Card>
</Col>)}
</Row>
</Container>
</section>
}
export {
RelatedProducts
}

View File

@ -0,0 +1,7 @@
import { ShopCatalog } from './Catalog'
import { ShopItem } from './Item'
export {
ShopCatalog,
ShopItem
}

View File

@ -8,6 +8,8 @@ import { AdminHome } from './AdminHome'
import { Signin } from './Signin'
import { Signup } from './Signup'
import { ShopCatalog, ShopItem } from './Shop'
import { BlogCatalog, BlogItem } from './Blog'
interface IPages {
[key: string]: React.FC<any>;
@ -15,6 +17,13 @@ interface IPages {
const pages: IPages = {
Home,
ShopCatalog,
ShopItem,
BlogCatalog,
BlogItem,
Counter,
FetchData,

View File

@ -40,6 +40,51 @@ export const actionCreators = {
const routes : IRoute[] = [
{ path: "/", component: "Home" },
{ path: "/home", component: "Home" },
{ path: "/shop",
childRoutes: [
{
path: "",
component: "ShopCatalog"
},
{
path: ":page",
childRoutes: [
{
path: ":slug",
component: "ShopItem"
}
]
}
]
},
{
path: "/blog",
childRoutes: [
{
path: "",
component: "BlogCatalog"
},
{
path: ":page",
component: "BlogCatalog"
},
{
path: ":page",
childRoutes: [
{
path: ":slug",
component: "BlogItem"
}
]
}
]
}
]
const adminRoutes : IRoute [] = [
{ path: "/admin", component: "AdminHome" },
{ path: "/counter", component: "Counter" },
{ path: "/fetch-data", component: "FetchData",
childRoutes: [
@ -48,11 +93,7 @@ export const actionCreators = {
component: "FetchData"
}
]
},
]
const adminRoutes : IRoute [] = [
{ path: "/admin", component: "AdminHome" },
}
]
const serviceRoutes : IRoute[] = [
@ -100,7 +141,16 @@ export const actionCreators = {
title: "Home",
target: "/"
},
{
icon: "",
title: "Shop",
target: "/shop",
},
{
icon: "",
title: "Blog",
target: "/blog"
},
{
icon: "",
title: "Signin",