اذهب إلى المحتوى

البحث في الموقع

المحتوى عن 'effects'.

  • ابحث بالكلمات المفتاحية

    أضف وسومًا وافصل بينها بفواصل ","
  • ابحث باسم الكاتب

نوع المحتوى


التصنيفات

  • الإدارة والقيادة
  • التخطيط وسير العمل
  • التمويل
  • فريق العمل
  • دراسة حالات
  • التعامل مع العملاء
  • التعهيد الخارجي
  • السلوك التنظيمي في المؤسسات
  • عالم الأعمال
  • التجارة والتجارة الإلكترونية
  • نصائح وإرشادات
  • مقالات ريادة أعمال عامة

التصنيفات

  • مقالات برمجة عامة
  • مقالات برمجة متقدمة
  • PHP
    • Laravel
    • ووردبريس
  • جافاسكربت
    • لغة TypeScript
    • Node.js
    • React
    • Vue.js
    • Angular
    • jQuery
    • Cordova
  • HTML
  • CSS
    • Sass
    • إطار عمل Bootstrap
  • SQL
  • لغة C#‎
    • ‎.NET
    • منصة Xamarin
  • لغة C++‎
  • لغة C
  • بايثون
    • Flask
    • Django
  • لغة روبي
    • إطار العمل Ruby on Rails
  • لغة Go
  • لغة جافا
  • لغة Kotlin
  • لغة Rust
  • برمجة أندرويد
  • لغة R
  • الذكاء الاصطناعي
  • صناعة الألعاب
  • سير العمل
    • Git
  • الأنظمة والأنظمة المدمجة

التصنيفات

  • تصميم تجربة المستخدم UX
  • تصميم واجهة المستخدم UI
  • الرسوميات
    • إنكسكيب
    • أدوبي إليستريتور
  • التصميم الجرافيكي
    • أدوبي فوتوشوب
    • أدوبي إن ديزاين
    • جيمب GIMP
    • كريتا Krita
  • التصميم ثلاثي الأبعاد
    • 3Ds Max
    • Blender
  • نصائح وإرشادات
  • مقالات تصميم عامة

التصنيفات

  • مقالات DevOps عامة
  • خوادم
    • الويب HTTP
    • البريد الإلكتروني
    • قواعد البيانات
    • DNS
    • Samba
  • الحوسبة السحابية
    • Docker
  • إدارة الإعدادات والنشر
    • Chef
    • Puppet
    • Ansible
  • لينكس
    • ريدهات (Red Hat)
  • خواديم ويندوز
  • FreeBSD
  • حماية
    • الجدران النارية
    • VPN
    • SSH
  • شبكات
    • سيسكو (Cisco)

التصنيفات

  • التسويق بالأداء
    • أدوات تحليل الزوار
  • تهيئة محركات البحث SEO
  • الشبكات الاجتماعية
  • التسويق بالبريد الالكتروني
  • التسويق الضمني
  • استسراع النمو
  • المبيعات
  • تجارب ونصائح
  • مبادئ علم التسويق

التصنيفات

  • مقالات عمل حر عامة
  • إدارة مالية
  • الإنتاجية
  • تجارب
  • مشاريع جانبية
  • التعامل مع العملاء
  • الحفاظ على الصحة
  • التسويق الذاتي
  • العمل الحر المهني
    • العمل بالترجمة
    • العمل كمساعد افتراضي
    • العمل بكتابة المحتوى

التصنيفات

  • الإنتاجية وسير العمل
    • مايكروسوفت أوفيس
    • ليبر أوفيس
    • جوجل درايف
    • شيربوينت
    • Evernote
    • Trello
  • تطبيقات الويب
    • ووردبريس
    • ماجنتو
    • بريستاشوب
    • أوبن كارت
    • دروبال
  • الترجمة بمساعدة الحاسوب
    • omegaT
    • memoQ
    • Trados
    • Memsource
  • برامج تخطيط موارد المؤسسات ERP
    • تطبيقات أودو odoo
  • أنظمة تشغيل الحواسيب والهواتف
    • ويندوز
    • لينكس
  • مقالات عامة

التصنيفات

  • آخر التحديثات

أسئلة وأجوبة

  • الأقسام
    • أسئلة البرمجة
    • أسئلة ريادة الأعمال
    • أسئلة العمل الحر
    • أسئلة التسويق والمبيعات
    • أسئلة التصميم
    • أسئلة DevOps
    • أسئلة البرامج والتطبيقات

التصنيفات

  • كتب ريادة الأعمال
  • كتب العمل الحر
  • كتب تسويق ومبيعات
  • كتب برمجة
  • كتب تصميم
  • كتب DevOps

ابحث في

ابحث عن


تاريخ الإنشاء

  • بداية

    نهاية


آخر تحديث

  • بداية

    نهاية


رشح النتائج حسب

تاريخ الانضمام

  • بداية

    نهاية


المجموعة


النبذة الشخصية

