201
});
202
// No layout effect.
203
expect(Scheduler).toHaveYielded(['Child']);
204
- if (gate(flags => flags.persistent)) {
205
- expect(root).toMatchRenderedOutput(<span hidden={true} prop="Child" />);
206
- } else {
207
- // TODO: Offscreen does not yet hide/unhide children correctly in mutation
208
- // mode. Until we do, it should only be used inside a host component
209
- // wrapper whose visibility is toggled simultaneously.
210
- expect(root).toMatchRenderedOutput(<span prop="Child" />);
211
- }
204
+ expect(root).toMatchRenderedOutput(<span hidden={true} prop="Child" />);
205
206
// Unhide the tree. The layout effect is mounted.
207
await act(async () => {
248
);
249
});
250
expect(Scheduler).toHaveYielded(['Unmount layout', 'Child']);
258
- if (gate(flags => flags.persistent)) {
259
- expect(root).toMatchRenderedOutput(<span hidden={true} prop="Child" />);
260
- } else {
261
- // TODO: Offscreen does not yet hide/unhide children correctly in mutation
262
- // mode. Until we do, it should only be used inside a host component
263
- // wrapper whose visibility is toggled simultaneously.
264
- expect(root).toMatchRenderedOutput(<span prop="Child" />);
265
- }
251
+ expect(root).toMatchRenderedOutput(<span hidden={true} prop="Child" />);
252
253
// Unhide the tree. The layout effect is re-mounted.
254
await act(async () => {
285
);
286
});
287
expect(Scheduler).toHaveYielded(['Child']);
302
- if (gate(flags => flags.persistent)) {
303
- expect(root).toMatchRenderedOutput(<span hidden={true} prop="Child" />);
304
- } else {
305
- // TODO: Offscreen does not yet hide/unhide children correctly in mutation
306
- // mode. Until we do, it should only be used inside a host component
307
- // wrapper whose visibility is toggled simultaneously.
308
- expect(root).toMatchRenderedOutput(<span prop="Child" />);
309
- }
288
+ expect(root).toMatchRenderedOutput(<span hidden={true} prop="Child" />);
289
290
// Show the tree. The layout effect is mounted.
291
await act(async () => {
307
);
308
});
309
expect(Scheduler).toHaveYielded(['Unmount layout', 'Child']);
331
- if (gate(flags => flags.persistent)) {
332
- expect(root).toMatchRenderedOutput(<span hidden={true} prop="Child" />);
333
- } else {
334
- // TODO: Offscreen does not yet hide/unhide children correctly in mutation
335
- // mode. Until we do, it should only be used inside a host component
336
- // wrapper whose visibility is toggled simultaneously.
337
- expect(root).toMatchRenderedOutput(<span prop="Child" />);
338
- }
310
+ expect(root).toMatchRenderedOutput(<span hidden={true} prop="Child" />);
311
});
312
313
// @gate experimental || www
357
});
358
expect(Scheduler).toHaveYielded(['Unmount layout']);
359
});
360
+
361
+ // @gate experimental || www
362
+ it('hides new insertions into an already hidden tree', async () => {
363
+ const root = ReactNoop.createRoot();
364
+ await act(async () => {
365
+ root.render(
366
+ <Offscreen mode="hidden">
367
+ <span>Hi</span>
368
+ </Offscreen>,
369
+ );
370
+ });
371
+ expect(root).toMatchRenderedOutput(<span hidden={true}>Hi</span>);
372
+
373
+ // Insert a new node into the hidden tree
374
+ await act(async () => {
375
+ root.render(
376
+ <Offscreen mode="hidden">
377
+ <span>Hi</span>
378
+ <span>Something new</span>
379
+ </Offscreen>,
380
+ );
381
+ });
382
+ expect(root).toMatchRenderedOutput(
383
+ <>
384
+ <span hidden={true}>Hi</span>
385
+ {/* This new node should also be hidden */}
386
+ <span hidden={true}>Something new</span>
387
+ </>,
388
+ );
389
+ });
390
+
391
+ // @gate experimental || www
392
+ it('hides updated nodes inside an already hidden tree', async () => {
393
+ const root = ReactNoop.createRoot();
394
+ await act(async () => {
395
+ root.render(
396
+ <Offscreen mode="hidden">
397
+ <span>Hi</span>
398
+ </Offscreen>,
399
+ );
400
+ });
401
+ expect(root).toMatchRenderedOutput(<span hidden={true}>Hi</span>);
402
+
403
+ // Set the `hidden` prop to on an already hidden node
404
+ await act(async () => {
405
+ root.render(
406
+ <Offscreen mode="hidden">
407
+ <span hidden={false}>Hi</span>
408
+ </Offscreen>,
409
+ );
410
+ });
411
+ // It should still be hidden, because the Offscreen container overrides it
412
+ expect(root).toMatchRenderedOutput(<span hidden={true}>Hi</span>);
413
+
414
+ // Unhide the boundary
415
+ await act(async () => {
416
+ root.render(
417
+ <Offscreen mode="visible">
418
+ <span hidden={true}>Hi</span>
419
+ </Offscreen>,
420
+ );
421
+ });
422
+ // It should still be hidden, because of the prop
423
+ expect(root).toMatchRenderedOutput(<span hidden={true}>Hi</span>);
424
+
425
+ // Remove the `hidden` prop
426
+ await act(async () => {
427
+ root.render(
428
+ <Offscreen mode="visible">
429
+ <span>Hi</span>
430
+ </Offscreen>,
431
+ );
432
+ });
433
+ // Now it's visible
434
+ expect(root).toMatchRenderedOutput(<span>Hi</span>);
435
+ });
436
});