start centralising rAF stuff

pull/1937/head
Richard Harris 7 years ago
parent 65dc6d693b
commit d58996534d

@ -1,4 +1,5 @@
import { transitionManager, linear, generateRule, hash } from './transitions.js';
import { loop } from './loop.js';
export function wrapAnimation(node, from, fn, params) {
if (!from) return;
@ -68,7 +69,35 @@ export function wrapAnimation(node, from, fn, params) {
}
};
transitionManager.add(animation);
// transitionManager.add(animation);
transitionManager.active += 1;
const { abort, promise } = loop(() => {
const now = window.performance.now();
if (animation.program && now >= animation.program.end) {
animation.done();
}
if (animation.pending && now >= animation.pending.start) {
animation.start(animation.pending);
}
if (animation.running) {
animation.update(now);
return true;
}
});
promise.then(() => {
transitionManager.active -= 1;
if (!transitionManager.active) {
let i = transitionManager.stylesheet.cssRules.length;
while (i--) transitionManager.stylesheet.deleteRule(i);
transitionManager.activeRules = {};
}
});
if (info.tick) info.tick(0, 1);

@ -3,6 +3,7 @@ export * from './await-block.js';
export * from './dom.js';
export * from './keyed-each.js';
export * from './lifecycle.js';
export * from './loop.js';
export * from './scheduler.js';
export * from './spread.js';
export * from './ssr.js';

@ -0,0 +1,38 @@
const tasks = new Set();
let running = false;
function run_tasks() {
tasks.forEach(task => {
if (!task[0]()) {
tasks.delete(task);
task[1]();
}
});
running = tasks.size > 0;
if (running) requestAnimationFrame(run_tasks);
}
export function clear_loops() {
// for testing...
tasks.forEach(task => tasks.delete(task));
running = false;
}
export function loop(fn) {
let task;
if (!running) {
running = true;
requestAnimationFrame(run_tasks);
}
return {
promise: new Promise(fulfil => {
tasks.add(task = [fn, fulfil]);
}),
abort() {
tasks.delete(task);
}
};
}

@ -1,5 +1,6 @@
import { createElement } from './dom.js';
import { noop, run } from './utils.js';
import { loop } from './loop.js';
export function linear(t) {
return t;
@ -83,8 +84,35 @@ export function wrapTransition(component, node, fn, params, intro) {
}
if (!this.running) {
transitionManager.active += 1;
this.running = true;
transitionManager.add(this);
// transitionManager.add(this);
const { abort, promise } = loop(() => {
const now = window.performance.now();
if (this.program && now >= this.program.end) {
this.done();
}
if (this.pending && now >= this.pending.start) {
this.start(this.pending);
}
if (this.running) {
this.update(now);
return true;
}
});
promise.then(() => {
transitionManager.active -= 1;
if (!transitionManager.active) {
let i = transitionManager.stylesheet.cssRules.length;
while (i--) transitionManager.stylesheet.deleteRule(i);
transitionManager.activeRules = {};
}
});
}
},
@ -173,6 +201,7 @@ export function groupOutros() {
}
export var transitionManager = {
active: 0,
running: false,
transitions: [],
bound: null,
@ -180,15 +209,6 @@ export var transitionManager = {
activeRules: {},
promise: null,
add(transition) {
this.transitions.push(transition);
if (!this.running) {
this.running = true;
requestAnimationFrame(this.bound || (this.bound = this.next.bind(this)));
}
},
addRule(rule, name) {
if (!this.stylesheet) {
const style = createElement('style');
@ -202,40 +222,6 @@ export var transitionManager = {
}
},
next() {
this.running = false;
const now = window.performance.now();
let i = this.transitions.length;
while (i--) {
const transition = this.transitions[i];
if (transition.program && now >= transition.program.end) {
transition.done();
}
if (transition.pending && now >= transition.pending.start) {
transition.start(transition.pending);
}
if (transition.running) {
transition.update(now);
this.running = true;
} else if (!transition.pending) {
this.transitions.splice(i, 1);
}
}
if (this.running) {
requestAnimationFrame(this.bound);
} else if (this.stylesheet) {
let i = this.stylesheet.cssRules.length;
while (i--) this.stylesheet.deleteRule(i);
this.activeRules = {};
}
},
deleteRule(node, name) {
node.style.animation = node.style.animation
.split(', ')

@ -1,5 +1,6 @@
import { writable } from 'svelte/store';
import { add_task, is_date } from './utils.js';
import { loop } from 'svelte/internal';
import { is_date } from './utils.js';
function get_initial_velocity(value) {
if (typeof value === 'number' || is_date(value)) return 0;
@ -116,7 +117,7 @@ export function spring(value, opts = {}) {
last_time = window.performance.now();
settled = false;
task = add_task(() => {
task = loop(() => {
const time = window.performance.now();
({ value, settled } = tick_spring(

@ -1,7 +1,7 @@
import { writable } from 'svelte/store';
import { assign } from 'svelte/internal';
import { assign, loop } from 'svelte/internal';
import { linear } from 'svelte/easing';
import { add_task, is_date } from './utils.js';
import { is_date } from './utils.js';
function get_interpolator(a, b) {
if (a === b || a !== a) return () => a;
@ -76,7 +76,7 @@ export function tweened(value, defaults = {}) {
const start = window.performance.now() + delay;
let fn;
task = add_task(() => {
task = loop(() => {
const time = window.performance.now();
if (time < start) return true;

@ -1,36 +1,3 @@
const tasks = new Set();
let running = false;
function run_tasks() {
tasks.forEach(task => {
if (!task[0]()) {
tasks.delete(task);
task[1]();
}
});
running = tasks.size > 0;
if (running) requestAnimationFrame(run_tasks);
}
export function add_task(fn) {
let task;
if (!running) {
running = true;
requestAnimationFrame(run_tasks);
}
return {
promise: new Promise(fulfil => {
tasks.add(task = [fn, fulfil]);
}),
abort() {
tasks.delete(task);
}
};
}
export function is_date(obj) {
return Object.prototype.toString.call(obj) === '[object Date]';
}

@ -3,7 +3,7 @@ import * as path from "path";
import * as fs from "fs";
import { rollup } from 'rollup';
import * as virtual from 'rollup-plugin-virtual';
import { transitionManager } from "../../internal.js";
import { transitionManager, clear_loops } from "../../internal.js";
import {
showOutput,
@ -96,6 +96,7 @@ describe("runtime", () => {
// set of hacks to support transition tests
transitionManager.running = false;
transitionManager.transitions = [];
clear_loops();
const raf = {
time: 0,

Loading…
Cancel
Save