99 KEY_BLOCK ,
1010 ROOT_BLOCK
1111} from './block.js' ;
12- import { destroy_each_item_block } from './each.js' ;
12+ import { destroy_each_item_block , get_first_element } from './each.js' ;
1313import { append_child } from './operations.js' ;
1414import { empty } from './render.js' ;
1515import {
@@ -21,6 +21,7 @@ import {
2121 managed_effect ,
2222 managed_pre_effect ,
2323 mark_subtree_inert ,
24+ schedule_task ,
2425 untrack
2526} from './runtime.js' ;
2627import { raf } from './timing.js' ;
@@ -411,13 +412,13 @@ function is_transition_block(block) {
411412/**
412413 * @template P
413414 * @param {HTMLElement } dom
414- * @param {import('./types.js').TransitionFn<P | undefined> | import('./types.js').AnimateFn<P | undefined> } transition_fn
415+ * @param {() => import('./types.js').TransitionFn<P | undefined> | import('./types.js').AnimateFn<P | undefined> } get_transition_fn
415416 * @param {(() => P) | null } props_fn
416417 * @param {'in' | 'out' | 'both' | 'key' } direction
417418 * @param {boolean } global
418419 * @returns {void }
419420 */
420- export function bind_transition ( dom , transition_fn , props_fn , direction , global ) {
421+ export function bind_transition ( dom , get_transition_fn , props_fn , direction , global ) {
421422 const transition_effect = /** @type {import('./types.js').EffectSignal } */ ( current_effect ) ;
422423 const block = current_block ;
423424 const props = props_fn === null ? { } : props_fn ( ) ;
@@ -432,6 +433,7 @@ export function bind_transition(dom, transition_fn, props_fn, direction, global)
432433 if ( transition_block . t === EACH_ITEM_BLOCK ) {
433434 // Lazily apply the each block transition
434435 transition_block . r = each_item_transition ;
436+ transition_block . a = each_item_animate ;
435437 transition_block = transition_block . p ;
436438 } else if ( transition_block . t === AWAIT_BLOCK && transition_block . n /* pending */ ) {
437439 can_show_intro_on_mount = false ;
@@ -458,6 +460,11 @@ export function bind_transition(dom, transition_fn, props_fn, direction, global)
458460 let transition ;
459461
460462 effect ( ( ) => {
463+ if ( transition !== undefined ) {
464+ // Destroy any existing transitions first
465+ transition . x ( ) ;
466+ }
467+ const transition_fn = get_transition_fn ( ) ;
461468 /** @param {DOMRect } [from] */
462469 const init = ( from ) =>
463470 untrack ( ( ) =>
@@ -641,3 +648,31 @@ function each_item_transition(transition) {
641648 } ) ;
642649 transitions . add ( transition ) ;
643650}
651+
652+ /**
653+ *
654+ * @param {import('./types.js').EachItemBlock } block
655+ * @param {Set<import('./types.js').Transition> } transitions
656+ * @param {number } index
657+ * @param {boolean } index_is_reactive
658+ */
659+ function each_item_animate ( block , transitions , index , index_is_reactive ) {
660+ let prev_index = block . i ;
661+ if ( index_is_reactive ) {
662+ prev_index = /** @type {import('./types.js').Signal<number> } */ ( prev_index ) . v ;
663+ }
664+ const items = block . p . v ;
665+ if ( prev_index !== index && /** @type {number } */ ( index ) < items . length ) {
666+ const from_dom = /** @type {Element } */ ( get_first_element ( block ) ) ;
667+ const from = from_dom . getBoundingClientRect ( ) ;
668+ // Cancel any existing key transitions
669+ for ( const transition of transitions ) {
670+ if ( transition . r === 'key' ) {
671+ transition . c ( ) ;
672+ }
673+ }
674+ schedule_task ( ( ) => {
675+ trigger_transitions ( transitions , 'key' , from ) ;
676+ } ) ;
677+ }
678+ }
0 commit comments