آخرین مطالب
LINK TABLES
خانه | پروژه های کاربردی | ساخت رقص نور با AVR

ساخت رقص نور با AVR

سلام می کنم خدمت دوستان، قصد داریم اولین پروژه ی آموزشیمون در رابطه با میکروکنترلرهای AVR رو انجام بدیم. این پروژه رو در ادامه ی پست پورت های ورودی و خروجی در AVR جهت یادگیری بیشتر در مورد پورت های AVR و طرزکار و برنامه نویسی شون تعریف می کنیم. یک پروژه ی بسیار ساده ولی مفید برای یادگرفتن کار با پورت های ورودی و خروجی.

• برنامه ی این پروژه در محیط CodeVision نوشته شده

• شبیه سازی در محیط Proteus  انجام گرفته

• فایل های مربوط به پروژه (شامل فایل های C و hex و همچنین فایل شبیه سازی) در پایان پست ضمیمه شده

این پروژه جزء ساده ترین کارهایی است که می توان با میکرو کنترلر AVR انجام داد. در این پروژه قصد داریم یک رقص نور ساده با استفاده از هشت عدد LED طراحی، برنامه نویسی و شبیه سازی کنیم. قطعات مورد استفاده عبارت اند از:

• میکروکنترلر ATtiny2313

• هشت عدد LED

• یک کلید فشاری (push button)

شماتیک مدار شبیه سازی شده در محیط نرم افزار Proteus به صورت زیر است:

TrainingProject1-schematic

می خواهیم برنامه ای بنویسیم که در آن میکروکنترلر منتظر فشار دادن کلید بماند. و هنگامی که کلید فشار داده شد رقص نور آغاز گردد و ادامه پیدا کند. اگر  کلید بار دیگر فشرده شود، رقص نور متوقف گردد. رقص نوری که می خواهیم داشته باشیم بسیار ساده می باشد، به این صورت که دیود اول روشن شده و پس از مدتی خاموش و دیود بعدی روشن شود. و به همین صورت ادامه یابد.

برای روشن کردن دیود نوری نیاز به مقاومت پول آپ و یا مقاومت پول داون می باشد. با توجه به این که میکروکنترلر AVR دارای مقاومت پول آپ داخلی می باشد، ما نیز از این مقاومت ها استفاده نموده و در برنامه ای که خواهیم نوشت مقاومت های پول آپ را فعال می نماییم. در شکل زیر شماتیک یک پین و مقاومت پول آپ آن نشان داده شده است.

internal-pullup

همان طور که در شکل مشاهده می شود اگر مقاومت پول آپ فعال باشد، وقتی که کلید فشار داده شود ورودی پین صفر می شود و در غیر این صورت در حالت یک باقی می ماند. در این جا هشت دیود نوری را به پورت B و کلید فشاری را به پین ۰ از پورت دی (PIND.0) متصل می کنیم. در برنامه ای که می نویسیم PIND.0 را ورودی کرده و مقاومت پول آپ آن را فعال می نماییم. همچنین پورت B را به عنوان خروجی تعریف می کنیم. و همان طور که توضیح داده شد، چون مقاومت پول آپ در PIND.0 فعال است، هنگامی که کلید فشرده شود مقدار PIND.0 برابر با صفر می شود و در حالت عادی همیشه روی مقدار یک باقی می ماند. به همین خاطر در برنامه ای که می نویسیم برای تشخیص فشرده شدن کلید عملا صفر شدن PIND.0  را بررسی می کنیم.

لرزش گیری:

هنگامی که کلیدی فشرده می شود تا وقتی که وضعیت کلید به طور پایدار تغییر کند ایجاد لرزش هایی می کند که در حد چند میلی ثانیه طول می کشند. در شکل زیر این لرزش ها توسط اسیلوسکوپ نشان داده شده اند:

 debounce

