Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

chore: ensure binding events are without context #14194

Merged
merged 2 commits into from
Nov 7, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import { DEV } from 'esm-env';
import { render_effect, teardown } from '../../../reactivity/effects.js';
import { listen_to_event_and_reset_event } from './shared.js';
import { listen_to_event_and_reset_event, without_reactive_context } from './shared.js';
import * as e from '../../../errors.js';
import { is } from '../../../proxy.js';
import { queue_micro_task } from '../../task.js';
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,10 @@
import { teardown } from '../../../reactivity/effects.js';
import {
active_effect,
active_reaction,
set_active_effect,
set_active_reaction
} from '../../../runtime.js';
import { add_form_reset_listener } from '../misc.js';

/**
Expand All @@ -25,6 +31,23 @@ export function listen(target, events, handler, call_handler_immediately = true)
});
}

/**
* @template T
* @param {() => T} fn
*/
export function without_reactive_context(fn) {
var previous_reaction = active_reaction;
var previous_effect = active_effect;
set_active_reaction(null);
set_active_effect(null);
try {
return fn();
} finally {
set_active_reaction(previous_reaction);
set_active_effect(previous_effect);
}
}

/**
* Listen to the given event, and then instantiate a global form reset listener if not already done,
* to notify all bindings when the form is reset
Expand All @@ -34,7 +57,7 @@ export function listen(target, events, handler, call_handler_immediately = true)
* @param {() => void} [on_reset]
*/
export function listen_to_event_and_reset_event(element, event, handler, on_reset = handler) {
element.addEventListener(event, handler);
element.addEventListener(event, () => without_reactive_context(handler));
trueadm marked this conversation as resolved.
Show resolved Hide resolved
// @ts-expect-error
const prev = element.__on_r;
if (prev) {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { effect, render_effect, teardown } from '../../../reactivity/effects.js';
import { listen } from './shared.js';
import { listen, without_reactive_context } from './shared.js';

/**
* @param {'x' | 'y'} type
Expand All @@ -10,13 +10,14 @@ import { listen } from './shared.js';
export function bind_window_scroll(type, get, set = get) {
var is_scrolling_x = type === 'x';

var target_handler = () => {
scrolling = true;
clearTimeout(timeout);
timeout = setTimeout(clear, 100); // TODO use scrollend event if supported (or when supported everywhere?)
var target_handler = () =>
without_reactive_context(() => {
scrolling = true;
clearTimeout(timeout);
timeout = setTimeout(clear, 100); // TODO use scrollend event if supported (or when supported everywhere?)

set(window[is_scrolling_x ? 'scrollX' : 'scrollY']);
};
set(window[is_scrolling_x ? 'scrollX' : 'scrollY']);
});

addEventListener('scroll', target_handler, {
passive: true
Expand Down Expand Up @@ -61,5 +62,5 @@ export function bind_window_scroll(type, get, set = get) {
* @param {(size: number) => void} set
*/
export function bind_window_size(type, set) {
listen(window, ['resize'], () => set(window[type]));
listen(window, ['resize'], () => without_reactive_context(() => set(window[type])));
}
13 changes: 3 additions & 10 deletions packages/svelte/src/internal/client/dom/elements/events.js
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ import {
set_active_effect,
set_active_reaction
} from '../../runtime.js';
import { without_reactive_context } from './bindings/shared.js';

/** @type {Set<string>} */
export const all_registered_events = new Set();
Expand Down Expand Up @@ -61,17 +62,9 @@ export function create_event(event_name, dom, handler, options) {
handle_event_propagation.call(dom, event);
}
if (!event.cancelBubble) {
var previous_reaction = active_reaction;
var previous_effect = active_effect;

set_active_reaction(null);
set_active_effect(null);
try {
return without_reactive_context(() => {
return handler.call(this, event);
} finally {
set_active_reaction(previous_reaction);
set_active_effect(previous_effect);
}
});
}
}

Expand Down
Loading