ทดลองติดต่อใช้งานอุปกรณ์ส่วนควบบนบอร์ด Easy-eIoT #2

สวัสดีครับ กลับมากับบทความสอนใช้งานบอร์ด Easy-eIoT HAT สำหรับใช้งานร่วมกับบอร์ด Raspberry Pi กันอีกแล้ว ในตอนที่ #2 ซึ่งในบทความที่ผ่านมาเราพูดถึงเรื่องการใช้งานจอสีและการอ่านค่าความชื้นและอุณหภูมิจากเซ็นเซอร์ HS3004 รวมไปถึงควบคุมหลอด LED บนบอร์ด Easi-eIoT กันไปเป็นที่เรียบร้อยแล้ว ในบทความนี้เราจะมาทำความรู้จักกันอุปกรณ์ส่วนควบที่ติดมากับบอร์ดที่เหลือกันครับ และจะมาทดลองใช้งานไปด้วยกัน โดยอ้างอิงจาก Pinout diagram ของเรากันก่อนว่าเรามีอุปกรณ์อะไรข้างและเชื่อมต่อกับขา GPIO อะไรบ้าง

โดยในบทความนี้เราจะมาพูดถึงการใช้งานอุปกรณ์ส่วนควบดังนี้
.
1. ปุ่มกดขนาด 12 มม.

2. Rotary encoder พร้อมป่มกด

3. Buzzer

โค้ดตัวอย่างทั้งหมดอยู่ที่ https://github.com/raspberrypi66/easy-eiot

การอ่านค่าจากปุ่มกด

โดยจะเริ่มจากปุ่มกดที่ต่อกับ GPIO26 กันก่อนครับซึ่งเราได้ต่อปุ่มนี้เป็นแบบ input pullup ไว้ เมื่อไม่มีการกดปุ่มค่าสถานะของขา GPIO26 จะอ่านได้ “1” เสมอ เมื่อมีการกดปุ่มสถานะของขา GPIO26 จะอ่านได้ “0” เอาล่ะครับเรามาลองดูตัวอย่างโค้ดกันเลยดีกว่า

จากโค้ด ในบรรทัดที่ 18 เราจะใช้การเรียก function press_sw_callback ขึ้นมาทุกครั้งที่ สถานะของขา GPIO26 เปลี่ยนเป็น “0” ผ่านการเรียกใช้ GPIO.add_event_detect()
โดยเราจะสามารถระบุค่า bounce time ที่เหมาะสมกับปุ่มกดของเราลงไปได้เพื่อป้องกันปัญหากดปุ่มครั้งเดียวแล้วอ่านค่าการกดได้มากกว่า 1 ครั้ง 

ในตัวอย่างเมื่อมีการกดปุ่มแล้ว function press_sw_callback ถูกเรียกขึ้นมา จะทำการเพิ่มค่าตัวแปร press_sw_counter ขึ้นทีละ 1 แล้วพิมพ์ออกมาแสดงผลทางหน้าจอของเรา ก็จบไปกับการใช้งานอ่านค่าปุ่มกดบนบอร์ด Easy-eIoT นะครับ เราจะทดลองการอ่านค่าจากเจ้า rotary encoder กันต่อไปเลย

การอ่านค่าจาก Rotary Encoder

เราจะมาทดลองอ่านค่าจาก rotary encoder ที่อยู่บนบอร์ด Easy-eIoT กันนะครับ แต่ก่อนที่เราจะไปลงเมือเขียนโปรแกรมนั้น เราต้องเข้าใจหลักการทำงานของ rotary encoder กันก่อนครับ เราอาจจะเคยใช้งานเข้าใจรูปแบบการใช้งานของมันอยู่แล้วว่าคือลูกบิดที่สามารถบิดหมุนรอบตัวได้และสามารถรู้ทิศทางการการหมุนได้รวมถึงให้ค่าออกมาทุกๆการหมุนด้วย รวมไปถึงตัวลูกบิดของมันสามารถทำงานเป็นปุ่มกดเพื่อใช้กดยืนยันได้ในตัวด้วย ก็ค่อนข้างมีประโยชน์ในการใช้งานควบคุมต่างๆโดยไม่ต้องมีปุ่มกดมากมากให้ยุ่งยากมากมาย เอาล่ะครับเรามาดูโครงสร้างของมันกันก่อนว่าทำไมมันถึงรู้ได้ว่าเราหมุนลูกบิดไปในทิศทางไหนได้อย่างไร

ภายในของ rotary encoder นั้นจะมีแผ่นทรงกลมที่เมื่อเราหมุนแล้วจะสร้างรูปคลื่นสี่เหลี่ยมออกมา 2 ชุดที่มีความเหลื่อมกันอยู่ที่ 90 องศา ซึ่งเราไม่ต้องทำอะไรเลยอย่างแรกเราก็สามารถอ่านค่าจำนวนลูกคลื่นที่ถูกสร้างออกมาจากการหมุนได้ทันที แต่ถ้าเราต้องการที่จะทราบทิศทางการของการหมุนด้วย เราจะสามารถทำได้ด้วยการพิจารณาความแตกต่างของลูกคลื่นจากสัญญาณขาออกทั้งสองชุดประกอบกันดังรูป

