Lua: выполнить функцию во время работы веб-сервера

У меня есть вопрос из-за маленькой проблемы. Я новичок и работаю с Lua и ESP8266 12-E. Я использую пример из randomnerdtutorials, который управляет цветом светодиодов с помощью веб-сервера. Между тем я могу контролировать цвета светодиодов с помощью узла-красного. Проблема заключается в том, что я хотел бы написать процедуру, которая будет постепенно угасать светодиодами разных цветов. Я написал цикл, который увеличил число столбцов с 0 до 999. Цикл находится в функции, которая вызывается из node-red. В этом цикле ESP сбрасывается в aprox. отсчет 500. Из того, что я прочитал, я понимаю, что цикл for и веб-сервер, ожидающий ввода, должны выполняться одновременно. Кто-нибудь может дать мне подсказку, как я мог это сделать. Я могу прервать цикл for, но не могу вернуться с веб-сервера, поскольку в нем нет цикла, в котором я мог бы поместить команду. Я надеюсь, что мой английский понятен. Это мой код:

dofile("anmeldedaten.lc")

function led(r, g, b)
    pwm.setduty(5, r)
    pwm.setduty(6, g)
    pwm.setduty(7, b)
end

pwm.setup(5, 1000, 1023)
pwm.setup(6, 1000, 1023)
pwm.setup(7, 1000, 1023)
pwm.start(5)
pwm.start(6)
pwm.start(7)

r=0
g=0
b=0
fade1=1
ic=0 --internal counter
ig=0 -- global counter
fade1on=0


    if srv ~= nil then
      srv:close()
    end

    srv=net.createServer(net.TCP)

    srv:listen(80,function(conn)

        conn:on("receive", function(client,request)
            local buf = "";
            buf = buf.."HTTP/1.1 200 OK\r\n\r\n"
            local _, _, method, path, vars = string.find(request, "([A-Z]+) (.+)?(.+) HTTP");
            if(method == nil)then
                _, _, method, path = string.find(request, "([A-Z]+) (.+) HTTP");
            end
            local _GET = {}
            if (vars ~= nil)then
                for k, v in string.gmatch(vars, "(%w+)=(%w+)&*") do
                    _GET[k] = v
                end
            end
            buf = buf.."<!DOCTYPE html><html><head>";
            buf = buf.."<meta charset=\"utf-8\">";
            buf = buf.."<meta http-equiv=\"X-UA-Compatible\" content=\"IE=edge\">";
            buf = buf.."<meta name=\"viewport\" content=\"width=device-width, initial-scale=1\">";
            buf = buf.."<link rel=\"stylesheet\" href=\"https://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/css/bootstrap.min.css\">";
            buf = buf.."<script src=\"https://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/js/bootstrap.min.js\"></script>";
            buf = buf.."<script src=\"https://cdnjs.cloudflare.com/ajax/libs/jscolor/2.0.4/jscolor.min.js\"></script>";
            buf = buf.."</head><body><div class=\"container\"><div class=\"row\"><h1>ESP Color Picker</h1>";       
            buf = buf.."<a type=\"submit\" id=\"change_color\" type=\"button\" class=\"btn btn-primary\">Change Color</a> ";
            buf = buf.."<input class=\"jscolor {onFineChange:'update(this)'}\" id=\"rgb\"></div></div>";
            buf = buf.."<script>function update(picker) {document.getElementById('rgb').innerHTML = Math.round(picker.rgb[0]) + ', ' +  Math.round(picker.rgb[1]) + ', ' + Math.round(picker.rgb[2]);";      
            buf = buf.."document.getElementById(\"change_color\").href=\"?r=\" + Math.round(picker.rgb[0]*4.0117) + \"&g=\" +  Math.round(picker.rgb[1]*4.0117) + \"&b=\" + Math.round(picker.rgb[2]*4.0117);}</script></body></html>";


            if(_GET.r or _GET.g or _GET.b or _GET.fade1) then
                print(_GET.r, _GET.g,_GET.b,_GET.fade1)

                    if _GET.fade1 == "OFF" then
                        fade1on=0
                        r = _GET.r
                        g = _GET.g
                        b = _GET.b
                        led(r,g,b)
                    elseif _GET.fade1 == "ON" then 
                        ig=0
                        ic=0
                        fade1on=1
                        fade()
                    end
                print(r,g,b,fade1)
            end

            client:send(buf);
            conn:on("sent", function() client:close() end)
            collectgarbage();
        end)   
    end)


function fade()

        for ic=0,999,1 do
            r=ic
            led(r,g,b)
            print(r)
        end
end

1 ответ

Онлайн-документация NodeMCU включает в себя часто задаваемые вопросы, которые охватывают все это. Стоит прочитать. В двух словах, API - это архитектура, управляемая событиями node.js, Система включает в себя сторожевой таймер, который будет сбрасывать процессор, если любая четкая задача занимает слишком много времени.

Правильный способ реализации постепенного изменения состоит в использовании обратного вызова таймера для выполнения линейного изменения. Опять же, прочитайте соответствующий раздел документации.

Другие вопросы по тегам