You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Svelte如何通过Store函数传回调获取模态框确认结果

Svelte全局确认模态框回调实现方案

这个需求完全可以实现,不需要调整模态框全局挂载的现有架构,只需要给store补充回调存储和触发逻辑即可,具体实现步骤如下:

1. 改造modal状态仓库

首先给模态框状态新增回调函数字段,同时补充确认/取消的触发方法,修改modal.ts代码如下:

//=== modal.ts ===
import { writable } from 'svelte/store'

// 扩展模态框状态类型,新增回调字段
export const modal = writable({
  title: '',
  message: '',
  button: '',
  mode: '',
  show: false,
  callback: null as ((confirmed: boolean) => void) | null // 存储用户操作后的回调
})

// 确认操作触发方法
export function confirmModal() {
  modal.update(state => {
    // 存在回调则传入true,代表用户确认操作
    if (state.callback) state.callback(true)
    // 关闭模态框,清空回调避免内存泄漏
    return {
      ...state,
      show: false,
      callback: null
    }
  })
}

// 取消/关闭模态框触发方法
export function cancelModal() {
  modal.update(state => {
    // 存在回调则传入false,代表用户取消操作
    if (state.callback) state.callback(false)
    // 关闭模态框,清空回调
    return {
      ...state,
      show: false,
      callback: null
    }
  })
}

// 唤起删除确认模态框方法,新增第四个回调参数
export function confirmTrash(
  modalTitle: string, 
  modalMessage: string, 
  buttonText: string,
  onAction: (confirmed: boolean) => void
){
  modal.set({
    title: modalTitle,
    message: modalMessage,
    button: buttonText,
    mode: 'trash',
    show: true,
    callback: onAction
  })
}

2. 调整全局挂载的Modal.svelte组件

给模态框的操作按钮绑定刚才写的确认/取消方法,不要直接修改modal的show状态,代码修改如下:

<!-- === Modal.svelte === -->
<script lang="ts">
import { modal, confirmModal, cancelModal } from '$lib/stores/modal'
// 其他自定义模态框逻辑保持不变
</script>

{#if $modal.show}
  <h2>{$modal.title}</h2>
  <p>{$modal.message}</p>

  <button on:click={confirmModal}>{$modal.button}</button>
  <!-- 建议补充取消按钮,绑定取消逻辑 -->
  <button on:click={cancelModal}>取消</button>
{/if}

注意:所有模态框关闭路径都要绑定对应方法:如果你的模态框支持点击蒙层关闭、按ESC键关闭,直接把这些关闭事件绑定到cancelModal方法上,保证用户任何操作都能正确触发回调,不会出现回调悬挂的问题。

3. 业务组件调用

直接在调用confirmTrash时传入回调函数即可拿到用户操作结果:

<!-- === Component.svelte === -->
<script lang="ts">
import { confirmTrash } from '$lib/stores/modal'

const handleTrash = () => {
  confirmTrash(
    '删除确认', 
    '该操作不可恢复,确定要删除该内容吗?', 
    '确认删除', 
    (confirmed) => {
      if (confirmed) {
        // 用户点击了删除按钮,在这里执行实际删除逻辑
        console.log('执行删除操作')
      } else {
        // 用户取消了操作
        console.log('用户取消删除')
      }
    }
  )
}
</script>

<a href="#trash" on:click|preventDefault={handleTrash}>删除</a>

注意给点击事件加|preventDefault修饰符,避免a标签的默认锚点跳转行为影响页面。

如果你习惯用async/await写法,也可以把confirmTrash改成返回Promise的形式,调用时直接用const confirmed = await confirmTrash(...)即可,逻辑和回调写法完全一致,只是把回调的触发放到Promise的resolve里就行。

内容的提问来源于stack exchange,提问作者Clifton Labrum

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.30 06:27:18