設(shè)計(jì)構(gòu)建一個(gè)帶有ESP32觸摸控制的觸摸燈
如果光輸出可以直接在設(shè)備上進(jìn)行交互控制,那就太好了。現(xiàn)在我們將構(gòu)建并編程一個(gè)設(shè)備。
幾個(gè)星期前,當(dāng)我去一家餐館的時(shí)候,這種臺(tái)燈的變體真的弄傷了我的手指。這東西是要通過觸摸來控制的,但要用一種神秘的方式。有足夠的理由進(jìn)一步研究使用ESP32。當(dāng)然,使用Micropython是成功的。這是該系列下一集的結(jié)果
帶有觸摸控制的臺(tái)燈
有了手機(jī)應(yīng)用程序,你自然有很多選擇來控制臺(tái)燈。但是問題已經(jīng)從決定開始了——無線局域網(wǎng)通過路由器還是通過控制器自己的接入點(diǎn)。這必須在課程中考慮到,或者在開始時(shí)就已經(jīng)有了。
如果光輸出可以直接在設(shè)備上進(jìn)行交互控制,那就太好了?,F(xiàn)在我們將構(gòu)建并編程一個(gè)設(shè)備。首選控制器是ESP32,因?yàn)樗杏|摸板輸入。進(jìn)一步考慮使用ESP8266或樹莓派Pico,然后產(chǎn)生了觸摸問題的進(jìn)一步解決方案。我們將在下一集中討論這些問題。今天我們繼續(xù)討論ESP32。我將展示如何將數(shù)據(jù)永久存儲(chǔ)在NVS區(qū)域中,以及如何實(shí)現(xiàn)進(jìn)程并行執(zhí)行。至少第一個(gè)功能只提供ESP32。
對(duì)于使用的控制器板ESP32 Dev Kit C V4,需要兩個(gè)面包板來開發(fā)電路,它們通過電流軌放在一起。這是為跳線獲得足夠自由接觸點(diǎn)的唯一方法。
圖1:ESP32的設(shè)置
作為觸摸板,我使用了電路板和波峰的剩余部分。小鋁孩子將服務(wù)于生產(chǎn)系統(tǒng)。
我使用RGB LED來顯示運(yùn)行狀態(tài)。戒指上led的顏色可以單獨(dú)設(shè)置和下調(diào)。RGB LED顯示顏色??偣灿形宸N情況:紅、綠、藍(lán)、白、中。
預(yù)電阻的尺寸是這樣的,一起發(fā)出白光。藍(lán)色的,尤其是綠色的LED比紅色的要亮得多。因此,電阻值的差異很大。如果你想要一個(gè)更輕的顯示,就取更小的歐姆值。
圖2中的電路圖顯示了所有部件是如何組合在一起的。
圖2:帶有ESP32和觸摸板的電路
作為能源供應(yīng),我選擇了18650型的鋰離子電池,加上一個(gè)帶有加載部分和5V輸出的電池所有者。我在USB A插座的連接旋轉(zhuǎn)上焊接了我的電路的供應(yīng)線。這樣我就不用USB插頭了,仍然可以使用板上的機(jī)械開關(guān)。它將指向房屋朝向地面,以及在圖2中板子上端的加載插座。
因?yàn)闊衾锓琶姘宓目臻g太小了,我設(shè)計(jì)了一個(gè)電路板,上面可以容納幾個(gè)單獨(dú)的零件。您可以按照下載PDF文件的方式進(jìn)行布局。
圖3:傳感器燈-布局
我在實(shí)驗(yàn)設(shè)置中使用了RGB LED模塊。對(duì)于燈本身,我發(fā)現(xiàn)該系列的一個(gè)led更理想,因?yàn)樗菀捉M裝在蓋子上。LED只是用雙組分粘合劑粘在框架上。
圖4:帶有公共陰極的RGB LED
燈具部件
房屋框架和蓋子由木材制成??蚣苡?5毫米的楓木板組成,45毫米× 150毫米。作為蓋子,我拿了一個(gè)5毫米厚的板,其中一個(gè)木制圓柱體粘在中間的黃銅管的中心。
圖5:燈具部件
圖6:粘接前的框架條
圖7:安裝在外殼框架和燈座在蓋子
圖8:傳感器按鍵和信號(hào)LED
燈頭坐落在一個(gè)230毫米長(zhǎng)的黃銅管與6mm ?。
圖9:燈頭內(nèi)的LED環(huán)
Micropython -語言-模塊和程序
要安裝托尼,你會(huì)在這里找到一個(gè)詳細(xì)的說明(英文版)。還有一個(gè)關(guān)于ESP芯片上的Micropython固件(截至2022年6月18日)如何被燒毀的描述。
Micropython是一種解釋器語言。Arduino IDE與Arduino IDE的主要區(qū)別在于,你只需要在ESP32上閃爍Micropython固件一次,以便控制器理解Micropython指令。您可以使用Thonny,μpycraft或ESPTOOL.PY。對(duì)于安東尼,我在這里描述了這個(gè)過程。
一旦固件閃過,你就可以很容易地在對(duì)話框中與控制器對(duì)話,測(cè)試單個(gè)命令并立即看到答案,而無需事先編譯和傳輸整個(gè)程序。這正是Arduino IDE困擾我的地方。如果您可以檢查語法和硬件的簡(jiǎn)單測(cè)試,以便在編寫程序之前通過命令行嘗試和改進(jìn)函數(shù)和整個(gè)程序部分,則可以節(jié)省大量時(shí)間。出于這個(gè)目的,我總是喜歡創(chuàng)建小型測(cè)試程序。作為一種宏,它們總結(jié)了重復(fù)出現(xiàn)的命令。然后從這些程序片段開發(fā)整個(gè)應(yīng)用程序。
自動(dòng)啟動(dòng)
如果程序要通過打開控制器自動(dòng)啟動(dòng),請(qǐng)將程序文本復(fù)制到新創(chuàng)建的空白磁貼中。將該文件保存在WorkSpace中的Main.py中,并將其上傳到ESP芯片。該程序?qū)⒃谙麓螐?fù)位或開機(jī)時(shí)自動(dòng)啟動(dòng)。
測(cè)試程序
tony - ide中當(dāng)前編輯器窗口中的程序通過F5按鈕手動(dòng)啟動(dòng)。這可以比鼠標(biāo)點(diǎn)擊開始按鈕或通過菜單運(yùn)行更快地完成。只有程序中使用的模塊必須在ESP32的flash中。
在兩者之間,Arduino id ?
如果您以后將控制器與Arduino IDE一起使用,只需以通常的方式刷新程序。然而,ESP32/ESP8266隨后忘記了它曾經(jīng)說過Micropython。相反,任何包含Arduino IDE或AT-Firmware或Lua或…可以很容易地提供micropython固件。這個(gè)過程總是像這里描述的那樣。
新像素環(huán)
類型WS2812新像素led包含三個(gè)單獨(dú)的led,釋放紅色,綠色或藍(lán)色光。它們由控制器尋址,控制器通過一種時(shí)鐘為800kHz的總線系統(tǒng)接收指令。
在I2C總線或SPI總線上,來自控制器(例如ESP32)的信號(hào)以相同的方式到達(dá)總線上的所有從機(jī),每個(gè)人都能看到一切。它與WS2812模塊不同。每個(gè)構(gòu)建塊都有一個(gè)數(shù)據(jù)輸入和數(shù)據(jù)輸出。通過連接I2C總線或SPI總線,幾個(gè)構(gòu)建模塊可以級(jí)聯(lián),來自控制器的信號(hào),例如ESP32,以相同的方式到達(dá)總線上的所有從機(jī),每個(gè)人都能看到一切。它與WS2812模塊不同。每個(gè)構(gòu)建塊都有一個(gè)數(shù)據(jù)輸入和數(shù)據(jù)輸出。幾個(gè)構(gòu)建塊可以級(jí)聯(lián)在I2C總線或SPI總線上,來自控制器的信號(hào),例如ESP32,以相同的方式到達(dá)總線上的所有從機(jī),每個(gè)人都看到一切。它與WS2812模塊不同。每個(gè)構(gòu)建塊都有一個(gè)數(shù)據(jù)輸入和數(shù)據(jù)輸出。幾個(gè)構(gòu)建塊可以為單個(gè)顏色級(jí)聯(lián)。我們以一個(gè)列表的形式給出顏色代碼,每個(gè)WS2812有三個(gè)字節(jié)。
讓我們從一個(gè)嘗試開始。我們使用圖2的結(jié)構(gòu)。首先導(dǎo)入Class Pin和Neopixel。我創(chuàng)建了一個(gè)GPIO引腳對(duì)象作為結(jié)果,從而實(shí)例化了一個(gè)具有八個(gè)組件的新像素對(duì)象。
neopixel實(shí)例neo包含一個(gè)Bytearar和write()方法,通過該方法Bytearar的內(nèi)容被傳輸?shù)絥eopixel環(huán)。
使用neoI處理數(shù)組的前三個(gè)元素,并傳遞紅色,綠色和藍(lán)色,0xe0, 0x07和0x3c的值。在內(nèi)部,這使得私有函數(shù)setitem()。這些值以改變后的順序輸入緩沖區(qū)。正如我們將看到的曲線,這是我在邏輯分析儀的幫助下記錄的。這些值是在緩沖區(qū)中發(fā)送的。一個(gè)0對(duì)應(yīng)于一個(gè)近似的窄脈沖。500NS寬度后面跟著a)。這些值以改變后的順序輸入緩沖區(qū)。正如我們將看到的曲線,這是我在邏輯分析儀的幫助下記錄的。這些值是在緩沖區(qū)中發(fā)送的。一個(gè)0對(duì)應(yīng)于一個(gè)近似的窄脈沖。500NS寬度后面跟著a)。這些值以改變后的順序輸入緩沖區(qū)。正如我們將看到的曲線,這是我在邏輯分析儀的幫助下記錄的。這些值是在緩沖區(qū)中發(fā)送的。一個(gè)0對(duì)應(yīng)于一個(gè)近似的窄脈沖。500NS的寬度按交換順序發(fā)送。這與數(shù)據(jù)表中的信息相對(duì)應(yīng),也可以通過以下方式進(jìn)行驗(yàn)證。
圖10:RGB = 0xe0, 0x07, 0x3c, 0xF0, 0xF0, 0xF0的脈沖序列
在第一個(gè)WS2812B的輸出中,丟失了三個(gè)字節(jié)0xe0、0x07和0x3c,這已經(jīng)吞噬了這個(gè)構(gòu)建塊。相反,代碼0xF0, 0xF0, 0xF0出現(xiàn)時(shí)間延遲,即第二個(gè)組件的代碼。邏輯分析儀通道1的輸入連接到第一個(gè)LED入口的測(cè)量,通道2連接到它的輸出。
現(xiàn)在我們知道WS2812B上的袋鼠是如何運(yùn)行的,并且可以轉(zhuǎn)向燈的程序。
這個(gè)項(xiàng)目
我們想用三個(gè)傳感器板來控制新led。通過GPIO33的觸摸板進(jìn)行顏色選擇。有五個(gè)通道:開/關(guān)、紅、綠、藍(lán)和明/暗。強(qiáng)度增加到GPIO32,降低到GPIO27。這三個(gè)活動(dòng)的操作在后臺(tái)以三個(gè)函數(shù)并行運(yùn)行。這是通過asyncio模塊實(shí)現(xiàn)的。
起初,我試圖做模塊為_thread使用。這在兩個(gè)過程中工作得很好,但拒絕為第三方服務(wù)。我找不出原因是什么。所以我們使用asyncio。
我們先從進(jìn)口業(yè)務(wù)說起。該模塊支持我們使用觸摸板的方法。我們需要LED輸出的引腳。在Neopixel上我們管理LED環(huán)的WS2812B。別名NP允許我們使用更短的拼寫。這些方法用于模塊時(shí)間的小小睡sleep和Sleep_ms。在C-Python中,我們也錯(cuò)過了這個(gè)模塊的別名。類NVS只對(duì)ESP32可用,ESP32可以從我們導(dǎo)入類的地方看到。NVS是非易失性存儲(chǔ)的縮寫。這允許我們?cè)谙到y(tǒng)中永久存儲(chǔ)數(shù)據(jù)。我們用它來取下我們最喜歡的顏色組合,然后在冷啟動(dòng)時(shí)再次自動(dòng)加載。(下載:timeout.py touch.py touchlamp .py)
NVS區(qū)域被劃分為名稱空間(name spaces),其中有符號(hào)32位數(shù)字和所謂的二進(jìn)制blob,所以字節(jié)對(duì)象所以字節(jié)字符串。我們的分區(qū)名為config。
這里我們?cè)O(shè)置觸摸板對(duì)象。第一個(gè)參數(shù)是GPIO引腳號(hào)。因此GPIO33代表Touch8, GPIO32代表Touch9, GPIO27代表Touch7。第二個(gè)參數(shù)是觸摸板被歸類為觸摸的限制。當(dāng)觸摸時(shí),讀取值和方法掉落,觸摸()傳遞1,否則傳遞0。
為了設(shè)置限制值,我們直接要求TP對(duì)象的相應(yīng)收據(jù),而不需要觸摸。
然后是觸摸。
我們將LED環(huán)的信號(hào)線連接到GPIO13上。戒指有8個(gè)led,同樣你也可以使用一個(gè)有12個(gè)led的戒指。當(dāng)然,它也會(huì)更快地耗盡電池。使用8系列環(huán),電流消耗在40mA到250ma之間。當(dāng)使用2200毫安時(shí),根據(jù)亮度設(shè)置的不同,負(fù)載足夠使用大約8小時(shí)。
我已經(jīng)列出了上面5個(gè)通道的含義。顏色的顏色作為代碼列表“All LEDs out”=[0.0.0]。
接下來是NVS區(qū)域中保存和讀取顏色代碼的例程定義。顏色名稱用作鍵,值來自列表元素。重要:只有使用commit()命令才能傳輸?shù)絻?nèi)存。
閱讀更容易。我們以列表的形式返回顏色值。如果省略方括號(hào),將得到一個(gè)返回對(duì)象Tupel。我們不需要這樣做,因?yàn)槲覀兿胍淖兂绦蛑械脑刂?,而這在tupel中是不可能的。
在開始時(shí),名稱空間config仍然為空。因此,讀訪問拋出一個(gè)Try Except攔截的異常。我們不讀取顏色代碼,而是在內(nèi)存中編寫上面定義的代碼。在下一個(gè)開始,鍵紅,綠和藍(lán)存在。
我們繼續(xù)定義其他變量和對(duì)象。如果我們?cè)诓僮鬟^程中切換led變暗,則實(shí)現(xiàn)是當(dāng)前顏色代碼的短暫中間存儲(chǔ)器。那我們就帶走真的。
然后我們定義RGB LED的輸出。我們把物體放在tupel led中。因?yàn)閷?duì)象引用沒有改變,所以可以安全地使用tupel。對(duì)于形狀,也可以采用tupel。這些元件依次是燃料,并決定如何將電纜切換到信號(hào)LED。channel中是四個(gè)通道的名稱,這是我們?cè)赗eplica中輸出所需要的。
函數(shù)lum()用顏色代碼填充新像素緩沖區(qū),并通過GPIO13輸出將緩沖區(qū)內(nèi)容發(fā)送到環(huán)。
現(xiàn)在開始使用asyncio模塊。因此,我們定義了三個(gè)用于觸摸控制的函數(shù)。使用TP1時(shí),如果我們切換通道,將當(dāng)前顏色保存為Nvs。config并將戒指調(diào)暗。我們用觸摸觸控板的周期來解碼每種情況下應(yīng)該發(fā)生的情況。
在異步系統(tǒng)中表示進(jìn)程的函數(shù)必須以asyncdef方式啟動(dòng)。該過程在函數(shù)離開后立即結(jié)束。我們不希望那樣,所以這個(gè)過程就像一個(gè)無限循環(huán)一樣運(yùn)行。對(duì)象的channel和color經(jīng)歷我們必須在其他地方使用的潛在變化,所以我們?cè)趩?dòng)函數(shù)時(shí)將它們聲明為全局。
我們用asyncio-Variant的asyncio.sleep_ms()代替正常的超時(shí)的Sleep_ms()。用線條
我們向系統(tǒng)發(fā)出信號(hào),告知該進(jìn)程可以在此時(shí)中斷,以便操作其他進(jìn)程。
只要pad TP1沒有被觸碰,那么這個(gè)循環(huán)就會(huì)空著運(yùn)行。如果確定了觸摸,則傳遞觸摸()1,并使用getduration()確定持續(xù)時(shí)間(以毫秒為單位)。
一個(gè)短的水龍頭帶來的周期遠(yuǎn)低于100。
如果保持時(shí)間小于500ms,我們計(jì)數(shù)通道并將信號(hào)RGB切換到相應(yīng)的顏色。通過模5除數(shù)的形成,我們將其取值范圍限制在0…4,從而接收到一個(gè)環(huán)形計(jì)數(shù)器。
如果保持時(shí)間在半秒到兩秒之間,我們觸發(fā)當(dāng)前顏色的存儲(chǔ)。
LED環(huán)變暗超過兩秒。
函數(shù)showchannel()操作信號(hào)LED的輸出。通道號(hào)被移交并測(cè)試是否符合有效區(qū)域。如果不是這種情況,則拋出異常。led (i)一個(gè)接一個(gè)地表示紅色,綠色和藍(lán)色的三個(gè)輸出。在num上訪問相應(yīng)的模式,并在模式的元組中尋址值。
showchannel(3)調(diào)用通道3(藍(lán)色)的模式(0.0.1),并設(shè)置Ledr = 0, LedG = 0和LEDB = 1。
具有Async Def的函數(shù)被啟動(dòng)時(shí),行為是協(xié)作的,它們?cè)试S多個(gè)進(jìn)程彼此并行執(zhí)行,因此被稱為協(xié)程。使用協(xié)同程序increate(),我們計(jì)算所設(shè)置通道的顏色值。顏色、實(shí)現(xiàn)和注釋的變化必須在流程之外可見,即全局可見。該進(jìn)程被永久地保存在while循環(huán)中,并且可以被中斷。
通道1到3,一個(gè)離散的顏色被控制。如果我們控制顏色值增加時(shí)的附加值。在第10次運(yùn)行時(shí),為了避免不必要的副作用,第5次運(yùn)行時(shí),我們將顏色值限制為最大255。列表中對(duì)應(yīng)的元素顏色為。1中的通道數(shù)減少1個(gè)PTR。
在通道4中,所有分量的顏色增加相同的值3。在[255,255,255]處結(jié)束。當(dāng)向后移動(dòng)時(shí),只有白光的強(qiáng)度降低。原來設(shè)定的顏色不再達(dá)到。目前這不是很好,但應(yīng)該在sensorlampy2.0的另一集中進(jìn)行優(yōu)化。
信號(hào)LED在通道0處變暗。在減少選項(xiàng)卡中,當(dāng)前的顏色代碼為realciintermediated,代碼為[0.0.0]。這里,在increate()中,顏色代碼被恢復(fù)并發(fā)送到環(huán)。旗子說:讓我們把它放回去。
函數(shù)遞減()如果我們做類似的工作,不是加,而是用顏色值做減法。
主程序也是作為協(xié)程編寫的。首先,我們創(chuàng)建一個(gè)事件循環(huán)。它接管了對(duì)任務(wù)過程的控制。作為參數(shù),我們傳遞函數(shù)并解釋事件循環(huán)應(yīng)該是一個(gè)永久的運(yùn)行器。
我們打開燈并啟動(dòng)Main()函數(shù)。在那之后,一切都自行進(jìn)行。在那之后,一切都是通過觸摸觸控板完成的。
本文編譯自hackster.io