need to implement Undo function using react hooks - reactjs

need to implement undo function in a state array data. i remove the data by id using filter method but i need to restore the data after click on undo button. how to implement in React Hooks?
const [dataSource, setDatasource] = useState([
{
id: 1,
name: 'john',
gender: 'm'
},
{
id: 2,
name: 'mary',
gender: 'f'
},
{
id: 3,
name: 'loki',
gender: 'M'
},
{
id: 4,
name: 'Thor',
gender: 'M'
},
]);

You will have to keep track of all the actions that the user performs, and calculate the end result from that. When a user clicks "undo", you can just remove the latest action.
const actions = [
{
operation: "create",
name: "Some name",
index: 1
},
{
operation: "delete",
index: 1
}
];
const state = (() => {
let appliedState = [];
for (const action of actions) {
if (action.operation === "create") {
appliedState .push(action.name);
} else if (action.operation === "delete") {
appliedState = appliedState .filter(currentState => currentState.index !== action.index);
}
}
return appliedState ;
})();
You can see a working react example here.

Related

Select or deselect item in array and increase or decrease its value react native

Basically i want to select an emoji from an array which contains objects (id, name, count) and if i select an item on the array i want to increase its value and if i deselct it i want to decrease its value
for now i've done this which basically increase the value of an item in the array, please help me, thanks.
this is the array
const [emojisArr, setEmojisArr] = React.useState([
{
name: 'like',
emoji: '👍',
count: 11,
},
{
name: 'heart',
emoji: '❤️',
count: 21,
},
{
name: 'joy',
emoji: '😂',
count: 31,
},
{
name: 'fire',
emoji: '🔥',
count: 34,
},
{
name: 'star',
emoji: '💯',
count: 5,
},
]);
and this is the function when i click on the button
const likePost = item => {
const index = emojisArr.findIndex(emoji => emoji.name === item);
emojisArr[index].count += 1;
setEmojisArr(old => [...old]);
}
Set this code see below. you can pass action (selected/deselected) as string. so, it can increment/decrement count on the behalf of action.
const post = (item, action) => {
const newState = emojisArr.map((emoji) => {
if (emoji.name === item) {
return {
...emoji,
count: action === "selected" ? emoji.count + 1 : emoji.count - 1
};
}
return emoji;
});
setEmojisArr(newState);
};

update State inside Map Function immediately React hooks

I tried with the below code but it is executing on the second attempt, I want to execute Alert on the Dropdown function, I am not rendering returnCount just using it to display an alert,
anyone knows the answer plz answer this, don't send any link, nothing is working out instead please write the answer
const [arrayList, setArrayList] = useState([
{ Id: 1, Name:'A', ItemDeliveryStatus:4 },
{ Id: 2, Name:'B', ItemDeliveryStatus:4 },
{ Id: 3, Name:'C', ItemDeliveryStatus:4 },
{ Id: 4, Name:'D', ItemDeliveryStatus:4 },
])
const [returnCount ,setReturnCount ]=useState(0)
//function on the picker, want to update returnCount immediately so that I can use it for below alert
function displayalertBox(){
arrayList.map(items =>
{
if(items.ItemDeliveryStatus=='4')
{
setReturnCount(prev=> prev+1)
}
})
if(returnCount==4)
{
alert('alert as returncount is equal to 4')
}
}
You need to do the desired functionality inside of an useEffect when using react hooks.
const [arrayList, setArrayList] = useState([{
Id: 1,
Name: 'A',
ItemDeliveryStatus: 4
},
{
Id: 2,
Name: 'B',
ItemDeliveryStatus: 4
},
{
Id: 3,
Name: 'C',
ItemDeliveryStatus: 4
},
{
Id: 4,
Name: 'D',
ItemDeliveryStatus: 4
},
])
const [returnCount, setReturnCount] = useState(0)
function displayalertBox() {
arrayList.map(items => {
if (items.ItemDeliveryStatus == '4') {
setReturnCount(prev => prev + 1)
}
})
}
// You cantry this too if needed.
function displayalertBox1() {
arrayList.map(items => {
if (items.ItemDeliveryStatus == '4') {
let count
setReturnCount(prev => {
count = prev + 1;
//since state update is guaranteed, you can try this too.
if (count === 4) {
alert('alert as returncount is equal to 4')
}
return count
})
}
})
}
useEffect(() => {
if (returnCount == 4) {
alert('alert as returncount is equal to 4')
}
}, [returnCount]);

Got a parsing error while assign a value on my state