این لرزش ها میکروکنترلر را در تغییر وضعیت کلید به اشتباه می اندازند. به روش های جلوگیری از اثرگذاری این لرزش ها در تصمیم گیری میکروکنترلر  لرزش گیری می گویند. برای لرزش گیری دو روش وجود دارد: ۱- استفاده از تایمرها و وقفه ها ۲- سرکشی به وضعیت کلید. ما در اینجا از روش دوم استفاده می کنیم، بدین صورت که اگر وضعیت کلید تغییر کرد پس از ۲۵ میلی ثانیه باز هم به وضعیت کلید سرکشی می کنیم. اگر کلید هنوز هم در حالت تغییر یافته قرار داشت بدین معناست که کلید فشرده شده است.

 برنامه ای که برای این انجام پروژه در محیط کدویژن می نویسیم به صورت زیر خواهد بود:

 پس از نوشتن این برنامه و کامپایل کردن آن، فایل HEX تولید شده را در محیط پروتئوس برای میکروکنترلر بارگذاری کرده و شبیه سازی را اجرا می کنیم. شبیه سازی به صورتی که در انیمیشن زیر مشاهده می شود، اجرا شده و می‌توانید رقص نور را مشاهده کنید:

پروژه آموزشی ۱- رقص نور

فایل های مورد نیاز این پروژه شامل فایل C ، فایل HEX و فایل DSN (شبیه سازی پروتئوس) را در لینک زیر دانلود کنید.

پسورد: www.microlearn.ir

دانلود فایل پروژه رقص نور

در این پست در مورد پورت ها و برنامه نویسی و شبیه سازی شون یاد گرفتیم. توصیه می کنم که حتما نرم افزارهای کد ویژن و پروتئوس رو نصب کرده و کار با اونا رو به طور مقدماتی یاد بگیرید و از دنیای قشنگ میکروکنترلرها لذت ببرید.  در ادامه پروژه های جالب تری تعریف خواهند شد که با مفاهیم دیگری مرتبط بوده و طبیعتا لذت بخش تر خواهند بود.

درباره ی مجتبی حکیمیان

کارشناس الکترونیک و کارشناس ارشد مخابرات سیستم | زمینه ی تحقیقاتی : پردازش تصویر و تعقیب اشیاء متحرک |‌فعال در حوزه ی الکترونیک مبتنی بر میکروکنترلر | برنامه نویس و طراح بردهای الکترونیکی مبتنی بر میکروکنترلر

