تدوير المحتوى باستخدام CSS

نعود اليوم، كما وعدنا في موضوع سابق، لفكرة تدوير المحتوى، إنما هذه المرة سنرى كيف نقوم بتنفيذها باستخدام CSS فقط، ونتعرف إلى إيجابيات وسلبيات هذه الطريقة.

تدوير المحتوى باستخدام CSS3

سنباشر دون مقدمات، افتح محرر النصوص المفضل لديك ولنبدأ:

1. شيفرة HTML:

نحتاج ضمن ملف HTML إلى البنية التالية:

<section class="css-slider">

    <!-- setup -->
    <input type="radio" name="slider" id="slide-1" class="slider-handle" checked="checked">
    <input type="radio" name="slider" id="slide-2" class="slider-handle">
    ...
    <input type="radio" name="slider" id="slide-5" class="slider-handle">

    <!-- controls (arrows) -->
    <div class="slider-controls">
        <label for="slide-1" class="slide-1-label">1</label>
        <label for="slide-2" class="slide-2-label">2</label>
        ...
        <label for="slide-5" class="slide-5-label">5</label>
    </div>

    <!-- navigation -->
    <div class="slider-nav">
        <label for="slide-1" class="slide-1-label">1</label>
        <label for="slide-2" class="slide-2-label">2</label>
        ...
        <label for="slide-5" class="slide-5-label">5</label>
    </div>

    <!-- slides -->
    <div class="slider-content">
        <div class="slider-panels">
            <article>Content 1</article>
            <article>Content 2</article>
            ...
            <article>Content 5</article>
        </div>
    </div>

</section>

لنقم بتشريح ما سبق (سنعتمد في العناوين على خاصية Class):

العنصر الحاوي (css-slider):

ببساطة هذا العنصر سيحوي كل ما يلزمنا: الشرائح وعناصر التحكم المخفية وأزرار التنقل.

عناصر التحكم (slider-handle):

مجموعة عناصر Radio، تملك جميعها نفس الاسم (slider) مع تفعيل أول عنصر منها (checked) ليتم إظهار الشريحة الأولى عند تحميل الصفحة.

الأسهم (slider-controls):

يحوي مجموعة عناصر Label يما يوافق عناصر التحكم. سيتم إظهار وإخفاء هذه العناصر بما يسمح بالانتقال للشريحة التالية والسابقة.

أزرار التنقل (slider-nav):

نفس البنية السابقة، لكن هذه العناصر تبقى ظاهرة بشكل دائم لتسمح بالانتقال لأي شريحة.

مساحة العرض (slider-content):

المنطقة التي تظهر فيها الشريحة المحددة، يجب أن تكون ذات أبعاد محددة.

ضمن هذا العنصر نجد عنصراً آخر (slider-panels) وهو بدوره يحوي جميع الشرائح، كل منها مغلفة بعنصر من نوع Article. عرض هذا العنصر يجب أن يساوي عرض مساحة العرض مضروبة بعدد الشرائح.

2. تنسيقات CSS:

نبدأ بالتنسيق الابتدائي للعنصر الحاوي (css-slider) لكامل المكوّن، يمكننا تعديل هذه التنسيقات فيما بعد، لكنها نقطة انطلاق كالعادة:

.css-slider {
    background: #28759a;
    margin: 0 auto;
    position: relative;
    width: 640px;
}

نقوم بإخفاء عناصر التحكم (slider-handle) لأننا سنتحكم بالمحدد منها باستخدام (Labels):

.css-slider .slider-handle {
    display: none;
}

بالنسبة للأسهم (slider-controls)، نقوم أولاً بتحديد تنسيقها العام وإخفائها كلها:

.css-slider .slider-controls label {
    background: #0d4864 url(img/arrows.png) no-repeat;
    cursor: pointer;
    display: none;
    height: 50px;
    margin-top: -25px;
    position: absolute;
    text-indent: -99999px;
    top: 50%;
    transition: opacity .3s;
    width: 50px;
}

ثم نقوم باستخدام محددات (nth-child) والعنصر المجاور (Sibling Selector) لإظهار عنصري Label الموافقين للشريحة التالية والسابقة مع إعطائهما شكلي السهمين المناسبين:

