#javascript #svelte
Вопрос:
Я работаю над небольшим приложением для работы со стройностью. Я перечисляю 10 задач из jsonplaceholder.
У меня есть это в приложении.стройная:
<script>
import { onMount } from "svelte";
import Header from './Header.svelte';
import ToDoList from './ToDoList.svelte';
import Footer from './Footer.svelte';
const apiURL = "https://jsonplaceholder.typicode.com/todos";
const limit = 10;
let todos = [];
export let unsolvedTodos = [];
onMount(() => {
getTodos();
});
const getTodos = () => {
fetch(`${apiURL}?amp;_limit=${limit}`)
.then(res => res.json())
.then((data) => todos = data)
.then(getUnsolvedTodos);
}
const getUnsolvedTodos = () => {
unsolvedTodos = todos.filter(todo => {
return todo.completed === false;
})
}
const deleteTodo = (todo) => {
let itemIdx = todos.findIndex(x => x == todo);
todos.splice(itemIdx, 1);
todos = todos;
}
</script>
<div class="app-wrapper">
<div id="toDoApp">
<Header />
<ToDoList todos={todos} />
<Footer />
</div>
</div>
В приложении ToDoList.app:
<script>
import TodoItem from './TodoItem.svelte';
export let todos;
let deleteTodo;
</script>
{#if todos.length > 0}
<ul class="todo-list">
{#each todos as todo, index}
<TodoItem {todo} on:deleteTodo = {deleteTodo(todo)} />
{/each}
</ul>
{/if}
В TodoItem.стройная:
<script>
import {createEventDispatcher} from 'svelte';
import { fade, fly } from 'svelte/transition';
import { flip } from 'svelte/animate';
export let todo;
const dispatch = createEventDispatcher();
const Delete = () => dispatch("deleteTodo", todo);
</script>
<li transition:fly="{{x:-100, duration:200}}">
<input type="checkbox" checked="{todo.completed}" />
<span class="title {todo.completed ? 'done' : ''}">{todo.title}</span>
<button on:click="{Delete}"><i class="fa fa-trash" aria-hidden="true"></i></button>
</li>
Должно быть, я что-то упускаю, потому что я получаю ошибку ctx[1] is not a function
, как видно из этого повторения.
Что я делаю не так?
Ответ №1:
В ToDoList.svelte
вы звоните deleteTodo(todo)
, но deleteTodo
не определено. Стройный действительно должен выдать здесь лучшее сообщение об ошибке…
Редактировать:
Кроме того, если вы назначаете обработчик событий, вы хотите передать ссылку на функцию типа on:deleteTodo = {() => deleteTodo(todo)}
или on:deleteTodo = {deleteTodo}
, а не вызывать функцию напрямую.
Комментарии:
1. У меня
let deleteTodo
в Тодолисте.стройная, наверху. У меня тоже есть<TodoItem {todo} on:deleteTodo = {deleteTodo(todo)} />
. См. РЕПЛ .2. У вас есть
let deleteTodo
, но это переменная, а не определение функции, поэтому ничего не происходит, когда вы вызываете ее как функцию. Кроме того, как сказал Леандер, вы неправильно называете это, если хотите передать аргумент функции с помощью обработчика событий, он не будет работать так, как{function(arg)}
вам нужно{()=> function(arg)}
. Этот ответ верен.3. Может быть, вы хотите передать
deleteTodo
функцию, которая объявлена вApp.svelte
toToDoList
. solet deleteTodo;
, должна статьexport let deleteTodo;
и<ToDoList todos={todos} />
может стать<ToDoList todos={todos} deleteTodo={deleteTodo} />
или сокращением<ToDoList {todos} {deleteTodo} />
. Это не лучший образец для подражания, но он работает