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

Newbranch #86

Open
wants to merge 7 commits into
base: main
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
40 changes: 32 additions & 8 deletions src/App.js
Original file line number Diff line number Diff line change
@@ -1,16 +1,40 @@
import React from 'react';
import 'bootstrap/dist/css/bootstrap.min.css'; 
import 'bootstrap/dist/css/bootstrap.min.css';


import { AppProvider } from './context/AppContext';
import CartValue from './components/CartValue';
import ExpenseList from './components/ExpenseList';
import ItemSelected from './components/ItemSelected';
import Location from './components/Location';

function App() {
return (
<div className="App">
</div>
);
}

const App = () => {
return (
<AppProvider>
<div className='container'>
<h1 className='mt-3'>Shopping App</h1>
<div className='row mt-3'>
<div className='col-sm'>
<CartValue />
</div>
<div className='col-sm'>
<Location />
</div>
</div>
<h3 className='mt-3'>Shopping Cart</h3>
<div className='row '>
<div className='col-sm'>
<ExpenseList />
</div>
</div>
<h3 className='mt-3'>Add Items</h3>
<div className='row mt-3'>
<div className='col-sm'>
<ItemSelected/>
</div>
</div>
</div>
</AppProvider>
);
};
export default App;
10 changes: 10 additions & 0 deletions src/components/CartValue.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,16 @@ import React, { useContext } from 'react';
import { AppContext } from '../context/AppContext';

const CartValue = () => {
const { expenses, Location } = useContext(AppContext);
const totalExpenses = expenses.reduce((total, item) => {
return (total += (item.unitprice * item.quantity));
}, 0);

return (
<div className='alert alert-primary'>
<span>Cart Value: {Location}{totalExpenses}</span>
</div>
);
};

export default CartValue;
23 changes: 23 additions & 0 deletions src/components/ExpenseItem.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,29 @@ import { AppContext } from '../context/AppContext';
import { FaTimesCircle } from 'react-icons/fa';

const ExpenseItem = (props) => {
const { dispatch, Location} = useContext(AppContext);

const handleDeleteItem = () => {
const item = {
name: props.name,
};

dispatch({
type: 'DELETE_ITEM',
payload: item,
});
};


return (
<tr>
<td>{props.name}</td>
<td>{props.quantity}</td>
<td>{Location}{parseInt(props.unitprice)}</td>
<td>{Location}{parseInt(props.quantity)*parseInt(props.unitprice)}</td>
<td><FaTimesCircle size='2.2em' color="red" onClick={handleDeleteItem}></FaTimesCircle></td>
</tr>
);
};

export default ExpenseItem;
21 changes: 21 additions & 0 deletions src/components/ExpenseList.js
Original file line number Diff line number Diff line change
@@ -1,7 +1,28 @@
import React, { useContext } from 'react';
import ExpenseItem from './ExpenseItem';
import { AppContext } from '../context/AppContext';

const ExpenseList = () => {
const { expenses } = useContext(AppContext);

return (
<table className='table'>
<thead className="thead-light">
<tr>
<th scope="col">Items</th>
<th scope="col">Quantity</th>
<th scope="col">Unit Price</th>
<th scope="col">Items Price</th>
<th scope="col">Remove</th>
</tr>
</thead>
<tbody>
{expenses.map((expense) => (
<ExpenseItem id={expense.id} key={expense.id} name={expense.name} quantity={expense.quantity} unitprice={expense.unitprice} />
))}
</tbody>
</table>
);
};

export default ExpenseList;
70 changes: 70 additions & 0 deletions src/components/ItemSelected.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,76 @@ import React, { useContext, useState } from 'react';
import { AppContext } from '../context/AppContext';

