สารบัญ:

เครื่องวัดอุณหภูมิและระดับแสงพร้อมการแสดงบน LCD NOKIA 5110: 4 ขั้นตอน
เครื่องวัดอุณหภูมิและระดับแสงพร้อมการแสดงบน LCD NOKIA 5110: 4 ขั้นตอน

วีดีโอ: เครื่องวัดอุณหภูมิและระดับแสงพร้อมการแสดงบน LCD NOKIA 5110: 4 ขั้นตอน

วีดีโอ: เครื่องวัดอุณหภูมิและระดับแสงพร้อมการแสดงบน LCD NOKIA 5110: 4 ขั้นตอน
วีดีโอ: สอนใช้งาน arduino กับ AMT1001 วัดอุณหภูมิและความชื้นในอากาศ พร้อมโค้ดตัวอย่าง 2024, กรกฎาคม
Anonim
Image
Image

สวัสดีทุกคน!

ในส่วนนี้ เราสร้างอุปกรณ์อิเล็กทรอนิกส์อย่างง่ายเพื่อตรวจสอบอุณหภูมิและระดับแสง การวัดค่าพารามิเตอร์เหล่านี้จะแสดงบน LCD NOKIA 5110 อุปกรณ์นี้ใช้ไมโครคอนโทรลเลอร์ AVR ATMEGA328P อุปกรณ์ตรวจสอบติดตั้งเทอร์โมมิเตอร์แบบดิจิตอล DS18B20 และโฟโตรีซีสเตอร์เพื่อวัดระดับแสง

ขั้นตอนที่ 1: คำอธิบายส่วนประกอบ

คำอธิบาย ส่วนประกอบ
คำอธิบาย ส่วนประกอบ
คำอธิบาย ส่วนประกอบ
คำอธิบาย ส่วนประกอบ

ส่วนประกอบพื้นฐานของอุปกรณ์ตรวจสอบ:

  • ไมโครคอนโทรลเลอร์ AVR «ATMEGA328P»
  • จอ LCD ขาวดำ «NOKIA 5110»
  • เทอร์โมมิเตอร์แบบดิจิตอล 1 สายความละเอียดที่ตั้งโปรแกรมได้ «DS18B20»
  • ตัวต้านทานที่ขึ้นกับแสง
  • สายไฟ

ไมโครคอนโทรลเลอร์ AVR «ATMEGA328P»

อุปกรณ์ตรวจสอบใช้คุณสมบัติต่อพ่วงของไมโครคอนโทรลเลอร์ดังต่อไปนี้:

  1. ตัวจับเวลา/ตัวนับขัดจังหวะ 16 บิต
  2. ADC. 8 ช่อง 10 บิต
  3. อินเทอร์เฟซแบบอนุกรม SPI หลัก/รอง

จอ LCD ขาวดำ «NOKIA 5110»

ข้อมูลจำเพาะ:

  1. จอแสดงผล LCD 48 x 84 Dot
  2. Serial Bus Interface ที่มีความเร็วสูงสุด 4 Mbits/S
  3. ตัวควบคุม/ไดรเวอร์ภายใน «PCD8544»
  4. ไฟหลัง LED
  5. ทำงานที่แรงดันไฟ 2.7-5 โวลต์
  6. การใช้พลังงานต่ำ; เหมาะสำหรับการใช้งานแบตเตอรี่
  7. ช่วงอุณหภูมิตั้งแต่ -25˚C ถึง +70˚C
  8. รองรับสัญญาณอินพุต CMOS

การจัดการที่อยู่ LCD (ที่อยู่):

การจัดเรียงที่อยู่ของหน่วยความจำที่แสดงบนจอ LCD (DDRAM) คือ Matrix ที่ประกอบด้วย 6 แถว (Y Address) จาก Y-Address 0 ถึง Y-Address 5 และ 84 คอลัมน์ (X Address) จาก X-Address 0 ถึง X- ที่อยู่ 83. หากผู้ใช้ต้องการเข้าถึงตำแหน่งแสดงผลบนจอ LCD ต้องอ้างอิงถึงความสัมพันธ์ระหว่าง X-Address และ Y-Address

ข้อมูลที่จะส่งไปแสดงผลคือ 8 บิต (1 ไบต์) และจะถูกจัดเรียงเป็นเส้นแนวตั้ง ในกรณีนี้ Bit MSB จะต่ำกว่าและ Bit LSB จะอยู่ด้านบนตามที่แสดงในภาพ

