ESP8266的网页web交互界面

ESP8266的网页web交互界面

  • arduino的菜单库

    • https://github.com/neu-rah/ArduinoMenu
  • 自带生成html界面

    • https://github.com/Hieromon/PageBuilder
  • star很多的esp固件

    • https://github.com/arendst/Tasmota
  • ESP UI

    • https://github.com/s00500/ESPUI
  • 方法:

    • 通过html上的JavaScript脚本向服务器put或pose实现交互

ESP8266做web服务器

https://swf.com.tw/?p=905

ESP8266的网页web交互界面_第1张图片

按照图中的结构将网页文件放在data文件夹中,然后在arduino中上传到spiffs

ESP8266的网页web交互界面_第2张图片

void rootRouter() {
  File file = SPIFFS.open("/index.htm", "r");//fs以data作为根目录,里面的index.htm的地址就是/index.htm,如果由文件夹image,里面的图片地址就是/image/xxx.png
  server.streamFile(file, "text/html");
  file.close();
}
void setup()
{
    ......//连接wifi
    server.on("/index.htm", rootRouter);//如果访问的网址是http://192.168.124.8/index.htm时,url是/index.htm,给回调函数rootRouter处理
}

但是这样有个弊端,就是每个url都需要写一个回调函数,比如html里面还有调用了图片,浏览器就会向esp8266更具url请求这个图片,但是esp8266没有写这个图片的url处理函数,所以就会显示不出来

改进方法

String getContentType(String filename){
    //通过url的结尾包含哪些字符,判断是什么格式
  if(server.hasArg("download")) return "application/octet-stream";
  else if(filename.endsWith(".htm")) return "text/html";
  else if(filename.endsWith(".html")) return "text/html";
  else if(filename.endsWith(".css")) return "text/css";
  else if(filename.endsWith(".js")) return "application/javascript";
  else if(filename.endsWith(".png")) return "image/png";
  else if(filename.endsWith(".gif")) return "image/gif";
  else if(filename.endsWith(".jpg")) return "image/jpeg";
  else if(filename.endsWith(".ico")) return "image/x-icon";
  else if(filename.endsWith(".xml")) return "text/xml";
  else if(filename.endsWith(".pdf")) return "application/x-pdf";
  else if(filename.endsWith(".zip")) return "application/x-zip";
  else if(filename.endsWith(".gz")) return "application/x-gzip";
  return "text/plain";
}

bool handleFileRead(String path){
  Serial.println("handleFileRead: " + path); // 在序列埠显示路径

    //在url为根目录的情况下,默认返回/index.htm这个文件
  if (path.endsWith("/")) {
    path += "index.htm";
  }

  String contentType = getContentType(path);//获取文件格式,给server.streamFile函数使用
  //调用SPIFFS.exists()判断这个url是否在文件系统中存在
  if (SPIFFS.exists(path)){
      //打开这个文件
    File file = SPIFFS.open(path, "r");
      //发送这个文件
    server.streamFile(file, contentType);
    file.close();

    return true;
  }
    //否则就返回没有,404
  return false;
}


void setup()
{
    //只写一个回调处理函数,只有在没有找到对应文件的情况下,才返回notfound
    server.onNotFound([](){
    if (!handleFileRead(server.uri())) {
      server.send(404, "text/plain", "FileNotFound");
    }
  });
}

使用Html与arduino交互

用form表单,使用iframe可以达到内部网页,实现不跳转新网页

<form action="" method="post" target="nm_iframe">
	<input type="text" id="id_input_text" name="nm_input_text" />
	<input type="submit" id="id_submit" name="nm_submit" value="提交" />
form>
 
<iframe id="id_iframe" name="nm_iframe" style="display:none;">iframe>

将结果跳转到新网页上显示

acction表示要请求的url地址,method指示是get还是post,taget指示是新开网页还是当前网页

<form action="toggle" method="get" target="_blank">
  <input type="submit" value="开关LED">
form>

更好的方式是用javascript,使用jQuery库进行开发

https://10.1pxeye.com/http-get-request-in-javascript/

JavaScript 是 HTML5 以及所有现代浏览器中的默认脚本语言

ESP8266的网页web交互界面_第3张图片

jQuery库

例子html

doctype html>
<html>
<head>
<script src="js/jquery.js"> script>//官网上下载的库
<script src="js/javascript.js">script>//自己的js脚本
<meta charset="utf-8">
<title>ESP8266title>
head>

<body>
<h2>This is a headingh2>
<p>This is a paragraph.p>
<p>This is another paragraph.p>
<button type="button">Click mebutton>//type是button的一个属性
body>

html>

例子js

$(document).ready(function(){//文档就绪函数
  $("button").click(function(){
    $("p").hide();
  });
});

$(this).hide() - 隐藏当前元素

$(“p”).hide() - 隐藏所有段落

$(".test").hide() - 隐藏所有 class=“test” 的所有元素

$("#test").hide() - 隐藏所有 id=“test” 的元素

button的type属性,

描述
submit 该按钮是提交按钮(除了 Internet Explorer,该值是其他浏览器的默认值)。
button 该按钮是可点击的按钮(Internet Explorer 的默认值)。
reset 该按钮是重置按钮(清除表单数据)。

jQuery 元素选择器

jQuery 使用 CSS 选择器来选取 HTML 元素。

$(“p”) 选取

元素。

$(“p.intro”) 选取所有 class=“intro” 的

元素。