const ItemSelected = (props) => {
const { dispatch} = useContext(AppContext);

const [name, setName] = useState('');
const [quantity, setQuantity] = useState('');
const [action, setAction] = useState('');


const submitEvent = () => {

const item = {
name: name,
quantity: parseInt(quantity),
};

if(action === "Reduce") {
dispatch({
type: 'RED_QUANTITY',
payload: item,
});
} else {
dispatch({
type: 'ADD_QUANTITY',
payload: item,
});
}
};

return (
<div>
<div className='row'>

<div className="input-group mb-3" style={{ marginLeft: '2rem' }}>
<div className="input-group-prepend">
<label className="input-group-text" htmlFor="inputGroupSelect01">Items</label>
</div>
<select className="custom-select" id="inputGroupSelect01" onChange={(event) => setName(event.target.value)}>
<option defaultValue>Choose...</option>
<option value="Shirt" name="Shirt"> Shirt</option>
<option value="Dress" name="Dress">Dress</option>
<option value="Jeans" name="Jeans">Jeans</option>
<option value="Dinner set" name="Dinner set">Dinner set</option>
<option value="Bags" name="Bags">Bags</option>
</select>

<div className="input-group-prepend" style={{ marginLeft: '2rem' }}>
<label className="input-group-text" htmlFor="inputGroupSelect02">Quantity</label>
</div>
<select className="custom-select" id="inputGroupSelect02" onChange={(event) => setAction(event.target.value)}>
<option defaultValue value="Add" name="Add">Add</option>
<option value="Reduce" name="Reduce">Reduce</option>
</select>
<span className="eco" style={{ marginLeft: '2rem', marginRight: '8px'}}></span>

<input
required='required'
type='number'
id='cost'
value={quantity}
style={{size: 10}}
onChange={(event) => setQuantity(event.target.value)}>
</input>

<button className="btn btn-primary" onClick={submitEvent} style={{ marginLeft: '2rem' }}>
Save
</button>
</div>
</div>

</div>
);
};

export default ItemSelected;
23 changes: 22 additions & 1 deletion src/components/Location.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,27 @@ import React, { useContext } from 'react';
import { AppContext } from '../context/AppContext';

const Location = () => {
const {dispatch } = useContext(AppContext);

const changeLocation = (val)=>{
dispatch({
type: 'CHG_LOCATION',
payload: val,
})
}


return (
<div className='alert alert-secondary'> Location {
<select name="Location" id="Location" onChange={event=>changeLocation(event.target.value)}>
<option value="£">Uk(£)</option>
<option value="₹">India(₹)</option>
<option value="€">Europe(€)</option>
<option value="CAD">Canada(CAD)</option>
</select>
}
</div>
);
};

export default Location;
export default Location;
101 changes: 100 additions & 1 deletion src/context/AppContext.js
Original file line number Diff line number Diff line change
@@ -1 +1,100 @@
import React, { createContext, useReducer } from 'react';
import React, { createContext, useReducer } from 'react';

// 5. The reducer - this is used to update the state, based on the action
export const AppReducer = (state, action) => {
let new_expenses = [];
switch (action.type) {
case 'ADD_QUANTITY':
let updatedqty = false;
state.expenses.map((expense)=>{
if(expense.name === action.payload.name) {
expense.quantity = expense.quantity + action.payload.quantity;
updatedqty = true;
}
new_expenses.push(expense);
return true;
})
state.expenses = new_expenses;
action.type = "DONE";
return {
...state,
};

case 'RED_QUANTITY':
state.expenses.map((expense)=>{
if(expense.name === action.payload.name) {
expense.quantity = expense.quantity - action.payload.quantity;
}
expense.quantity = expense.quantity < 0 ? 0: expense.quantity;
new_expenses.push(expense);
return true;
})
state.expenses = new_expenses;
action.type = "DONE";
return {
...state,
};
case 'DELETE_ITEM':
state.expenses.map((expense)=>{
if(expense.name === action.payload.name) {
expense.quantity = 0;
}
new_expenses.push(expense);
return true;
})
state.expenses = new_expenses;
action.type = "DONE";
return {
...state,
};
case 'CHG_LOCATION':
action.type = "DONE";
state.Location = action.payload;
return {
...state
}

default:
return state;
}
};

// 1. Sets the initial state when the app loads
const initialState = {
expenses: [
{ id: "Shirt", name: 'Shirt', quantity: 0, unitprice: 500 },
{ id: "Jeans", name: 'Jeans', quantity: 0, unitprice: 300 },
{ id: "Dress", name: 'Dress', quantity: 0, unitprice: 400 },
{ id: "Dinner set", name: 'Dinner set', quantity: 0, unitprice: 600 },
{ id: "Bags", name: 'Bags', quantity: 0, unitprice: 200 },
],
Location: '£'
};

// 2. Creates the context this is the thing our components import and use to get the state
export const AppContext = createContext();

// 3. Provider component - wraps the components we want to give access to the state
// Accepts the children, which are the nested(wrapped) components
export const AppProvider = (props) => {
// 4. Sets up the app state. takes a reducer, and an initial state
const [state, dispatch] = useReducer(AppReducer, initialState);

const totalExpenses = state.expenses.reduce((total, item) => {
return (total = total + (item.unitprice*item.quantity));
}, 0);
state.CartValue = totalExpenses;

return (
<AppContext.Provider
value={{
expenses: state.expenses,
CartValue: state.CartValue,
dispatch,
Location: state.Location
}}
>
{props.children}
</AppContext.Provider>
);
};