ความละเอียดที่ตั้งโปรแกรมได้ 1-Wire Digital Thermometer DALLAS «DS18B20»

คุณสมบัติ:

  1. อินเทอร์เฟซ 1-Wire® ที่ไม่ซ้ำใครต้องใช้พินพอร์ตเดียวสำหรับการสื่อสาร
  2. ลดจำนวนส่วนประกอบด้วยเซ็นเซอร์อุณหภูมิในตัวและ EEPROM
  3. วัดอุณหภูมิตั้งแต่ -55 °C ถึง +125°C (-67°F ถึง +257°F)
  4. ความแม่นยำ ±0.5°C ตั้งแต่ -10°C ถึง +85°C
  5. ความละเอียดที่ตั้งโปรแกรมได้ตั้งแต่ 9 บิตถึง 12 บิต
  6. ไม่จำเป็นต้องมีส่วนประกอบภายนอก
  7. โหมด Parasitic Power ต้องการเพียง 2 พินสำหรับการทำงาน (DQ และ GND)
  8. ลดความซับซ้อนของแอพพลิเคชั่นตรวจจับอุณหภูมิแบบกระจายด้วยความสามารถ Multidrop
  9. อุปกรณ์แต่ละตัวมีรหัสซีเรียล 64 บิตที่ไม่ซ้ำกันซึ่งจัดเก็บไว้ใน ROM ออนบอร์ด
  10. การตั้งค่าสัญญาณเตือนแบบไม่ลบเลือนที่ผู้ใช้กำหนดได้ (NV) ที่ยืดหยุ่นพร้อมคำสั่งค้นหาสัญญาณเตือนจะระบุอุปกรณ์ที่มีอุณหภูมิเกินขีดจำกัดที่ตั้งโปรแกรมไว้

การใช้งาน:

  1. ตัวควบคุมอุณหภูมิ
  2. ระบบอุตสาหกรรม
  3. สินค้าอุปโภคบริโภค
  4. เครื่องวัดอุณหภูมิ
  5. ระบบไวต่อความร้อน

ตัวต้านทานที่ขึ้นกับแสง

ตัวต้านทานแบบพึ่งพาแสง (LDR) เป็นทรานสดิวเซอร์ที่เปลี่ยนความต้านทานเมื่อแสงตกบนพื้นผิวเปลี่ยนแปลง

โดยทั่วไปแล้ว LDR จะมีตั้งแต่หนึ่งเมกะโอห์มถึงสองเมกะโอห์มที่ความมืดทั้งหมด จากสิบถึงยี่สิบกิโลโอห์มที่สิบ LUX จากสองถึงห้ากิโลโอห์มที่ 100 LUX ความต้านทานระหว่างหน้าสัมผัสทั้งสองของเซ็นเซอร์ลดลงตามความเข้มของแสงหรือค่าการนำไฟฟ้าระหว่างหน้าสัมผัสสองตัวของเซ็นเซอร์เพิ่มขึ้น

ใช้วงจรแบ่งแรงดันเพื่อแปลงการเปลี่ยนแปลงความต้านทานเป็นการเปลี่ยนแปลงแรงดัน

ขั้นตอนที่ 2: รหัสเฟิร์มแวร์ไมโครคอนโทรลเลอร์

#ifndef F_CPU#define F_CPU 16000000UL // บอกความถี่คริสตัลคอนโทรลเลอร์ (16 MHz AVR ATMega328P) #endif

// SPI INTERFACE กำหนด #define MOSI 3 // MOSI เป็น PORT B, PIN 3 #define MISO 4 // MISO เป็น PORT B, PIN 4 #define SCK 5 // SCK เป็น PORT B, PIN 5 #define SS 2 // SS มันคือ PORT B, PIN 2

// RESET THE DISPLAY #define RST 0 // RESET เป็น PORT B, PIN 0

// DISPLAY MODE SELECT - อินพุตเพื่อเลือกคำสั่ง/ที่อยู่หรืออินพุตข้อมูล #define DC 1 // DC คือ PORT B, PIN 1

// รหัสอาร์เรย์ของสัญญาณเชิงลบ const ถ่านที่ไม่ได้ลงนาม [4] = {0x30, 0x30, 0x30, 0x30};

