設(shè)計(jì)與實(shí)現(xiàn))
1. 從“無(wú)接觸”到“低成本”一個(gè)創(chuàng)客項(xiàng)目的誕生最近在整理工作室的舊項(xiàng)目時(shí)翻出了一個(gè)兩年前做的小玩意兒我把它叫做“Free ‘COVID’ Touch”。這個(gè)名字聽起來(lái)有點(diǎn)故弄玄虛其實(shí)核心很簡(jiǎn)單一個(gè)利用常見電子垃圾和開源硬件實(shí)現(xiàn)低成本、非接觸式交互的裝置。它誕生的背景是當(dāng)時(shí)大家對(duì)公共接觸面衛(wèi)生的普遍擔(dān)憂催生了對(duì)各種“無(wú)接觸”解決方案的需求。市面上的商用非接觸感應(yīng)設(shè)備比如自動(dòng)感應(yīng)洗手液機(jī)、感應(yīng)水龍頭好用是好用但價(jià)格不菲而且內(nèi)部結(jié)構(gòu)封閉壞了很難修想自己定制功能更是無(wú)從下手。作為一個(gè)喜歡折騰的創(chuàng)客我的想法是能不能用最便宜、最容易獲取的材料自己做一個(gè)功能類似但完全可控的“非接觸觸發(fā)器”這個(gè)“COVID”在項(xiàng)目名里更像是一個(gè)時(shí)代印記和問題引子它指向的不是疾病本身而是那個(gè)時(shí)期所凸顯的、對(duì)“減少非必要接觸”這一需求的集中關(guān)注。真正的目標(biāo)是探索一種普適的、低成本的接近感應(yīng)方案它可以用來(lái)控制燈、播放聲音、觸發(fā)相機(jī)或者像我最初做的那樣改裝成一個(gè)自動(dòng)感應(yīng)消毒液瓶。這個(gè)項(xiàng)目的樂趣和挑戰(zhàn)都在于“Free”——它既是“免費(fèi)”或“低成本”的也是“自由”的。你不再被成品設(shè)備的功能所限制可以根據(jù)自己的需要用代碼和電路賦予它任何交互邏輯。下面我就把這個(gè)項(xiàng)目的完整實(shí)現(xiàn)思路、核心原理、踩過(guò)的坑以及擴(kuò)展玩法毫無(wú)保留地分享出來(lái)。2. 核心原理我們?nèi)绾巍案艨铡备兄獙?shí)現(xiàn)非接觸感應(yīng)市面上有紅外對(duì)管、超聲波、激光雷達(dá)、毫米波雷達(dá)等多種方案。我們的目標(biāo)是極致的低成本和高可玩性因此選擇了最常見、也最經(jīng)典的HC-SR04超聲波測(cè)距模塊作為感知核心。很多人認(rèn)為它只能用于機(jī)器人避障或測(cè)距其實(shí)稍加改造它就是一個(gè)非常靈敏的“存在”探測(cè)器。2.1 超聲波模塊的工作邏輯與局限HC-SR04模塊的工作原理是聲納。它有一個(gè)發(fā)射器T和一個(gè)接收器R。工作時(shí)微控制器給Trig引腳一個(gè)至少10微秒的高電平脈沖模塊會(huì)自動(dòng)發(fā)射一組8個(gè)40kHz的超聲波。超聲波遇到物體反射回來(lái)被接收器捕獲。模塊的Echo引腳會(huì)輸出一個(gè)高電平脈沖這個(gè)脈沖的寬度與超聲波從發(fā)射到返回的時(shí)間成正比。計(jì)算距離的公式是初中物理知識(shí)距離 (高電平時(shí)間 * 聲速) / 2。聲速在常溫下約340米/秒。模塊的有效測(cè)距通常在2cm到400cm之間精度能達(dá)到3mm左右對(duì)于我們的手勢(shì)感應(yīng)需求來(lái)說(shuō)綽綽有余。但是直接用它來(lái)做“感應(yīng)開關(guān)”會(huì)遇到幾個(gè)問題持續(xù)觸發(fā)如果物體一直停留在感應(yīng)區(qū)內(nèi)模塊會(huì)持續(xù)返回距離值你的設(shè)備比如燈就會(huì)一直亮著這通常不是我們想要的。我們更需要的是“掠過(guò)”或“靠近”的瞬間觸發(fā)。響應(yīng)延遲模塊完成一次測(cè)距循環(huán)需要幾十毫秒對(duì)于快速的手勢(shì)可能不夠靈敏。環(huán)境干擾柔軟的織物、復(fù)雜的表面可能吸收或散射聲波導(dǎo)致測(cè)距不準(zhǔn)或失效。因此我們不能簡(jiǎn)單地讀取距離值然后判斷必須在微控制器的邏輯層面對(duì)原始信號(hào)進(jìn)行“加工”和“解釋”。2.2 從“距離數(shù)據(jù)”到“交互事件”的信號(hào)處理這是本項(xiàng)目在軟件層面的核心。我們需要在固件中實(shí)現(xiàn)一個(gè)簡(jiǎn)單的狀態(tài)機(jī)來(lái)識(shí)別特定的交互模式。以下是我經(jīng)過(guò)多次調(diào)試后確定的邏輯以Arduino代碼為例說(shuō)明// 定義關(guān)鍵參數(shù) const int TRIG_PIN 9; const int ECHO_PIN 10; const int DETECTION_THRESHOLD 15; // 感應(yīng)閾值單位厘米 const int DEBOUNCE_DELAY_MS 200; // 防抖延時(shí)毫秒 long duration, distance; bool objectInRange false; unsigned long lastTriggerTime 0; void setup() { pinMode(TRIG_PIN, OUTPUT); pinMode(ECHO_PIN, INPUT); // 初始化其他部件如繼電器、LED等 } void loop() { // 1. 觸發(fā)一次測(cè)距 digitalWrite(TRIG_PIN, LOW); delayMicroseconds(2); digitalWrite(TRIG_PIN, HIGH); delayMicroseconds(10); digitalWrite(TRIG_PIN, LOW); duration pulseIn(ECHO_PIN, HIGH); distance duration * 0.034 / 2; // 換算成厘米 // 2. 判斷邏輯實(shí)現(xiàn)“單次觸發(fā)” if (distance 0 distance DETECTION_THRESHOLD) { // 有物體進(jìn)入閾值范圍 if (!objectInRange) { // 且之前不在范圍內(nèi)說(shuō)明是“新進(jìn)入”事件 objectInRange true; if (millis() - lastTriggerTime DEBOUNCE_DELAY_MS) { // 防抖處理避免重復(fù)觸發(fā) triggerAction(); // 執(zhí)行你的動(dòng)作如打開繼電器 lastTriggerTime millis(); } } // 如果物體持續(xù)在范圍內(nèi)objectInRange保持true不會(huì)重復(fù)觸發(fā) } else { // 物體離開或不在范圍內(nèi) objectInRange false; } delay(50); // 控制測(cè)距頻率避免過(guò)于頻繁 } void triggerAction() { // 這里控制你的執(zhí)行器例如 digitalWrite(RELAY_PIN, HIGH); delay(1000); // 假設(shè)讓消毒泵工作1秒 digitalWrite(RELAY_PIN, LOW); }這段代碼實(shí)現(xiàn)了一個(gè)最基礎(chǔ)的“靠近-觸發(fā)-離開-重置”循環(huán)。DEBOUNCE_DELAY_MS參數(shù)至關(guān)重要它防止了因?yàn)槭植课⑿《秳?dòng)或在邊界徘徊導(dǎo)致的誤觸發(fā)。你可以把它理解為一個(gè)“冷卻時(shí)間”。注意pulseIn函數(shù)在未收到回波時(shí)會(huì)阻塞等待超時(shí)這可能導(dǎo)致程序卡住。更穩(wěn)健的做法是使用中斷來(lái)測(cè)量Echo引腳的高電平時(shí)間或者選用帶有超時(shí)返回的庫(kù)。這是第一個(gè)容易踩的坑。3. 硬件選型與搭建如何實(shí)現(xiàn)真正的“Free”“Free”意味著我們要盡可能利用手邊資源。以下是不同完成度的方案從“零成本”到“極低成本”。3.1 方案一最小系統(tǒng)核心驗(yàn)證這是最精簡(jiǎn)的版本僅用于驗(yàn)證邏輯。主控任何一款A(yù)rduino兼容板最便宜的是ATmega328P最小系統(tǒng)板約10元或ESP8266NodeMCU約15元自帶Wi-Fi可用于后續(xù)擴(kuò)展。傳感器HC-SR04超聲波模塊約3元。電源舊的手機(jī)充電寶或5V手機(jī)充電器。執(zhí)行器可選為了看到效果可以接一個(gè)LED燈。如果想控制家電需要一個(gè)5V繼電器模塊約2元。連接杜邦線若干。接線示意圖VCC - 5VGND - GNDTrig - 數(shù)字引腳如D9Echo - 數(shù)字引腳如D10這個(gè)組合成本可以控制在20元以內(nèi)。焊接功底好的話甚至可以從舊玩具、小家電里拆出類似的元件。3.2 方案二實(shí)用化改裝以自動(dòng)感應(yīng)瓶為例這是項(xiàng)目的典型應(yīng)用。你需要增加一個(gè)執(zhí)行機(jī)構(gòu)。新增核心部件微型直流水泵用于擠洗手液或舵機(jī)用于按壓瓶嘴。水泵更直接但需要液體管路舵機(jī)改裝更通用。驅(qū)動(dòng)考慮水泵或舵機(jī)的工作電流可能超過(guò)單片機(jī)引腳驅(qū)動(dòng)能力通常20mA上限。絕對(duì)不能直接連接必須通過(guò)晶體管如S8050或上述的繼電器模塊來(lái)驅(qū)動(dòng)。結(jié)構(gòu)外殼利用廢舊塑料盒、紙巾盒來(lái)固定傳感器和電路。關(guān)鍵點(diǎn)在于傳感器探頭必須裸露并且前方不能有障礙物同時(shí)要避免外殼對(duì)聲波的反射造成干擾。我用的是一個(gè)剃須刀的外殼在前面為傳感器開了兩個(gè)小孔。驅(qū)動(dòng)電路提示 如果使用繼電器控制水泵int relayPin 8; void setup() { pinMode(relayPin, OUTPUT); } void triggerAction() { digitalWrite(relayPin, HIGH); // 繼電器吸合水泵通電 delay(800); // 根據(jù)泵的流量調(diào)整時(shí)長(zhǎng)控制擠出量 digitalWrite(relayPin, LOW); }如果使用晶體管驅(qū)動(dòng)小水泵3-5V 需要在單片機(jī)引腳和晶體管基極之間串聯(lián)一個(gè)1kΩ的限流電阻水泵連接在晶體管集電極和電源之間。3.3 方案三增強(qiáng)與擴(kuò)展在基礎(chǔ)功能實(shí)現(xiàn)后可以玩些花樣增加反饋加入一個(gè)蜂鳴器或RGB LED在手勢(shì)被識(shí)別時(shí)給出聲音或燈光反饋體驗(yàn)更佳。調(diào)節(jié)靈敏度增加一個(gè)旋轉(zhuǎn)電位器連接到模擬輸入引腳實(shí)時(shí)調(diào)節(jié)DETECTION_THRESHOLD適應(yīng)不同安裝環(huán)境。模式切換增加一個(gè)按鈕切換不同的觸發(fā)模式例如“常亮模式”手持續(xù)靠近則燈常亮和“點(diǎn)動(dòng)模式”每次靠近觸發(fā)固定時(shí)長(zhǎng)。聯(lián)網(wǎng)與智能化使用ESP8266/ESP32將設(shè)備接入家庭Wi-Fi通過(guò)MQTT協(xié)議將觸發(fā)事件上報(bào)到服務(wù)器實(shí)現(xiàn)與其他智能家居聯(lián)動(dòng)或者記錄使用次數(shù)。這是將“Free Touch”升級(jí)為智能設(shè)備的鑰匙。4. 調(diào)優(yōu)與避坑讓項(xiàng)目從“能動(dòng)”到“好用”硬件搭好代碼燒錄傳感器有反應(yīng)了但這只是成功了一半。接下來(lái)的調(diào)試階段才是決定這個(gè)項(xiàng)目是“玩具”還是“工具”的關(guān)鍵。4.1 安裝位置的“玄學(xué)”超聲波傳感器的感知區(qū)域是一個(gè)圓錐形。安裝時(shí)必須確保這個(gè)圓錐覆蓋你希望感應(yīng)的區(qū)域同時(shí)要避開其他固定物體。錯(cuò)誤示范將傳感器對(duì)著墻壁安裝且距離小于最大探測(cè)距離。那么墻壁會(huì)被一直識(shí)別為“物體”導(dǎo)致功能失效。正確做法傳感器前方至少保留20-30厘米的凈空區(qū)域。感應(yīng)區(qū)域最好與人的操作路徑垂直。例如做感應(yīng)洗手液機(jī)傳感器應(yīng)水平安裝感應(yīng)前方水平方向的手部靠近做感應(yīng)燈則可以朝下安裝感應(yīng)下方區(qū)域的物體。4.2 閾值與防抖的精細(xì)調(diào)整代碼中的DETECTION_THRESHOLD和DEBOUNCE_DELAY_MS需要根據(jù)實(shí)際場(chǎng)景反復(fù)測(cè)試。閾值太小如5cm需要手非??拷庞|發(fā)體驗(yàn)不佳。閾值太大如30cm可能路過(guò)就會(huì)被觸發(fā)產(chǎn)生誤動(dòng)作。防抖時(shí)間太短手部抖動(dòng)可能觸發(fā)多次。防抖時(shí)間太長(zhǎng)快速連續(xù)兩次手勢(shì)可能無(wú)法識(shí)別。我的經(jīng)驗(yàn)是先設(shè)置一個(gè)較大的閾值如20cm和一個(gè)較短的防抖時(shí)間如150ms然后用手模擬正常使用動(dòng)作逐步微調(diào)??梢蕴砑哟诖蛴」δ軐?shí)時(shí)輸出測(cè)距值這是調(diào)試的利器。void loop() { // ... 測(cè)量距離的代碼 ... Serial.print(Distance: ); Serial.print(distance); Serial.println( cm); // ... 判斷邏輯 ... }打開Arduino IDE的串口監(jiān)視器你就能清楚地看到手部移動(dòng)時(shí)距離的變化從而科學(xué)地確定閾值。4.3 環(huán)境干擾的應(yīng)對(duì)超聲波在空氣中的傳播受溫度、濕度影響但家用環(huán)境下最主要干擾是空氣流動(dòng)和柔軟表面。風(fēng)扇/空調(diào)風(fēng)持續(xù)的氣流可能會(huì)擾動(dòng)聲波導(dǎo)致測(cè)距值小幅跳動(dòng)。解決方法是通過(guò)軟件濾波例如連續(xù)采樣5次取中位數(shù)或平均值作為有效距離能極大提升穩(wěn)定性。目標(biāo)物是窗簾、羽絨服這類材料吸音可能導(dǎo)致回波信號(hào)微弱甚至丟失感應(yīng)距離變短或不穩(wěn)定。這是物理限制通常只能通過(guò)降低閾值、將傳感器更靠近來(lái)緩解。4.4 供電的穩(wěn)定性整個(gè)系統(tǒng)對(duì)電源噪聲比較敏感。如果使用劣質(zhì)USB電源或長(zhǎng)導(dǎo)線供電可能導(dǎo)致單片機(jī)復(fù)位或傳感器工作異常。務(wù)必在單片機(jī)的VCC和GND之間并聯(lián)一個(gè)100μF的電解電容和一個(gè)0.1μF的瓷片電容分別濾除低頻和高頻噪聲。如果驅(qū)動(dòng)電機(jī)類負(fù)載如水泵務(wù)必為電機(jī)單獨(dú)供電并與單片機(jī)電源共地。最好在電機(jī)兩端并聯(lián)一個(gè)續(xù)流二極管如1N4007防止電機(jī)停轉(zhuǎn)時(shí)產(chǎn)生的反向電動(dòng)勢(shì)擊穿驅(qū)動(dòng)晶體管。5. 超越“感應(yīng)”項(xiàng)目的無(wú)限擴(kuò)展可能基礎(chǔ)功能穩(wěn)定后這個(gè)開源框架的想象力空間才真正打開。它本質(zhì)上是一個(gè)“由特定空間事件觸發(fā)動(dòng)作”的通用控制器。5.1 交互模式的創(chuàng)新除了簡(jiǎn)單的靠近觸發(fā)我們可以編程實(shí)現(xiàn)更復(fù)雜的交互手勢(shì)識(shí)別雛形利用超聲波持續(xù)測(cè)距通過(guò)分析距離隨時(shí)間變化的波形可以簡(jiǎn)單區(qū)分“快速揮手”距離驟變和“緩慢靠近”距離緩變從而觸發(fā)不同功能。這需要更復(fù)雜的算法但用Arduino也能實(shí)現(xiàn)基礎(chǔ)版本。存在檢測(cè)長(zhǎng)亮燈修改邏輯當(dāng)檢測(cè)到物體時(shí)打開燈物體離開后延遲一段時(shí)間如10秒再關(guān)燈。這就成了一個(gè)簡(jiǎn)易的衛(wèi)生間或衣柜感應(yīng)燈。計(jì)數(shù)器與統(tǒng)計(jì)每次觸發(fā)時(shí)通過(guò)串口發(fā)送一條記錄或者驅(qū)動(dòng)一個(gè)OLED屏幕顯示計(jì)數(shù)??梢杂糜诮y(tǒng)計(jì)門口人流、物品取用次數(shù)等。5.2 執(zhí)行機(jī)構(gòu)的多樣化觸發(fā)信號(hào)可以控制幾乎任何低壓電器控制繼電器通斷臺(tái)燈、風(fēng)扇、咖啡機(jī)??刂贫鏅C(jī)制作自動(dòng)開蓋的垃圾桶、喂食器。觸發(fā)攝像頭制作防盜報(bào)警觸發(fā)拍照裝置需配合樹莓派等。發(fā)送網(wǎng)絡(luò)信號(hào)通過(guò)ESP8266觸發(fā)IFTTT、向手機(jī)發(fā)送通知、控制智能插座。5.3 融合其他傳感器單一傳感器總有局限融合是王道增加紅外熱釋電PIR傳感器超聲波可能被靜止物體誤觸發(fā)比如放在桌上的杯子。PIR傳感器只對(duì)移動(dòng)的生物體熱源敏感。將兩者結(jié)合邏輯設(shè)為“只有當(dāng)PIR檢測(cè)到移動(dòng)且超聲波檢測(cè)到近距離物體時(shí)才觸發(fā)”能極大降低誤報(bào)率實(shí)現(xiàn)更精準(zhǔn)的人體感應(yīng)。增加光敏電阻只在環(huán)境光暗的時(shí)候才啟動(dòng)感應(yīng)功能白天自動(dòng)休眠節(jié)省電能。這個(gè)“Free ‘COVID’ Touch”項(xiàng)目其價(jià)值遠(yuǎn)不止于制作一個(gè)免接觸設(shè)備。它更像一個(gè)入口帶你走進(jìn)物理計(jì)算和交互設(shè)計(jì)的世界。通過(guò)它你實(shí)踐了傳感器數(shù)據(jù)采集、信號(hào)處理、狀態(tài)機(jī)編程、驅(qū)動(dòng)電路設(shè)計(jì)等一系列核心技能。最重要的是它讓你以一種低成本、高自由度的方式將想法轉(zhuǎn)化為可以觸摸、可以互動(dòng)的現(xiàn)實(shí)。最初那個(gè)讓洗手變得更安全的小念頭最終變成了一把打開創(chuàng)造之門的鑰匙。