Home > Software design >  Why is my check complete button is not working
Why is my check complete button is not working

Time:01-03

I wanna make the function that whenever i click on the complete button, the complete state will turn true and there will be a line through in my todo. However, my function is not working and i don't know why? can anyone help me? Thank you so much!

import React, { useState } from "react";

function App() {
  const [value, setValue] = useState("");
  const [todos, setTodos] = useState([]);

  // you can use the submit itself, no need for an extra addTodo function
  const handleSubmit = (e) => {
    e.preventDefault();
    setTodos([...todos, { value, id: Date.now() }]);
    setValue("");
  };

  const handleDelete = (id) => {
    setTodos((todos) => todos.filter((todo) => todo.id !== id));
  };

  return (
    <div>
      <form onSubmit={handleSubmit}>
        <input
          onChange={(e) => setValue(e.target.value)}
          type="text"
          placeholder="add todo"
        />
        <button type="submit">Add</button>
      </form>
      {todos.map((todo) => (
        <div key={todo.id}>
          <h3 complete ? "line-through" : "">{todo.value}</h3>

          <button onClick={() => handleDelete(todo.id)}>X</button>
          <button onClick={()=>setComplete(!complete)}>complete</button>
        </div>
      ))}
    </div>
  );
}
export default App;

Sandbox link: https://codesandbox.io/s/stoic-mendeleev-6fetl?file=/src/App.js

CodePudding user response:

complete state missing

h3 add style={{ textDecoration: complete ? "line-through" : "" }}

import React, { useState } from "react";

function App() {
  const [value, setValue] = useState("");
  const [todos, setTodos] = useState([]);
  const [complete, setComplete] = useState(false);

  // you can use the submit itself, no need for an extra addTodo function
  const handleSubmit = (e) => {
    e.preventDefault();
    setTodos([...todos, { value, id: Date.now() }]);
    setValue("");
  };

  const handleDelete = (id) => {
    setTodos((todos) => todos.filter((todo) => todo.id !== id));
  };

  return (
    <div>
      <form onSubmit={handleSubmit}>
        <input
          onChange={(e) => setValue(e.target.value)}
          type="text"
          placeholder="add todo"
          value={value}
        />
        <button type="submit">Add</button>
      </form>
      {todos.map((todo) => (
        <div key={todo.id}>
          <h3 style={{ textDecoration: complete ? "line-through" : "" }}>
            {todo.value}
          </h3>

          <button onClick={() => handleDelete(todo.id)}>X</button>
          <button onClick={() => setComplete((perv) => !perv)}>complete</button>
        </div>
      ))}
    </div>
  );
}
export default App;

CodePudding user response:

Try this

import React, { useState } from "react";

function App() {
  const [value, setValue] = useState("");
  const [todos, setTodos] = useState([]);
  const [complete, setComplete] = useState({});

  // you can use the submit itself, no need for an extra addTodo function
  const handleSubmit = (e) => {
    e.preventDefault();
    const id = Date.now();
    setTodos([...todos, { value, id }]);
    setComplete({ ...complete, [id]: false });
    setValue("");
  };

  const handleDelete = (id) => {
    setTodos((todos) => todos.filter((todo) => todo.id !== id));
  };
  console.log(complete);
  return (
    <div>
      <form onSubmit={handleSubmit}>
        <input
          onChange={(e) => setValue(e.target.value)}
          type="text"
          placeholder="add todo"
          value={value}
        />
        <button type="submit">Add</button>
      </form>
      {todos.map((todo) => (
        <div key={todo.id}>
          <h3 className={complete[todo.id] ? "line-through" : ""}>
            {todo.value}
          </h3>

          <button onClick={() => handleDelete(todo.id)}>X</button>
          <button
            onClick={() =>
              setComplete({ ...complete, [todo.id]: !complete[todo.id] })
            }
          >
            complete
          </button>
        </div>
      ))}
    </div>
  );
}
export default App;

*Note you will need to specify styling for your line-through class to see the strike through

CodePudding user response:

I have updated the codesandbox. you can have look on the codesandbox.

https://codesandbox.io/s/compassionate-frost-8255y

CodePudding user response:

Try below code. You need to create setComplete menthod. import React, { useState } from "react";

function App() {
  const [value, setValue] = useState("");
  const [todos, setTodos] = useState([]);

  // you can use the submit itself, no need for an extra addTodo function
  const handleSubmit = (e) => {
    e.preventDefault();
    setTodos([...todos, { value, id: Date.now(), complete: false }]);
    setValue("");
  };

  const handleDelete = (id) => {
    setTodos((todos) => todos.filter((todo) => todo.id !== id));
  };

  const handleComplete = (id) => {
    let compTodo = todos.filter((todo) => todo.id === id);
    compTodo[0].complete = true;
    let allTodo = todos.filter((todo) => todo.id !== id);    
    setTodos([...allTodo, compTodo[0]]);
  };

  return (
    <div>
      <form onSubmit={handleSubmit}>
        <input
          onChange={(e) => setValue(e.target.value)}
          type="text"
          placeholder="add todo"
          value={value}
        />
        <button type="submit">Add</button>
      </form>
      {todos.map((todo) => {
        return (
          <div key={todo.id}>
            <h3
              style={{
                textDecoration: todo.complete ? "line-through" : "none"
              }}
            >
              {todo.value}
            </h3>

            <button onClick={() => handleDelete(todo.id)}>X</button>
            <button onClick={() => handleComplete(todo.id)}>complete</button>
          </div>
        );
      })}
    </div>
  );
}
export default App;
  • Related