// รหัสอาร์เรย์ของตัวเลข [0..9] คงที่ const ถ่านที่ไม่ได้ลงชื่อ font6x8 [16] = { 0xFC, 0xFE, 0xFE, 0x06, 0x06, 0xFE, 0xFE, 0xFC, 0x01, 0x03, 0x03, 0x03, 0x03, 0x03, 0x03, 0x01}, // 0 { 0x00, 0x00, 0x18, 0x1C, 0xFE, 0xFE, 0xFC, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x03, 0x01, 0x00}, // 1 { 0x0C, 0x8E, 0xCE, 0xE6, 0xE6, 0xBE, 0x9E, 0x0C, 0x01, 0x03, 0x03, 0x03, 0x03, 0x03, 0x03, 0x01}, // 2 { 0x00, 0x04, 0x06, 0x26, 0x76, 0xFE, 0x8C, 0x00, 0x01, 0x03, 0x03, 0x03, 0x03, 0x03, 0x01}, // 3 { 0x3C, 0x3E, 0x7C, 0x60, 0x60, 0xFC, 0xFE, 0xFC, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x03, 0x01}, // 4 { 0x1C, 0x3E, 0x3E, 0x36, 0x36, 0xF6, 0xF6, 0xE4, 0x01, 0x03, 0x03, 0x03, 0x03, 0x03, 0x03, 0x01}, // 5 { 0xFC, 0xFE, 0xFE, 0x36, 0x36, 0xF6, 0xF6, 0xE4, 0x01, 0x03, 0x03, 0x03, 0x03, 0x03, 0x03, 0x01}, // 6 { 0x04, 0x06, 0x06, 0x86, 0xE6, 0xFEx1C7E, 0xFEx1C7E,, 0x00, 0x00, 0x00, 0x01, 0x03, 0x01, 0x00, 0x00}, // 7 { 0xCC, 0xFE, 0xFE, 0x36, 0x36, 0xFE, 0xFE, 0xCC, 0x01, 0x03, 0x03, 0x03, 0x03, 0x03, 0x0 3, 0x01}, // 8 { 0x3C, 0x7E, 0x7E, 0x66, 0x66, 0xFE, 0xFE, 0xFC, 0x01, 0x03, 0x03, 0x03, 0x03, 0x03, 0x03, 0x01} // 9 };

// รหัสอาร์เรย์ของคำว่า "TEMP:" คงที่ const unsigned char TEMP_1 [165] = { 0x02, 0x06, 0x06, 0xFE, 0xFE, 0xFE, 0x06, 0x06, 0x02, 0x00, 0xFC, 0xFE, 0xFE, 0x26, 0x26, 0x24, 0x00, 0xFC, 0xFE, 0xFE, 0x1C, 0x38, 0x70, 0x38, 0x1C, 0xFE, 0xFE, 0xFC, 0x00, 0xFC, 0xFE, 0xFE, 0x66, 0x66, 0x7E, 0x7E, 0x3C8, 0x00, 0x00 0x00, 0x00, 0x00, 0x01, 0x03, 0x01, 0x00, 0x00, 0x00, 0x00, 0x01, 0x03, 0x03, 0x03, 0x03, 0x01, 0x00, 0x01, 0x03, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00 0x01, 0x03, 0x01, 0x00, 0x01, 0x03, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x01, 0x0C, 0x1E, 0x33, 0x33, 0x1E, 0x0C, 0x00x00, 0xF8, 0xFC 0x9C, 0x98, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x03, 0x03, 0x03, 0x01, };

// รหัสอาร์เรย์ของคำว่า "LUX:" const unsigned char TEMP_2 [60] = { 0xFC, 0xFE, 0xFC, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFC, 0xFE, 0xFC, 0x00, 0x00, 0xFC, 0xFE, 0xFC, 0x00, 0x04, 0x8E, 0xDE, 0xFC, 0xF8, 0xFC, 0xDE, 0x8E, 0x04, 0x00, 0x8C, 0x8C, 0x01, 0x03, 0x03, 0x03, 0x03, 0x03, 0x03, 0x01, 0x01, 0x03, 0x03, 0x03, 0x03, 0x03, 0x03, 0x01, 0x00, 0x01, 0x03, 0x03, 0x01, 0x00, 0x01, 0x03, 0x03, 0x01, 0x00, 0x01, 0x01 };

#รวม

#รวม #รวม