.css-slider .slider-handle:nth-child(1):checked ~ .slider-controls .slide-5-label,
.css-slider .slider-handle:nth-child(2):checked ~ .slider-controls .slide-1-label,
...
.css-slider .slider-handle:nth-child(5):checked ~ .slider-controls .slide-4-label {
    background-position: center right;
    border-radius: 50% 0 0 50%;
    display: block;
    right: 0;
}

.css-slider .slider-handle:nth-child(1):checked ~ .slider-controls .slide-2-label,
.css-slider .slider-handle:nth-child(2):checked ~ .slider-controls .slide-3-label,
...
.css-slider .slider-handle:nth-child(5):checked ~ .slider-controls .slide-1-label {
    background-position: center left;
    border-radius: 0 50% 50% 0;
    display: block;
    left: 0;
}

نلاحظ مما سبق أننا عند ظهور الشريحة الأولى نظهر معها سهمي الشريحة الأخيرة (السابق) والشريحة الثانية (التالي)، وعند ظهور الشريحة الثانية نظهر معها سهمي الشريحة الأولى (السابق) والشريحة الثالثة (التالي)، وهكذا دواليك…

نقوم بشيئ مشابه بالنسبة لأزرار التنقل (slider-nav)، لكننا لا نخفي أياً منها، إنما نحدد تنسيقها العام ونعطي تنسيقاً خاصاً للزر الموافق للشريحة الحالية:

.css-slider .slider-nav {
    bottom: -10px;
    left: 0;
    position: absolute;
    right: 0;
    text-align: center;
}

.css-slider .slider-nav label {
    background: #28759a;
    box-shadow: inset 0 0 0 3px #0d4864;
    border-radius: 50%;
    cursor: pointer;
    display: inline-block;
    font-size: 0;
    height: 20px;
    text-indent: -99999px;
    transition: box-shadow .3s;
    width: 20px;
}

.css-slider .slider-handle:nth-child(1):checked ~ .slider-nav .slide-1-label,
.css-slider .slider-handle:nth-child(2):checked ~ .slider-nav .slide-2-label,
...
.css-slider .slider-handle:nth-child(5):checked ~ .slider-nav .slide-5-label {
    box-shadow: inset 0 0 0 10px #0d4864;
}

نصل بعدها لمساحة العرض (slider-content)، حيث نعطيها أبعاداً محددة (يمكن جعلها تجاوبية ببعض الجهد، لكن ذلك خارج إطار حديثنا هنا) ونقوم بإخفاء المحتوى الإضافي ضمنها بمنع ظهور أشرطة التمرير:

.css-slider .slider-content {
    height: 360px;
    overflow: hidden;
    width: 640px;
}

ثم نعطي العنصر الداخلي (slider-panels) عرضاً يساوي عرض مساحة العرض مضروباً بعدد الشرائح، كما نقوم بإعداد الحركة ضمنه لأنه العنصر الذي سيتحرك لإظهار الشريحة الحالية:

.css-slider .slider-panels {
    transition: margin-right 1s;
    width: 500%;
}

نعطي كل شريحة نفس أبعاد مساحة العرض:

.css-slider .slider-panels article {
    float: right;
    height: 360px;
    width: 640px;
}

يمكنك تخيل ما سبق كشريط فيلم سينمائي، تعطيك مساحة العرض إطاراً واحداً من الفيلم في كل لحظة، ويحوي العنصر الداخلي جميع الإطارات بشكل متسلسل. الصورة التالية توضح ذلك:

طريقة العمل

يبقى أن نحدد الشريحة الحالية ونظهرها:

.css-slider .slider-handle:nth-child(1):checked ~ .slider-content .slider-panels { margin-right: 0; }

.css-slider .slider-handle:nth-child(2):checked ~ .slider-content .slider-panels { margin-right: -100%; }

...

.css-slider .slider-handle:nth-child(5):checked ~ .slider-content .slider-panels { margin-right: -400%; }

وهذا كل ما يلزم لإعداد المحتوى الدوار باستخدام CSS3.

3. مزايا وسلبيات:

