apply event modifiers to <svelte:body> events (#4279)

pull/4283/head
Conduitry 5 years ago committed by GitHub
parent bda254e250
commit b39282a918
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23

@ -5,6 +5,7 @@
* Disallow two-way binding to a variable declared by an `{#await}` block ([#4012](https://github.com/sveltejs/svelte/issues/4012))
* Allow access to `let:` variables in sibling attributes on slot root ([#4173](https://github.com/sveltejs/svelte/issues/4173))
* Add some more known globals ([#4276](https://github.com/sveltejs/svelte/pull/4276))
* Correctly apply event modifiers to `<svelte:body>` events ([#4278](https://github.com/sveltejs/svelte/issues/4278))
## 3.17.1

@ -1,26 +1,23 @@
import Block from '../Block';
import Wrapper from './shared/Wrapper';
import { b } from 'code-red';
import { x } from 'code-red';
import Body from '../../nodes/Body';
import { Identifier } from 'estree';
import EventHandler from './Element/EventHandler';
import add_event_handlers from './shared/add_event_handlers';
import { TemplateNode } from '../../../interfaces';
import Renderer from '../Renderer';
export default class BodyWrapper extends Wrapper {
node: Body;
handlers: EventHandler[];
render(block: Block, _parent_node: Identifier, _parent_nodes: Identifier) {
this.node.handlers
.map(handler => new EventHandler(handler, this))
.forEach(handler => {
const snippet = handler.get_snippet(block);
block.chunks.init.push(b`
@_document.body.addEventListener("${handler.node.name}", ${snippet});
`);
constructor(renderer: Renderer, block: Block, parent: Wrapper, node: TemplateNode) {
super(renderer, block, parent, node);
this.handlers = this.node.handlers.map(handler => new EventHandler(handler, this));
}
block.chunks.destroy.push(b`
@_document.body.removeEventListener("${handler.node.name}", ${snippet});
`);
});
render(block: Block, _parent_node: Identifier, _parent_nodes: Identifier) {
add_event_handlers(block, x`@_document.body`, this.handlers);
}
}

@ -2,6 +2,7 @@ import EventHandler from '../../../nodes/EventHandler';
import Wrapper from '../shared/Wrapper';
import Block from '../../Block';
import { b, x, p } from 'code-red';
import { Expression } from 'estree';
const TRUE = x`true`;
const FALSE = x`false`;
@ -35,7 +36,7 @@ export default class EventHandlerWrapper {
return snippet;
}
render(block: Block, target: string) {
render(block: Block, target: string | Expression) {
let snippet = this.get_snippet(block);
if (this.node.modifiers.has('preventDefault')) snippet = x`@prevent_default(${snippet})`;

@ -1,9 +1,10 @@
import Block from '../../Block';
import EventHandler from '../Element/EventHandler';
import { Expression } from 'estree';
export default function add_event_handlers(
block: Block,
target: string,
target: string | Expression,
handlers: EventHandler[]
) {
handlers.forEach(handler => add_event_handler(block, target, handler));
@ -11,7 +12,7 @@ export default function add_event_handlers(
export function add_event_handler(
block: Block,
target: string,
target: string | Expression,
handler: EventHandler
) {
handler.render(block, target);

@ -0,0 +1,11 @@
export default {
async test({ assert, component, window }) {
const event = new window.MouseEvent('click');
await window.document.body.dispatchEvent(event);
assert.equal(component.count, 1);
await window.document.body.dispatchEvent(event);
assert.equal(component.count, 1);
}
};

@ -0,0 +1,5 @@
<script>
export let count = 0;
</script>
<svelte:body on:click|once="{() => count += 1}"/>
Loading…
Cancel
Save