// การเริ่มต้นพอร์ตเป็นโมฆะ Port_Init() { DDRB = (1<<MOSI)| (1<<SCK)|(1<<SS)|(1<<RST)|(1<<DC);// ตั้งค่า MOSI, SCK, SS, RST, DC เป็นเอาต์พุต, อินพุตอื่นๆ ทั้งหมด PORTB |= (1<<RST);// ตั้งค่าพิน RST เป็น PORTB สูง |= (1<<SS);// ตั้งค่าพิน SS ให้สูง - แสดง ปิดการใช้งาน DDRC=0xFFu; // ตั้งค่าพินทั้งหมดของ PORTC เป็นเอาต์พุต DDRC &= ~(1<<0);//สร้างพินแรกของ PORTC เป็นอินพุต PORTC=0x00u; // ตั้งค่าพินทั้งหมดของ PORTC ให้ต่ำ ซึ่งจะปิด }

// การเริ่มต้น ADC เป็นโมฆะ ADC_init () { // เปิดใช้งาน ADC, ความถี่สุ่มตัวอย่าง = osc_freq/128 ตั้งค่าพรีสเกลเลอร์เป็นค่าสูงสุด, 128 ADCSRA |= (1<<ADEN) | (1<<ADPS2)| (1<<ADPS1)| (1<<ADPS0); ADMUX = (1<<REFS0); // เลือกการอ้างอิงแรงดันไฟฟ้าสำหรับ ADC // เลือกศูนย์ช่องสัญญาณตามค่าเริ่มต้นโดยใช้ ADC Multiplexer Select register (ADC0) }

// ฟังก์ชั่นอ่านผลลัพธ์ของการแปลงอนาล็อกเป็นดิจิตอล uint16_t get_LightLevel() { _delay_ms(10); // รอสักครู่เพื่อให้ช่องได้รับเลือก ADCSRA |= (1<<ADSC); // เริ่มการแปลง ADC โดยการตั้งค่าบิต ADSC เขียน 1 ถึง ADSC ในขณะที่ (ADCSRA & (1<<ADSC)); // รอให้การแปลงเสร็จสิ้น // ADSC กลายเป็น 0 อีกครั้งจนกว่าจะถึงตอนนั้น ให้รันลูปอย่างต่อเนื่อง _delay_ms(10); ผลตอบแทน (ADC); // ส่งคืนผลลัพธ์ 10 บิต }

// การเริ่มต้น SPI เป็นโมฆะ SPI_Init () { SPCR = (1<<SPE) | (1<<MSTR) | (1<<SPR0); // เปิดใช้งาน SPI ตั้งเป็น Master ตั้งค่า Prescaler เป็น Fosc/16 ในการควบคุม SPI ลงทะเบียน }

// เริ่มต้น 16 บิต Timer1, อินเตอร์รัปต์และตัวแปร void TIMER1_init () {// ตั้งค่าตัวจับเวลาด้วย prescaler = 256 และโหมด CTC TCCR1B |= (1 << WGM12) | (1 << CS12); // เริ่มต้นตัวนับ TCNT1 = 0; // เริ่มต้นเปรียบเทียบค่า - 1 วินาที OCR1A = 62500; // เปิดใช้งานการเปรียบเทียบการขัดจังหวะ TIMSK1 |= (1 << OCIE1A); // เปิดใช้งานการขัดจังหวะทั่วโลก sei(); }

// เปิดใช้งานการแสดงผลเป็นโมฆะ SPI_SS_Enable () { PORTB &= ~ (1<<SS); // เปิดใช้งาน SS pin เพื่อตรรกะ 0 }

// แสดงปิดการใช้งานโมฆะ SPI_SS_Disable () { PORTB |= (1<<SS); // ปิดการใช้งาน SS pin เป็นลอจิก 1 }

// ฟังก์ชันในการส่งข้อมูลไปยังบัฟเฟอร์การแสดงผลเป็นโมฆะ SPI_Tranceiver (ข้อมูลถ่านที่ไม่ได้ลงนาม) { SPDR = data; //โหลดข้อมูลลงในบัฟเฟอร์ while(!(SPSR & (1<<SPIF)))); //รอจนกว่าการส่งจะเสร็จสิ้น }

// รีเซ็ตจอแสดงผลเมื่อเริ่มต้นการเริ่มต้นเป็นโมฆะ Display_Reset () { PORTB &= ~ (1<<RST); _delay_ms(100); PORTB |= (1<<RST); }