أرى عدة مزايا واضحة لهذه الطريقة:

  1. لا تستخدم JavaScript، ولكن يمكن إضافتها لدعم بعض المستعرضات القديمة أو المتخلفة عقلياً مثل Internet Explorer، لكن أي مستعرض يحترم نفسه يجب أن يكون قادراً على عرض الشرائح بطريقة صحيحة (قمت بالتجربة على FireFox 25 و Chrom 30 و Opera 12). وهذا يقودنا للميزة الثانية.
  2. قابلية وصول عالية (Accessibility) بما أن كل ما يوجد ضمن الصفحة هو شيفرة HTML صحيحة.
  3. لنفس السبب ستحب محركات البحث موقعك أكثر.
  4. سهولة في التنفيذ وفهم طريقة العمل على عكس سكريبتات JavaScript التي تحوي عادة الكثير من التعقيدات (والتي معظمها لا يدعم الاتجاه من اليمين لليسار).
  5. الحركة مبنية باستخدام CSS وأثرها على الأداء أقل بكثير من الجرائم التي ترتكبها JavaScript.
  6. قابلية عالية للتخصيص باستخدام HTML و CSS (كما سترون في المثال).

طبعاً هنالك بعض السلبيات الواضحة أيضاً:

  1. مع أنها سهلة التنفيذ للمرة الأولى، لكنها أحياناً ليست سهلة الصيانة والتعديل.
  2. ليست ديناميكية بما يكفي، يجب أن نعرف عدد الشرائح وبعض المحددات مسبقاً لعرض عناصر تحكم وكتابة تنسيقات CSS موافقة لها، قد يمكن الاعتماد جزئياً على JavaScript لإيجاد مساومة مناسبة بين سهولة الاستخدام والمزايا السابقة، أو قد يجد شخص أذكى مني حلاً أنسب.
  3. تكرار المكوّن نفسه ضمن الصفحة (مع أني أعارض ذلك بشدة) يحتاج إلى تغيير اسم عناصر Radio وخاصية ID لعدة عناصر وبعض الإضافات لشيفرة CSS.
  4. لا يمكن تغيير ترتيب العناصر ضمن شيفرة HTML، حيث أن محدد العنصر المجاور (Sibling Selector) يعمل فقط على العناصر التالية وليس السابقة.

4. كلمة أخيرة:

هذه ما لدينا لليوم، يمكنكم استعراض المثال أو تحميل ملفاته.

وعلى فكرة، ما طرحته هنا لا يتعارض مع ما ذكرته في مقال توقف عن استخدام سكريبتات تدوير المحتوى، لأني أعي تماماً أننا حتى لو تبنينا هذا الفكر كمصممين، فالعملاء لن يقتنعوا بسرعة بهذه النظرة، فالتطوير وتغيير الأفكار يحصل بالتدريج. المهم أني أردت هنا أن أعرض ما أراه الحل الأبسط والأفضل في الوقت الحالي، وإذا لاحظتم فأنا لم أقم بجعل الشرائح تدور تلقائياً لتأمين تجربة استخدام أفضل.

هذه الطريقة مطروحة على عدة مدونات وقد قرأت عنها في أكثر من مكان، وبالتالي لم أقم بترجمتها من مصدر محدد.

هل لديكم تطويرات؟ تحسينات؟ أو فكرتم بمزايا وسلبيات غير ما ذكر؟ شاركونا في التعليقات.

محمود الدعاس

من مواليد دمشق. ابتدأ بعد التخرج كمبرمج ويب عام 2005 مع شركة إيميا، انتقل بعدها إلى شركة تكنوليد للأتمتة المتكاملة ومنها إلى شقيقتها أتمتة للحلول المتقدمة كمصمم غرافيك ومصمم ومطور ويب. أسس مع مجموعة من زملاء الدراسة موقع HOMELESS-PRO.com لنشر قصص مصورة باللغة العربية للشباب، و Guestra كوكالة تصميم وتطوير.

مواضيع الكاتبموقع الكاتب

لمتابعة الكاتب:
TwitterFacebookPinterest

2 thoughts on “تدوير المحتوى باستخدام CSS

  1. شكراً أخي على المجهود الرائع

    ماذا لو أردنا أن تدور الشرائح بشكل تلقائي ؟ كيف نفعل ذلك ؟

أضف تعليقاً

لن يتم نشر عنوان بريدك الإلكتروني. الحقول الإلزامية مشار إليها بـ *