@@ -181,7 +181,7 @@ internal IEnumerable<CacheEntry> CompleteGeneration(int endIndex)
181
181
return unusedEntries ;
182
182
}
183
183
184
- internal ( UIElement container , bool isNew ) GetOrCreate ( int index )
184
+ internal ( CacheEntry entry , CacheEntryKind kind ) GetOrCreate ( int index )
185
185
{
186
186
Debug . Assert ( _host is { } ) ;
187
187
Debug . Assert ( _generationStartIndex <= index ) ;
@@ -223,7 +223,7 @@ internal IEnumerable<CacheEntry> CompleteGeneration(int endIndex)
223
223
224
224
Debug . Assert ( entry . Index == index ) ;
225
225
226
- return ( entry . Container , false ) ;
226
+ return ( entry , CacheEntryKind . Kept ) ;
227
227
}
228
228
229
229
case GenerationState . Before :
@@ -233,19 +233,19 @@ internal IEnumerable<CacheEntry> CompleteGeneration(int endIndex)
233
233
var item = _host ! [ index ] ;
234
234
235
235
CacheEntry entry ;
236
- bool isNew ;
236
+ CacheEntryKind kind ;
237
237
if ( _generationRecyclableBefore . count > 0 )
238
238
{
239
239
entry = _entries [ _generationRecyclableBefore . at ] ;
240
- isNew = false ;
240
+ kind = CacheEntryKind . Recycled ;
241
241
242
242
_generationRecyclableBefore . at ++ ;
243
243
_generationRecyclableBefore . count -- ;
244
244
}
245
245
else if ( _generationRecyclableAfter . count > 0 )
246
246
{
247
247
entry = _entries [ _generationRecyclableAfter . at + _generationRecyclableAfter . count - 1 ] ;
248
- isNew = false ;
248
+ kind = CacheEntryKind . Recycled ;
249
249
250
250
_generationRecyclableAfter . count -- ;
251
251
@@ -255,7 +255,7 @@ internal IEnumerable<CacheEntry> CompleteGeneration(int endIndex)
255
255
{
256
256
var container = ( UIElement ) _host . GetContainerForItem ( item , null ) ;
257
257
entry = new CacheEntry ( container ) ;
258
- isNew = true ;
258
+ kind = CacheEntryKind . New ;
259
259
260
260
_entries . Add ( entry ) ;
261
261
}
@@ -265,7 +265,7 @@ internal IEnumerable<CacheEntry> CompleteGeneration(int endIndex)
265
265
266
266
_host . PrepareItemContainer ( entry . Container , item ) ;
267
267
268
- return ( entry . Container , isNew ) ;
268
+ return ( entry , kind ) ;
269
269
}
270
270
}
271
271
@@ -309,6 +309,13 @@ private class CacheEntryComparer : IComparer<CacheEntry>
309
309
public int Compare ( CacheEntry x , CacheEntry y ) => x . Index . CompareTo ( y . Index ) ;
310
310
}
311
311
312
+ private enum CacheEntryKind
313
+ {
314
+ New ,
315
+ Kept ,
316
+ Recycled
317
+ }
318
+
312
319
internal event VisibleIndicesUpdatedEventCallback VisibleIndicesUpdated ;
313
320
314
321
private readonly ContainersCache _cache = new ContainersCache ( ) ;
@@ -328,8 +335,8 @@ private void base_Initialize()
328
335
#region Private and internal API required by UWP code
329
336
internal int FirstVisibleIndexBase { get ; private set ; }
330
337
internal int LastVisibleIndexBase { get ; private set ; }
331
- internal int FirstCacheIndexBase { get ; private set ; }
332
- internal int LastCacheIndexBase { get ; private set ; }
338
+ internal int FirstCacheIndexBase => _cache . StartIndex ;
339
+ internal int LastCacheIndexBase => _cache . EndIndex ;
333
340
334
341
[ NotImplemented ]
335
342
internal PanelScrollingDirection PanningDirectionBase { get ; } = PanelScrollingDirection . None ;
@@ -370,14 +377,10 @@ internal void ScrollItemIntoView(int index, ScrollIntoViewAlignment alignment, d
370
377
}
371
378
372
379
private Size GetViewportSize ( )
373
- {
374
- return _lastLayoutedViewport . Size . AtLeast ( _defaultHardCodedSize ) . FiniteOrDefault ( _defaultHardCodedSize ) ;
375
- }
380
+ => _lastLayoutedViewport . Size . AtLeast ( _defaultHardCodedSize ) . FiniteOrDefault ( _defaultHardCodedSize ) ;
376
381
377
382
internal Size GetDesiredViewportSize ( )
378
- {
379
- return _layoutStrategy . GetDesiredViewportSize ( ) ;
380
- }
383
+ => _layoutStrategy ? . GetDesiredViewportSize ( ) ?? default ;
381
384
382
385
[ NotImplemented ]
383
386
internal void GetTargetIndexFromNavigationAction (
@@ -396,9 +399,7 @@ internal void GetTargetIndexFromNavigationAction(
396
399
}
397
400
398
401
internal IItemContainerMapping GetItemContainerMapping ( )
399
- {
400
- throw new NotImplementedException ( ) ;
401
- }
402
+ => _cache ;
402
403
403
404
private void SetLayoutStrategyBase ( CalendarLayoutStrategy spLayoutStrategy )
404
405
{
@@ -463,10 +464,10 @@ private Size base_MeasureOverride(Size availableSize)
463
464
|| _layoutStrategy . ShouldContinueFillingUpSpace ( ElementType . ItemContainer , index , layout , remainingWindowToFill ) )
464
465
)
465
466
{
466
- var ( container , isNew ) = _cache . GetOrCreate ( index ) ;
467
- if ( isNew )
467
+ var ( entry , kind ) = _cache . GetOrCreate ( index ) ;
468
+ if ( kind == CacheEntryKind . New )
468
469
{
469
- Children . Add ( container ) ;
470
+ Children . Add ( entry . Container ) ;
470
471
}
471
472
472
473
var itemSize = _layoutStrategy . GetElementMeasureSize ( ElementType . ItemContainer , index , renderWindow ) ; // Note: It's actually the same for all items
@@ -480,8 +481,19 @@ private Size base_MeasureOverride(Size availableSize)
480
481
return default ;
481
482
}
482
483
483
- container . Measure ( itemSize ) ;
484
- container . GetVirtualizationInformation ( ) . MeasureSize = itemSize ;
484
+ entry . Container . Measure ( itemSize ) ;
485
+ entry . Container . GetVirtualizationInformation ( ) . MeasureSize = itemSize ;
486
+ switch ( kind )
487
+ {
488
+ case CacheEntryKind . New :
489
+ _host . SetupContainerContentChangingAfterPrepare ( entry . Container , entry . Item , entry . Index , itemSize ) ;
490
+ break ;
491
+
492
+ case CacheEntryKind . Recycled :
493
+ // Note: ModernBasePanel seems to use only SetupContainerContentChangingAfterPrepare
494
+ _host . RaiseContainerContentChangingOnRecycle ( entry . Container , entry . Item ) ;
495
+ break ;
496
+ }
485
497
486
498
var isVisible = viewport . Contains ( itemBounds . Location ) ;
487
499
if ( firstVisibleIndex == - 1 && isVisible )
0 commit comments