۲۸ دیدگاه

  1. سلام خسته نباشید.
    میشه یه توضیحی برای خطوط ۳۸ و ۴۰ بدید؟؟؟

    • سلام و عرض ادب
      این تابع برای تشخیص فشرده شدن کلید هست. البته در اون لرزش گیری کلید هم در نظر گرفته شده. پس وقتی فشرده شدن کلید را تشخیص داد ۲۵ میلی ثانیه صبر میکنه و دوباره چک میکنه. در صورتی که واقعا کلید فشرده شده بود عدد یک را بر میگردونه. در صورتی هم که کلید فشرده نشده بود عدد صفر را در خروجی تابع بر میگردونه.

  2. با سلام میشه خط ۱۸ برنامه رو یه مقداری توضیح بدین تو این خط میاد مقدار باینری a رو شیفت میده به چپ و در خط ۲۰ میاد هر بار یه واحد به a اضافه میکنه پس یه همچین دنباله ای رو برای out خواهیم داشت ۰,۱۰,۱۰۰,۱۱۰,۱۰۰۰,۱۰۱۰,…

  3. Excellent post. I am facing a few of these issues as well..

  4. با سلام
    ببخشید وقتی breack مینویسیم که از حلقه بیاد بیرون اگه چندتا حلقه تودرتو داشته باشیم منظور از اولین حلقه میاد بیرون؟

    • سلام
      از حلقه ای که در حال حاضر داخلش هستیم، میایم بیرون. مثلا دو تا حلقه ی for تو در تو نوشتیم، در حلقه ی دوم اگه جایی break نوشتیم، ازش خارج میشیم و به حلقه ی اول برمیگردیم.

  5. و سوال دیگه اینکه در ابتدای برنامه اگر فایل هدر مربوط به میکرو tiny2313را الصاق کنیم با وجود آنکه سخت افزار ATmega32 است باز هم اجرا می شه و درست کار میکنه!
    (از این که فایل دیگری به جای فایل مورد نظر اشتباها اجرا نمیشود اطمینان دارم چون با تغییر کد مثلا تاخیر…سرعت چشمک زدن به خوبی تغییر می کند )

    • فایل هدری که اضافه میشه برای تعریف متغیرهایی هست مثل DDRA یا OCIE2 یا TOV1 و … . حالا اگه توی برنامه تون مثلا از تایمر ۲ استفاده کنید و میکرویی که فایل هدرش رو ادد کردین تایمر ۲ نداشته باشه، کامپایلر ارور میده. البته ممکنه شما اشتباها فایل هدر رو ادد کنید و از روی شانس ایرادی هم گرفته نشه. اما یادتون نره که چیزی که تعیین کننده ی قطعه ی سخت افزار و مشخصاتی مثل رم و … هست، قسمت configure و نام قطعه ی انتخاب شده در IDE هست (مثلا در کدویژن در منوی project قسمت configure و در تب C compiler). و دقیقا به همین دلایلی که گفتم شما هدر رو عوض می کنی وچون متغیرها مشترکن اتفاقی نمیفته و چون سخت افزار رو عوض نمیکنی هم در شبیه ساز اجرا میشه.

  6. مدار بالا را با ATmega32 شبیه سازی و اجرا کردم. با فرکانس های ساعت کمتر از ۴مگ(به ویژه ۱ مگ) عملکرد مدار تغییر می کنه مثلا با یکبار فشار دادن کلید شروع به کار نمی کنه.
    علتش چیه؟

    • شما وقتی قصد دارین که فرکانس کاری میکروکنترلر رو تغییر بدین، هم باید در محیط برنامه نویسی اون رو عوض کنید و هم باید در شبیه سازی تغییرش بدین. مثلا توی کدویژن باید در منوی project قسمت configure و در تب C compiler مقدار منبع ساعت رو تغییر بدی. در پروتئوس هم با دابل کلیک روی میکرو همین کارو انجام بدی.

  7. خیلی متشکرم
    توضیح کامل و خوبی بود.

  8. و اگر ممکنه کمی در مورد کد های زیر توضیح بدین. با حذف این ها برنامه کار نکرد…

    CLKPR=(1<<CLKPCE);
    CLKPR=(0<<CLKPCE) | (0<<CLKPS3) | (0<<CLKPS2) | (0<<CLKPS1) | (0<<CLKPS0);

    • سلام، سوال بسیار خوبی پرسیدین.
      در بعضی از سری های AVR مانند : ATmega48/88/168/328 قابلیت تقسیم فرکانس ساعت میکروکنترلر وجود داره. مهم هم نیست که منبع ساعتتون داخلی باشه یا خارجی. مثلا شما یه کریستال ۱۶ مگاهرتزی دارین ولی میخواین میکروکنترلرتون با فرکانس ۸ مگاهرتز کار کنه. در این صورت از این قابلیت استفاده می کنین و فرکانستون رو به عامل ۲ تقسیم کرده و به فرکانس مطلوب ۸ مگ می رسین.
      میکروکنترلرهایی که این قابلیت رو دارن دارای یک رجیستر به نام CLKPR هستن. همچنین یه بیت فیوز به نام CLKDIV8 دارن. اجازه بدین که اول در مورد بیت فیوز صحبت کنم:
      – اگه این بیت فیوز پروگرام بشه، (مثلا در برنامه ی پروگرامرت تیکش رو بزنی) فرکانس ساعت به هشت تقسیم میشه. حواست باشه که به طور پیش فرض تیک این بیت فیوز خورده یا به عبارتی programmed شده. برای همین اگه نمیخوای فرکانس به هشت تقسیم بشه یا بعدا به صورت نرم افزاری میخوای اونو به عامل های دیگه تقسیم کنی، باید قبل از پروگرام کردن فایل هگز، تیک این بیت فیوز رو برداری. یا در شبیه سازی پروتئوس اون رو به حالت unprogrammed دربیاری. (با دابل کلیک کردن روی میکروکنترلر و مراجعه به قسمت CLKDIV8)
      – اگه بخوای به صورت نرم افزاری درون برنامه ت عامل تقسیم فرکانس رو تعیین کنی باید همون دو خطی که در موردشون پرسیدی رو اول برنامه ت بنویسی. حواست باشه که بعدا به هنگام پروگرام کردن میکروکنترلر میتونی بیت فیوز CLKDIV8 رو پاک کنی یا دست بهش نزنی. چون در هرصورت به صورت نرم افزاری تنظیماتی که میخوای اعمال میشن. برای تنظیم نرم افزاری همیشه خط اول باید نوشته بشه. بلافاصله در خط دوم هم باید بیت های CLKPS3 ، CLKPS2، CLKPS1 ،CLKPS0 رو با توجه به این که فرکانس به چند تقسیم بشه، تنظیم کنی. و بیت CLKPCE رو همزمان صفر کنی. مثلا در خطی که خودت آوردی همشون صفرن و یعنی عامل ۱٫ که یعنی فرکانس ساعت بدون تغییر بمونه. با توجه به مقادیر مختلف این بیت ها میتونی فرکانست رو به ۱ ، ۲، ۴، ۸، ۱۶، ۳۲، ۶۴، ۱۲۸ و ۲۵۶ تقسیم کنی.

      فرض کنیم که شما اصلا قصد تغییر فرکانس ساعت رو نداری، چه کاری باید انجام بدی؟
      جواب: میتونی خطوطی که پاک کردی رو بذاری باقی بمونه و تمام. یا همون خط هایی که گفتی رو پاک کن و در ضمن در شبیه سازت بیت فیوز CLKDIV8 رو غیرفعال کن. همچنین هنگام پروگرام کردن میکروکنترلر، تیک CLKDIV8 رو بردار. علت این که با پاک کردن این خطوط برنامه ت میریزه به هم اینه که شما بیت فیوز را غیرفعال نکردی.

  9. ذو کد زیر مثل هم هستند؟!
    DDRD=1
    DDRD=0xff
    انتظار داشتم این طور باشه اما نیست!
    چرا؟

    • نه مثل هم نیستند. ما در نهایت مقداری که روی رجیستر DDR می ریزیم رو باید به صورت باینری تحلیل کنیم:
      – وقتی مینویسیم : DDRD = 1 ٬ عدد ۱ در مبنای ۱۰ هست و به لحاظ باینری یعنی: DDRD = 0b00000001
      – وقتی می نویسیم DDRD = 0xff چون داریم از ۰x استفاده میکنیم یعنی عدد در مبنای ۱۶ هست و به لحاظ باینری یعنی ‌: DDRD = 0b11111111
      در مورد اول فقط پین شماره ی صفر به عنوان خروجی تعریف میشه٬ اما در مورد دوم هر هشت پین به عنوان خروجی تعیین میشن. پس با هم فرق دارن.
      سوالی بود در خدمتم.

  10. سلام وقتتون بخیر
    اولا خیلی ممنون از مطالب زیباتون.
    خودم دانشجوی ارشدم ولی رشته من خیلی ب الکترونیک ربط نداره،
    خیلی هم علاقه مندم که ساخت مداراتو یاد بگیرم،فقط موندم از کجا شروع کنم،
    ممنون میشم ک راهنمایی بفرمائید.
    با تشکر

    • سلام
      خواهش می کنم، امیدوارم که مفید بوده باشه.
      اول از همه بگم علیرغم اینکه رشته ت الکترونیک نیست، اعتماد به نفست رو از دست نده. شخصا خیلی ها رو می شناسم که رشته شون هیچ ارتباطی با الکترونیک و کامپیوتر نداره و صرفا با تلاشی که داشتن افرادی بسیار موفق در این حوزه هستند.
      دوم این که اعضای تیم میکرولرن بسیار خوشحال میشیم که بتونیم کمکی بهتون بکنیم تا راحت تر این مسیر رو برید و بهتر یاد بگیرید.
      اما یه سوال: تا الان چه چیزهایی رو یادگرفتین و چه چیزهایی رو کار کردین؟ در زمینه ی میکروکنترلر در چه سطحی هستین؟
      جواب دقیقتون به این سوال بهمون کمک می کنه که بهتر در خدمتتون باشیم.

      • با سلام مجدد
        یه آشنایی جزئی با پایه های میکروکنترلر کارهاشون یکمم برنامه نویسی ساده و وسایلی که بیشتر مورد استفاده در مدار هستن،شاید بشه گفت پنج درصدو بلد باشم.
        اینم بگم که علاقه شدیدی به این رشته دارم اگر زمان قابل بازگشت بود حتما این رشته رو میخوندم.
        بازم ممنون از مطالب مفیدتون.

        • سلام
          سالار جان حتما می دونی که برای کاری که میخوای باید سه تا چیز رو بلد باشی:
          برنامه نویسی + الکترونیک + میکروکنترلر
          خوشبختانه ما بر روی هر سه مورد کار کردیم و مطالبی رو در هر سه دسته ارائه دادیم. سعی مون هم بر این بوده که مطالب روان باشن. در کنار مطالب سایت می تونی از کتاب های موجود هم استفاده کنی. من برای شما کتاب های « مرجع کامل میکروکنترلرهای AVR» از پرتویی فر و «میکروکنترلرهای AVR» از جابر الوندی رو پیشنهاد می دم. توی این کتاب ها برنامه نویسی مقدماتی C هم آموزش داده شده. اما چون ممکنه جاهایی از این کتاب ها برات نامفهوم باشن (چون رشته ت الکترونیک نیست) پیشنهاد می دم که از مطالب سایت هم استفاده کنی تا در صورتی که سوالی برات پیش اومد سوالاتت رو بپرسی و ما هم مطمئنا در جواب گویی در خدمتت هستیم.
          در سایت هم برنامه نویسی با هدف کاربرد در میکروکنترلر آموزش داده شده و هم الکترونیک از ب بسم الله آموزش هاش شروع شده و ادامه هم داره. همین طور در قسمت میکروکنترلر هم می تونی با AVR، امکانات، اجزای داخلیش و مثال ها و پروژه های کاربردی هم آشنا بشی. هرجا هم سوالی بود که مطمئنا اعضای گروه سعی می کنن در اسرع وقت پاسخ بدن.
          اگه باز هم سوالی هست در خدمتم.

          • سلام
            خیلی ممنون هم بابت راهنماییتون هم بابت مطالب مفیدتون،
            به نکات و راهنماییهاتون حتما عمل میکنم.
            اگر بازم مشکل یا سوالی بود حتما مززاحمتون میشم.
            با تشکر

  11. با عرض سلام و تشکر بابت سایت خوبتون
    من تازه گیا با دنیای الکترونیک و برنامه نویسی آشنا شدم
    و میخواستم برای شروع کار این مداری که آموزش دادین رو بسازم
    فقط محل منبع تغذیه رو مشخص نکردین
    GND میتونه قطب منفی باشه ولی قطب مثبت به کدام قسمت مدار وصل میشه؟ قبل از کلید قرار میگیره؟ یا مستقیم به میکروکنترلر وصل میشه؟
    خیلی ممنون میشم اگه راهنماییم کنید

    • سلام دوست عزیز
      توی این مدار علاوه بر این که GND مدار به قطب منفی منبع تغذیه تون وصل میشه، باید پایه های VCC و GND میکروکنترلر رو هم به ترتیب به قطب مثبت و منفی منبع تغذیه متصل کنید.
      با توجه به این که میکروکنترلری که این جا استفاده کردیم ATtiny 2313 هست، پین VCC پایه ی شماره ی ۲۰ و پین GND پایه ی شماره ی ۱۰ هست. شکل زیر چینش پایه های آرایش DIP این میکروکنترلر رو نشون میده:

      http://microlearn.ir/wp-content/uploads/2016/01/ATtiny-2313.jpg

      البته مطالب در مورد اتصال سخت افزاری میکرکنترلری در پست های آینده منتشر خواهد شد که جزییات بیشتر رو در اون پست خواهید خواند.
      با تشکر

  12. سلام من نظر سنجیی نمیبینم!میشه راهنمایی کنید کجا نظر بدم?

    • سلام
      در ستون سمت راست سایت، قسمت «درباره ی خودت بگو» یه نظرسنجی از بازدیدکنندگان سایت وجود داره. دلیل این نظر سنجی مطلع شدن ما از اینه که بازدیدکنندگان در چه سطحی هستند و بیشتر با چه زبانی و با چه میکروکنترلری کار می کنند. تا بتونیم مطالبی رو توی سایت بذاریم که بیشتر باب میل بازدیدکنندگان باشه.
      با تشکر

دیدگاهتان را بنویسید

نشانی ایمیل شما منتشر نخواهد شد. بخش‌های موردنیاز علامت‌گذاری شده‌اند *