$(“p#demo”) 选取所有 id=“demo” 的

元素。

jQuery 属性选择器

jQuery 使用 XPath 表达式来选择带有给定属性的元素。

$("[href]") 选取所有带有 href 属性的元素。

$("[href=’#’]") 选取所有带有 href 值等于 “#” 的元素。

$("[href!=’#’]") 选取所有带有 href 值不等于 “#” 的元素。

( " [ h r e f ("[href ("[href=’.jpg’]") 选取所有 href 值以 “.jpg” 结尾的元素。

button的name就需要用属性选择器

还可以用id的方式

<script type="text/javascript">
$(document).ready(function(){
  $("#hide").click(function(){
  $("p").hide();
  });
  $("#show").click(function(){
  $("p").show();
  });
});
script>

<button id="hide" type="button">隐藏button>
<button id="show" type="button">显示button>

事件

Event 函数 绑定函数至
$(document).ready(function) 将函数绑定到文档的就绪事件(当文档完成加载时)
$(selector).click(function) 触发或将函数绑定到被选元素的点击事件
$(selector).dblclick(function) 触发或将函数绑定到被选元素的双击事件
$(selector).focus(function) 触发或将函数绑定到被选元素的获得焦点事件
$(selector).mouseover(function) 触发或将函数绑定到被选元素的鼠标悬停事件

隐藏显示

jQuery hide() 和 show(),jQuery toggle()

AJAX

https://www.w3school.com.cn/jquery/jquery_ajax_get_post.asp

arduino的webserver库教程

在不重载全部网页的情况下,和服务器做数据交换

能够使用 HTTP Get 和 HTTP Post 从远程服务器上请求文本、HTML、XML 或 JSON

  • jQuery load() 方法

    jQuery load() 方法是简单但强大的 AJAX 方法。

    load() 方法从服务器加载数据,并把返回的数据放入被选元素中。

  • jQuery - AJAX get() 和 post() 方法

    $("button").click(function(){
      $.get("demo_test.asp",function(data,status){
        alert("Data: " + data + "\nStatus: " + status);
      });
    });
    

HTML语法

  • HTML 段落是通过

    标签进行定义的。

  • HTML 链接是通过 标签进行定义的。

  • HTML 标题(Heading)是通过

    -

    等标签进行定义的。

  • HTML 图像是通过 标签进行定义的。

    • 
      

HTML属性

class classname 规定元素的类名(classname)
id id 规定元素的唯一 id
style style_definition 规定元素的行内样式(inline style)
title text 规定元素的额外信息(可在工具提示中显示)

网页模板

https://aspx.sc.chinaz.com/query.aspx?keyword=%E5%90%8E%E5%8F%B0&classID=12

搜索后台,就可以

还可以搜响应菜单

或者搜索Admin Template

有纯html5的,也有用CSS3,也有用Jquery的

定时器

使用js的定时器

教程在菜鸟JS 浏览器BOM

https://www.runoob.com/js/js-timing.html

var int=self.setInterval("clock()",1000);
function clock()
{
  var d=new Date();
  var t=d.toLocaleTimeString();
  $("#time").text(t);
}  
//要和jquery分开写 
//或者这样写成匿名函数
self.setInterval(function(){
  var d=new Date();
  var t=d.toLocaleTimeString();
  $("#time").text(t);
},1000);

使用jquery的定时器好像不行

居中

<style> 
body{text-align:center} 
style> 

实例

https://www.runoob.com/js/js-examples.html

表格

<table border="2" cellpadding="10" align=center>
  <tr>
    <td>
      <b>控制中心
    td> 
    <td>
      <p>
        切换板载LED灯: <button id="toggle" type="button">Togglebutton>
      p>
    td> 
  tr>
  <tr>
    <td>
      <b>数据中心
    td> 
    <td>
      <p id="time">运行时间p>
    td>
  tr>
table>

获取单选框的值

https://www.cnblogs.com/zsg88/p/10635219.html

所以选择器参考https://www.w3school.com.cn/jquery/jquery_ref_selectors.asp

:冒号是取type是xxx的所有元素

:checked $(":checked") 所有被选中的 input 元素
:radio $(":radio") 所有 type=“radio” 的 元素
      <input type="radio" id="led" name="led" value="on"><input type="radio" id="led" name="led" value="off"><button id="setLed" type="button">设置LEDbutton>

radio单选框,在name相同的时候,才只能选一个

  $("#setLed").click(function(){
      //使用post发送数据
    $.post("setLed",
      {
        value:$("#led:checked").val()//使用id确定单选框,checked确定勾选的,然后取他的value属性
      },
      function(data,status){
        if(data=="true")
        {
          alert("切换成功");
        }
        else
        {
          alert("切换失败");
        }
    });
  });

arduino使用arg来获取post的数据

void setLedCallback() {
  if(server.arg("value") == "on")
    digitalWrite(LED_BUILTIN, LOW);
  else
    digitalWrite(LED_BUILTIN, HIGH);
  server.send(200, "text/plain", "true");
}

arduino使用**server.args()**获取一共有多少各参数

使用**server.argName(0)**获取第几个参数的键名

POST数组

在js中是可以post数组的,但是只能以键值对发送

 {
        value:$("input:radio[name=led]:checked").val(),
        list:[1,2,3]
	},

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-JwmI5ysQ-1648294918509)(C:\Users\87698\AppData\Roaming\Typora\typora-user-images\image-20220109212613173.png)]

这个%5B和%5D其实就是[]

arg[1]=list[]1

接收到的ascii码的键名是list[],值为1

arduino不能直接处理这个格式,需要其他类型转换

你可能感兴趣的:(arduino,c++,嵌入式硬件)