MST

星途 面试题库

面试题:Svelte 项目模块化中的组件通信

在 Svelte 项目中,如何实现父子组件之间以及非父子组件之间的通信?请分别阐述并给出简单代码示例。
47.3万 热度难度
前端开发Svelte

知识考点

AI 面试

面试题答案

一键面试

父子组件通信

  1. 父组件向子组件传递数据
    • 在 Svelte 中,父组件可以通过属性(props)向子组件传递数据。
    • 示例:
      • 父组件 Parent.svelte
<script>
    let message = 'Hello from parent';
</script>

<Child {message}/>

<script>
    import Child from './Child.svelte';
</script>
 - **子组件 `Child.svelte`**
<script>
    export let message;
</script>

<p>{message}</p>
  1. 子组件向父组件传递数据
    • 子组件通过 createEventDispatcher 来创建一个事件分发器,然后通过触发自定义事件向父组件传递数据。
    • 示例:
      • 父组件 Parent.svelte
<script>
    let receivedMessage;
    const handleChildMessage = (e) => {
        receivedMessage = e.detail;
    };
</script>

<Child on:childMessage={handleChildMessage}/>

<p>{receivedMessage}</p>

<script>
    import Child from './Child.svelte';
</script>
 - **子组件 `Child.svelte`**
<script>
    import { createEventDispatcher } from'svelte';
    const dispatch = createEventDispatcher();
    const sendMessage = () => {
        dispatch('childMessage', 'Hello from child');
    };
</script>

<button on:click={sendMessage}>Send message to parent</button>

非父子组件通信

  1. 通过上下文(Context API)
    • 适用于有共同祖先的非父子组件。祖先组件使用 setContext 设置上下文,后代组件使用 getContext 获取上下文。
    • 示例:
      • 祖先组件 Ancestor.svelte
<script>
    import { setContext } from'svelte';
    let sharedData = 'Shared data';
    setContext('sharedContext', sharedData);
</script>

<Descendant1/>
<Descendant2/>
 - **后代组件 `Descendant1.svelte`**
<script>
    import { getContext } from'svelte';
    let sharedData = getContext('sharedContext');
</script>

<p>{sharedData}</p>
 - **后代组件 `Descendant2.svelte`**
<script>
    import { getContext } from'svelte';
    let sharedData = getContext('sharedContext');
</script>

<p>{sharedData}</p>
  1. 通过事件总线(自定义事件全局管理)
    • 创建一个独立的模块来管理自定义事件,组件之间通过这个模块来订阅和发布事件。
    • 示例:
      • 事件总线模块 eventBus.js
import { writable } from'svelte/store';

const eventBus = {
    events: {},
    on(eventName, callback) {
        if (!this.events[eventName]) {
            this.events[eventName] = [];
        }
        this.events[eventName].push(callback);
    },
    emit(eventName, data) {
        if (this.events[eventName]) {
            this.events[eventName].forEach(callback => callback(data));
        }
    }
};

export default eventBus;
 - **组件1 `Component1.svelte`**
<script>
    import eventBus from './eventBus.js';
    const sendData = () => {
        eventBus.emit('customEvent', 'Data from Component1');
    };
</script>

<button on:click={sendData}>Send data</button>
 - **组件2 `Component2.svelte`**
<script>
    import eventBus from './eventBus.js';
    let receivedData;
    eventBus.on('customEvent', (data) => {
        receivedData = data;
    });
</script>

<p>{receivedData}</p>