تم العثور على 3 نتائج

  1. أهلًا بك في هذه السلسلة التي تتحدث عن تأثيرات التمرير (Scrolling Effects)، سنستعرض في هذه السلسلة عددٌ من تأثيرات التمرير وسنشرح آلية عملها وسنجرِّبها عمليًا. يمكننا الاستفادة من الحدث scroll في JavaScript لإجراء تأثيرات عند تمرير صفحة الويب؛ لكن إن فعلنا ذلك دون إتقان فالنتيجة كارثية، أما إذا أحسنا صنعنا فيمكن لتأثيرات التمرير أن تبهر الزوار وتشعرهم أنَّ موقعك مميز. تحدثنا في المقالتين السابقتين عن التأثيرات الآتية: إخفاء صورة خلفية تدريجيًا عند التمرير توضيح الصورة عند التمرير تدوير العناصر عند التمرير تأثير اختلاف المظهر parallax إظهار صورة الخلفية عند التمرير باستخدام CSS فقط تمرير سلس للصفحة تطبيق تأثير عدم الوضوح على المحتوى خلف شريط الانتقال وسنشرح في هذه المقالة (الثالثة) طريقة إنشاء: عنصر قابل للتمرير مع إمكانية وصول مخصصة من لوحة المفاتيح تأثير غروب الشمس باستخدام SVG إظهار فيديو في الخلفية صور متحركة بتأثير parallax باستخدام CSS 3D و JavaScript سأقدِّم لك في بداية كل قسم رابطًا لتجربة المثال تجربةً حيةً على المتصفح. سيسهل عليك كثيرًا أن تفهم الشرح والشيفرات بعد تجربتك للتأثير. عنصرٌ قابلٌ للتمرير مع إمكانية وصول مخصصة من لوحة المفاتيح (تجربة حية) كقاعدة عامة، إخفاء المعلومات المهمة داخل عنصر قابل للتمرير هي فكرةٌ سيئة، لكنه تُستعمَل عادةً من المصممين لأنها تبدو «ذات مظهرٍ جيد» بدلًا من التفكير حول قابلية استخدامها؛ لكن هنالك حالات يمكن فيها من الضروري فعل ذلك، وعندئذٍ يجب أن تكون الروابط داخل تلك العناصر قابلةً للوصول عبر لوحة المفاتيح. شيفرات HTML و CSS الأساسية تقريبًا جميع العناصر يمكن أن تُضبَط لها الخاصية overflow: scroll، لذا لن يصعب علينا إنشاء شيفرة HTML. سأذكر في هذا المثال بعض الأماكن في أفريقيا: <ol id="scrolling-list"> <li><a href=#><img src="tunisia.jpg" alt>Tunisia</a> <li><a href=#><img src="botswana.jpg" alt>Botswana</a> <li><a href=#><img src="south-africa.jpg" alt>South Africa</a> <li><a href=#><img src="kenya.jpg" alt>Kenya</a> <li><a href=#><img src="nigeria.jpg" alt>Nigeria</a> <li><a href=#><img src="tanzania.jpg" alt>Tanzania</a> </ol> ستعرض شيفرة CSS التي سنكتبها القائمةَ بارتفاعٍ معيّن، الخاصية height نفسها لن تؤثر على طريقة العرض، فالقاعدة العامة هي أنَّ المحتوى سيُعرَض دومًا حتى لو تجاوز حدود العنصر الحاوي له. إذا أردنا أن نعكس هذا السلوك، فعلينا القيام بخطواتٍ معيّنة، وفي هذه الحالة، سنضبط الخاصية overflow-y: scroll لنتيح إمكانية التمرير داخل القائمة. لاحظ استخدامنا للكلمة المحجوزة currentcolor وغيرها من الاختصارات التي تجعل عملية التطوير أسهل. ol#scrolling-list { font-size: 0; background: #333; list-style-type: none; padding-left: 0; height: 230px; overflow-y: scroll; font-weight: 100; color: #999; } ol#scrolling-list li { border-bottom: 1px dashed; } ol#scrolling-list li a { font-size: 1.2rem; text-decoration: none; line-height: 2; color: currentcolor; display: block; transition: .4s background; } ol#scrolling-list li a img { width: 20%; vertical-align: top; margin-right: .5rem; } عملية تخصيص شريط التمرير أصبحت محدودة: ففي وقتٍ سابقٍ كان متصفحا Internet Explorer و Firefox يستعملان مُحدِّدات CSS ‏(CSS selectors) لفعل ذلك، لكنهما أهملا دعمها لاحقًا. ما يزال بإمكاننا تخصيص شريط التمرير في المتصفحات التي تعتمد على المحرك Webkit، بسلسلة من المُحدِّدات الخاصية بهذا النوع من المتصفحات (والتي تُشبه تلك التي نستعملها لتخصيص حقل range للإدخال): ol#scrolling-list::-webkit-scrollbar { background: #000; } ol#scrolling-list::-webkit-scrollbar-thumb { background-color: hsl(33,100%,50%); } في النهاية، سنُخصِّص حالة ‎:hover للروابط وسنُخصِّص حالة ‎:focus أيضًا بتجميعهما معًا وذلك لتوضيح ما هو الرابط الذي نُحدِّده عبر لوحة المفاتيح: ol#scrolling-list li a:hover, ol#scrolling-list li a:focus { background: #111; } تحسين قابلية الوصول باستخدام JavaScript بافتراض أنَّ لديك إمكانية كاملة للتنقل باستخدام لوحة المفاتيح في متصفحك (أسهل متصفح لتجربة ذلك هو Chrome، إذ تتطلب بقية المتصفحات أن تضبط بعض الخيارات أولًا) وستجد أنَّك إذا ضغطتَ على زر TAB فستنتقل بين الروابط في السلسلة، فبعد أن تصبح داخل السلسلة ستتمكن من الانتقال إلى الأمام (أي إلى الروابط التالية) باستخدام TAB أو إلى الخلف (أي إلى الروابط السابقة) باستخدام SHIFT+TAB، وتتحكم أزرار الأسهم بتمرير العنصر. لا يوجد شيءٌ خاطئٌ في ما سبق، لكن في بعض الحالات سترغب بالسماح للمستخدم باستعمال أزرار الأسهم لاختيار العناصر في القائمة بدلًا من التمرير. سنحتاج في البداية إلى تحديد بعض الكائنات باستخدام JavaScript: var locales = document.getElementById('scrolling-list'), listItems = locales.children, allLnks = new Array(); for (var i = 0;i<listItems.length;i++) { allLnks[i] = listItems[i].firstElementChild; } المتغير listItems يمثِّل العناصر المُشكِّلة للقائمة، بينما allLnks فهو مصفوفة للروابط الموجودة داخل عناصر القائمة. ولأننا وضعنا تلك العناصر داخل بعضها بعضًا فهذا سيجعل بقية السكربت معقدة قليلًا: locales.addEventListener('keydown', function(e) { var focusedElement = document.activeElement, index = allLnks.indexOf(focusedElement); if (index >= 0) { if (e.keyCode == 40 || e.keyCode == 39) { if (focusedElement.parentNode.nextElementSibling) { var nextNode = focusedElement.parentNode.nextElementSibling.firstElementChild; nextNode.focus(); } else { listItems[0].firstElementChild.focus(); } } if (e.keyCode == 38 || e.keyCode == 37) { if (focusedElement.parentNode.previousElementSibling) { var previousNode = focusedElement.parentNode.previousElementSibling.firstElementChild; previousNode.focus(); } else { locales.lastElementChild.firstElementChild.focus(); } } } }); أنشأنا دالةً لمعالجة الحدث keydown (الذي يُطلَق عندما يُضغَط على أحد الأزرار في لوحة المفاتيح) عندما يَحدُثُ داخل الكائن locales، لكننا نريد أن نُغيّر سلوك مفاتيح الأسهم إذا كان أحد عناصر القائمة مُركَّزًا عليه (focused)، وإلا فسنتحكّم بسلوك مفاتيح الأسهم من بداية تحمل الصفحة، وهذا ما سيمنع المستخدمين من التمرير في الصفحة باستخدامها. لفعل ذلك سنتحقق من العنصر المُركَّز عليه حاليًا (عبر document.activeElement) وسنرى إن كان يُطابِق أحد عناصر مصفوفة الروابط التي أنشأناها، فإن طابق أحدها فسنتحقق إن كان الزر المضغوط مساوٍ لرمز السهم السفلي أو الأيمن، فإن كان كذلك فسيتم التحقق من وجود عنصرٍ يلي العنصرَ الحالي، فإن وجد فسيتم نقل التركيز إلى العنصر التالي، وإلا فسيتم التركيز على أوّل عنصر في القائمة. الشيفرة الخاصة بتغيير سلوك السهم العلوي أو الأيسر مشابهة لما سبق، حيث سيُنقَل التركيز إلى العنصر الذي يسبق العنصر الحالي، وسيُنقَل التركيز إلى آخر رابط إن وصلنا إلى أعلى القائمة. الخلاصة إذا فكّرتَ قليلًا بالسكربت وخططت له، فيمكنك إنشاء شريط تنقل جميل وقابل للوصول، وذلك بتطبيق ما تعلمته هنا لكن مع بعض التحسينات. تأثير غروب الشمس باستخدام SVG (تجربة حية) الرسوميات التي تصوِّر الطبيعة مناسبةٌ جدًا لتأثيرات parallax، وعادةً تتحرك عناصر تلك الرسوميات شاقوليًا، وتستخدم عددًا هائلًا من صور PNG (التي لها شفافية) كطبقات. وخطر ببالي أنَّه يمكن توظيف رسومات SVG كبديل ممتاز لما سبق: حيث أنَّ حجم الصورة صغيرٌ جدًا، ويمكن إعادة تلوين عناصرها أو تحريكهم كلًا على حدة كما هو ظاهر في هذا المثال. بناء الهضبات مستوية السطح تتألف الصورة من سلسلة من الهضبات مستوية السطح التي هي مسارات مغلقة (closed paths)، باستثناء الشمس التي هي دائرة مُنشَأة بعنصر <circle>: <svg id="arizona" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 750 279"> <circle id="sun" fill="#FFF7EB" cx="655" cy="128" r="41.5"/> <path fill="hsl(32, 89%, 75%)" d="M750 ... "/> <path fill="hsl(31, 74%, 71%)" d="M745 ..." /> أنشأنا المسارات البعيدة أولًا، أي أنَّ أبعد هضبة ستُعرَّف في البداية، ثم تليها الأقرب فالأقرب. السماء والتدرجات بدلًا من إنشاء عنصر <rect> للسماء، فسيتم ملء خلفية عنصر <svg> باستخدام CSS: #arizona { background: hsl(47, 100%, 86%); } استخدام ألوان HSL (سواءً داخل شيفرات SVG أو عبر أنماط CSS) هو المفتاح الرئيسي لهذا التأثير، وذلك بتغير درجة السطوع (luminosity) لكل عنصر وذلك عند التمرير، وبذلك سنعطي انطباعًا بشروق أو غروب الشمس. الجزء الصعب هو استخراج قيمة HSL لكل عنصر، ولفعل ذلك سأستخدم التعابير النمطية (regular expressions) في JavaScript، هذه الشيفرة تُعرِّف التعبير النمطي الذي سنستخدمه مع جمع بعض المعلومات عن عنصر SVG: var regex = /hsl\((\d+),\s*([\d.]+)%,\s*([\d.]+)%\)/, arizona = document.getElementById("arizona"), mesaLayers = arizona.querySelectorAll("path"), SVGoffsettop = arizona.getBoundingClientRect().top, vertHeight = arizona.getBoundingClientRect().height, sun = document.getElementById("sun"); المتغير mesaLayers يضم جميع العناصر المُشكِّلة للهضبات معًا، وسيتم التعامل مع التمرير داخل دالة: function scrollHandler() { if (window.scrollY < vertHeight) { Array.prototype.forEach.call(mesaLayers, function(layer) { var layerFill = layer.getAttribute("fill"), vertRoll = Math.abs(window.scrollY - vertHeight) / vertHeight; hslComponents = layerFill.match(regex).slice(1), newLum = parseFloat(hslComponents[2]) * vertRoll; layer.style.fill = "hsl(" + hslComponents[0] +", " + hslComponents[1] + "%, " + newLum + "%)"; arizona.style.background = "hsl(48, " + 100 * vertRoll + "%, " + 88 * vertRoll + "%)"; sun.style.transform = "translate3d(0," + window.scrollY / 10 + "px, 0)"; }) } هذه الدالة تفعل ما يلي بالترتيب: الحصول على الخاصية fill لكل عنصر path تحديد مدى تمرير النافذة استخلاص قيمة HSL من كل عنصر path تعديل سطوع العنصر اعتمادًا على مقدار التمرير إعادة تجميع لون HSL لكل عنصر path الذي يضم السطوع الجديد، وتطبيقه على كل عنصر تعديل خاصية background لعنصر SVG، وأيضًا اعتمادًا على مقدار التمرير تمرير عنصر sun إلى الأسفل باستخدام translate3d لإنشاء تأثير الغروب ملاحظة: لا تعمل ميزة CSS transforms على عناصر SVG في متصفح Internet Explorer أو Edge بعد، على الرغم من أنَّ مفترض أن تدعم الإصدارات القادمة تلك الميزة. تُستدعى الدالة باستخدام requestAnimationFrame لتحسين الأداء: window.onscroll = function() { window.requestAnimationFrame(scrollHandler); } تبطيء التأثير قد تواجه إشكاليات عند ربط العناصر بالتمرير، فقد تتحول العناصر بسرعة كبيرة مما يجعلك تفقد شعورك بالتأثير… لذا فإنَّ أسهل طريقة لتبطيء التأثير هي استخدام مقياس للتمرير. غيّر الشيفرة السابقة لتصبح كما يلي: if (window.scrollY < SVGoffsettop * 4) { Array.prototype.forEach.call(mesaLayers, function(layer) { var layerFill = layer.getAttribute("fill"), vertRoll = Math.abs((window.scrollY / 4 ) - SVGoffsettop) / SVGoffsettop; … الخلاصة وأمور يمكن تحسينها عادةً يُستعمَل هذا التأثير بعد ضبط الخاصية position: fixed على عنصر SVG لإبقائه ظاهرًا أثناء تمرير الصفحة، إلا أنني لم أفعل ذلك هنا لأغراضٍ توضيحية. يمكن أيضًا دمج تأثير parallax معه عند التمرير، لكنني قررتُ أن أركِّز على تأثير غروب الشمس فقط. هنالك جانبان يمكن تطويرهما في السكربت: تكرار استخراج قيم ألوان HSL وتركيبها، فمن الأفضل جعل تلك القيم كخاصيات لكل عنصر لكي يتم الوصول إليها بسهولة عبر السكربت، بدلًا من إعادة حسابها كل مرة. ألوان خلفية السماء مكتوبة ضمن السكربت؛ ومن الأفضل إسناد الألوان باستخدام CSS، مما يجعل السكربت قادرًا على التعامل مع التغييرات في العرض دون الحاجة إلى تكرار التغييرات. إظهار فيديو في الخلفية (تجربة حية) نُشِرَت مقالة عن كيفية إنشاء فيديو في كامل خلفية الصفحة باستخدام HTML5 ، لكن أتت أسئلة على ذاك المقال للسؤال عن كيفية إنشاء فيديو يظهر خلف المحتوى، لكن يمكن تمريره كباقي محتويات الصفحة. فاجأني ذلك قليلًا، لأنَّ بالإمكان فعل ذلك باستخدام CSS مع نفس التقنيات التي نستعملها مع الصور… لكن أتتني الفرصة هنا لإعطاء مثال عن أنماط الاندماج (blend modes). الشيفرات تبدو شيفرة إضافة مقطع الفيديو تقليديةً، حيث سنضعها داخل وسم <main> (بدلًا من وضعها مباشرةً بعد العنصر <body> كما في المقالة الأصلية)، وسأفترض في هذا المثال أنَّ وسم video موجودٌ داخل العنصر <header> ضمن وسم <main>: <main> <header> <video autoplay loop> <source src="forest-fire.webm"> <source src="forest-fire.mp4"> </video> </header> ملاحظة: يجب أن يتبع الفيديو نفس القواعد العامة لمقاطع الفيديو التي تعمل في الخلفية الموجودة في المقالة الأصلية. يجب تنسيق الفيديو بأنماط CSS مماثلة لتلك التي كنتَ ستستعملها لعرض الصور المتجاوبة بكامل العرض: main { width: 80%; max-width: 750px; margin: 0 auto; } main > header video { width: 100%; height: auto; } ملاحظة: إذا أردتَ أن يظهر الفيديو بكامل عرض الشاشة، فبدِّل قيمة الخاصيتين width و max-width للعنصر main لتوسعته. يجب إضافة «طبقة» أمام مقطع الفيديو فيها ترويسة ورابط للانتقال إلى محتوى الصفحة. العناصر التالية يجب أن توضع بعد الوسم <video>: <h1>A world Aflame</h1> <a href="#maincontent">▼</a> </header> سيؤدي الضغط على الرابط إلى الانتقال إلى العنصر ذي المعرِّف maincontent. يجب أن نُعدِّل CSS الآن للسماح بإظهار العناصر الجديدة كطبقة تعلو مقطع الفيديو: main > header { position: relative; } أنماط CSS للترويسة <h1> وللرابط: main > header h1 { position: absolute; bottom: 40%; left: 1rem; font-size: 4rem; text-transform: uppercase; mix-blend-mode: overlay; } main > header a { display: block; text-decoration: none; font-size: 2rem; color: #fff; opacity: .5; position: absolute; bottom: 1.5rem; width: 100%; text-align: center; transition: .3s; animation: downwardprompt 2s 1s; } main > header a:hover { opacity: 1; } سيتم تطبيق تأثير حركي على السهم بعد عدِّة ثواني من تحميل الصفحة، مما يلفت انتباه المستخدم إليه: @keyframes downwardprompt { to { transform: translateY(2rem); opacity: 0; } } هذا كل ما في الأمر، بالطبع يمكنك القيام بالكثير باستخدام هذه التقنية، إلا أنَّ شيفرات CSS الأساسية ستبقى نفسها تقريبًا. صور متحركة بتأثير parallax باستخدام CSS 3D و JavaScript (تجربة حية) صحيحٌ أنَّ هنالك الكثير من الطرائق والتقنيات الموجودة على الويب لإنشاء تأثير parallax، لكنني أرى أنَّها تُزِّيف تأثير العمق في الصور، لكنني وجدتُ أنَّ تقنيةCSS 3D تسمح بتغيير مكان الصور على المحور z، مما يجعل تأثير تغيير المنظور حقيقيًا أثناء تحريك الصور إلى الأعلى وإلى الأسفل. وصحيحٌ أنَّ شيفرة هذا المثال ما تزال بدائيةً وبسيطةً، إلا أنَّني أرى أنها تستحق المشاركة. الشيفرات الأساسية هنالك شيفرة HTML بسيطة جدًا في هذا المثال، وهي عبارة عن عنصر <div> بسيط: <div id="parallax-container"> </div> سيُملأ هذا العنصر بالصور المُحمَّلة عبر شيفرة JavaScript، لكن علينا أولًا أن نضبط الأنماط اللازمة لعنصر <div> وللصور التي ستظهر داخله: #parallax-container { background: #16161d; margin: 0; overflow: hidden; perspective: 1200px; height: 100vh; width: 100vw; transform-style: preserve-3d; } #parallax-container img { transform-origin: center; box-shadow: 0 0 12px 12px rgba(0, 0, 0, 0.4); position: relative; } ملاحظة: إن لم تكن تألف التعامل مع واحدات vw و vh أو CSS 3D، فاقرأ المزيد عنها في هذه السلاسل. الصور المتحركة الخطوة التالية هي إضافة الصور، وتنسيقها باستخدام CSS، ثم جعل JavaScript تخفيها ثم تُجري عمليات عليها لتحقيق التأثير المطلوب. ولأنَّ أسماء ملفات الصور لها نفس النمط في هذا المثال (أي wave1.jpg و wave2.jpg …إلخ.) فيمكنني استخدام JavaScript لتوليد أسماء الملفات مع إنشاء بعض المتغيرات التي ستلزمنا لاحقًا في السكربت: var container = document.getElementById("parallax-container"), waveSrc = [], waves = [], imgLoc = "", j = 0; for (var i = 0; i < 10; i++) { waveSrc[i] = imgLoc+"wave"+(i+1)+".jpg"; } سنحتاج أيضًا إلى بعض الأرقام العشوائية، لذا سأولدها باستخدام هذه الدالة: function getRandomInRange(min, max) { return Math.floor(Math.random() * (max - min + 1)) + min; } سنحتاج أيضًا إلى مرجع (reference) إلى الصور التي جرى تحميلها، بالإضافة إلى عرض وارتفاع الشاشة الحالي (بافتراض أنَّ نافذة المتصفح مُكبَّرَة). var screenWidth = window.screen.width, screenHeight = window.screen.height; وعند اكتمال تحميل الصور وإضافتها إلى عنصر <div>، فسنوفِّر لها خاصيات –وهي ‎.xPlane و ‎.yPlane و ‎.zPlane– بقيمٍ عشوائية، والتي ستُحدِّد موضع الصورة في فضاءٍ ثلاثي الأبعاد. سأترك قيم الخاصية alt في هذا المثال فارغةً وذلك للاختصار: function preloadImage(filename){ var img=new Image(); img.onload = function(){ img.xPlane = getRandomInRange(-500, screenWidth - 500); img.yPlane = getRandomInRange(500, 1000); img.zPlane = getRandomInRange(300,2000); img.style = "transform: translate3d(" + img.xPlane +"px, " + img.yPlane + "px, -" + img.zPlane +"px)"; container.appendChild(img); }; imgLoc = ""; img.src= imgLoc + filename; img.alt = ""; waves[j] = img; j++; } function loadImages(){ for (var i = 0; i < waveSrc.length; ++i) { var filename = waveSrc[i]; preloadImage(filename); } } أخيرًا، ستُحرَّك الصور باستخدام دالة: function moveImages(){ waves.forEach(function(image) { image.yPlane = image.yPlane - 2; image.style.cssText = "transform: translate3d(" + image.xPlane+"px, " + image.yPlane+"px, -" + image.zPlane + "px); z-index: " + image.zIndex; }); window.requestAnimationFrame(moveImages); } وسيتم تشغيل المثال باستدعاء الدوال المناسبة في نهاية السكربت: loadImages(); window.addEventListener("load", function() { window.requestAnimationFrame(moveImages); }); تحسينات إضافية على المثال ما يزال هذا المثال مبدئيًا، وهنالك عدِّة أشياء يمكن إجراؤها لتطويره: 1. سيستمر تشغيل السكربت حتى بعد أن تختفي الصور من أعلى العنصر الحاوي لها، وستستمر بالحركة إلى اللانهاية؛ لذا من الأفضل أنَّ نُزيل الصور من بداية المصفوفة بعد اختفائها ثم إضافتها مرةً أخرى لتظهر مجددًا. 2. ربما من الأفضل أنَّ نُقلِّل من العشوائية في مواضع الصور، فالآن يمكن أن تظهر إحدى الصور خلف صورةٍ أخرى مباشرةً، أو قريبة منها كثيرًا في البُعد z (وبالتالي ستتحرك الصورتان بسرعةٍ قريبةٍ من بعضهما). ولفعل ذلك علينا أن نقارن أماكن الصور الجديدة بتلك التي أنشأناها من قبل في المصفوفة، وتوليد قيمة جديدة إن كانت القيمتان متقاربتين. 3. سيتم تحريك الصور تلقائيًا، إذا أردتَ أن تربط حركة الصور بتغيير شريط التمرير في الصفحة، فعليك أن تُغيّر موضع الصور بالنسبة إلى window.scrollY. ترجمة وبتصرّف للمقالات A Custom Scrolling Element With Keyboard Accessibility و Scrolling Background Video with Layered Content و A Scrolling SVG Sunset و Parallax Image Scrolling Animation with CSS 3D and JavaScript لصاحبها Dudley Storey
  2. أهلًا بك في هذه السلسلة التي تتحدث عن تأثيرات التمرير (Scrolling Effects)، سنستعرض في هذه السلسلة عددٌ من تأثيرات التمرير وسنشرح آلية عملها وسنجرِّبها عمليًا. يمكننا الاستفادة من الحدث scroll في JavaScript لإجراء تأثيرات عند تمرير صفحة الويب؛ لكن إن فعلنا ذلك دون إتقان فالنتيجة كارثية، أما إذا أحسنا صنعنا فيمكن لتأثيرات التمرير أن تبهر الزوار وتشعرهم أنَّ موقعك مميز. تحدثنا في المقالة السابقة عن التأثيرات الآتية: إخفاء صورة خلفية تدريجيًا عند التمرير توضيح الصورة عند التمرير تدوير العناصر عند التمرير تأثير اختلاف المظهر parallax أما المقالة الحالية (الثانية) فهي تتضمن التأثيرات الآتية: إظهار صورة الخلفية عند التمرير باستخدام CSS فقط تمرير سلس للصفحة تطبيق تأثير عدم الوضوح على المحتوى خلف شريط الانتقال وسنشرح في آخر مقالة طريقة إنشاء: عنصر قابل للتمرير مع إمكانية وصول مخصصة من لوحة المفاتيح تأثير غروب الشمس باستخدام SVG إظهار فيديو في الخلفية صور متحركة بتأثير parallax باستخدام CSS 3D و JavaScript سأقدِّم لك في بداية كل قسم رابطًا لتجربة المثال تجربةً حيةً على المتصفح. سيسهل عليك كثيرًا أن تفهم الشرح والشيفرات بعد تجربتك للتأثير. إظهار صورة الخلفية عند التمرير باستخدام CSS فقط (تجربة حية) طريقة عرض جميلة وشائعة هي «إظهار صورة الخلفية عند التمرير»: فكلما مَرَّرنا إلى الأسفل، فستصبح صورة الخلفية المخفية ظاهرةً للمستخدم. صحيحٌ أنَّ طريقة العرض هذه أصبحت شائعة في الآونة الأخيرة، إلا أنَّها جيدة حيث تجعل المحتوى مركَّزًا ومختصرًا إلى بضع صور وفقرات قصيرة من النص. يُحقَّق هذا التأثير عادةً باستخدام إطار عمل من إطارات JavaScript مع إحدى الإضافات؛ وهذا غير ضروري أبدًا في المتصفحات الحديثة، وسأريك طريقة فعل ذلك. «النوافذ والجدران» الفكرة الأساسية لهذا التأثير هي إنشاء سلسلة من «النوافذ» المفتوحة و«الجدران» المغلقة فوق بعضها بعضًا، وكلٌ منها له نفس الطول والعرض الخاص بإطار العرض (viewport). لنبدأ بإنشاء شيفرة HTML بسيطة. يمكن إنشاء «النوافذ» و«الجدران» من أيّ عنصر HTML قادر على احتواء العناصر الأخرى؛ وسنستخدم في هذا المثال وسوم <section>: <section> <h1>Come To Iceland</h1> </section> <section> <h1>The last settled part of Europe, much of Iceland remains pristine and untouched.</h1> </section> … لجعل قياس جميع العناصر صحيحًا، فسأحذف أيّة هوامش (margin) من العنصر <body>، تأكد أنَّ العناصر <section> مُقاسة عبر border-box، وتأكد أنَّ لكل عنصرٍ منها له نفس ارتفاع إطار العرض باستخدام واحدات vm. يجب تنسيق النص ليستخدم نفس الواحدات السابقة: body { margin: 0; } section { box-sizing: border-box; height: 100vh; text-align: center; padding: 2vw; font-size: 6vw; } عناصر <section> تأخذ كامل عرض نافذة المتصفح، ولتوسيط محتواها فسنستعمل flexbox، ويجب إجراء المثل على عناصر <section> التي ستعرض صور الخلفية، لذا سأُضمِّن أنماطها أيضًا: section { display: flex; align-items: center; justify-content: center; text-align: center; flex-direction: column; background-size: cover; background-repeat: no-repeat; background-attachment: fixed; } تُستخدم الخاصية flex-direction لإغلاق أيّة «نوافذ» التي تحتوي عدِّة أسطر نصية. ويجب علينا إضافة نمط خاص بأوّل عنصر <section> لأنَّ النص فيه أكبر، ولونه أبيض، ومكتوبٌ بأحرفٍ كبيرة، مع استخدام الخاصية text-shadow لإضافة ظل لتميزه عن الخلفية: section:first-of-type { text-transform: uppercase; color: #fff; font-size: 8vw; text-shadow: 0 0 5px rgba(0,0,0,0.4); } عناصر <section> الزوجية لها خلفية بيضاء: section:nth-of-type(even) { background: #fff; } أما عناصر <section> الفردية فلها صور خلفية: section:nth-of-type(1) { background-image: url(iceland-fjords.jpg); } section:nth-of-type(3) { background-image: url(iceland-pool-faces.jpg); } section:nth-of-type(5) { background-image: url(iceland-ice.jpg); } وهذا كل ما في الأمر! صحيحٌ أنَّ المثال السابق يعمل على المتصفحات الحديثة فقط والتي تدعم vh و vm و flexbox؛ وإذا كنتَ تنوي دعم المتصفحات القديمة فعليك استخدام بدائل مثل نمط العرض table-row لكل عنصر <section> … تمرير سلس للصفحة (تجربة حية) تتواجد في HTML ميزة الانتقال إلى أماكن معيّن في الصفحة، وذلك بتوفير خاصية id للعنصر الذي تريد الانتقال إليه، ومن ثم ربط ذلك عبر عناصر <a>. لكن الحركة غير سلسة وستنتقل فوريًا إلى العنصر الهدف؛ ولكن بغرض تحسين طريقة عرض واستخدام الموقع، فيتطلّب أحيانًا تصميم الموقع أن يتم التمرير بشكلٍ سلسٍ أو بطيء إلى نقطةٍ معيّنةٍ في الصفحة. قديمًا كانت تُستعمَل jQuery لذلك، لكن من غير المعقول تحميل إطار عمل كامل لاستخدام هذه الميزة فقط؛ وتوفِّر JavaScript طريقةً أفضل وأسرع (من ناحية الأداء) وهي الدالة window.scrollTo. سنستخدم عنصر <a> كأساس لهذه التقنية، وبهذه الطريقة سيتم الانتقال إلى الهدف حتى لو لم تعمل شيفرة التمرير السلس لسببٍ من الأسباب. <a href="#destination">Click me: I’m <em>smoooooth</em>.</a> … <p id="destination">This is the target, further down the page. وكما هو واضح، يجب أن تكون الصفحة طويلةً بعض الشيء وتمتد إلى ما بعد أسفل إطار العرض لكي تعمل هذه التقنية، لأنَّه إذا عُرِضَت كامل محتويات الصفحة في نافذة المتصفح، فلا حاجة إلى التمرير من الأساس؛ ولهذا السبب عليك أن تضع الكثير من المحتوى في الصفحة للتجربة. طريقتان للتمرير بسلاسة قد يبدو الأمر مربكًا بعض الشيء، إلا أنَّ البنية البرمجية للتمرير السلس موجودة في CSS وفي JavaScript، وأنَّ بعض المتصفحات تدعم تلك البنية البرمجية والأخرى لا تدعمها (انظر فقرة «دعم المتصفحات» في الأسفل). ففي CSS إذا أردنا أنَّ يكون التمرير سلسًا لأحد العناصر (وعادةً ما نستخدم العنصر body لكن ذلك ليس ضروريًا) فعلينا أن نضبط الخاصية scroll-behavior ونسند القيمة smooth إليها: body { scroll-behavior: smooth; } لاحظ أنَّ كلمة «behavior» (في scroll-behavior) لا تحتوي على حرف «u». طريقة JavaScript سنضيف شيفرة JavaScript إلى نهاية الصفحة لكي تُنفَّذ بعد انتهاء تحميل الصفحة: var anchorLink = document.querySelector("a[href='#destination']"), target = document.getElementById("destination"); anchorLink.addEventListener("click", function(e) { if (window.scrollTo) { e.preventDefault(); window.scrollTo({"behavior": "smooth", "top": target.offsetTop}); } }) الدالة querySelector تستعمل نفس طريقة كتابة محدِّدات CSS للعثور على أوّل رابط الذي يشير إلى ‎#destination؛ والضغط على هذا الرابط سيؤدي إلى تنفيذ عبارة شرطية للتأكد من دعم المتصفح للدالة scrollTo، فإن دعمها المتصفح فستوقف الدالة e.preventDefault المتصفحَ من الانتقال مباشرةً إلى الفقرة الهدف، وسنستخدم الدالة scrollTo بدلًا من ذلك بعد ضبطها ليكون التمرير سلسًا. تأخذ الدالة scrollTo وسيطين هما behavior و top، مع وسيطٍ اختياريٍ هوleft، ويقبل آخر وسطين إحداثيات المكان الذي نريد الانتقال إليه. يمكن استخدام الدالةwindow.scrollفي المثال السابق، لأنَّ وظيفتها مماثلة لوظيفة الدالةwindow.scrollTo`. مقارنةً مع استخدام إطار عمل، فإنَّ هذه الطريقة أبسط بكثير؛ لكن الجانب السلبي لها هو أنَّها لا تسمح للمصمم بتغيير دالة التوقيت أو حركات التمرير، لتجنّب استعمال المصممين استعمالًا سلبيًا لها. إنشاء سكربت عام السكربت السابق يعمل عمله بشكلٍ صحيح، لكنه يتطلب أن تعرف ما هو اسم العنصر الهدف، ولا يمكن تطبيقه إلا على رابطٍ وحيد. ماذا إذا أردت إنشاء سلسلة من الروابط التي تُشير إلى عناصر مختلفة؟ سنحتاج في هذه الحالة إلى جعل السكربت عامًا. سنبدأ السكربت بإنشاء دالة التي تسمح لنا بمعالجة كل رابط بحلقة forEach: var forEach = function (array, callback, scope) { for (var i = 0; i < array.length; i++) { callback.call(scope, i, array[i]); } }; ثم سأُحدِّد جميع الروابط، وأرى ما هو العنصر التي تشير إليه، ومن ثم سأطبِّق scrollTo عند النقر عليها: var anchorLinks = document.querySelectorAll("a[href^='#']"); if (window.scrollTo) { forEach(anchorLinks, function(index, element) { var target = document.getElementById(element.getAttribute("href").substring(1)); element.addEventListener("click", function(el) { el.preventDefault(); window.scrollTo(0, target.offsetTop); }) }); } لاحظ أنَّ هذا قد يتطلب وضع الخاصية scroll-behavior لعنصر body كما سبق ذكره. دعم المتصفحات هنالك إشكالية وحيدة عند استخدام هذه الطريقة في الوقت الراهن ألا وهي دعم المتصفحات؛ حيث تعمل الدالة window.scrollTo في متصفحات الويب الحديثة. ولأننا كتبنا السكربت بطريقة تجعله يتحقق أولًا من دعم المتصفح للدالة scrollTo، فستعمل الصفحة بشكل سليم على المتصفحات القديمة إلا أنَّ التمرير سيكون فوريًا وليس سلسًا؛ ويمكنك أن تستعمل إحدى الإضافات أو الطرائق الأخرى لدعم المتصفحات القديمة. تطبيق تأثير عدم الوضوح على المحتوى خلف شريط الانتقال (تجربة حية) أحد أنماط تصميم الواجهات الشائعة خصوصًا بعد إصدار نسخة iOS 7 هو شريط الانتقال الذي تظهر محتويات الصفحة التي خلفه مشوشةً؛ ربما تظن أنَّ تطبيق المُرشِّح blur في CSS هو الطريقة السهلة والواضحة لتطبيق هذا التأثير في صفحة ويب، وهذا صحيحٌ إلا أنَّ هنالك إشكالية: تأثيرات CSS ستُطبَّق على المحتوى داخل العنصر وليس خلفه. أي لا يوجد تأثير من تأثيرات CSS الذي يمكن أن يؤدي إلى تشويش العناصر خلفه، باستثناء خاصية اختبارية متوافرة في متصفح Safari 9 فقط باسم ‎-webkit-backdrop-filter-؛ لكن بالطبع سنجد حلًا! إنشاء شريط الانتقال الشريط نفسه هو عنصرٌ فارغٌ يملك القيمة fixed للخاصية position، وعناصر التنقل تأتي «فوق» ذاك العنصر باستعمال نفس الأبعاد. سأكتبُ ذلك باستخدامSass لأنَّها أقصر: #blurrycontent { padding: 1rem; top: 0; left: 0; width: 100%; height: 5rem; overflow: hidden; position: fixed; filter: blur(4px); } nav { @extend #blurrycontent; filter: none; text-align: right; } يجب أن تتواجد بقية الصفحة داخل العنصر <main>، وليس داخل العنصر <body>، وذلك لأسبابٍ سنوضِّحها بعد لحظات: <main id="content"> <h1>London</h1> <p>With roots at least 7,000 years old, London is an accretion of artifacts old and new, from the remnants of wooden Neolithic settlements buried in the mud of the Thames to gleaming 21st century spires of glass and steel… </main> ولأنَّ العنصرين ‎#blurrycontent و <nav> متموضعَين فوق بعضهما في مكانٍ ثابتٍ في أعلى الشاشة، فيجب تنسيق العنصر <main> لكي يأخذ مكان بقية المحتوى: main { margin: 0; background: url(london_background.jpg); background-size: cover; padding: 2rem; } حسنًا، تبدو الصفحة جيدةً، لكننا لم نرَ أيّة تأثيرات في منطقة شريط التنقل عندما يتم التمرير؛ وهذا ما سنفعله في الخطوة الآتية. إنشاء تأثير «الزجاج»! كما ذكرتُ في البداية، لا تُطبّق تأثيرات CSS إلا على المحتوى الموجود داخل العنصر، وليس تحته؛ لذا سنأخذ نسخةً من العنصر <main> ونضعها داخل العنصر ‎#blurrycontent باستخدام الدالة cloneNode عبر سكربت موجود في أسفل الصفحة: var pageContent = document.getElementById("content"), pagecopy = pageContent.cloneNode(true), blurryContent = document.getElementById("blurrycontent"); blurryContent.appendChild(pagecopy); قد لا تستطيع ملاحظة التأثير في هذه المرحلة، لأنَّ المحتوى الموجود داخل العنصر ‎#blurrycontent لن يُمرَّر مع بقية المستند، وعلينا مزامنة حركتهما بإضافة السطر الآتي إلى السكربت: window.onscroll = function() { blurryContent.scrollTop = window.pageYOffset; } بعد أن ربطناهما مع بعضهما بعضًا، فيمكننا أن نُمرِّر الصفحة وسنحصل على نفس المحتوى الموجود تحت شريط التنقل في عنصر ‎#blurrycontent لكنه مشوش. ولأنَّ العنصر <nav> غير موجود داخل العنصر ‎#blurrycontent فلن يخضع لتأثير عدم الوضوح. محدوديات هذه الطريقة كما هو واضح، إنشاء نسخة من محتوى الصفحة وتطبيق تأثير عدم الوضوح عليها سيؤدي إلى عبءٍ إضافيٍ على المتصفح وعلى المعالج الرسومي، لذا كن حذرًا في ذلك وقدِّر كمية المحتوى الموجود ضمن العنصر <main> قبل نسخه. الدالة cloneNode تنسخ العنصر نسخًا حيًا، أي أنَّ أيّة تعديلات على العنصر الأصلي ستُطبَّق أيضًا على العنصر المنسوخ، لكن ربما تلاحظ تأثيرًا بسيطًا حتى تتم مزامنة كلا النسختين. هذه أربع نقاط أخيرة يجب ملاحظتها: لأنَّ بعض إصدارات متصفح Internet Explorer لا تدعم تأثيرات CSS (وأوقف المتصفح دعم النسخة الخاصة به من هذا التأثير، والتي كانت متاحةً في الإصدارات القديمة منه)، فلن تلاحظ أيّة تغييرات في شريط التنقل في متصفح IE. يجب أن تتجنب استخدام العناصر ذات الموضع الثابت (fixed) في صفحات الويب على الهواتف الذكية والأجهزة اللوحية، فمنذ فترةٍ قريبةٍ كانت طريقة تعامل متصفحات الهواتف مع position: fixed سيئةً، وسيتم حجز مساحة من الشاشة الصغيرة. وصحيحٌ أنَّ هذا التأثير مستوحى من أحد أنظمة الهواتف، ألا أنَّه من الأفضل إيقافه في الشاشات الصغيرة باستخدام مجموعة من media queries (أو يمكنك أن تصمم الموقع للهواتف أولًا [mobile-first] ولا تُشغِّل التأثير حتى تصبح الشاشة بمقاسٍ معيّن). يجب أخذ قابلية الوصول (Accessibility) بعين الاعتبار عند إنشاء مثل هذا التأثير، فستُفسِّر قارئات الشاشة شجرة DOM، وليس ما تراه على الشاشة، وهذا يعني أنَّ قارئات الشاشة ستحصل على نسختين من محتوى الصفحة افتراضيًا، ولتنجب ذلك فسأضع aria-hidden="true"‎ في العنصر ‎#blurrycontent: <div id="blurrycontent" aria-hidden="true"></div> وبهذا سترى قارئات الشاشة النسخةَ الأصلية من الصفحة فقط دونًا عن النسخة الموجودة في العنصر ‎#blurrycontent. يجب أن تكون حذرًا عند نسخ العناصر التي لها الخاصية id، فقد يؤدي تكرار قيم الخاصية id إلى تضاربات ومشاكل في CSS و JavaScript. ترجمة وبتصرّف للمقالات Background Reveal Scroll In Pure CSSو Smooth Page Scroll in 5 Lines of JavaScript و Scroll-Behind Blurred Site Navigation Barلصاحبها Dudley Storey
  3. code { font-size: 1rem !important; }تجعل jQuery إضافة التأثيرات الحركيّة على الصّفحة أمرًا سهلًا للغاية، ويمكن لهذه التأثيرات أن تعتمد الإعدادات المبدئيّة أو إعدادات يُعيّنها المُطوّر. بإمكانك أيضًا إنشاء حركاتٍ مُخصّصة من خصائص CSS عشوائيّة. اطّلع على وثائق التأثيرات لتفاصيل أكثر عن تأثيرات jQuery. ملاحظة مهمّة عن الحركات: يكون إنجاز الحركات باستخدام CSS بدل JavaScript أكثر كفاءةً في المُتصفّحات الحديثة، وخصوصًا في الأجهزة المحمولة. تفاصيل إنجاز هذه الحركات خارجةٌ عن نطاق السّلسلة، ولكن إن كنت تستهدف المُتصفّحات والأجهزة المحمولة الّتي تدعم حركات CSS، فقد ترغب بتعيين الإعداد jQuery.fx.off إلى القيمة true على الأجهزة ذات المواصفات الضّعيفة؛ فهذا من شأنه إبطال الحركات والوصول بالعنصر المطلوب تحريكه إلى حالته النّهائية مباشرةً دون تطبيق الحركة. التأثيرات المُرفقة مع jQueryتُرفَق الحركات المُستخدم بكثرة مع jQuery كوظائف يمكنك استدعاؤها على أي كائن jQuery: ‏‎.show()‎: أظهر العناصر المُحدّدة.‏‎.hide()‎: أخفِ العناصر المُحدّدة.‏‎.fadeIn()‎: حرّك ظلاليّة العناصر (opacity) المُحدّدة إلى 100%.‏‎.fadeOut()‎: حرّك ظلاليّة العناصر المُحدّدة إلى 0%.‏‎.slideDown()‎: أظهر العناصر المُحدّدة بحركة سحب شاقوليّة.‏‎.slideUp()‎: أخفِ العناصر المُحدّدة بحركة سحب شاقوليّة.‏‎.slideToggle()‎: أخفِ العناصر المُحدّدة أو أظهرها بحركة سحبٍ شاقوليّة، اعتمادًا على كون العناصر المُحدّدة مخفيّة أو ظاهرة.يسهل تطبيق إحدى هذه التأثيرات على التّحديد بعد إنشائه: $( '.hidden' ).show();جرّب المثال في ساحة التّجربة (تأكد من ضغط الزرّ Run with JS في هذ المثال وكلّ الأمثلة التّالية) بإمكانك أيضًا تحديدُ مدّة للتأثيرات السّابقة، وهناك طريقتان لتحديدها، الأولى: تعيين الوقت بالميللي ثانيّة: $( '.hidden' ).show( 300 );جرّب المثال في ساحة التّجربة والثّانية استخدام إحدى السُرعات المُعرّفة مُسبقًا: $( '.hidden' ).show( 'slow' );جرّب المثال في ساحة التّجربة عُرِّفت هذه السُرعات في الكائن jQuert.fx.speeds؛ ممّا يعني أنّ بإمكانك تعديله لتغيير القيم المبدئيّة، أو إضافة سُرعات جديدة إليه: // أعد تعيين سرعةٍ مُعرّفة jQuery.fx.speeds.fast = 50; // عرّف سرعة جديدة jQuery.fx.speeds.turtle = 3000; // بما أنّنا غيّر قيمة السّرعة `fast`، فإنّ هذه الحركة ستستغرق 50 ميللي ثانية $( '.hidden' ).hide( 'fast' ); // بإمكاننا استخدام السّرعات الّتي عرفناها بأنفسنا تمامًا كتلك المُعرّفة مسبقًا $( '.other-hidden' ).show( 'turtle' );كثيرًا ما يرغب المُطوّر بفعل شيءٍ ما بعد انتهاء الحركة مباشرةً، فإن حاول فعله قبل انتهاء الحركة، فقد يسبّب تشوّه الحركة وتقطّعها، أو قد يحذف سهوًا عناصر تتحرّك في لحظة حركتها. بإمكانك تمرير استدعاء راجع (callback) إلى وظائف الحركة إن رغبت بتنفيذ أمرٍ ما بعد انتهاء التأثير، وتُشير this داخل هذا الاستدعاء إلى عنصر DOM الخام الّذي طُبقّت عليه الحركة، ومثلها ومثل دوالّ تولّي الأحداث، يمكن إحاطة this بالوظيفة ‎$()‎ لاستخدامها ككائن jQuery: $( 'p.old' ).fadeOut( 300, function() { $( this ).remove(); });جرّب المثال في ساحة التّجربة إن لم يحوِ التّحديد أيّة عناصر، فلن تُستدعى الدّالة. إن احتجت إلى استدعاء الدّالة بصرف النّظر عن وجود العناصر أو غيابها في التّحديد، بإمكانك إنشاء دالّة تتعامل مع الحالتين: var oldElements = $( 'p.old' ); var thingToAnimate = $( '#nonexistent' ); // هذه الدّالة ستكون الاستدعاء الرّاجع للوظيفة `show` في حال وجود عناصر نريد إظهارها، فإن لم توجد أيّة عناصر، فإنّنا نستدعيها مباشرةً بأنفسنا. var removeOldElements = function() { oldElements.remove(); }; if ( thingToAnimate.length ) { // ستُستدعى وظيفتنا بعد انتهاء الحركة thingToAnimate.show( 'slow', removeOldElements ); } else { removeOldElements(); }جرّب المثال في ساحة التّجربة تأثيرات مُخصّصة باستخدام ‎.animate()‎إن لم تُلبِّ الحركات المُرفقة مع jQuery حاجتك، فبإمكانك استخدام الوظيفة ‎.animate()‎ لإنشاء حركات مخصّصة قائمة على خصائص CSS مُتعدّدة (إحدى الاستثناءات: الخاصّ' color الّتي لا يمكن تحريكها، ولكن تتوفّر إضافة تسمح بذلك). تقبل الوظيفة ‎.animate()‎ ثلاثة مُعاملات على الأكثر: كائن يُحدّد الخصائص الّتي يُراد تحريكهامدّة الحركة، مُقدّرة بالميللي ثانيةدالّة تُستدعى عند انتهاء الحركةيمكن أن تُعيّن قيمة الحركة بكتابة القيمة النّهائيّة المُراد التّحريك إليها، أو كتابة المقدار الّذي يجب تحريكه (الفرق بين موضعي الحركة): $( '.funtimes' ).animate({ left: '+=50', // زد بمقدار 50 opacity: 0.25, fontSize: '12px' }, 300, function() { // تنفّذ عند انتهاء الحركة } );جرّب المثال في ساحة التّجربة ملاحظة: إن أردت تحريك خاصّة CSS يحوي اسمها على الإشارة "-"، فعليك تحويل الاسم إلى صيغة camelCase أوّلًا إن لم تشأ إحاطة اسم الخاصّة بعلامات اقتباس، فمثلًا الخاصّة font-size تُصبح fontSize. إدارة الحركاتتُوفّر jQuery وظيفتين مُهمّتين لإدارة الحركات: ‏‎.stop()‎: تُوقف الحركات الجارية على العناصر المُحدّدة.‏‎.delay()‎: تُؤخِّر بدء الحركة القادمة بالمقدار الذي يُمرّر إليها (بالميللي ثانية).تُوفّر jQuery أيضًا وظائف لإدارة تعاقب الحركات وتنظيمها في "طوابير"، وإنشاء طوابير مُخصّة، وإضافة دوالّ مُخصّصة إلى هذه الطّوابير. مناقشة هذه الوظائف موضوع أكبر من هذه السّلسلة، ولكن قد ترغب بالاطّلاع عليها في وثائق jQuery. ترجمة (بشيء من التصرف) للجزء الخامس من سلسلة  jQuery Fundamentals لمؤلّفتها Rebecca Murphey.
×
×
  • أضف...