// ฟังก์ชันเขียนคำสั่งเป็นโมฆะ Display_Cmnd (ข้อมูลถ่านที่ไม่ได้ลงชื่อ) { PORTB &= ~ (1<<DC); // ทำให้ DC pin เป็นตรรกะ 0 สำหรับการดำเนินการคำสั่ง SPI_Tranceiver (ข้อมูล); // ส่งข้อมูลบน data register PORTB |= (1<<DC); // ทำให้ DC pin เป็นตรรกะสูงสำหรับการดำเนินการข้อมูล }

// การเริ่มต้นของการแสดงผลเป็นโมฆะ Display_init () { Display_Reset (); // รีเซ็ตจอแสดงผล Display_Cmnd(0x21); // ชุดคำสั่งในโหมดเพิ่มเติม Display_Cmnd(0xC0); // ตั้งค่าแรงดันไฟฟ้าโดยส่ง C0 หมายถึง VOP = 5V Display_Cmnd(0x07); //ตั้งอุณหภูมิ ค่าสัมประสิทธิ์ถึง 3 Display_Cmnd(0x13); // ตั้งค่าของ Voltage Bias System Display_Cmnd(0x20); // ชุดคำสั่งในโหมดพื้นฐาน Display_Cmnd(0x0C); // แสดงผลในโหมดปกติ }

// เคลียร์ Display void Display_Clear() { PORTB |= (1<<DC); // ทำให้ DC pin เป็นตรรกะสูงสำหรับการดำเนินการข้อมูลสำหรับ (int k=0; k<=503; k++){SPI_Tranceiver(0x00);} PORTB &= ~(1<<DC); // ทำให้ DC pin เป็นตรรกะ ศูนย์สำหรับการดำเนินการคำสั่ง }

// ตั้งค่าคอลัมน์และแถวเป็นตำแหน่งแสดงผลบนจอ LCD ถือเป็นโมฆะ Display_SetXY (ถ่านที่ไม่ได้ลงชื่อ x, ถ่านที่ไม่ได้ลงชื่อ) { Display_Cmnd (0x80 | x); // คอลัมน์ (0-83) Display_Cmnd(0x40|y); // แถว (0-5) }

// ฟังก์ชั่นแสดงเครื่องหมายลบเป็นโมฆะ Display_Neg (ถ่านที่ไม่ได้ลงชื่อ) { Display_SetXY (41, 0); // ตั้งค่าที่อยู่ของตำแหน่งที่แสดงสำหรับ (int index=0; index0) {SPDR = 0x30;} //โหลดข้อมูลลงในบัฟเฟอร์ของการแสดงผล (แสดงเครื่องหมายลบ) อื่น {SPDR = 0x00;} // โหลดข้อมูลลงใน บัฟเฟอร์ของการแสดงผล (ล้างเครื่องหมายลบ) ในขณะที่(!(SPSR & (1<<SPIF)))); //รอจนกว่าการส่งจะเสร็จสมบูรณ์ _delay_ms(100); } }

// ฟังก์ชันเพื่อล้างเครื่องหมายดิจิทัลเป็นโมฆะ Off_Dig (ถ่านที่ไม่ได้ลงชื่อ x, ถ่านที่ไม่ได้ลงชื่อ y) { Display_SetXY (x, y); // ตั้งค่าที่อยู่ของตำแหน่งที่แสดง (แถวบนสุด) สำหรับ (int index=0; index<8; index++) {SPI_Tranceiver(0);} //โหลดข้อมูลลงในบัฟเฟอร์ของจอแสดงผล (ล้างส่วนบนของป้ายดิจิตอล) ย++; Display_SetXY(x, y);// ตั้งค่าที่อยู่ของตำแหน่งบนจอแสดงผล (แถวล่าง) สำหรับ (ดัชนี int=0; ดัชนี<8; ดัชนี++) {SPI_Tranceiver(0);}// โหลดข้อมูลลงในบัฟเฟอร์ของจอแสดงผล (ล้างส่วนล่างของป้ายดิจิตอล) }

