ساخت انیمیشن با جاوا اسکریپت – آموزش از صفر تا صد
![ساخت انیمیشن با جاوا اسکریپت – آموزش از صفر تا صد](https://blog.faradars.org/wp-content/webp-express/webp-images/doc-root/wp-content/uploads/2023/12/js-animations-1-1.jpeg.webp)
جاوا اسکریپت به عنوان یکی از سنگ بناهای توسعه وب امروزی قابلیتهای بسیار فراوان و گستردهای دارد و میتوان این زبان را در زمره یکی از جذابترین و در عین حال پرکاربردترین زبانهای برنامه نویسی دنیا قرار دارد. یکی از قابلیتهای جذابی که با این زبان امکانپذیر است، قابلیت ساخت انیمیشن است که در این مطلب از «مجله فرادرس» قصد داریم مفاهیم پایه و مقدماتی ساخت انیمیشن با جاوا اسکریپت را مورد بررسی قرار دهیم. در مطلب پیشِ رو قرار است که در کنار بحث در مورد ساخت انیمیشن با جاوا اسکریپت و روشهای ایجاد انیمیشنهای تعاملی، به پیادهسازی مثالهای عملی و جذابی بپردازیم. کاربران پس از خواندن این مطلب درک مطلوبی از ساخت انیمیشن با JavaScript بهدست خواهند آورد و میتوانند به عنوان نوعی تمرین جاوا اسکریپت به پیادهسازی انواع انیمیشنها بپردازند.
دلایل ساخت انیمیشن با جاوا اسکریپت چیست؟
انتخاب جاوا اسکریپت برای امور انیمیشنسازی مزیت متمایزی نسبت به ساخت انیمیشن با CSS و سایر فناوریهای وب دارد. ساخت انیمیشن با جاوا اسکریپت آزادی و کنترل عمل بیشتری را در مقایسه با انیمیشنهای CSS به ارمغان میآورد.
در حالی که CSS با اجازه دادن به کاربر در تنظیم نقاط شروع و پایان انیمیشن و همچنین برخی از مراحل میانی، کارها را ساده میکند اما کار واقعی و انتقال بین حالتهای انیمیشن در این مراحل بهوسیله مرورگر مدیریت میشود. اتکا به مرورگر برای انجام این کار محدودیتهای زیادی دارد زیرا کاربر باید در نوشتن دستورالعملهای خود بسیار دقیق باشد که این محدودیت به خصوص برای انیمیشنهای پیچیدهتر خودش را بهخوبی نشان میدهد. تصاویر زیر نحوه ساخت انیمیشن با CSS را نشان میدهد:
![تصویری از نحوه ساخت انیمیشن با سی اس اس](https://blog.faradars.org/wp-content/uploads/2023/12/start_end_blue.png)
اگر انیمیشن دارای فریمهای کلیدی باشد ممکن است به چندین حالت میانی نیاز باشد، مانند تصویر زیر:
![تصویری از ساخت انیمیشن با سی اس اس دارای چندین حالت میانی](https://blog.faradars.org/wp-content/uploads/2023/12/start_intermediate_blue.png)
دو تصویر بالا در اصل نوعی انیمیشن نیستند و برای تبدیل تصاویر بالا به انیمیشن نیاز به درونیابی بین نقاط و اتصال آنها است که این کار به وسیله مرورگر انجام خواهد شد. تصویر زیر بیانگر این مفهوم است:
![درونیابی بین نقاط با مرورگر برای ساخت انیمیشن](https://blog.faradars.org/wp-content/uploads/2023/12/animation_ready_2.png)
برای ساخت انیمیشن، جاوا اسکریپت به کاربر کنترل عملی بیشتری بر هر جنبه از انیمیشن میدهد. این بدان معنی است که کاربر میتواند طیف گستردهای از انیمیشنها را بدون نگرانی در مورد چالشهای فنی ایجاد کند. به عنوان مثال ساخت انیمیشن بارش برف بدون استفاده از جاوا اسکریپت در مرورگرهای وب تقریباً غیرممکن است. در ادامه این آموزش، پیچیدگیهای انیمیشنسازی با جاوا اسکریپت را بررسی خواهیم کرد.
حلقه انیمیشن در جاوا اسکریپت چیست؟
یکی از تفاوتهای فنی کلیدی بین انیمیشنهای CSS و جاوا اسکریپت، «حلقه انیمیشن» (Animation Loop) است. این حلقه تابعی محسوب میشود که در فواصل زمانی منظم، معمولاً ۶۰ بار در ثانیه اجرا شده و حاوی کدی است که مسئول تنظیم و تغییر مقادیر ویژگیهایی است که انیمیشن را تعریف میکند. برای درک بهتر این مفهوم مثالی ذکر خواهیم کرد. در مثال فرضی ما، دایره آبی ثابتی موجود است که اگر کاربر روی دکمه فرضی «Move» که برای آن تعریفشده است، کلیک کند دایره در صفحه به سمت راست حرکت خواهد کرد.
![یک انیمیشن ساخته شده با جاوا اسکریپت که با زدن دکمه خاصی دایره در آن حرکت میکند](https://blog.faradars.org/wp-content/uploads/2023/12/js-anomations.gif)
هر بار با کلیک روی دکمه، دایره کمی به سمت راست به حرکت خود ادامه میدهد. هر سریعتر دکمه زده شود، حرکت دایره نیز سریعتر خواهد بود. با زدن کلید Move به صورت مکرر، دایره آبیرنگ از صفحه محو میشود و دوباره از سمت چپ در صفحه ظاهر خواهد شد. این حلقه پیوسته از انیمیشن چیزی است که به ما کنترل و انعطافپذیری در ایجاد حرکات پویا و جذاب میدهد. قطعه کد انیمیشن فرضی ما به صورت زیر است:
1<!DOCTYPE html>
2<html>
3
4<head>
5 <meta charset="utf-8">
6 <title>Animating in Code!</title>
7 <style>
8 body {
9 background-color: #FFF;
10 margin: 30px;
11 margin-top: 10px;
12 display: flex;
13 align-items: center;
14 justify-content: center;
15 flex-direction: column;
16 }
17
18 #contentContainer {
19 width: 550px;
20 height: 350px;
21 border: 5px black solid;
22 overflow: hidden;
23 background-color: #DFF2FF;
24 display: flex;
25 align-items: center;
26 }
27
28 #circle {
29 width: 200px;
30 height: 200px;
31 background-color: #20A6FF;
32 border-radius: 50%;
33 }
34
35 #move {
36 background-color: gold;
37 margin-top: 20px;
38 font-size: 16px;
39 font-weight: bold;
40 border: 5px solid #333;
41 outline: none;
42 }
43 #move:hover {
44 background-color: coral;
45 }
46 #move:active {
47 background-color: yellowgreen;
48 }
49 </style>
50</head>
51
52<body>
53 <div id="contentContainer">
54 <div id="circle"></div>
55 </div>
56
57 <input id="move" type="button" value="move"></input>
58
59 <script>
60 var circle = document.querySelector("#circle");
61
62 var button = document.querySelector("#move");
63 button.addEventListener("click", animate, false);
64
65 var xPos = 0;
66
67 function animate() {
68 xPos += 10;
69
70 circle.style.transform = `translate3d(${xPos}px, 0, 0)`;
71
72 if (Math.abs(xPos) >= 900) {
73 xPos = -500;
74 }
75 }
76 </script>
77</body>
78
79</html>
برای تعامل فعال با کدهای این مثال روی کامپیوتر شخصی خود و آزمایش آن، کار خود را با ساخت نوعی سند جدید HTML شروع خواهیم کرد و کل قطعه کد ارائهشده در بالا را کپی کرده و در سند جایگذاری میکنیم. سپس فایل را با نامی دلخواه ذخیره کرده و آن را در مرورگر وب دلخواه خود بازخواهیم کرد. پس از بارگیری، شاهد همان مثال قبلی خواهید بود که اکنون به صورت محلی در کامپیوتر ما اجرا میشود. این رویکرد عملی به کاربر امکان میدهد مفاهیم انیمیشن را به طور مستقیم کشف کرده و کد را مطابق با ترجیحات خود تنظیم کند. خروجی انیمیشن در مروگر به صوت محلی به صورت زیر است:
![تصویری از یک انمیشن ساخته شده با جاوا اسکریپت](https://blog.faradars.org/wp-content/uploads/2023/12/js-anomations1.png)
حال مثال فوق از ساخت انیمیشن با جاوا اسکریپت را با جزئیات دقیقتری مورد بررسی قرار میدهیم. تمرین جاوا اسکریپت بالا علاوه بر اینکه نوعی پروژه جذاب است، به عنوان آزمونی عملی از دانش پایه در HTML ،CSS و جاوا اسکریپت نیز عمل میکند. در مثال بالا، حرکت دایره با فراخوانی تابع animateهر زمان که دکمه moveرویداد کلیک را ثبت میکند، آغاز میشود که قطعه کد زیر برای انجام این کار است:
1var button = document.querySelector("#move");
2button.addEventListener("click", animate, false);
حال کدهای خود تابع animateبه صورت زیر است:
1var xPos = 0;
2
3function animate() {
4 xPos += 10;
5
6 circle.style.transform = `translate3d(${xPos}px, 0, 0)`;
7
8 if (Math.abs(xPos) >= 900) {
9 xPos = -500;
10 }
11}
در کد بالا xPosروی صفر تنظیم شده است و با هر تماس برای متحرکسازی، مقدار آن ۱۰ واحد افزایش خواهد یافت. این افزایش، به لطف ویژگی transform، دایره را به سمت راست حرکت میدهد که کد زیر برای انجام این عمل است:
1circle.style.transform = `translate3d(${xPos}px, 0, 0)`;
وقتی xPosبهاندازهای بزرگ شد که دایره در سمت راست ناپدید شود، xPosبه -500بازنشانی خواهد شد، طبق قطعه کد زیر:
1if (Math.abs(xPos) >= 900) {
2 xPos = -500;
3}
کد بالا باعث میشود که دایره دوباره با کلیکهای متوالی روی دکمه حرکت از سمت چپ ظاهر شود. تا به اینجا همهچیز واضح و روشن است.
چیزی که الان داریم در اصل انیمیشن نیست. با کلیک بر روی دکمه move، تابع animateفعال میشود و هر بار دایره چند پیکسل به سمت راست حرکت میکند. برای اینکه دایره به صورت خودکار حرکت کند، به حلقه انیمیشن نیاز است. این حلقه انیمیشن شامل فراخوانی تابع animateبه طور مکرر در فواصل زمانی منظم است. ساخت حلقه انیمیشن به وسیله تابع requestAnimationFrameتسهیل میشود. حال کد بهروز شده در این مرحله از ساخت انیمیشن با جاوا اسکریپت به صورت زیر است:
1var circle = document.querySelector("#circle");
2
3var xPos = 0;
4
5function animate() {
6 xPos += 10;
7
8 circle.style.transform = `translate3d(${xPos}px, 0, 0)`;
9
10 if (Math.abs(xPos) >= 900) {
11 xPos = -500;
12 }
13
14 requestAnimationFrame(animate);
15}
16animate();
کد بهروز شده دو تغییر کلیدی با کد اولیه دارد:
- در کد جدید به صراحت تابع animateفراخوانی شده تا به صورت خودکار اجرا شود و این قابلیت نیاز به کلیک بر روی دکمه moveرا از بین میبرد.
- در پایان تابع animate، از requestAnimationFrameبرای فراخوانی تابع animateدر هر بازه تجدید فریم استفاده شده و حلقه انیمیشن ایجاد شده است.
علاوه بر این، ما در این مثال کدهای مرتبط با دکمه حرکت را حذف میکنیم زیرا دیگر به آنها نیازی نیست ولی با این حال این کار اختیاری است. خروجی کلی انیمیشن ساخته شده با جاوا اسکریپت این بار به صورت زیر است:
![یک انیمیشن واقعی ساخته شده با جاوا اسکریپت، سی اس اس و اچ تی ام ال](https://blog.faradars.org/wp-content/uploads/2023/12/js-anomations2.gif)
تغییرات گستردهای در کدهای بالا انجام نشده است و فقط با اضافه شدن فراخوان requestAnimationFrame، تابع animateقبلی به نوعی حلقه انیمیشن جذاب تبدیل شده است. این حلقه اکنون به صورت پویا دایره آبیرنگ را با هر بهروزرسانی فریم، ۱۰ پیکسل به سمت راست حرکت میدهد.
پیچیده تر کردن انیمیشن ساخته شده با جاوا اسکریپت
در این بخش مثال بالا را کمی پیچیدهتر و جذابتر میکنیم. تا اینجا، با مفهوم حلقه انیمیشن آشنا شدیم و نوعی انیمیشن تعاملی را پیادهسازی کردیم. دایره محرک بالا را میتوان بدون کدنویسی اضافی با نوعی انیمیشن CSS که فقط شامل دو فریم کلیدی است، راحتتر ساخت. در این بخش، مثال قبلی را تقویت کرده تا واقعاً قابلیتهای انیمیشنی که کاملاً با کدهای جاوا اسکریپت ساخته شده است را به نمایش بگذاریم. برای رسیدن به این هدف کدهای زیر را به کدهای قبلی اضافه کرده و اصلاحات لازم را انجام خواهیم داد.
1var circle = document.querySelector("#circle");
2
3var xPos = 0;
4var yPos = 0;
5var angle = 0;
6
7function animate() {
8 xPos += 5;
9 angle += .1;
10
11 yPos = Math.round(50 * Math.sin(angle));
12
13 circle.style.transform = `translate3d(${xPos}px, ${yPos}px, 0)`;
14
15 if (Math.abs(xPos) >= 900) {
16 xPos = -500;
17 }
18
19 if (angle > 2 * Math.PI) {
20 angle = 0;
21 }
22
23 requestAnimationFrame(animate);
24}
25animate();
اصلاحاتی که در کد صورت گرفت نوعی جهش اضافی از نوع حرکت سینوسی به دایره متحرک وارد میکند که این کار فقط با کدهای جاوا اسکریپت امکانپذیر است. این بار خروجی انیمیشن ساخته شده به صورت زیر خواهد بود:
![انیمیشی دایره ای با حرکت سینوسی در صفحه وب که با جاوا اسکریپت ساخته شده است](https://blog.faradars.org/wp-content/uploads/2023/12/js-anomations8.gif)
افکت پرش یا جهش تصویر بالا که به کد اضافه شده به وسیله تابع Math.sinبه دست میآید. هدف اصلی این مثال نشان دادن برخی از قابلیتهای ساخت انیمیشن در جاوا اسکریپت بود که دستیابی به آنها با استفاده از CSS به این سادگی نیست. در ادامه مثالی دیگر از ساخت انیمیشن با جاوا اسکریپت با رویکردی متفاوت ارائه خواهیم کرد.
ساخت انیمیشن با عناصر Canvas در جاوا اسکریپت
استفاده از جاوا اسکریپت برای فرمان دادن به عناصر canvas، ساخت انیمیشنها (تعاملی) را به طور قابلملاحظهای ساده میکند. در این بخش، اصول ساخت انیمیشنهای ساخته شده با عناصر canvasرا بررسی خواهیم کرد.
استفاده از این رویکرد برای ساخت انیمیشن با Javascript محدودیتهایی دارد. برای مثال هنگامیکه شکلی روی canvasکشیده میشود، ثابت میماند. برای متحرک کردن آن، ترسیم مجدد آن شکل و هر چیزی که قبل از آن شکل ترسیم شده است، لازم خواهد بود. ترسیم مجدد فریمهای پیچیده میتواند زمانبر باشد و عملکرد آن به طور قابلتوجهی بر اساس سرعت پردازش کامپیوتر متفاوت است.
Canvas در ساخت انیمیشن چیست؟
منظور از «Canvas» نوعی عنصر HTML است که فضای طراحی را در صفحه وب فراهم میکند. Canvas به توسعهدهندگان اجازه میدهد تا از جاوا اسکریپت برای دستکاری و ترسیم گرافیکها، اشکال و انیمیشنها به صورت پویا استفاده کنند. به بیانی دیگر و به صورت خلاصه عنصر Canvas ابزاری همهکاره برای ایجاد عناصر بصری تعاملی در صفحه وب است.
مراحل ساخت انیمیشن با جاوا اسکریپت به وسیله عناصر Canvas
برای ایجاد فریم در انیمیشن، مراحل زیر باید دنبال شود:
- پاک کردن canvas: اگر canvasکاملاً به وسیله اشکالی که کشیده میشود پر نشود (مثلاً هنگام استفاده از تصویر پسزمینه)، باید از متد clearRect()برای حذف هر شکلی که قبلاً ترسیم شده است، استفاده شود.
- ذخیره حالت canvas: اگر در حال ایجاد تغییراتی باشیم (مثلاً تغییر سبک و استایل) که بر وضعیت canvasتأثیر میگذارد، وضعیت فعلی canvasباید ذخیره شود. این کار تضمین میکند که قبل از ترسیم هر فریم جدید، حالت اولیه بازیابی میشود.
- رسم اشکال متحرک: مرحله اصلی که در آن رندر واقعی فریم اجرا میشود رسم اشکال متحرک است که شامل ترسیم اشکال یا عناصری خواهد بود که انیمیشن را تشکیل میدهند.
- بازیابی حالت canvas: اگر قبلاً حالت canvasذخیره شده باشد باید آن را بازیابی کرد. این کار تضمین میکند که canvasقبل از آماده شدن برای فریم بعدی به پیکربندی اصلی خود بازمیگردد.
این مراحل فرآیند اساسی برای ایجاد انیمیشنهای پویا و در حال تکامل بر روی canvasبه شیوهای ساختاریافته و سازمان یافته را تشکیل میدهند.
کنترل انیمیشن ساخته شده با Canvas
مدیریت و کنترل انیمیشن شامل کشیدن اشکال بر روی canvasبا استفاده از متدهای canvasمستقیم یا توابع سفارشی است. به طور معمول، این نقاشیها پس از پایان اجرای اسکریپت روی canvasقابلمشاهده میشوند. با این حال، برای انیمیشنها ما به متدی برای اجرای توابع در مدتزمان مشخصی نیاز داریم. راهحل بهروزرسانیهای برنامهریزیشده برای کنترل چنین انیمیشنهایی وجود دارد که عناصر زیر در آن دخیل هستند:
- setInterval(): اجرای مکرر تابع مشخصی را در هر بازه تعریفشده آغاز میکند.
- setTimeout(): تابع مشخصشده را پس از تأخیر تعیینشده اجرا میکند.
- requestAnimationFrame(callback): مرورگر را در مورد قصد انجام انیمیشن مطلع میکند و از مرورگر درخواست خواهد کرد تا قبل از ترسیم عناصر مجدد بعدی، تابع مشخصی را برای بهروزرسانی انیمیشن فراخوانی کند.
برای انیمیشنهای بدون تعامل کاربر، متد SetInterval در جاوا اسکریپت بسیار مفید است زیرا کد ارائهشده را مکرراً اجرا میکند. در سناریوهایی که شامل انیمیشنهای کنترلشده به وسیله کاربر خواهد بود، رویدادهای صفحهکلید یا ماوس میتوانند مورداستفاده قرار گیرند و setTimeout()برای آن مفید واقع خواهد شد. همچنین «AddEventListener» برای تنظیم شنونده رویداد در جاوا اسکریپت، به وسیله تعاملات کاربر باعث اجرای توابع انیمیشن میشود.
توجه: مثالهای زیر از متد window.requestAnimationFrame()برای کنترل انیمیشن استفاده میکنند. این متد با ترغیب مرورگر به فراخوانی فریم انیمیشن زمانی که سیستم آماده نقاشی کردن آن است، رویکرد روانتر و کارآمدتری برای انیمیشن ارائه میکند.
ساخت انیمیشن منظومه شمسی متحرک با جاوا اسکریپت
در این بخش از ساخت انیمیشن با جاوا اسکریپت در «مجله فرادرس»، به ساخت انیمیشن منظومه شمسی با جاوا اسکریپت با رویکرد استفاده از عناصر canvasخواهیم پرداخت. قطعه کد پایه HTML انیمیشن منظومه شمسی به صورت زیر است:
1<canvas id="canvas" width="300" height="300"></canvas>
همچنین قطعه کد جاوا اسکریپت این مثال از ساخت انیمیشن به صورت زیر است:
1const sun = new Image();
2const moon = new Image();
3const earth = new Image();
4function init() {
5 sun.src = "canvas_sun.png";
6 moon.src = "canvas_moon.png";
7 earth.src = "canvas_earth.png";
8 window.requestAnimationFrame(draw);
9}
10
11function draw() {
12 const ctx = document.getElementById("canvas").getContext("2d");
13
14 ctx.globalCompositeOperation = "destination-over";
15 ctx.clearRect(0, 0, 300, 300); // clear canvas
16
17 ctx.fillStyle = "rgba(0, 0, 0, 0.4)";
18 ctx.strokeStyle = "rgba(0, 153, 255, 0.4)";
19 ctx.save();
20 ctx.translate(150, 150);
21
22 // Earth
23 const time = new Date();
24 ctx.rotate(
25 ((2 * Math.PI) / 60) * time.getSeconds() +
26 ((2 * Math.PI) / 60000) * time.getMilliseconds(),
27 );
28 ctx.translate(105, 0);
29 ctx.fillRect(0, -12, 40, 24); // Shadow
30 ctx.drawImage(earth, -12, -12);
31
32 // Moon
33 ctx.save();
34 ctx.rotate(
35 ((2 * Math.PI) / 6) * time.getSeconds() +
36 ((2 * Math.PI) / 6000) * time.getMilliseconds(),
37 );
38 ctx.translate(0, 28.5);
39 ctx.drawImage(moon, -3.5, -3.5);
40 ctx.restore();
41
42 ctx.restore();
43
44 ctx.beginPath();
45 ctx.arc(150, 150, 105, 0, Math.PI * 2, false); // Earth orbit
46 ctx.stroke();
47
48 ctx.drawImage(sun, 0, 0, 300, 300);
49
50 window.requestAnimationFrame(draw);
51}
52
53init();
خروجی مثال فوق در مرحله اول به صورت زیر است:
![انیمیشن منظومه شمسی ساخته شده با جاوا اسکریپت](https://blog.faradars.org/wp-content/uploads/2023/12/SOLAR.gif)
ساخت ساعت با جاوا اسکریپت
مثال زیر مربوط به ساخت ساعت با جاوا اسکریپت در قالب نوعی انیمیشن است له قطعه کد HTML آن به صورت زیر خواهد بود:
1<canvas id="canvas" width="150" height="150">The current time</canvas>
همچنین قطعه کد جاوا اسکریپت این مثال به صورت زیر است:
1function clock() {
2 const now = new Date();
3 const canvas = document.getElementById("canvas");
4 const ctx = canvas.getContext("2d");
5 ctx.save();
6 ctx.clearRect(0, 0, 150, 150);
7 ctx.translate(75, 75);
8 ctx.scale(0.4, 0.4);
9 ctx.rotate(-Math.PI / 2);
10 ctx.strokeStyle = "black";
11 ctx.fillStyle = "white";
12 ctx.lineWidth = 8;
13 ctx.lineCap = "round";
14
15 // Hour marks
16 ctx.save();
17 for (let i = 0; i < 12; i++) {
18 ctx.beginPath();
19 ctx.rotate(Math.PI / 6);
20 ctx.moveTo(100, 0);
21 ctx.lineTo(120, 0);
22 ctx.stroke();
23 }
24 ctx.restore();
25
26 // Minute marks
27 ctx.save();
28 ctx.lineWidth = 5;
29 for (let i = 0; i < 60; i++) {
30 if (i % 5 !== 0) {
31 ctx.beginPath();
32 ctx.moveTo(117, 0);
33 ctx.lineTo(120, 0);
34 ctx.stroke();
35 }
36 ctx.rotate(Math.PI / 30);
37 }
38 ctx.restore();
39
40 const sec = now.getSeconds();
41 // To display a clock with a sweeping second hand, use:
42 // const sec = now.getSeconds() + now.getMilliseconds() / 1000;
43 const min = now.getMinutes();
44 const hr = now.getHours() % 12;
45
46 ctx.fillStyle = "black";
47
48 // Write image description
49 canvas.innerText = `The time is: ${hr}:${min}`;
50
51 // Write Hours
52 ctx.save();
53 ctx.rotate(
54 (Math.PI / 6) * hr + (Math.PI / 360) * min + (Math.PI / 21600) * sec,
55 );
56 ctx.lineWidth = 14;
57 ctx.beginPath();
58 ctx.moveTo(-20, 0);
59 ctx.lineTo(80, 0);
60 ctx.stroke();
61 ctx.restore();
62
63 // Write Minutes
64 ctx.save();
65 ctx.rotate((Math.PI / 30) * min + (Math.PI / 1800) * sec);
66 ctx.lineWidth = 10;
67 ctx.beginPath();
68 ctx.moveTo(-28, 0);
69 ctx.lineTo(112, 0);
70 ctx.stroke();
71 ctx.restore();
72
73 // Write seconds
74 ctx.save();
75 ctx.rotate((sec * Math.PI) / 30);
76 ctx.strokeStyle = "#D40000";
77 ctx.fillStyle = "#D40000";
78 ctx.lineWidth = 6;
79 ctx.beginPath();
80 ctx.moveTo(-30, 0);
81 ctx.lineTo(83, 0);
82 ctx.stroke();
83 ctx.beginPath();
84 ctx.arc(0, 0, 10, 0, Math.PI * 2, true);
85 ctx.fill();
86 ctx.beginPath();
87 ctx.arc(95, 0, 10, 0, Math.PI * 2, true);
88 ctx.stroke();
89 ctx.fillStyle = "rgba(0, 0, 0, 0)";
90 ctx.arc(0, 0, 3, 0, Math.PI * 2, true);
91 ctx.fill();
92 ctx.restore();
93
94 ctx.beginPath();
95 ctx.lineWidth = 14;
96 ctx.strokeStyle = "#325FA2";
97 ctx.arc(0, 0, 142, 0, Math.PI * 2, true);
98 ctx.stroke();
99
100 ctx.restore();
101
102 window.requestAnimationFrame(clock);
103}
104
105window.requestAnimationFrame(clock);
خروجی کدهای بالا به صورت زیر است:
![یک ساعت ساخته شده انیمیشن مانند با جاوا اسکریپت و اچ تی ام ال](https://blog.faradars.org/wp-content/uploads/2023/12/clock-animations.gif)
توجه: در حالی که بهروزرسانیهای ساعت با سرعت یک بار در ثانیه انجام میشوند، تصویر متحرک با سرعت ۶۰ فریم در ثانیه بهروزرسانی خواهد شد که با نرخ تازهسازی نمایشگر مرورگر وب کاربر هماهنگ است.
انیمیشن پانورامای چرخشی (Loop)
مثال زیر از ساخت انیمیشن با جاوا اسکریپت مربوط به نمایش عکس پانوراما یا سراسرنما است. پانورامای پیوستهای که در این مثال ایجاد میشود از چپ به راست حرکت میکند. قطعه کد HTML آن به صورت زیر است:
1<canvas id="canvas" width="800" height="200"
2 >Yosemite National Park, meadow at the base of El Capitan</canvas
3>
HTML عنصر canvasرا که مسئول تصویر پانوراما بوده، در خود جای داده است. باید اطمینان حاصل شود که عرض و ارتفاع مشخص شده در کد HTML با مقادیر اختصاص داده شده به متغیرهای «canvasXSize» و «canvasYSize» در کد جاوا اسکریپت مطابقت دارد. قطعه کد جاوا اسکریپت مثال فوق به صورت زیر است:
1const img = new Image();
2
3// User Variables - customize these to change the image being scrolled, its
4// direction, and the speed.
5img.src = "capitan_meadows_yosemite_national_park.jpg";
6const canvasXSize = 800;
7const canvasYSize = 200;
8const speed = 30; // lower is faster
9const scale = 1.05;
10const y = -4.5; // vertical offset
11
12// Main program
13const dx = 0.75;
14let imgW;
15let imgH;
16let x = 0;
17let clearX;
18let clearY;
19let ctx;
20
21img.onload = () => {
22 imgW = img.width * scale;
23 imgH = img.height * scale;
24
25 if (imgW > canvasXSize) {
26 // Image larger than canvas
27 x = canvasXSize - imgW;
28 }
29
30 // Check if image dimension is larger than canvas
31 clearX = Math.max(imgW, canvasXSize);
32 clearY = Math.max(imgH, canvasYSize);
33
34 // Get canvas context
35 ctx = document.getElementById("canvas").getContext("2d");
36
37 // Set refresh rate
38 return setInterval(draw, speed);
39};
40
41function draw() {
42 ctx.clearRect(0, 0, clearX, clearY); // clear the canvas
43
44 // If image is <= canvas size
45 if (imgW <= canvasXSize) {
46 // Reset, start from beginning
47 if (x > canvasXSize) {
48 x = -imgW + x;
49 }
50
51 // Draw additional image1
52 if (x > 0) {
53 ctx.drawImage(img, -imgW + x, y, imgW, imgH);
54 }
55
56 // Draw additional image2
57 if (x - imgW > 0) {
58 ctx.drawImage(img, -imgW * 2 + x, y, imgW, imgH);
59 }
60 } else {
61 // Image is > canvas size
62 // Reset, start from beginning
63 if (x > canvasXSize) {
64 x = canvasXSize - imgW;
65 }
66
67 // Draw additional image
68 if (x > canvasXSize - imgW) {
69 ctx.drawImage(img, x - imgW + 1, y, imgW, imgH);
70 }
71 }
72
73 // Draw image
74 ctx.drawImage(img, x, y, imgW, imgH);
75
76 // Amount to move
77 x += dx;
78}
خروجی کدهای بالا به صورت زیر است:
![تصویری از نمایش تصاویر پانوراما به صورت انیمیشن در صفحات وب](https://blog.faradars.org/wp-content/uploads/2023/12/panorama.gif)
انیمیشن دنبال کردن ماوس در صفحه
آخرین انیمیشنی که قرار است در این بخش پیادهسازی آن انجام شود، انیمیشن دنبال کردن ماوس در صفحه خواهد بود که از سه بخش کد جاوا اسکریپت، HTML و Css تشکیل شده و قطعه کد HTML آن به صورت زیر است.
1<canvas id="cw"
2 >Animation creating multi-colored disappearing stream of light that follow the
3 cursor as it moves over the image
4</canvas>
قطعه کد Css این پروژه جاوا اسکریپت به صورت زیر است:
1#cw {
2 position: fixed;
3 z-index: -1;
4}
5
6body {
7 margin: 0;
8 padding: 0;
9 background-color: rgba(0, 0, 0, 0.05);
10}
در نهایت قطعه کد جاوا اسکریپت این پروژه ساخت انیمیشن با جاوا اسکریپت به صورت زیر است:
1const canvas = document.getElementById("cw");
2const context = canvas.getContext("2d");
3context.globalAlpha = 0.5;
4
5const cursor = {
6 x: innerWidth / 2,
7 y: innerHeight / 2,
8};
9
10let particlesArray = [];
11
12generateParticles(101);
13setSize();
14anim();
15
16addEventListener("mousemove", (e) => {
17 cursor.x = e.clientX;
18 cursor.y = e.clientY;
19});
20
21addEventListener(
22 "touchmove",
23 (e) => {
24 e.preventDefault();
25 cursor.x = e.touches[0].clientX;
26 cursor.y = e.touches[0].clientY;
27 },
28 { passive: false },
29);
30
31addEventListener("resize", () => setSize());
32
33function generateParticles(amount) {
34 for (let i = 0; i < amount; i++) {
35 particlesArray[i] = new Particle(
36 innerWidth / 2,
37 innerHeight / 2,
38 4,
39 generateColor(),
40 0.02,
41 );
42 }
43}
44
45function generateColor() {
46 let hexSet = "0123456789ABCDEF";
47 let finalHexString = "#";
48 for (let i = 0; i < 6; i++) {
49 finalHexString += hexSet[Math.ceil(Math.random() * 15)];
50 }
51 return finalHexString;
52}
53
54function setSize() {
55 canvas.height = innerHeight;
56 canvas.width = innerWidth;
57}
58
59function Particle(x, y, particleTrailWidth, strokeColor, rotateSpeed) {
60 this.x = x;
61 this.y = y;
62 this.particleTrailWidth = particleTrailWidth;
63 this.strokeColor = strokeColor;
64 this.theta = Math.random() * Math.PI * 2;
65 this.rotateSpeed = rotateSpeed;
66 this.t = Math.random() * 150;
67
68 this.rotate = () => {
69 const ls = {
70 x: this.x,
71 y: this.y,
72 };
73 this.theta += this.rotateSpeed;
74 this.x = cursor.x + Math.cos(this.theta) * this.t;
75 this.y = cursor.y + Math.sin(this.theta) * this.t;
76 context.beginPath();
77 context.lineWidth = this.particleTrailWidth;
78 context.strokeStyle = this.strokeColor;
79 context.moveTo(ls.x, ls.y);
80 context.lineTo(this.x, this.y);
81 context.stroke();
82 };
83}
84
85function anim() {
86 requestAnimationFrame(anim);
87
88 context.fillStyle = "rgba(0,0,0,0.05)";
89 context.fillRect(0, 0, canvas.width, canvas.height);
90
91 particlesArray.forEach((particle) => particle.rotate());
92}
تصویر زیر نمایانگر خروجی کدهای بالا برای ساخت انمیشن دنبال کردن ماوس در صفحه است:
![انیمیشنی که با جاوا اسکریپت ساخته شده است و ماوس را دنبال میکند.](https://blog.faradars.org/wp-content/uploads/2023/12/ani-mations-js.gif)
سخن پایانی
جاوا اسکریپت به عنوان یکی از کاربردیترین زبانهای برنامه نویسی نقش به سزایی در بهینهسازی تجربه کاربری در پلترفرمهای مبنیبر وب ارائه میکند و میتوان گفت که به طراحیها روح و جان تازهای میبخشد. یکی از مهمترین قابلیتهایی که با جاوا اسکریپت امکان پیادهسازی آن وجود دارد و در واقع یکی از کاربردهای جاوا اسکریپت محسوب میشود، امور مرتبط با انیمیشنسازی است.
در مطلب فوق از «مجله فرادرس» در کنار بررسی مفاهیم و مقدمات ساخت انیمیشن با جاوا اسکریپت، در رابطه با تفاوتها و همچنین برتریهای جاوا اسکریپت نسبت به CSS برای کارهای انیمیشنسازی سخن به میان آمد. همچنین در مطلب فوق پیادهسازی گامبهگام انیمیشنی ساده ارائه شد و به دنبال آن با رویکردی متمایز و با استفاده از عناصر canvasدر HTML، چندین مثال کاربردی نیز همراه با کدهای کامل ارائه شدند.