เนื่องจากลูกคลื่นของ output a (สีฟ้า) จะล้ำหน้า output b (สีเขียว) อยู่ 90 องศา ดังนั้นหากเราพิจารณาที่การเปลี่ยนแปลงของสัญญาณเช่น เมื่อหมุนลูกบิดไปตามทิศทางการหมุมของเข็มนาฬิกา เมื่อลูกคลื่นของ output a เปลี่ยนเป็น “0” ในช่วงเวลาเดียวกันที่ output b  ลูกคลื่นจะยังมีค่าเป็น “1” อยู่ หรือเมื่อ output a เปลี่ยนเป็น “1” ในช่วงเวลาเดียวกันที่ output b  ลูกคลื่นจะยังมีค่าเป็น “0” จึงกล่าวได้ว่าหากเราพบว่าในขณะที่มีการเปลี่ยนแปลงของลูกคลื่นจาก output ใดๆ หากเปรียบเทียบสัญญาณกับอีก output แล้วพบว่ามีความแตกต่างกัน rotary encoder ของเรากำลังหมุนไปในทิศทางตามเข็มนาฬิกา 

แต่หากเราหมุนลูกบิดไปตามทิศทางทวนการหมุมของเข็มนาฬิกา เมื่อลูกคลื่นของ output a เปลี่ยนเป็น “0” ในช่วงเวลาเดียวกันที่ output b  ลูกคลื่นจะยังมีค่าเป็น “0” อยู่ หรือเมื่อ output a เปลี่ยนเป็น “1” ในช่วงเวลาเดียวกันที่ output b  ลูกคลื่นจะยังมีค่าเป็น “1” จึงกล่าวได้ว่าหากเราพบว่าในขณะที่มีการเปลี่ยนแปลงของลูกคลื่นจาก output ใดๆ หากเปรียบเทียบสัญญาณกับอีก output แล้วพบว่ามีค่าเท่ากัน rotary encoder ของเรากำลังหมุนไปในทิศทางการหมุนทวนเข็มนาฬิกา เราจึงสามารถเขียนโค้ดได้ดังนี้

โดยจากโค้ดเราจะทำการเขียนโค้ดตามหลักการทำงานที่อธิบายไปด้านบนคือทำการสนใจการเปลี่ยนแปลงของสัญญาณนาฬิกาที่ขา B ของ rotary encoder โดยเมื่อตรวจจับการเปลี่ยนแปลงขอบขาลงจาก “1” เป็น “0” ได้ก็จะการเรียก function ที่ชื่อ rotary_callback() ขึ้นมา โดยบรรทัดที่ 14-15 จะทำการอ่านค่าของ GPIO ที่ต่อกับ rotary encoder ทั้ง 2 ขาขึ้นมาและทำการเปรียบเทียบกันในบรรทัดที่ 16 ทำให้เมื่อเราหมุนลูกบิดไปในทิศทางตามเข็มนาฬิกาจะมีการเพิ่มค่าในตัวแปร counter เพิ่มขึ้น และหากมีการหมุนไปในทิศทางทวนเข็มนาฬิกาจะเป็นการลดค่าในตัวแปร counter ลงและพิมพ์ออกแสดงผลทางหน้าจอ โดยเมื่อมีการกดปุ่มบน rotary encoder ก็จะทำการ reset ค่าตัวแปร counter ให้กลับมาเป็นค่าเริ่มต้น 

การสั่งงาน Buzzer

buzzer ที่ต่ออยู่บน Easy-eIoT HAT นั้นเป็นแบบ passive buzzer คือไม่มีแหล่งกำเนิดสัญญาณความถี่อยู่ภายในตัวของมันจำเป็นที่เราจะต้องสร้างความถี่เพื่อส่งไปขับ buzzer ให้เกิดเสียงขึ้นมา โดนเราสามารถใช้ความสามารถในการสร้างสัญญาณ PWM จากขา GPIO ของบอร์ด Raspberry Pi ได้ดังโค้ดตัวอย่าง

จากโค้ดเราทำการสั่งให้ขา GPIO 13 ที่ต่อกับ buzzer โดยกำหนด duty cycle ของสัญญาณ PWM ไว้ที่ 50% แล้วสั่ง ChangeFrequency() เพื่อเปลี่ยนค่าความถี่ที่จะส่งออกไปขับ buzzer เพียงเท่านี้เราก็สามารถที่จะส่งเสียงความถี่ต่างๆตามที่ต้องการไปยัง buzzer ได้แล้วครับ

ในบทความถัดไปเราจะทดลองควบคุมหลอด WS2812B บน Easy-eIoT HAT กัน
และจะเป็นการทดลองเขียนโปรแกรมเพื่อควบคุมการแสดงผลบนจอภาพด้วย pygame กันอีกด้วย ถ้าชอบก็ช่วยกันแชร์บทความให้ด้วยนะครับ

โค้ดตัวอย่างทั้งหมดอยู่ที่ https://github.com/raspberrypi66/easy-eiot

ภาพประกอบเรื่อง rotary encoder จาก https://howtomechatronics.com/tutorials/arduino/rotary-encoder-works-use-arduino/

Leave a Comment