// ฟังก์ชั่นแสดงสัญญาณดิจิทัลเป็นโมฆะ Display_Dig (int dig, ถ่าน x ที่ไม่ได้ลงชื่อ, ถ่าน y ที่ไม่ได้ลงชื่อ) { Display_SetXY (x, y); // ตั้งค่าที่อยู่ของตำแหน่งที่แสดง (แถวบนสุด) สำหรับ (ดัชนี int = 0; ดัชนี <16; index++) { if (index==8){y++;Display_SetXY(x, y);} // ตั้งค่าที่อยู่ของตำแหน่งที่แสดง (แถวล่าง) SPI_Tranceiver(font6x8[dig][index]); // โหลดโค้ดอาร์เรย์ของข้อมูลตัวเลขลงในบัฟเฟอร์ของ display _delay_ms(10); } }

// การเริ่มต้นของ DS18B20 ถ่านที่ไม่ได้ลงนาม DS18B20_init () { DDRD |= (1 << 2); // ตั้งค่าพิน PD2 ของ PORTD เป็นเอาต์พุต PORTD &= ~(1 << 2); // ตั้งค่าพิน PD2 ให้ต่ำ _delay_us(490); // การกำหนดเวลาเริ่มต้น DDRD &= ~ (1 << 2); // ตั้งค่าพิน PD2 ของ PORTD เป็นอินพุต _delay_us(68); // ระยะเวลา OK_Flag = (PIND & (1 << 2)); // รับชีพจรเซ็นเซอร์ _delay_us (422); กลับ OK_Flag; // ส่งคืนเซ็นเซอร์ 0-ok เป็นปลั๊ก, เซ็นเซอร์ข้อผิดพลาด 1 รายการถูกถอดออก }

// ฟังก์ชั่นอ่านไบต์จาก DS18B20 ถ่านที่ไม่ได้ลงนาม read_18b20 () { ถ่านที่ไม่ได้ลงชื่อ, ข้อมูล = 0; สำหรับ (i = 0; i <8; i++) { DDRD |= (1 << 2); // ตั้งค่าพิน PD2 ของ PORTD เป็นเอาต์พุต _delay_us (2); // Timing DDRD &= ~ (1 1; // บิตถัดไป if (PIND & (1 << 2)) data |= 0x80; // ใส่บิตลงในไบต์ _delay_us (62); } ส่งคืนข้อมูล }

// ฟังก์ชั่นการเขียนไบต์ไปยัง DS18B20 ถือเป็นโมฆะ write_18b20 (ข้อมูลถ่านที่ไม่ได้ลงนาม) { ถ่าน i ที่ไม่ได้ลงชื่อ; สำหรับ (i = 0; i <8; i++) { DDRD |= (1 << 2); // ตั้งค่าพิน PD2 ของ PORTD เป็นเอาต์พุต _delay_us (2); // เวลาถ้า (ข้อมูล & 0x01) DDRD &= ~ (1 << 2); // ถ้าเราต้องการเขียน 1 ให้ปล่อยบรรทัดอื่น DDRD |= (1 1; // บิตถัดไป _delay_us(62); // Timing DDRD &= ~ (1 << 2); // ตั้งค่าพิน PD2 ของ PORTD เป็นอินพุต _delay_us(2); } }

// ฟังก์ชั่นแสดงระดับแสงเป็นโมฆะ Read_Lux () { uint16_t buffer; int ที่ไม่ได้ลงชื่อ temp_int_1, temp_int_2, temp_int_3, temp_int_0; // หลักเดียว สองหลัก สามหลัก บัฟเฟอร์หลักสี่ = get_LightLevel(); // อ่านผลลัพธ์ของการแปลงระดับแสงแบบแอนะล็อกเป็นดิจิตอล temp_int_0 = บัฟเฟอร์ % 10000 / 1000; // ตัวเลขสี่หลัก temp_int_1 = บัฟเฟอร์ % 1,000/100; // สามหลัก temp_int_2 = บัฟเฟอร์ % 100 / 10; // สองหลัก temp_int_3 = บัฟเฟอร์ % 10; // ตัวเลขหลักเดียว if (temp_int_0 > 0) // ถ้าผลลัพธ์เป็นตัวเลขหลักสี่ { Display_Dig (temp_int_0, 32, 2); // แสดงระดับแสง 1 หลัก Display_Dig(temp_int_1, 41, 2); // แสดงระดับแสง 2 หลัก Display_Dig(temp_int_2, 50, 2); // แสดงระดับแสง 3 หลัก Display_Dig(temp_int_3, 59, 2); // แสดงระดับแสง 4 หลัก } else { if(temp_int_1 > 0) // ถ้าผลลัพธ์เป็นตัวเลขสามหลัก { Off_Dig (32, 2); // ล้างตัวเลข 1 ตัว Display_Dig(temp_int_1, 41, 2); // แสดงระดับแสง 1 หลัก Display_Dig(temp_int_2, 50, 2); // แสดงระดับแสง 2 หลัก Display_Dig(temp_int_3, 59, 2); // แสดงระดับแสง 3 หลัก } else { if(temp_int_2 > 0) // ถ้าผลลัพธ์เป็นตัวเลขสองหลัก { Off_Dig (32, 2); // เคลียร์เลข 1 ตัว Off_Dig(41, 2); // ล้างตัวเลข 2 ตัว Display_Dig(temp_int_2, 50, 2); // แสดงระดับแสง 1 หลัก Display_Dig(temp_int_3, 59, 2); // แสดงระดับแสง 2 หลัก } อื่น // หากผลลัพธ์เป็นตัวเลขหลักเดียว { Off_Dig (32, 2); // เคลียร์เลข 1 ตัว Off_Dig(41, 2); // เคลียร์เลข 2 ตัว Off_Dig(50, 2); // ล้างตัวเลข 3 ตัว Display_Dig(temp_int_3, 59, 2); // แสดงระดับแสง 1 หลัก } } } }

