انتقالات عناصر المجموعة

عند إضافة عناصر إلى قائمة أو إزالتها منها أو إعادة ترتيبها، يمكن أن تساعد الانتقالات المستخدمين في الحفاظ على السياق. توفّر انتقالات العرض طريقة للانتقال بين حالتَين لعنصر من خلال منح العنصر view-transition-name فريدًا. عندما تتشارك عناصر متعددة في صفحة سلوك الانتقال نفسه، يتيح لك view-transition-class تحديد هذا المنطق مرة واحدة في CSS بدلاً من تكراره لكل view-transition-name فريد. يساعد ذلك في الحفاظ على أوراق الأنماط مع ضمان اتساق الصور المتحركة في مجموعة من العناصر.

خطوات التنفيذ

  1. تحديد أسماء فريدة وصف مشترَك

    يجب أن يكون لكل عنصر يجب تتبُّعه بشكل فردي أثناء عملية الانتقال سمة view-transition-name فريدة.

    <!-- Mandatory: Each element must have a unique view-transition-name -->
    <li style="view-transition-name: item-1" class="item">Item 1</li>
    <li style="view-transition-name: item-2" class="item">Item 2</li>
    

    لتطبيق الأنماط المشتركة، يجب أيضًا تعيين view-transition-class.

    .item {
      view-transition-class: list-item;
    }
    
  2. تحديد منطق الانتقال المشترك

    استخدِم العنصر الزائف ::view-transition-group() مع محدّد الفئة لتطبيق الأنماط على جميع عناصر تلك المجموعة.

    /* Targets any view transition group that has the 'list-item' class */
    ::view-transition-group(.list-item) {
      animation-duration: 0.5s;
      animation-timing-function: ease-in-out;
    }
    
    /* Handle accessibility by respecting motion preferences */
    @media (prefers-reduced-motion: reduce) {
      /* Disable all group transitions, including the default `root` group. */
      ::view-transition-group(*),
      ::view-transition-old(*),
      ::view-transition-new(*) {
        animation: none !important;
      }
    }
    
  3. اختياري: تحديد حركات الدخول والخروج

    استخدِم أداة الاختيار :only-child لإضافة تأثيرات انتقالية معيّنة إلى العناصر التي تتم إضافتها أو إزالتها. العنصران الزائفان ::view-transition-new() و::view-transition-old() هما عنصران فرعيان للعنصر الزائف ::view-transition-image-pair()، لذا يمكننا تحديد ما إذا كان العنصر مضافًا أو مُزالاً إذا كان العنصر الفرعي الوحيد.

    /* A `::view-transition-new()` element is the only child if it wasn't present before the view transition, so it is an added element. */
    ::view-transition-new(.list-item):only-child {
      animation-name: slide-in;
      /* Specify an animation duration if you want something different than the UA default of 0.5s */
      animation-duration: 1s;
    }
    /* A `::view-transition-old()` element is the only child if it isn't present after the view transition, so it is a removed element. */
    ::view-transition-old(.list-item):only-child {
      animation-name: slide-out;
      /* Specify an animation duration if you want something different than the UA default of 0.5s */
      animation-duration: 1s;
    }
    
    @keyframes slide-in {
      from {
        translate: -100vw 0;
      }
    }
    @keyframes slide-out {
      to {
        translate: -100vw 0;
      }
    }
    
  4. بدء عملية النقل

    يجب تضمين تعديل نموذج العناصر في المستند (DOM) في document.startViewTransition(). سيلتقط المتصفّح الحالة القديمة، وينفّذ التعديل، ثم ينتقل إلى الحالة الجديدة.

    function updateList(newData) {
      document.startViewTransition(() => {
        // All DOM changes inside this callback will be transitioned
        render(newData);
      });
    }
    
  5. الحفاظ على تفاعلية العناصر التي لم يتم نقلها

تعمل انتقالات العرض من خلال تراكب لقطات من عناصر DOM، ثم نقل اللقطات. هذا يعني أنّه أثناء الانتقال، لا تكون العناصر تفاعلية. إذا كانت هناك عناصر تفاعلية لم يتم نقلها، يمكنك جعلها تفاعلية من خلال إيقاف أحداث اللمس في انتقالات العرض.

::view-transition {
  /* Non-transitioned elements below the view transitions remain interactive */
  pointer-events: none;
}

بالإضافة إلى ذلك، يتضمّن العنصر :root تلقائيًا انتقالاً للعرض باسم root، ما يتيح الانتقالات التلقائية للصفحة الكاملة. إذا لم تكن هناك تغييرات على العنصر الجذر، سيكون هذا انتقالاً بين لقطتَين متطابقتَين غير تفاعليتَين. بما أنّنا ننقل عناصر معيّنة فقط وليس الشاشة بأكملها، يمكننا إيقاف انتقال root.

:root {
  /* Disable the root transition because we are only transitioning specific elements. */
  view-transition-name: none;
}

استراتيجيات احتياطية

تُعدّ View Transitions تحسينًا تدريجيًا. إذا كان المتصفّح لا يتيح استخدام document.startViewTransition، يجب أن يتم تحديث DOM على الفور، ما يوفّر تجربة وظيفية ولكن غير متحركة.

if (document.startViewTransition) {
  document.startViewTransition(() => updateDOM());
} else {
  // Fallback: Perform the update without animation
  updateDOM();
}

بالنسبة إلى CSS، فإنّ المتصفّحات التي لا تتعرّف على view-transition-class أو أداة اختيار الفئة ::view-transition-group() ستتجاهل هذه القواعد ببساطة، ولن يتم تطبيق أيّ تأثيرات حركية.