Hi friends,
I'm getting a little trouble putting that to work.
This method intend to put check if there's a product in the cart, if true, sum the same product.
onAddProductToCart = (productId) => {
const productInCart = this.state.productsInCart.find(
(product) => productId === product.id
);
if (productInCart) {
const newProductsInCart = this.state.productsInCart.map(product => {
if(productId === product.id) {
return {
...product,
quantity = product.quantity + 1
}
}
return product
})
this.setState({productsInCart: newProductsInCart})
}
};
I'm getting this error point to my assignment "=" bellow
Parsing error unexpected token:
quantity = product.quantity + 1
This method is inside the App class component , with has some mocked data.
class App extends Component {
state = {
minFilter: "100",
maxFilter: "2000",
nameFilter: "Produto",
productsInCart: [
{
id: 3,
name: "Produto 3",
price: 300.77,
photo: "https://picsum.photos/200/200?a=3",
quantity: 1,
},
{
id: 4,
name: "Produto 4",
price: 400,
photo: "https://picsum.photos/200/200?a=4",
quantity: 2,
},
],
};
You have to use colon : when set a object property
return {
...product,
quantity:product.quantity + 1
}
Using a colon would do the trick
quantity: product.quantity + 1

Update array value inside observable typescript

How do you write a function that takes an Observable<T[]> and updates the value inside the observable.
I tried with the below approach but i felt i am not doing the update on proper way.
I want to update the values of the observable with the row object.
import { of } from 'rxjs';
import { map } from 'rxjs/operators';
let gridData = [
{
id: '1',
firstName: 'Sophie',
lastName: 'Beckham',
gender: 'F',
jobTitle: 'Senior Associate-L1',
jobArea: 'London',
monthlyWage: '$100000',
},
{
id: '2',
firstName: 'Sophie',
lastName: 'Beckham',
gender: 'F',
jobTitle: 'Senior Associate-L2',
jobArea: 'London',
monthlyWage: '$100000',
},
{
id: '3',
firstName: 'Chloe',
lastName: 'Bryson',
gender: 'F',
jobTitle: 'Senior Associate-L3',
jobArea: 'London',
monthlyWage: '$100000',
},
];
let gridData$ = of(gridData);
let row = {
id: '2',
firstName: 'TAN',
lastName: 'Ara',
gender: 'M',
jobTitle: 'Senior Associate',
jobArea: 'ATL',
monthlyWage: '$130000',
}
gridData$.subscribe((val: any) => {
val.forEach((list: any) => {
if(list['id'] === row['id']){
for (const property in row) {
list[property] = row[property];
}
}
})
})
gridData$.subscribe((v) => console.log(v));
In my approach i have used for loop and based on the object id updating the value. If there is a better approach, kindly share your approach.
StackBlitz : https://stackblitz.com/edit/rxjs-gdgkyk?devtoolsheight=60
Observables are stateless and its recommended that emitted values are immutable.
But you can return a new observable that returns what you want by using the map operator (on all values).
Note that I've used from instead of of operator.
import { from } from 'rxjs';
import { map } from 'rxjs/operators';
...
let gridData$ = from(gridData);
...
gridData$ = gridData$.pipe(
map((val: any) => {
if(val['id'] === row['id']){
for (const property in row) {
val[property] = row[property];
}
}
return val;
})
);
gridData$.subscribe((v) => console.log(v));
Now each time you call gridData$ it will execute the new observable.
https://stackblitz.com/edit/rxjs-6mh6iu

How to update state of one object in array React Native using hooks

I'd like to update a state of one object in array, not updating the state of whole array.
const [users, setUsers] = useState;
const data = [
{
id: 1,
name: "John",
activeAccount: 1
},
{
id: 2,
name: "Mary",
activeAccount: 1
},
{
id: 3,
name: "Max",
activeAccount: 1
}
]
For example, John deactivate his account and state of activeAccount should be updated to 0.
So only one object should be updated (he has no data from other users and cannot update all array) - just example, why i use here user.id
const index = users.findIndex(obj => obj.id === user.id); // find index of object
users[index].activeAccount = 0
setUsers(users) // Nothing updated
I also tried to use Immutability Helper
import update from 'immutability-helper';
const index = users.findIndex(obj => obj.id === user.id); // find index of object
setUsers({
users: update(...users, {index: {activeAccount: {$set: 0 }}})
})
Could anyone help? Is there a solution?
Solution:
const index = users.findIndex(obj => obj.id === user.id);
setUsers([...users, users[index].activateAccount = 0])
There might be a problem in calling
setUsers({
users: update(...users, {index: {activeAccount: {$set: 0 }}})
})
In case you are initialising your state with:
const data = [
{
id: 1,
name: "John",
activeAccount: 1
},
{
id: 2,
name: "Mary",
activeAccount: 1
},
{
id: 3,
name: "Max",
activeAccount: 1
}
]
const [users, setUsers] = useState(data);
then you need to call setUsers without object:
setUsers(
update(...users, {index: {activeAccount: {$set: 0 }}})
)

Resources