// ฟังก์ชั่นแสดงอุณหภูมิเป็นโมฆะ Read_Temp () { บัฟเฟอร์ int ที่ไม่ได้ลงนาม; int ที่ไม่ได้ลงชื่อ temp_int_1, temp_int_2, temp_int_3; // หลักเดียว, สองหลัก, สามหลัก, ตัวเลขสี่หลักที่ไม่ได้ลงชื่อ ถ่าน Temp_H, Temp_L, OK_Flag, temp_flag; DS18B20_init(); // การเริ่มต้นของ DS18B20 write_18b20(0xCC); // ตรวจสอบรหัสเซ็นเซอร์ write_18b20(0x44); // เริ่มการแปลงอุณหภูมิ _delay_ms(1000); // ความล่าช้าในการสำรวจเซนเซอร์ DS18B20_init(); // การเริ่มต้นของ DS18B20 write_18b20(0xCC); // ตรวจสอบรหัสเซ็นเซอร์ write_18b20(0xBE); // คำสั่งให้อ่านเนื้อหาของ Sensor RAM Temp_L = read_18b20(); // อ่านสองไบต์แรก Temp_H = read_18b20(); temp_flag = 1; // อุณหภูมิบวก 1, อุณหภูมิลบ 0 // รับอุณหภูมิติดลบถ้า (Temp_H & (1 << 3)) // ตรวจสอบการตรวจสอบบิต (ถ้าตั้งค่าบิต - อุณหภูมิติดลบ) { อุณหภูมิ int ที่ลงนาม; temp_flag = 0; // ตั้งค่าสถานะ 0 - อุณหภูมิติดลบ temp = (Temp_H <<8)|Temp_L; อุณหภูมิ = -อุณหภูมิ; // แปลงรหัสเพิ่มเติมโดยตรง Temp_L = temp; Temp_H = อุณหภูมิ>> 8; } บัฟเฟอร์ = ((Temp_H 4); temp_int_1 = บัฟเฟอร์ % 1000/100; // สามหลัก temp_int_2 = บัฟเฟอร์ % 100 / 10; // สองหลัก temp_int_3 = บัฟเฟอร์ % 10; // ตัวเลขเดียว

// หากอุณหภูมิเป็นลบ แสดงว่าอุณหภูมิเป็นลบ มิฉะนั้นให้ชัดเจน

if(temp_flag == 0) {Display_Neg(1);} else {Display_Neg(0);} if(temp_int_1 > 0) // ถ้าผลลัพธ์เป็นตัวเลขสามหลัก { Display_Dig(temp_int_1, 45, 0); // แสดงอุณหภูมิ 1 หลัก Display_Dig(temp_int_2, 54, 0); // แสดงอุณหภูมิ 2 หลัก Display_Dig(temp_int_3, 63, 0); // แสดงอุณหภูมิ 3 หลัก } else { if(temp_int_2 > 0) // ถ้าผลลัพธ์เป็นตัวเลขสองหลัก { Off_Dig (45, 0); // ล้างตัวเลข 1 ตัว Display_Dig(temp_int_2, 54, 0); // แสดงอุณหภูมิ 1 หลัก Display_Dig(temp_int_3, 63, 0); // แสดงอุณหภูมิ 2 หลัก } else // ถ้าผลลัพธ์เป็นตัวเลขหลักเดียว { Off_Dig(45, 0); // เคลียร์เลข 1 ตัว Off_Dig(54, 0); // ล้างตัวเลข 2 ตัว Display_Dig(temp_int_3, 63, 0); // แสดงอุณหภูมิ 1 หลัก } } }

