@@ -1101,6 +1101,31 @@ export class Datetime implements ComponentInterface {
11011101 this . initializeKeyboardListeners ( ) ;
11021102 }
11031103
1104+ /**
1105+ * Fallback to ensure the datetime becomes ready even if
1106+ * IntersectionObserver never reports it as intersecting.
1107+ *
1108+ * This is primarily used in environments where the observer
1109+ * might not fire as expected, such as when running under
1110+ * synthetic tests that stub IntersectionObserver.
1111+ */
1112+ private ensureReadyIfVisible = ( ) => {
1113+ if ( this . el . classList . contains ( 'datetime-ready' ) ) {
1114+ return ;
1115+ }
1116+
1117+ const rect = this . el . getBoundingClientRect ( ) ;
1118+ if ( rect . width === 0 || rect . height === 0 ) {
1119+ return ;
1120+ }
1121+
1122+ this . initializeListeners ( ) ;
1123+
1124+ writeTask ( ( ) => {
1125+ this . el . classList . add ( 'datetime-ready' ) ;
1126+ } ) ;
1127+ } ;
1128+
11041129 componentDidLoad ( ) {
11051130 const { el, intersectionTrackerRef } = this ;
11061131
@@ -1141,6 +1166,21 @@ export class Datetime implements ComponentInterface {
11411166 */
11421167 raf ( ( ) => visibleIO ?. observe ( intersectionTrackerRef ! ) ) ;
11431168
1169+ /**
1170+ * Fallback: If IntersectionObserver never reports that the
1171+ * datetime is visible but the host clearly has layout, ensure
1172+ * we still initialize listeners and mark the component as ready.
1173+ *
1174+ * We schedule this a couple of frames after load so that any
1175+ * initial layout/animations (such as a parent modal presenting)
1176+ * have had a chance to run.
1177+ */
1178+ raf ( ( ) => {
1179+ raf ( ( ) => {
1180+ this . ensureReadyIfVisible ( ) ;
1181+ } ) ;
1182+ } ) ;
1183+
11441184 /**
11451185 * We need to clean up listeners when the datetime is hidden
11461186 * in a popover/modal so that we can properly scroll containers
@@ -2664,9 +2704,9 @@ export class Datetime implements ComponentInterface {
26642704
26652705 We can work around this by observing .intersection-tracker and using the host
26662706 (ion-datetime) as the "root". This allows the IO callback to fire the moment
2667- the datetime is visible. The .intersection-tracker element should not have
2668- dimensions or additional styles , and it should not be positioned absolutely
2669- otherwise the IO callback may fire at unexpected times.
2707+ the datetime is visible. The .intersection-tracker element uses a minimal,
2708+ invisible block size so it participates in layout , and it should not be
2709+ positioned absolutely otherwise the IO callback may fire at unexpected times.
26702710 */ }
26712711 < div class = "intersection-tracker" ref = { ( el ) => ( this . intersectionTrackerRef = el ) } > </ div >
26722712 { this . renderDatetime ( mode ) }
0 commit comments