سیسوگ در قسمت یازدهم آموزش میکروکنترلر STM8 راه اندازی LCD کاراکتری توسط میکروکنترلر STM8 را آموزش داد. در این قسمت از مجموعه مقالات آموزش میکروکنترلر STM8 سیسوگ قصد دارد مبحث مهم و کاربردی مبدل آنالوگ به دیجیتال (ADC) را آموزش دهد. با سیسوگ همراه باشید.
مبدل آنالوگ به دیجیتال (ADC):
گاهی لازم است ورودی آنالوگ به میکروکنترلر داده شود و این ورودی مورد پردازش قرار گیرد. در میکروکنترلرهای مدرن امروزی مبدل آنالوگ به دیجیتال (ADC) قابلیت مهمی به شمار می آید. برای خواندن خروجی آنالوگ از سنسورها، اندازه گیری ولتاژ و غیره از ADC استفاده می شود. برای مثال، ما میتوانیم از یک ADC برای خواندن سنسور دمای LM35 استفاده کنیم. ولتاژ خروجی سنسور متناسب با درجه حرارت است و ما میتوانیم از اطلاعات ولتاژ برای محاسبه دما استفاده کنیم. میکروکنترلر STM8 دارای چندین کانال و بلوک ADC است. به عنوان مثال، STM8S3F3 دارای 5 کانال و یک بلوک ADC است. ADC میکروکنترلر STM8 نیز مانند ADC دیگر میکروکنترلرهاست. تنها چند ویژگی اضافی دارد. شکل زیر نشانگر بلوک ADC میکروکنترلر STM8 است:
قبل از استفاده از ADC، باید چند نکته را که باعث افزایش عملکرد ADC میشود، بیان کنم:
امپدانس ورودی باید کمتر از 10kΩ باشد.
بهتر است کلاک ADC را در حدود 4 مگاهرتز یا کمتر قرار دهید.
اشیمیت تریگر باید غیرفعال شود.
در صورت امکان، از بافر ورودی و مدار فیلتر استفاده کنید.
اگر ADC دارای پین رفرنس باشد، این پین باید به یک رفرنس دقیق مانند LM336 متصل شود. توصیه میشود از یک تراشه رگولاتور LDO مناسب استفاده کنید.
پینهای ADC که مورد استفاده قرار نمیگیرند باید غیرفعال یا پیکربندی شوند. این کار باعث کاهش مصرف برق خواهد شد.
خواندن ADC باید در فواصل زمانی منظم و ثابت باشد تا از نوسانات زمانی در خواندن ADC جلوگیری شود.
برای افزایش پایداری بهتر است از بیتهای سمت راست (بیت های پرارزش ADC) استفاده کنید تا تأثیرات نویز را حذف نمایید.
فاصله ترکهای PCB / سیمها به کانال های ADC باید کوتاه باشد تا نویز را کاهش دهند.
اتصالات سخت افزاری
کد نمونه ADC
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 | #include "STM8S.h" #include "STM8S_lcd.h" void clock_setup(void); void GPIO_setup(void); void ADC1_setup(void); void lcd_print(unsigned char x_pos, unsigned char y_pos, unsigned int value); void main() { int j; unsigned int A0 = 0x0000; clock_setup(); GPIO_setup(); ADC1_setup(); LCD_init(); LCD_clear_home(); LCD_goto(4, 0); LCD_putstr("STM8 ADC"); LCD_goto(4, 1); LCD_putstr("A0"); while(TRUE) { ADC1_StartConversion(); while(ADC1_GetFlagStatus(ADC1_FLAG_EOC) == FALSE); A0 = ADC1_GetConversionValue(); ADC1_ClearFlag(ADC1_FLAG_EOC); lcd_print(8, 1, A0); for(j=0;j<9000;j++); }; } void clock_setup(void) { CLK_DeInit(); CLK_HSECmd(DISABLE); CLK_LSICmd(DISABLE); CLK_HSICmd(ENABLE); while(CLK_GetFlagStatus(CLK_FLAG_HSIRDY) == FALSE); CLK_ClockSwitchCmd(ENABLE); CLK_HSIPrescalerConfig(CLK_PRESCALER_HSIDIV2); CLK_SYSCLKConfig(CLK_PRESCALER_CPUDIV4); CLK_ClockSwitchConfig(CLK_SWITCHMODE_AUTO, CLK_SOURCE_HSI, DISABLE, CLK_CURRENTCLOCKSTATE_ENABLE); CLK_PeripheralClockConfig(CLK_PERIPHERAL_SPI, DISABLE); CLK_PeripheralClockConfig(CLK_PERIPHERAL_I2C, DISABLE); CLK_PeripheralClockConfig(CLK_PERIPHERAL_ADC, ENABLE); CLK_PeripheralClockConfig(CLK_PERIPHERAL_AWU, DISABLE); CLK_PeripheralClockConfig(CLK_PERIPHERAL_UART1, DISABLE); CLK_PeripheralClockConfig(CLK_PERIPHERAL_TIMER1, DISABLE); CLK_PeripheralClockConfig(CLK_PERIPHERAL_TIMER2, DISABLE); CLK_PeripheralClockConfig(CLK_PERIPHERAL_TIMER4, DISABLE); } void GPIO_setup(void) { GPIO_DeInit(GPIOD); GPIO_Init(GPIOD, GPIO_PIN_3, GPIO_MODE_IN_FL_NO_IT); GPIO_DeInit(GPIOC); GPIO_DeInit(GPIOB); } void ADC1_setup(void) { ADC1_DeInit(); ADC1_Init(ADC1_CONVERSIONMODE_CONTINUOUS, ADC1_CHANNEL_4, ADC1_PRESSEL_FCPU_D18, ADC1_EXTTRIG_GPIO, DISABLE, ADC1_ALIGN_RIGHT, ADC1_SCHMITTTRIG_CHANNEL4, DISABLE); ADC1_Cmd(ENABLE); } void lcd_print(unsigned char x_pos, unsigned char y_pos, unsigned int value) { char chr = 0x00; chr = ((value / 1000) + 0x30); LCD_goto(x_pos, y_pos); LCD_putchar(chr); chr = (((value / 100) % 10) + 0x30); LCD_goto((x_pos + 1), y_pos); LCD_putchar(chr); chr = (((value / 10) % 10) + 0x30); LCD_goto((x_pos + 2), y_pos); LCD_putchar(chr); chr = ((value % 10) + 0x30); LCD_goto((x_pos + 3), y_pos); LCD_putchar(chr); } |
توضیحات
در ابتدا، باید کلاک ماژول ADC را فعال کنیم:
1 | CLK_PeripheralClockConfig(CLK_PERIPHERAL_ADC, ENABLE); |
در مرحله دوم، باید پین ADC را به عنوان یک GPIO شناور بدون وقفه تنظیم کنیم.
1 | GPIO_Init(GPIOD, GPIO_PIN_3, GPIO_MODE_IN_FL_NO_IT); |
برای راه اندازی ADC به اطلاعاتی در مورد کانال ADC مورد نظر نیاز است:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 | void ADC1_setup(void) { ADC1_DeInit(); ADC1_Init(ADC1_CONVERSIONMODE_CONTINUOUS, ADC1_CHANNEL_4, ADC1_PRESSEL_FCPU_D18, ADC1_EXTTRIG_GPIO, DISABLE, ADC1_ALIGN_RIGHT, ADC1_SCHMITTTRIG_CHANNEL4, DISABLE); ADC1_Cmd(ENABLE); } |
خط دوم تابع فوق بیان می کند که ما قصد داریم از کانال ADC 4 (PD3) بدون هیچ اشمیت تریگری استفاده کنیم. همچنین نمی خواهیم از تریگرهای خارجی ماژول GPIO استفاده کنیم. از آنجا که کلاک اصلی در 8 مگاهرتز در حال اجرا است، ADC با تقسیم کلاک اصلی / کلاک ADC فرکانس نمونه برداری 444 کیلوهرتز را دریافت می کند.همچنین می خواهیم از حالت تبدیل مستمر استفاده کنیم زیرا می خواهیم به طور مداوم ورودی ADC را بخوانیم و نمی خواهیم آن را در فواصل خاص اندازه گیری کنیم. در نهایت استفاده از بیت های سمت راست ADC باعث می شود مقدار پایدارتری داشته باشیم.
در حلقه اصلی، باید تبدیل ADC را شروع کنیم و صبر کنیم تا تبدیل به پایان برسد. از آنجا که از وقفه استفاده نکردیم باید به پایان رسیدن تبدیل ADC را چک کنیم. در پایان تبدیل، می توانیم ADC را بخوانیم و پرچم اتمام تبدیل ADC را پاک کنیم.
1 2 3 4 5 | ADC1_StartConversion(); while(ADC1_GetFlagStatus(ADC1_FLAG_EOC) == FALSE); A0 = ADC1_GetConversionValue(); ADC1_ClearFlag(ADC1_FLAG_EOC); |
بقیه کد مربوط به چاپ داده های ADC بر روی LCD است.
سیسوگ در قسمت سیزدهم قصد دارد تایمر نگهبان آنالوگ (AWD) را آموزش دهد. در ادامه آموزش های میکروکنترلر STM32 سیسوگ را همراهی کنید.
لینکهای دانلود
مطالب مرتبط
- قسمت اول − میکروکنترلر STM8 چیست و از کجا آمده است؟
- قسمت دوم − معرفی بردهای Discovery میکروکنترلر STM8
- قسمت سوم − کامپایلر و پروگرامر
- قسمت چهارم − STM8CubeMX
- قسمت پنجم − آماده سازی ابزارهای نرمافزاری برای STM8
- قسمت ششم − چگونه برنامه خود را روی STM8 آپلود کنیم؟
- قسمت هفتم− LED چشمکزن
- قسمت هشتم − کلاک سیستم (CLK)
- قسمت نهم − وقفه خارجی (EXTI)
- قسمت دهم − Beeper
- قسمت یازدهم − LCD کاراکتری
- قسمت سیزدهم − تایمر نگهبان آنالوگ (AWD)
- قسمت چهادهم − تایمر نگهبان (IWDG)
- قسمت پانزدهم − تایمر نگهبان محدوده ای (WWDG)
- قسمت شانزدهم− اصول اولیه تایمرها
- قسمت هفدهم− تایمر 2
- قسمت هجدهم −تایمر 4
- قسمت نوزدهم −PWM
- قسمت بیستم − PWM تایمر 1
- قسمت بیست و یکم − بررسی اجمالی ارتباطات
- قسمت بیست و دوم − رابط سریال (UART)
- قسمت بیست و سوم − رابط کاربری سریال (SPI)
- قسمت بیست و چهارم − رابط I2C
- دوره رایگان آموزش میکروکنترلر STM8 – سیسوگ
سلام برا ساخت ضبط صدا با میکروstm میشه راهنمایی کنید
ممنون
سلام
خوب برای دخیره صدا در اولین اقدام باید بتونی حداقل ۸ کیلو سمپل از ADC بگیری، که فکر نمیکنم مشکل خاصی باشه
بعد اگر بخوای به شکل فایل ذخیره کنی، باید فایل سیستم رو هندل کنی که میتونی از کتابخانه elm-chanاستفاده کنی
و فایل رو با فرمت pcm wave توی یه فایل ذخیره کنی
این کل مراحلی هست که لازمه طی بشه
با عرض سلام و خسته نباشید. سوالی داشتم. میخواستم بدانم برای اتصال نمایشگر oled با تراشه ssd1306 به میکروکنترلر stm8 کتابخانه ای هست برای برنامه نویسی؟ چطور باید وصل کنیم و برنامه اش را بنویسیم؟ باتشکر
سلام دوست عزیز
فکر نمیکنم کار خیلی سختی باشه شما کتابخانه ای که برای میکروی دیگری نوشته شده رو میتونید برای این منظور استفاده کنید تنها نیاز است که بخش ارتباطی رو باز نویسی کنید و به همین قشنگی باقی بخش ها کار خواهد کرد.
با سلام
ممنون بابت آموزشهای کاربردی که در سایت قرار دادید خیلی قابل استفاده بود
موفق باشید
سلام خواهش میکنم دوست عزیز
سلام میشه یه مقدار بیشتر درباره مقاومت ورودی توضیح بدین؟
مثلا من میخوام برا اندازه گیریه یه ولتاژ بالا از تقسیم مقاومتی 100 کیلو و 3.3 کیلو استفاده کنم میشه ؟
باید ببینید مقاومت ورودی میکروکنترلر چقدر هست (فکر کنم حدود ده کیلو یا صد کیلو باشه) خوب این مقاومت پایه ورودی adc با زمین خواهد بود که احتمالا در نمونه شما موازی خواهد شد مقاومت ۳٫۳ کیلو اهم شما که در نوع خود باعث ایجاد خطای اندکی خواهد شد.
برای جلوگیری از حالت خیلی راحت میتوان از یه تقویت کننده عملیاتی استفاده کرد به عنوان بافر
سلام چطور سنسور با 5v رو با این کد راه اندازی کنم ؟
سلام میتونید تقسیم مقاومتی بگذارید
سلام برای راه اندازی یه سنسور آنالوگ با ورودی ۵ ولت باید چه تغییراتی توی کد داد ؟ ممنون میشم جواب بدید متشکر
سلام
احتمالا باید از تقسیم مقاومتی استفاده کنید
البته توجه داشته باید رینج خروجی سنسور مورد استفاده تون چیه
با سلام
یه سوال کوچیک!!
“اشیمیت تریگر باید غیرفعال شود” منظور از اشمیت تریگر adc چیه ؟ و کاربردش چگونه است؟
سلام دوست عزیز
از پورت های آنالوگ میتوان به صورت دیجیتال هم استفاده کرد. اینجا گفتیم اشمیت تریگر را خاموش کنید تا پورت برای استفاده آنالوگ کانفیگ بشه.
موفق باشید.
سلام خسته نباشید
کد اتصال دو ADC چطوری میشه؟
لطفا راهنمایی کنید خیلی واجبه
سلام ببخشید منظورتون رو متوجه نشدم ؛ یعنی میخواید با استفاده از دو واحد ADC از یک سینگال نمونه برداری کنید تا نرخ نمونه برداری رو افزایش بدید یا خیر منظورتون این هست که از دو کانال ADC استفاده کنید ؟
سلام خسته نباشید
سوال بنده هم همین مورده چطور میشه دو کانال رو خوند مثلا کانال 5 و کانال 6
سلام دوست عزیز
خوب برای این کار چندین راه وجود داره ولی مرسوم ترین راه ها یکی این هست که اول کانال یک رو بخونید بعد کانال دو و الی آخر (استفاده از اینتراپت اتمام تبدیل خیلی کمک میکنه که پردازنده گیر نکنه)
راه مرسوم دیگه استفاده از dma هست که کلا پردازنده درگیر نمیشه – فقط باید تنظیم کنید که خود adc تبدیل رو به شکل چرخشی انجام بده و dma نمونه ها رو کپی کنه توی متغییری که تعریف کردید.
مثالش هم فکر میکنم توی مثال های st بتونید پیدا کنید.
با عرض سلام و خسته نباشید
در آموزش فوق عنوان کرده بودید از فیلتر استفاده بشه ، می خواستم ببینم چطور می شه این کارو کرد و البته از چه فیلتری ؟یعنی انقدر نویز روی سنسورهای حرارتی زیاده؟
با تشکر از وقتی که برای آموزش بدون چشم داشت می گذارید.
موفق باشید!
سلام
شاید مدار بدون فیلتر هم تا حدودی زیادی خوب کار کنه و با چند فیلتر نرم افزاری بشه کلا بی خیال مدارات فیلتر خارجی شد ؛ اما چیزی که مشخصه نویز همیشه توی همه شرایطی وجود داره و برای حصول نتیجه دلخواه لازمه که نویز های غیر ضرروری رو حذف کنید در واقع نتیجه ایده آل اینه ممکنه نویز تا حدود مشخصی نتیجه رو اینقدری روی نتیجه تاثیر گذار نباشه و بشه ازش چشم پوشی کرد
به صورت میشه فیلتر رو پیاده سازی کرد ، یه شکل یک نرم افزار و با پردازش سینگال این کار رو انجام داد یا با استفاده از یک مدار خارجی !
مدار فیلتر میتونه اکتیو یا پسیو باشه که نوع المان های مورد استفاده متفاوته و نوع فیلتر با نوع استفاده مشخص میشه
اینجا منظور فیلتر پایین گذر مدنظر هست که در ساده ترین حالت ممکن با مقاومت و خازن میشه ساختش
دوست بزرگوار خیلی لطف کردی امیدوارم همواره موفق باشید .
در نمونه برنامه ای فیلتر های FIR استفاده کرده بود . با متلب ضرایب فیلترو محاسبه کرده بود و بعد یه کد C++ واسش نوشته بود .
خیلی متوجه نشدم چطور حساب کرده ولی امیدوارم خیلی زود بفهمم. 🙂
در پناه خدا باشید.
خواهش میکنم دوست عزیز
نرم افزاری زیادی برای محاسبه فیلتر های دیجیتال و حتی آنالوگ وجود داره حتی برخی از این نرم افزار های کد برنامه رو هم تولید میکنند
به عنوان نمونه میتونید نرم افزار filter solution رو سرچ کنید.
خیلی ممنون.
خیلی لطف کردید.
موفق و موید باشید!
خواهش میکنم
سلامت باشید
سلام
کارتون عالیه
کمتر کسیه که با STM8 کار کنه …
ممنون از آموزش خوبتون
سلام
خواهش میکنم دوست عزیز… خوشحال میشیم اگه کمکی به یادگیری همراهان سیسوگ کرده باشیم