// ISR นี้เริ่มทำงานทุกครั้งที่มีการจับคู่เกิดขึ้นของการนับตัวจับเวลาด้วยค่าเปรียบเทียบ (ทุกๆ 1 วินาที) ISR (TIMER1_COMPA_vect) {// การอ่าน แสดงอุณหภูมิและระดับแสง Read_Temp(); Read_Lux(); }

// ฟังก์ชั่นแสดงคำว่า "TEMP" และ "LUX" เป็นโมฆะ Display_label () { // Word "TEMP" Display_SetXY (0, 0); // กำหนดแอดเดรสของตำแหน่งที่แสดง (แถวบน) สำหรับ (int index=0; index<105; index++) { if (index==40){Display_SetXY(0, 1);} // กำหนดแอดเดรสของตำแหน่ง บนจอแสดงผล (แถวล่าง) if (index==80){Display_SetXY(72, 0);} // ตั้งค่าที่อยู่ของตำแหน่งบนจอแสดงผล (แถวบน) if (index==92){Display_SetXY(72, 1); } // ตั้งค่าที่อยู่ของตำแหน่งที่แสดง (แถวล่าง) SPDR = TEMP_1[index]; // โหลดข้อมูลโค้ดอาร์เรย์ลงในบัฟเฟอร์ของ display while(!(SPSR & (1<<SPIF)))); // รอจนกว่าการส่งจะเสร็จสมบูรณ์ _delay_ms(10); } // คำว่า "LUX" Display_SetXY(0, 2); // กำหนดแอดเดรสของตำแหน่งที่แสดง (แถวบน) สำหรับ (int index=0; index<60; index++) { if (index==30){Display_SetXY(0, 3);} // กำหนดแอดเดรสของตำแหน่ง บนจอแสดงผล (แถวล่าง) SPDR = TEMP_2[ดัชนี]; // โหลดข้อมูลโค้ดอาร์เรย์ลงในบัฟเฟอร์ของ display while(!(SPSR & (1<<SPIF)))); // รอจนกว่าการส่งจะเสร็จสิ้น _delay_ms(10); } }

int หลัก (เป็นโมฆะ)

{ Port_Init(); // การเริ่มต้นพอร์ต ADC_init (); // การเริ่มต้น ADC SPI_Init (); // การเริ่มต้น SPI SPI_SS_Enable (); // เปิดใช้งานการแสดงผล DS18B20_init(); // การเริ่มต้นของ DS18B20 Display_init(); // แสดงการเริ่มต้น Display_Clear(); // แสดงชัดเจน Display_label(); // แสดงคำว่า "TEMP" และ "LUX" TIMER1_init(); // การเริ่มต้นจับเวลา 1 เริ่มการตรวจสอบ รับพารามิเตอร์ทุก ๆ หนึ่งวินาที // อินฟินิตี้วนในขณะที่ (1) { } }

ขั้นตอนที่ 3: แฟลชเฟิร์มแวร์ไปยังไมโครคอนโทรลเลอร์

การอัปโหลดไฟล์ HEX ลงในหน่วยความจำแฟลชไมโครคอนโทรลเลอร์ ดูวิดีโอพร้อมคำอธิบายโดยละเอียดของการเบิร์นหน่วยความจำแฟลชไมโครคอนโทรลเลอร์: การเบิร์นหน่วยความจำแฟลชไมโครคอนโทรลเลอร์…

ขั้นตอนที่ 4: การตรวจสอบการประกอบวงจรอุปกรณ์

การตรวจสอบการประกอบวงจรอุปกรณ์
การตรวจสอบการประกอบวงจรอุปกรณ์
การตรวจสอบการประกอบวงจรอุปกรณ์
การตรวจสอบการประกอบวงจรอุปกรณ์

เชื่อมต่อส่วนประกอบตามแผนผังไดอะแกรม

เสียบปลั๊กใช้งานได้เลย!

แนะนำ: