Przeglądaj źródła

修整数据结构,添加ui

guohui 1 rok temu
rodzic
commit
5d0c5e8008

+ 639 - 0
f407/applications/data.js

@@ -0,0 +1,639 @@
+
+var PKT_TYPE=function(){
+    var len = 0;
+    return {
+        PKT_TYPE_ACK:len++,             
+        PKT_TYPE_PARAS:len++,             
+        PKT_TYPE_POWER_CH:len++,          //power_ch_t
+        PKT_TYPE_POWER_TOTAL:len++,       //power_total_t
+        PKT_TYPE_SENSOR:len++,
+        PKT_TYPE_BREAKER:len++,
+        PKT_TYPE_STAT:len++,
+        PKT_TYPE_MESG:len++,
+        PKT_TYPE_FILE:len++,
+    }
+}();
+
+
+///////////////////////////////////////////////////////
+function array_to_string(data){
+    var s = "";
+    for(var i=0;i<data.length  && data[i] !=0;i++){
+        s +=String.fromCharCode(data[i]);
+    }
+    return s;
+}
+
+function string_to_array(data,attr){
+    for(var i=0;i<data.length;i++){
+        attr[i] = data.charCodeAt(i);
+    }
+    return attr;
+}
+function array_cat(a1,a2){
+    var tlen=a1.byteLength+a2.byteLength;
+    var buffer = new ArrayBuffer(tlen);
+    var vw = new Uint8Array(buffer);
+    
+    var vw1 = new Uint8Array(a1);
+    for(var i=0; i<a1.byteLength; i++) {
+        vw[i] = vw1[i];
+    }
+    
+    var vw2 = new Uint8Array(a2);
+    for(var i=0; i<a2.byteLength; i++) {
+        vw[i+a1.byteLength] = vw2[i];
+    }
+    return buffer;
+}
+///////////////////////////////////////////////////
+function bin_to_hdr(bin) {
+    var tmp, length=0;
+
+    tmp = new DataView(bin, length);
+    this.magic = tmp.getUint32(0,true);
+    length += 4;
+
+    tmp = new DataView(bin, length);
+    this.type = tmp.getUint32(0,true);
+    length += 4;
+
+    tmp = new DataView(bin, length);
+    this.nack = tmp.getUint32(0,true);
+    length += 4;
+
+    tmp = new DataView(bin, length);
+    this.dlen = tmp.getUint32(0,true);
+    length += 4;
+
+    this.len = length;
+}
+function bin_to_info(bin) {
+    var tmp, length=0;
+
+    tmp = new DataView(bin, length);
+    this.type = tmp.getUint8(0,true);
+    length += 1;
+
+    tmp = new DataView(bin, length);
+    this.addr = tmp.getUint8(0,true);
+    length += 1;
+
+    tmp = new DataView(bin, length);
+    this.ch = tmp.getUint8(0,true);
+    length += 1;
+
+    tmp = new DataView(bin, length);
+    this.sch = tmp.getUint8(0,true);
+    length += 1;
+    
+    tmp = new DataView(bin, length);
+    this.pid = tmp.getUint8(0,true);
+    length += 1;
+    
+    tmp = new DataView(bin, length);
+    this.start_delay = tmp.getUint16(0,true);
+    length += 2;
+    
+    tmp = new DataView(bin, length);
+    this.stop_delay = tmp.getUint16(0,true);
+    length += 2;
+
+    this.len = length;
+}
+function bin_to_power(bin) {
+    var tmp, length=0;
+
+    tmp = new DataView(bin, length);
+    this.voltage = tmp.getFloat32(0,true);
+    length += 4;
+
+    tmp = new DataView(bin, length);
+    this.current = tmp.getFloat32(0,true);
+    length += 4;
+
+    tmp = new DataView(bin, length);
+    this.power = tmp.getFloat32(0,true);
+    length += 4;
+
+    tmp = new DataView(bin, length);
+    this.freq = tmp.getFloat32(0,true);
+    length += 4;
+    
+    tmp = new DataView(bin, length);
+    this.factor = tmp.getFloat32(0,true);
+    length += 4;
+
+    tmp = new DataView(bin, length);
+    this.consump = tmp.getFloat32(0,true);
+    length += 4;
+
+    tmp = new DataView(bin, length);
+    this.status = tmp.getUint8(0,true);
+    length += 1;
+
+    tmp = new DataView(bin, length);
+    this.nwire = tmp.getUint8(0,true);
+    length += 1;
+
+    this.len = length;
+}
+function bin_to_alarm(bin) {
+    var tmp, length=0;
+
+    tmp = new DataView(bin, length);
+    this.v_upper = tmp.getUint8(0,true);
+    length += 1;
+
+    tmp = new DataView(bin, length);
+    this.v_lower = tmp.getUint8(0,true);
+    length += 1;
+
+    tmp = new DataView(bin, length);
+    this.c_upper = tmp.getUint8(0,true);
+    length += 1;
+
+    tmp = new DataView(bin, length);
+    this.p_upper = tmp.getUint8(0,true);
+    length += 1;
+    
+    tmp = new DataView(bin, length);
+    this.w_upper = tmp.getUint8(0,true);
+    length += 1;
+    
+    tmp = new DataView(bin, length);
+    this.ph_loss = tmp.getUint8(0,true);
+    length += 1;
+
+    this.len = length;
+}
+function bin_to_powerc(bin) {
+    var tmp, bin2, length=0;
+
+    this.info = new bin_to_info(bin);
+    length += this.info.len;
+    
+    this.power = [];
+    for(var i=0; i<3; i++) {
+        this.power[i] = new bin_to_power(bin.slice(length));
+        length += this.power[i].len;
+    }
+    
+    this.alarm = new bin_to_alarm(bin.slice(length));
+    length += this.alarm.len;
+    
+    tmp = new DataView(bin, length);
+    this.time = tmp.getUint32(0,true);
+    length += this.time.len;
+
+    this.len = length;
+}
+function bin_to_total(bin) {
+    var tmp, length=0;
+
+    tmp = new DataView(bin, length);
+    this.voltage = tmp.getFloat32 (0,true);
+    length += 4;
+
+    tmp = new DataView(bin, length);
+    this.current = tmp.getFloat32(0,true);
+    length += 4;
+
+    tmp = new DataView(bin, length);
+    this.power = tmp.getFloat32(0,true);
+    length += 4;
+
+    tmp = new DataView(bin, length);
+    this.freq = tmp.getFloat32(0,true);
+    length += 4;
+    
+    tmp = new DataView(bin, length);
+    this.consump = tmp.getFloat32 (0,true);
+    length += 4;
+
+    tmp = new DataView(bin, length);
+    this.active = tmp.getFloat32(0,true);
+    length += 4;
+
+    tmp = new DataView(bin, length);
+    this.reactive = tmp.getFloat32(0,true);
+    length += 4;
+
+    tmp = new DataView(bin, length);
+    this.apparent = tmp.getFloat32(0,true);
+    length += 4;
+    
+    this.len = length;
+}
+function bin_to_powert(bin) {
+    var tmp, length=0;
+
+    tmp = new DataView(bin, length);
+    this.type = tmp.getUint8(0,true);
+    length += 1;
+
+    this.total = [];
+    for(var i=0; i<3; i++) {
+        this.total[i] = new bin_to_total(bin.slice(length));
+        length += this.total[i].len;
+    }
+    
+    this.len = length;
+}
+///////////////////////////////////////////////////
+function hdr_to_bin(js) {
+    var tmp, length=0;
+    var buffer = new ArrayBuffer(js.len);
+
+    tmp = new DataView(buffer, length);
+    tmp.setUint32(0,js.magic,true);
+    length += 4;
+
+    tmp = new DataView(buffer, length);
+    tmp.setUint32(0,js.type,true);
+    length += 4;
+
+    tmp = new DataView(buffer, length);
+    tmp.setUint32(0,js.nack,true);
+    length += 4;
+    
+    tmp = new DataView(buffer, length);
+    tmp.setUint32(0,js.dlen,true);
+    length += 4;
+
+    return buffer;
+}
+function info_to_bin(js) {
+    var tmp, length=0;
+    var buffer = new ArrayBuffer(js.len);
+
+    tmp = new DataView(buffer, length);
+    tmp.setUint8(0,js.type,true);
+    length += 1;
+
+    tmp = new DataView(buffer, length);
+    tmp.setUint8(0,js.addr,true);
+    length += 1;
+    
+    tmp = new DataView(buffer, length);
+    tmp.setUint8(0,js.ch,true);
+    length += 1;
+    
+    tmp = new DataView(buffer, length);
+    tmp.setUint8(0,js.sch,true);
+    length += 1;
+
+    tmp = new DataView(buffer, length);
+    tmp.setUint8(0,js.pid,true);
+    length += 1;
+    
+    tmp = new DataView(buffer, length);
+    tmp.setUint16(0,js.start_delay,true);
+    length += 2;
+    
+    tmp = new DataView(buffer, length);
+    tmp.setUint16(0,js.stop_delay,true);
+    length += 2;
+
+    return buffer;
+}
+function power_to_bin(js) {
+    var tmp, length=0;
+    var buffer = new ArrayBuffer(js.len);
+
+    tmp = new DataView(buffer, length);
+    tmp.setFloat32(0,js.voltage,true);
+    length += 4;
+
+    tmp = new DataView(buffer, length);
+    tmp.setFloat32(0,js.current,true);
+    length += 4;
+
+    tmp = new DataView(buffer, length);
+    tmp.setFloat32(0,js.power,true);
+    length += 4;
+
+    tmp = new DataView(buffer, length);
+    tmp.setFloat32(0,js.freq,true);
+    length += 4;
+    
+    tmp = new DataView(buffer, length);
+    tmp.setFloat32(0,js.factor,true);
+    length += 4;
+
+    tmp = new DataView(buffer, length);
+    tmp.setFloat32(0,js.consump,true);
+    length += 4;
+
+    tmp = new DataView(buffer, length);
+    tmp.setUint8(0,js.status,true);
+    length += 1;
+
+    tmp = new DataView(buffer, length);
+    tmp.setUint8(0,js.nwire,true);
+    length += 1;
+
+    return buffer;
+}
+function alarm_to_bin(js) {
+    var tmp, length=0;
+    var buffer = new ArrayBuffer(js.len);
+
+    tmp = new DataView(buffer, length);
+    tmp.setUint8(0,js.v_upper,true);
+    length += 1;
+
+    tmp = new DataView(buffer, length);
+    tmp.setUint8(0,js.v_lower,true);
+    length += 1;
+
+    tmp = new DataView(buffer, length);
+    tmp.setUint8(0,js.c_upper,true);
+    length += 1;
+
+    tmp = new DataView(buffer, length);
+    tmp.setUint8(0,js.p_upper,true);
+    length += 1;
+    
+    tmp = new DataView(buffer, length);
+    tmp.setUint8(0,js.w_upper,true);
+    length += 1;
+    
+    tmp = new DataView(buffer, length);
+    tmp.setUint8(0,js.ph_loss,true);
+    length += 1;
+
+    return buffer;
+}
+function powerc_to_bin(js) {
+    var bin,tmp, length=0;
+    
+    bin = info_to_bin(js.info);
+    
+    for(var i=0; i<3; i++) {
+        tmp = power_to_bin(js.power[i]);
+        bin = array_cat(bin, tmp);
+    }
+    
+    tmp = alarm_to_bin(js.alarm);
+    bin = array_cat(bin, tmp);
+    
+    var buf = new ArrayBuffer(4);
+    tmp = new DataView(buf, 0);
+    tmp.setUint32(0,js.time,true);
+    
+    bin = array_cat(bin, buf);
+
+    return bin;
+}
+function total_to_bin(js) {
+    var tmp, length=0;
+    var buffer = new ArrayBuffer(js.len);
+
+    tmp = new DataView(buffer, length);
+    tmp.setFloat32(0,js.voltage,true);
+    length += 4;
+
+    tmp = new DataView(buffer, length);
+    tmp.setFloat32(0,js.current,true);
+    length += 4;
+
+    tmp = new DataView(buffer, length);
+    tmp.setFloat32(0,js.power,true);
+    length += 4;
+
+    tmp = new DataView(buffer, length);
+    tmp.setFloat32(0,js.freq,true);
+    length += 4;
+    
+    tmp = new DataView(buffer, length);
+    tmp.setFloat32(0,js.consump,true);
+    length += 4;
+    
+    ///
+    tmp = new DataView(buffer, length);
+    tmp.setFloat32(0,js.active,true);
+    length += 4;
+    
+    tmp = new DataView(buffer, length);
+    tmp.setFloat32(0,js.reactive,true);
+    length += 4;
+    
+    tmp = new DataView(buffer, length);
+    tmp.setFloat32(0,js.apparent,true);
+    length += 4;
+
+    return buffer;
+}
+function powert_to_bin(js) {
+    var tmp,bin2,length=0;
+    var bin = new ArrayBuffer(1);
+
+    tmp = new DataView(bin, length);
+    tmp.setUint8(0,js.type,true);
+    length += 4;
+
+    for(var i=0; i<3; i++) {
+        bin2 = new total_to_bin(js.total[i]);
+        bin = array_cat(bin, bin2);
+    }
+
+    return bin;
+}
+//////////////////////////////////////////////////////////////
+
+var XXX ={};
+XXX.hdr = function() {
+    this.j2b = function (js) {
+        var tmp;
+        var hdr = new hdr_to_bin(js);
+
+        switch(js.type){
+            case PKT_TYPE.PKT_TYPE_POWER_CH:
+                tmp = BIN.powerc.j2b(js.powerc);
+                break;
+
+            case PKT_TYPE.PKT_TYPE_POWER_TOTAL:
+                tmp = BIN.powert.j2b(js.powert);
+                break;
+        }
+        return array_cat(hdr,tmp);
+    };
+
+    this.b2j = function (bin) {
+        var tmp;
+        var hdr = new bin_to_hdr(bin);
+        
+        if(hdr.nack == 1){
+            //tmp = myBinary.ack.bin2js(bin,this.hdr.len,true);
+            //myLog('log',tmp);
+            //var data = tmp.data;
+        }
+        
+        var data = bin.slice(hdr.len);
+        switch(hdr.type) {
+            case PKT_TYPE.PKT_TYPE_POWER_CH:
+                hdr.powerc = BIN.powerc.b2j(data);
+                break;
+
+            case PKT_TYPE.PKT_TYPE_POWER_TOTAL:
+                hdr.powert = BIN.powert.b2j(data);
+                break;
+
+            default :
+                console.log("wrong hdr type: "+hdr.type);
+        }
+        return hdr;
+    }
+};
+XXX.paras=function() {
+    this.j2b = function (js) {
+        
+    }
+    
+    this.b2j = function (bin) {
+        
+    }
+};
+XXX.powerc=function() {
+    this.j2b = function (js) {
+        return new powerc_to_bin(js);
+    }
+
+    this.b2j = function (bin) {
+        return new bin_to_powerc(bin);
+    }
+};
+XXX.powert=function() {
+    this.j2b = function (js) {
+        return new powert_to_bin(js);
+    }
+
+    this.b2j = function (bin) {
+        return new bin_to_powert(bin);
+    }
+};
+
+
+var BIN=new function() {
+    this.hdr = new XXX.hdr();
+    this.paras = new XXX.paras();
+    this.powerc = new XXX.powerc();
+    this.powert = new XXX.powert();
+}();
+
+
+//////////////////////////////////////////
+function LOG(){
+    var data = [];
+    for(var i= 1,len=arguments.length;i<len;i++){
+        data.push(arguments[i])
+    }
+    console.log(data);
+
+}
+
+var PKT_TYPE=function(){
+    var len = 0;
+    return {
+        PKT_TYPE_ACK:len++,             
+        PKT_TYPE_PARAS:len++,             
+        PKT_TYPE_POWER_CH:len++,          //power_ch_t
+        PKT_TYPE_POWER_TOTAL:len++,       //power_total_t
+        PKT_TYPE_SENSOR:len++,
+        PKT_TYPE_BREAKER:len++,
+        PKT_TYPE_STAT:len++,
+        PKT_TYPE_MESG:len++,
+        PKT_TYPE_FILE:len++,
+    }
+}();
+
+
+function WS(url,fn) {
+    this.url = url;
+    this.name = 'myWebs';
+    this.open = _open;
+    this.reopen = _reopen;
+    this.close = _close;
+    this.send = _send;
+    this.state = _state;
+    this.setcb = _setcb;
+    this.closeCount = 0;
+    this.maxConnect = 100;
+    var his = this;
+    this.open();
+    function _open() {
+        console.log("____ url: \n", his.url);
+        his.ws = new WebSocket(his.url);
+        his.ws.binaryType = 'arraybuffer';
+        his.ws.onopen = _onopen;
+        his.ws.onclose = _onclose;
+        his.ws.onmessage = _onmsg;
+        his.ws.onerror = _onerror;
+    }
+
+    function _reopen() {
+        _close();
+        _open(his.url);
+    }
+
+    function _close() {
+        his.ws.close();
+    }
+
+    function _send(msg) {
+        if (his.ws.readyState != WebSocket.OPEN)
+            return;
+        his.ws.send(msg);
+    }
+
+    function _state() {
+        return his.ws.readyState;
+    }
+
+    function _setcb(tp, f) {
+        switch (tp) {
+            case "open":
+                his.ws.onopen = f;
+                break;
+
+            case "close":
+                his.ws.onclose = f;
+                break;
+
+            case "msg":
+                his.ws.onmessage = f;
+                break;
+
+            case "err":
+                his.ws.onerror = f;
+                break;
+        }
+    }
+
+    function _onopen(evt) {
+        his.closeCount = 0;
+        console.log("___ ws.onopen");
+    }
+
+    function _onclose(evt) {
+        LOG("ws.onclose");
+        setTimeout(_reopen, 3000);
+        his.closeCount += 1;
+    }
+
+    function _onmsg(evt) {
+        console.log("___ ws.onmsg");
+        if (evt.data instanceof ArrayBuffer) {
+            fn(evt.data);
+        }
+    }
+
+    function _onerror(evt) {
+        console.log("___ ws.onerror");
+        //write_scr('<span style="color: red;">ERROR:</span> '+ evt.data);
+    }
+
+}
+
+

+ 220 - 73
f407/applications/datadef.h

@@ -8,6 +8,12 @@
 #define CH_MAX          12
 #define BRD_MAX         32
 
+enum{
+    A_P = 0,
+    B_P = 1,
+    C_P = 2,
+};
+
 
 enum {
     RW_READ=0,                                 //读
@@ -33,7 +39,7 @@ enum {
     PDU_DC_I1O1,
     PDU_AC_I3O3=3,
     PDU_AC_I3O1,
-    PDU_AC_I3O3_X,
+    PDU_AC_I3O3_H,
 };
 
 enum {
@@ -97,17 +103,17 @@ enum {
 };
 enum
 {
-    SENSOR_TYPE_TEMP_HUMI   = 0 , //温湿度传感器
-    SENSOR_TYPE_SMOKE       = 1 , //烟雾传感器
-    SENSOR_TYPE_WATER       = 2 , //水浸传感器
-    SENSOR_TYPE_ACCESS      = 3 , //门禁传感器
-    SENSOR_TYPE_GAS         = 4 , //气体传感器
-    SENSOR_TYPE_AIR_PRESS   = 5 , //气压传感器
-    SENSOR_TYPE_AIR_COND    = 6,  //空条传感器
-    SENSOR_TYPE_LEAK        = 7,  //泄漏传感器
-    SENSOR_TYPE_TEMP        = 8,  //温度传感器
-    SENSOR_TYPE_TEMP_DOUBLE = 9,  //双温度传感器
-    SENSOR_TYPE_PRESS       = 10, //压力传感器
+    SENSOR_TYPE_TEMP_HUMI=0,    //温湿度传感器
+    SENSOR_TYPE_SMOKE,          //烟雾传感器
+    SENSOR_TYPE_WATER,          //水浸传感器
+    SENSOR_TYPE_ACCESS,         //门禁传感器
+    SENSOR_TYPE_GAS,            //气体传感器
+    SENSOR_TYPE_AIR_PRESS,      //气压传感器
+    SENSOR_TYPE_AIR_COND,       //空条传感器
+    SENSOR_TYPE_LEAK,           //泄漏传感器
+    SENSOR_TYPE_TEMP,           //温度传感器
+    SENSOR_TYPE_TEMP_DOUBLE,    //双温度传感器
+    SENSOR_TYPE_PRESS,          //压力传感器
 
     SENSOR_TYPE_MAX,
 };
@@ -157,12 +163,12 @@ typedef struct
 
 typedef struct
 {
-    int                 mode;               //0:DHCP  1:STATIC  
-    char                ipaddr[48];         //
-    char                mask[48];           //
-    char                gateway[48];        //
-    char                dns1[48];           //dns1
-    char                dns2[48];           //dns2
+    uint8_t     mode;               //0:DHCP  1:STATIC  
+    char        ipaddr[48];         //
+    char        mask[48];           //
+    char        gateway[48];        //
+    char        dns1[48];           //dns1
+    char        dns2[48];           //dns2
 }network_data_t;
 
 typedef struct {
@@ -191,6 +197,9 @@ typedef struct {
 typedef struct {
     uint8_t             watchdog;
     int32_t             flip_time;
+    uint8_t             led;
+    uint8_t             beep;
+    uint8_t             rotate;
 }misc_data_t;
 
 typedef struct {
@@ -220,20 +229,38 @@ typedef struct {
     uint8_t             lang;
 }sys_data_t;
 
-typedef struct {
-    
-}sys_stat_t;
 
-typedef struct {
+typedef struct power_data{
     float               voltage;                //电压
     float               current;                //电流
     float               power;                  //功率
     float               freq;                   //频率
     float               consump;                //耗电量consumption
-    float               factor;                 //功率因素    
+    float               factor;                 //功率因素
+
     uint8_t             status;                 //开关状态     
-    uint8_t             nwire;                  //零线状态
-}elect_data_t;
+    uint8_t             nwire;                  //零线状态    
+}power_t;
+
+typedef union board_wanning{
+    uint8_t             data[3];
+}power_wanning_t;
+
+typedef struct {
+    uint8_t             en;
+    float               val;                    //threashold value
+    uint8_t             act;
+    uint8_t             act_para;
+}thrd_val_t;
+typedef struct {
+    thrd_val_t          volt_upper;
+    thrd_val_t          volt_lower;
+    thrd_val_t          volt_over;
+    thrd_val_t          curr_upper;             //current
+    thrd_val_t          power_upper;
+    thrd_val_t          pcons_upper;            //power consumption
+}thrd_t;
+
 typedef struct {
     uint8_t             v_upper;                //电压超上限
     uint8_t             v_lower;                //电压超下限
@@ -242,36 +269,59 @@ typedef struct {
     uint8_t             w_upper;                //耗电量超上限
     
     uint8_t             ph_loss;                //缺相
-}alarm_data_t;
+}alarm_t;
 typedef struct {
     uint8_t             type;
     uint8_t             addr;
     uint8_t             ch;                      //该通道在全部板上的所排序号,程序始于0,用户始于1
     uint8_t             sch;                     //该通道在其所在的板上的序号,程序始于0,用户始于1
-    uint8_t             pid;                     //phase id, 0:L1相 1:L2相 2:L3相
-}info_ch_t;
+    uint8_t             ph_id;                   //phase id, 0:L1相 1:L2相 2:L3相
+    
+    uint16_t            start_delay;
+    uint16_t            stop_delay;
+}info_t;
 typedef struct {
-    info_ch_t           info;
-    elect_data_t        *pele;                  //电力信息
-    alarm_data_t        alarm;
+    info_t              info;
+    power_t             power[3];                  //电力信息
+    thrd_t              thrd;                      //阈值
+    alarm_t             alarm;
     uint32_t            time;
 }power_ch_t;
 
 typedef struct {
+    uint8_t (*get_elec_data)(power_ch_t *pch);
+    uint8_t (*get_waning)(power_ch_t *pch);                          //参数后续补齐
+    uint8_t (*open_chn)    (power_ch_t *pch);                        //参数后续补齐
+    uint8_t (*close_chn)(power_ch_t *pch);                           //参数后续补齐
+    uint8_t (*set_open_delay)(power_ch_t *pch);                      //参数后续补齐
+    uint8_t (*set_close_delay)(power_ch_t *pch);                     //参数后续补齐
+    uint8_t (*set_meter)(power_ch_t *pch);                           //参数后续补齐
+    uint8_t (*over_func)(power_ch_t *pch);
+    uint8_t (*reset_consumer)(power_ch_t *pch);
+
+    uint8_t (*get_info)(uint8_t addr);
+    uint8_t (*detect)(uint8_t addr);                                //参数后续补齐
+    uint8_t (*open_all)(uint8_t addr);                                
+    uint8_t (*close_all)(uint8_t addr);
+}board_fn_t;
+
+typedef struct {
+    board_fn_t          *fn;
     uint8_t             type;
     uint8_t             addr;
-    
     uint8_t             chs;
+    uint8_t             sw;                     //开关监测状态
+    board_info_t        info;
     power_ch_t          *pch;                   //根据实际通道数申请连续内存
-}power_brd_t;
+}board_data_t;
 
 typedef struct {
     uint8_t             chs;                    //所有控制板的总通道数
     power_ch_t          **pch;                  //动态指针
     
     uint8_t             cnt;
-    power_brd_t         *pbrd[BRD_MAX];
-}power_all_t;
+    board_data_t        *pbrd[BRD_MAX];
+}board_all_t;
 
 typedef struct {
     float               voltage;                //电压
@@ -283,6 +333,10 @@ typedef struct {
     float               active;                 //有功功率
     float               reactive;               //无功功率
     float               apparent;               //视在功率
+}total_t;
+typedef struct {
+    uint8_t             type;
+    total_t             total[3];
 }power_total_t;
 
 typedef struct {
@@ -291,21 +345,6 @@ typedef struct {
     uint8_t             time;
 }sensor_data_t;
 
-typedef struct {
-    uint8_t             en;
-    float               val;                    //threashold value
-    uint8_t             act;
-    uint8_t             act_para;
-}threshold_t;
-typedef struct {
-    threshold_t         volt_upper;
-    threshold_t         volt_lower;
-    threshold_t         volt_over;
-    threshold_t         curr_upper;             //current
-    threshold_t         power_upper;
-    threshold_t         pcons_upper;            //power consumption
-}threshold_ch_t;
-
 typedef struct {
     uint8_t             type;
     uint32_t            str_id;
@@ -324,29 +363,93 @@ typedef struct {
     int32_t             loop_times;             //循环次数, 负值为无限循环
 }schedule_data_t;
 
+typedef struct cascade_saddr{
+    uint8_t      addr;
+    uint16_t     channels;
+    board_fn_t   *fn;
+    power_ch_t   ch[];
+}cascade_saddr_t;
+
+
+typedef struct cascade_data{
+    cascade_saddr_t *c_s[BRD_MAX];                        //从机最多个数
+}cascade_data_t;
+
+
+typedef struct sensor_info{
+    uint8_t     type;
+    float       v[2];
+}sensor_info_t;
+
+typedef struct md_ac_dc{
+    uint16_t          dev_cnt;                   //设备类型和通道数
+    power_t           power[64];                 //最大64通道
+    uint16_t          temp_hum;
+    uint16_t          switch_stu[64];
+    uint16_t          delay_open[64];
+    uint16_t          delay_close[64];
+    sensor_info_t     md_s[8];
+    uint16_t          dry_node[4]; 
+}md_ac_dc_t;
+
+typedef struct all_info{
+    uint32_t voltage;
+    uint32_t current;
+    uint32_t power;
+    uint32_t consumer;
+}all_info_t;
+
+typedef struct {
+    uint32_t power;
+    uint32_t freq;
+    uint32_t consumer;
+    uint16_t fac;
+    uint32_t out_type;
+}all_chn_info_t;
+
+typedef struct chn_phase_info{
+    uint32_t p_voltage;
+    uint32_t p_current;
+    uint32_t p_power;
+    uint32_t p_consumer;
+    uint32_t p_status;
+}chn_phase_info_t;
+
+typedef struct md_3_ac{
+    uint16_t            dev_cnt;                                        //设备类型和通道数
+    all_info_t          ac_3_all_pw[3];
+    all_chn_info_t      ac_3_all_chn[64];
+    chn_phase_info_t    ac_3_chn_p[64][3];
+    uint16_t            temp_hum;
+    uint16_t            switch_chn[64];
+    uint16_t            delay_open[64];
+    uint16_t            delay_close[64];
+    sensor_info_t       md_s[8];
+    uint16_t            dry_node[4];
+}md_3_ac_t;
 typedef struct {
     sys_data_t          sys;
     
-    power_all_t         pall;
+    board_all_t         ball;
     power_total_t       pttl;
 }all_data_t;
 //////////////////////////////
 typedef struct 
 {
-    uint8_t             userID;    				//用户ID
+    uint8_t             userID;                 //用户ID
     char                name[32];               //用户名-登录
-    char                password[32]; 		    //用户密码
-    char                nick[32]; 			    //用户名称
-    uint8_t             roleID;    		        //角色ID
+    char                password[32];           //用户密码
+    char                nick[32];               //用户名称
+    uint8_t             roleID;                 //角色ID
     uint32_t            time;                   //用户创建时间     
 }user_data_t;
 typedef struct 
 {
-    uint8_t             roleID;    				//角色ID
+    uint8_t             roleID;                 //角色ID
     char                roleName[32];           //角色名称
-    uint8_t             roleLevel; 		        //角色等级
-    char                auth[32]; 		        //角色权限
-    int                 roleSort;    		    //显示顺序
+    uint8_t             roleLevel;              //角色等级
+    char                auth[32];               //角色权限
+    int                 roleSort;               //显示顺序
     uint32_t            time;                   //创建时间
 }role_data_t;
 
@@ -378,12 +481,12 @@ typedef struct
 typedef struct 
 {
     uint8_t             id;
-    uint8_t             mode;    				        //0: open   1: close
+    uint8_t             mode;                           //0: open   1: close
     char                account[64];                    //用户账号
-    char                password[24]; 		            //用户密码
-    char                server[64]; 			        //服务器
-    char                port[10];    		            //端口
-    char                auth[16];    			        //认证方式  
+    char                password[24];                   //用户密码
+    char                server[64];                     //服务器
+    char                port[10];                       //端口
+    char                auth[16];                       //认证方式  
     char                *ca;                            //ca cert
 }mail_send_t;
 typedef struct
@@ -402,15 +505,15 @@ enum {
 };
 
 typedef struct {
-    uint8_t             id;    		                    //id
-    uint8_t             plat;                           //0: emqx   1: aliyun
-    uint8_t             mode;    				        //0: open   1: close
-    char                proto[16];                      //mqtt, mqtts, ws, wss
-    char                name[32];                       //server name
-    char                server[256]; 		            //server ip
-    char                port[10]; 			            //server port
-    char                cid[64];    		            //client ID
-    char                user[32];    			        //
+    uint8_t             id;                              //id
+    uint8_t             plat;                            //0: emqx   1: aliyun
+    uint8_t             mode;                            //0: open   1: close
+    char                proto[16];                       //mqtt, mqtts, ws, wss
+    char                name[32];                        //server name
+    char                server[256];                     //server ip
+    char                port[10];                        //server port
+    char                cid[64];                         //client ID
+    char                user[32];                        //
     char                password[32];
     char                *cert;
     uint8_t             status;
@@ -420,6 +523,50 @@ typedef struct {
     mqtt_server_t       ser[MQTT_SER_MAX];
 }mqtt_info_t;
 
+///////////////////////////////////////////////////////////
+
+typedef struct {
+    uint8_t             flag;
+}sys_stat_t;
+
+typedef struct {
+    uint8_t             flag;
+}mesg_data_t;
+
+enum {
+    PKT_TYPE_ACK=0,             
+    PKT_TYPE_PARAS,             
+    PKT_TYPE_POWER_CH,          //all_ch_t
+    PKT_TYPE_POWER_TOTAL,       //power_total_t
+    PKT_TYPE_SENSOR,
+    PKT_TYPE_BREAKER,
+    PKT_TYPE_STAT,
+    PKT_TYPE_MESG,
+    PKT_TYPE_FILE,
+    
+    PKT_TYPE_MAX
+};
+
+#define PKT_MAGIC  0xdeadbeef
+typedef struct {
+    uint32_t  magic;
+    uint32_t  type;
+    uint32_t  nack;
+    uint32_t  dlen;
+    uint8_t   data[0];
+}pkt_hdr_t;
+
+
+
+
+
+
+
+
+
+
+
+
 #pragma pack ()
 
 #define DB_NAME         "smartPDU.db"

+ 6 - 55
f407/applications/main.c

@@ -3,12 +3,13 @@
 #include <drv_gpio.h>
 #include <drv_usbh.h>
 #include <dfs_fs.h>
-
 #include <sys/socket.h>
 #include <netdb.h>
 #include <unistd.h>
 #include "web.h"
 #include "fs.h"
+#include "ui.h"
+#include "sys.h"
 #include "power.h"
 #include "cfg.h"
 
@@ -16,35 +17,8 @@
 
 extern void lwip_sys_init(void);
 
-#ifdef BOARD_EVB_ATK
-    #define LED0_PIN    GET_PIN(F, 9)
-    #define LED1_PIN    GET_PIN(F, 10)
-#else
-    #define LED0_PIN    GET_PIN(E, 6)
-#endif
 
 
-static void led_init(void)
-{
-#ifdef BOARD_EVB_ATK
-    rt_pin_mode(LED0_PIN, PIN_MODE_OUTPUT);
-    rt_pin_mode(LED1_PIN, PIN_MODE_OUTPUT);
-#else
-    rt_pin_mode(LED0_PIN, PIN_MODE_OUTPUT);
-#endif
-}
-static void led_toggle(void)
-{
-    static rt_ssize_t v=PIN_LOW;
-#ifdef BOARD_EVB_ATK
-    rt_pin_write(LED0_PIN, v);
-    rt_pin_write(LED1_PIN, v);
-#else
-    rt_pin_write(LED0_PIN, v);
-#endif
-    v = (v==PIN_LOW)?PIN_HIGH:PIN_LOW;
-}
-
 static rt_device_t serial;
 static int log_init(void)
 {
@@ -145,7 +119,8 @@ static int sd_mount(void)
 static int user_init(void)
 {
     int r,n=0;
-    led_init();
+    
+    ui_init();
     //rt_hw_lcd_init();
     //net_init("0.0.0.0", SERVER_PORT);
     
@@ -164,38 +139,14 @@ static int user_init(void)
     return 0;
 }
 
-#define THRAD_MAX  3
-static int flags[THRAD_MAX];
-static void my_thread(void *arg)
-{
-    int i,j,p=*(int*)arg;
-    while(1) {
-        for(i=0; i<10; i++) {
-            while(j++<100000);
-        }
-        sleep(1);
-    }
-}
-static void my_start(void)
-{
-    int i;
-    
-    for(i=0; i<THRAD_MAX; i++) {
-        flags[i] = i;
-        rt_thread_t tid = rt_thread_create(NULL, my_thread, &flags[i], 2048, 5, 20);
-        if(tid==NULL) {
-            rt_kprintf("___ thread %d create failed\n", i);
-        }
-        rt_thread_startup(tid);
-    }
-}
 
 
 int main(void)
 {
+    sys_init();
     user_init();
     while (1) {
-        led_toggle();
+        
         rt_thread_mdelay(500);
     }
 }

+ 38 - 228
f407/applications/paras.c

@@ -43,7 +43,7 @@ extern paras_data_t DFLT_PARAS;
 
 typedef struct {
     dictionary          *dic;
-    paras_data_t         paras;
+    paras_data_t        paras;
     char                path[200];
 }paras_handle_t;
 static paras_handle_t  paraHandle={0};
@@ -231,7 +231,7 @@ static int proc_prod(dictionary *dic, int op, product_data_t *prod)
             LOGE("___ check product.type %d is wrong\n", prod->type);
             r = -1;
         }
-        if(prod->pwr_type>PDU_AC_I3O3_X) {
+        if(prod->pwr_type>PDU_AC_I3O3_H) {
             LOGE("___ check product.pwr_type %d is wrong\n", prod->pwr_type);
             r = -1;
         }
@@ -551,219 +551,60 @@ static int proc_modbus(dictionary *dic, int op, modbus_data_t *mb)
 
     return r;
 }
-
-#if 0
-static int proc_ptotal(dictionary *dic, int op, PowerTotal_t *ptotal)
+static int proc_misc(dictionary *dic, int op, misc_data_t *misc)
 {
     int r=0;
     char temp[100];
     char *p,*token=NULL;
 
     if(op==PARAS_CHECK) {
-        if(ptotal->voltage<=0) {
-            LOGE("___ check ptotal, voltage is invalid, must greater than 0\n");
-            r = -1; 
-        }
-
-        if(ptotal->current<=0) {
-            LOGE("___ check ptotal, current is invalid, must greater than 0\n");
-            r = -1; 
-        }
-
-        if(ptotal->power<=0) {
-            LOGE("___ check ptotal, power is invalid, must greater than 0\n");
-            r = -1; 
-        }
-
-        if(ptotal->brdMax<=0) {
-            LOGE("___ check ptotal, brdMax is invalid, must greater than 0\n");
-            r = -1; 
-        }
-        return r;
-    }
-    else if (op==PARAS_WRITE) {
-        r = proc_ptotal(dic, PARAS_CHECK, ptotal);
-        if(r) {
-            return -1;
-        }
-    }
-
-    token = "ptotal:voltage";
-    if(op==PARAS_READ) {
-        r = iniparser_getint(dic, token, -1);
-        if(r==-1) {
-            LOGE("___ iniparser_getint %s failed\n", token);
-            return -1;
-        } else {
-            ptotal->voltage = r;
-        }
-    }
-    else {
-        sprintf(temp, "%d", ptotal->voltage);
-        r = iniparser_set(dic, token, temp);
-        if(r) {
-            LOGE("___ iniparser_set %s failed\n", token);
-            return -1;
-        }
-    }
-
-    token = "ptotal:current";
-    if(op==PARAS_READ) {
-        r = iniparser_getint(dic, token, -1);
-        if(r==-1) {
-            LOGE("___ iniparser_getint %s failed\n", token);
-            return -1;
-        } else {
-            ptotal->current = r;
-        }
-    }
-    else {
-        sprintf(temp, "%d", ptotal->current);
-        r = iniparser_set(dic, token, temp);
-        if(r) {
-            LOGE("___ iniparser_set %s failed\n", token);
-            return -1;
-        }
-    }
-
-    token = "ptotal:power";
-    if(op==PARAS_READ) {
-        r = iniparser_getint(dic, token, -1);
-        if(r==-1) {
-            LOGE("___ iniparser_getint %s failed\n", token);
-            return -1;
-        } else {
-            ptotal->power = r;
-        }
-    }
-    else {
-        sprintf(temp, "%d", ptotal->power);
-        r = iniparser_set(dic, token, temp);
-        if(r) {
-            LOGE("___ iniparser_set %s failed\n", token);
-            return -1;
-        }
-    }
-
-    token = "ptotal:brd_max";
-    if(op==PARAS_READ) {
-        r = iniparser_getint(dic, token, -1);
-        if(r==-1) {
-            LOGE("___ iniparser_getint %s failed\n", token);
-            return -1;
-        } else {
-            ptotal->brdMax = r;
-        }
-    }
-    else {
-        sprintf(temp, "%d", ptotal->brdMax);
-        r = iniparser_set(dic, token, temp);
-        if(r) {
-            LOGE("___ iniparser_set %s failed\n", token);
-            return -1;
-        }
-    }
-
-    r = 0;
-    if(op==PARAS_READ) {
-        r = proc_ptotal(dic, PARAS_CHECK, ptotal);
-    }
-
-    return r;
-}
-static int proc_webcfg(dictionary *dic, int op, WebcfgInfo_t *webcfg)
-{
-    int r=0;
-    char temp[100];
-    char *p,*token=NULL;
-
-    if(op==PARAS_CHECK) {
-        if(webcfg->monway<0 || webcfg->monway>3) {
-            LOGE("___ check webcfg, mon_way is invalid, correct value is 1/2/3\n");
+        if(misc->watchdog<0 || misc->watchdog>1) {
+            LOGE("___ check misc, watchdog is invalid, correct value is 0/1\n");
             r = -1; 
         }
 
-        if(webcfg->netsw!=0  && webcfg->netsw!=1) {
-            LOGE("___ check webcfg, netsw is invalid, correct value is 0/1\n");
+        if(misc->flip_time<=0) {
+            LOGE("___ check misc, flip_time is invalid, must greater than 0\n");
             r = -1; 
         }
 
-        if(webcfg->nwire!=0  && webcfg->nwire!=1) {
-            LOGE("___ check webcfg, nwire is invalid, correct value is 0/1\n");
+        if(misc->led<0 || misc->led>1) {
+            LOGE("___ check misc, led is invalid, correct value is 0/1\n");
             r = -1; 
         }
 
-        if(webcfg->ipv4!=0  && webcfg->ipv4!=1) {
-            LOGE("___ check webcfg, ipv4_use is invalid, correct value is 0/1\n");
+        if(misc->beep<0 || misc->beep>1) {
+            LOGE("___ check misc, beep is invalid, correct value is 0/1\n");
             r = -1; 
         }
 
-        if(webcfg->ipv6!=0  && webcfg->ipv6!=1) {
-            LOGE("___ check webcfg, ipv6_use is invalid, correct value is 0/1\n");
+        if(misc->rotate!=0 && misc->rotate!=90 && misc->rotate!=180 && misc->rotate!=270) {
+            LOGE("___ check misc, rotate is invalid, correct value is 0/90/180/270\n");
             r = -1; 
         }
-        return r;
     }
     else if (op==PARAS_CREATE) {
 
     }
     else if (op==PARAS_WRITE) {
-        r = proc_webcfg(dic, PARAS_CHECK, webcfg);
-        if(r) {
-            return -1;
-        }
-    }
-
-    token = "webcfg:monway";
-    if(op==PARAS_READ) {
-        r = iniparser_getint(dic, token, -1);
-        if(r==-1) {
-            LOGE("___ iniparser_getint %s failed\n", token);
-            return -1;
-        } else {
-            webcfg->monway = r;
-        }
-    }
-    else {
-        sprintf(temp, "%d", webcfg->monway);
-        r = iniparser_set(dic, token, temp);
-        if(r) {
-            LOGE("___ iniparser_set %s failed\n", token);
-            return -1;
-        }
-    }
-
-    token = "webcfg:netsw";
-    if(op==PARAS_READ) {
-        r = iniparser_getint(dic, token, -1);
-        if(r==-1) {
-            LOGE("___ iniparser_getint %s failed\n", token);
-            return -1;
-        } else {
-            webcfg->netsw = r;
-        }
-    }
-    else {
-        sprintf(temp, "%d", webcfg->netsw);
-        r = iniparser_set(dic, token, temp);
+        r = proc_misc(dic, PARAS_CHECK, misc);
         if(r) {
-            LOGE("___ iniparser_set %s failed\n", token);
             return -1;
         }
     }
 
-    token = "webcfg:nwire";
+    token = "misc:watchdog";
     if(op==PARAS_READ) {
         r = iniparser_getint(dic, token, -1);
         if(r==-1) {
             LOGE("___ iniparser_getint %s failed\n", token);
             return -1;
         } else {
-            webcfg->nwire = r;
+            misc->watchdog = r;
         }
     }
     else {
-        sprintf(temp, "%d", webcfg->nwire);
+        sprintf(temp, "%d", misc->watchdog);
         r = iniparser_set(dic, token, temp);
         if(r) {
             LOGE("___ iniparser_set %s failed\n", token);
@@ -771,18 +612,18 @@ static int proc_webcfg(dictionary *dic, int op, WebcfgInfo_t *webcfg)
         }
     }
 
-    token = "webcfg:ipv4";
+    token = "misc:fliptime";
     if(op==PARAS_READ) {
         r = iniparser_getint(dic, token, -1);
         if(r==-1) {
             LOGE("___ iniparser_getint %s failed\n", token);
             return -1;
         } else {
-            webcfg->ipv4 = r;
+            misc->flip_time = r;
         }
     }
     else {
-        sprintf(temp, "%d", webcfg->ipv4);
+        sprintf(temp, "%d", misc->flip_time);
         r = iniparser_set(dic, token, temp);
         if(r) {
             LOGE("___ iniparser_set %s failed\n", token);
@@ -790,18 +631,18 @@ static int proc_webcfg(dictionary *dic, int op, WebcfgInfo_t *webcfg)
         }
     }
 
-    token = "webcfg:ipv6";
+    token = "misc:led";
     if(op==PARAS_READ) {
         r = iniparser_getint(dic, token, -1);
         if(r==-1) {
             LOGE("___ iniparser_getint %s failed\n", token);
             return -1;
         } else {
-            webcfg->ipv6 = r;
+            misc->led = r;
         }
     }
     else {
-        sprintf(temp, "%d", webcfg->ipv6);
+        sprintf(temp, "%d", misc->led);
         r = iniparser_set(dic, token, temp);
         if(r) {
             LOGE("___ iniparser_set %s failed\n", token);
@@ -809,52 +650,18 @@ static int proc_webcfg(dictionary *dic, int op, WebcfgInfo_t *webcfg)
         }
     }
 
-    r = 0;
-    if(op==PARAS_READ) {
-        r = proc_webcfg(dic, PARAS_CHECK, webcfg);
-    }
-
-    return r;
-}
-static int proc_misc(dictionary *dic, int op, MiscInfo_t *misc)
-{
-    int r=0;
-    char temp[100];
-    char *p,*token=NULL;
-
-    if(op==PARAS_CHECK) {
-        if(misc->watchdog<0 || misc->watchdog>1) {
-            LOGE("___ check misc, watchdog is invalid, correct value is 0/1\n");
-            r = -1; 
-        }
-
-        if(misc->flip_time<=0) {
-            LOGE("___ check misc, flip_time is invalid, must greater than 0\n");
-            r = -1; 
-        }
-    }
-    else if (op==PARAS_CREATE) {
-
-    }
-    else if (op==PARAS_WRITE) {
-        r = proc_misc(dic, PARAS_CHECK, misc);
-        if(r) {
-            return -1;
-        }
-    }
-
-    token = "misc:watchdog";
+    token = "misc:beep";
     if(op==PARAS_READ) {
         r = iniparser_getint(dic, token, -1);
         if(r==-1) {
             LOGE("___ iniparser_getint %s failed\n", token);
             return -1;
         } else {
-            misc->watchdog = r;
+            misc->beep = r;
         }
     }
     else {
-        sprintf(temp, "%d", misc->watchdog);
+        sprintf(temp, "%d", misc->beep);
         r = iniparser_set(dic, token, temp);
         if(r) {
             LOGE("___ iniparser_set %s failed\n", token);
@@ -862,18 +669,18 @@ static int proc_misc(dictionary *dic, int op, MiscInfo_t *misc)
         }
     }
 
-    token = "misc:fliptime";
+    token = "misc:rotate";
     if(op==PARAS_READ) {
         r = iniparser_getint(dic, token, -1);
         if(r==-1) {
             LOGE("___ iniparser_getint %s failed\n", token);
             return -1;
         } else {
-            misc->flip_time = r;
+            misc->rotate = r;
         }
     }
     else {
-        sprintf(temp, "%d", misc->flip_time);
+        sprintf(temp, "%d", misc->rotate);
         r = iniparser_set(dic, token, temp);
         if(r) {
             LOGE("___ iniparser_set %s failed\n", token);
@@ -889,7 +696,7 @@ static int proc_misc(dictionary *dic, int op, MiscInfo_t *misc)
     return r;
 }
 
-
+#if 0
 static int proc_ntp(char *path, int op, NTPManager *ntp)
 {
     int r=0;
@@ -3205,8 +3012,7 @@ quit:
     return r;
 }
 #endif
-/////////////////////////////////////////////////////////////////////////////////
-
+/////////////////////////////////////////////////////////////////
 static dictionary* ini_load(char *path, paras_data_t *info)
 {
     int r=-1;
@@ -3226,12 +3032,10 @@ static dictionary* ini_load(char *path, paras_data_t *info)
         LOGE("___proc_modbus failed\n");
     }
 
-#if 0
     r = proc_misc(dic, PARAS_READ, &info->misc);
     if(r) {
         LOGE("___proc_misc failed\n");
     }
-#endif
     
     return dic;
 }
@@ -3432,7 +3236,6 @@ static int get_prod(paras_data_t *info)
 }
 
 
-
 int paras_init(void)
 {
     int r=0;
@@ -3466,6 +3269,13 @@ int paras_deinit(void)
 }
 
 
+paras_data_t* paras_get(void)
+{
+    paras_handle_t *h=&paraHandle;
+    return &h->paras;
+}
+
+
 int paras_check(char *path)
 {
     int r=0;

+ 4 - 0
f407/applications/paras.h

@@ -1,6 +1,8 @@
 #ifndef __PARAS_Hx__
 #define __PARAS_Hx__
 
+#include "datadef.h"
+
 enum {
     PARAS_IMPORT=0,
     PARAS_EXPORT,
@@ -26,6 +28,8 @@ enum {
 int paras_init(void);
 int paras_deinit(void);
 
+paras_data_t* paras_get(void);
+
 int paras_check(char *path);
 int paras_load(char *path);
 int paras_reset(void);

+ 17 - 22
f407/applications/power.c

@@ -13,7 +13,9 @@ typedef struct {
 typedef struct {
     void*           mb;
     
-    power_all_t     pall;
+    power_total_t   pttl;
+    board_all_t     ball;
+    
     lock_t          lck;
 }power_handle_t;
 static power_handle_t pwrHandle={0};
@@ -61,7 +63,8 @@ static int power_scan(power_handle_t *h, int max_addr)
 {
     int r,i,j,idx=0,chs=0;
     ch_info_t info;
-    
+
+#if 0    
     lock_d_hold(h->lck);
     for(i=1; i<=max_addr; i++) {
         r = get_info(h, i, &info);
@@ -102,14 +105,14 @@ static int power_scan(power_handle_t *h, int max_addr)
             } 
         }
     }
-    
+#endif
     
     lock_d_release(h->lck);
     
     return 0;
 }
 
-static int get_brd(power_handle_t *h, uint8_t addr, power_brd_t *pbrd)
+static int get_brd(power_handle_t *h, uint8_t addr, board_data_t *pbrd)
 {
     int r,i,j;
     uint32_t val;
@@ -133,22 +136,22 @@ static int get_brd(power_handle_t *h, uint8_t addr, power_brd_t *pbrd)
                     int idx = i * 12;
                     // 解电压数据
                     val = (tmp[1 + idx] << 16) | tmp[0 + idx];
-                    pbrd->pch[i].pele[0].voltage = val / 1000.0;
+                    pbrd->pch[i].power[0].voltage = val / 1000.0;
                     // 解电流数据
                     val = (tmp[3 + idx] << 16) | tmp[2 + idx];
-                    pbrd->pch[i].pele[0].current = val / 1000.0;
+                    pbrd->pch[i].power[0].current = val / 1000.0;
                     // 解功率数据
                     val = (tmp[5 + idx] << 16) | tmp[4 + idx];
-                    pbrd->pch[i].pele[0].power = val / 1000.0;
+                    pbrd->pch[i].power[0].power = val / 1000.0;
                     // 解频率数据
                     val = (tmp[7 + idx] << 16) | tmp[6 + idx];
-                    pbrd->pch[i].pele[0].freq = val / 1000.0;
+                    pbrd->pch[i].power[0].freq = val / 1000.0;
                     // 解耗电量数据
                     val = (tmp[9 + idx] << 16) | tmp[8 + idx];
-                    pbrd->pch[i].pele[0].consump = val / 1000.0;
+                    pbrd->pch[i].power[0].consump = val / 1000.0;
                     // 解功率因素数据
                     val = (tmp[11 + idx] << 16) | tmp[10 + idx];
-                    pbrd->pch[i].pele[0].factor = val / 1000.0;
+                    pbrd->pch[i].power[0].factor = val / 1000.0;
                 }
             }
             
@@ -269,7 +272,8 @@ int power_clear(void)
 {
     int i,j;
     power_handle_t *h=&pwrHandle;
-    
+
+#if 0    
     lock_d_hold(h->lck);
     for(i=0; i<BRD_MAX; i++) {
         if(h->pall.pbrd[i]) {
@@ -286,12 +290,13 @@ int power_clear(void)
         h->pall.cnt = 0;
     }
     lock_d_release(h->lck);
+#endif
     
     return 0;
 }
 
 
-int power_rw_threshold(int rw, threshold_t *thr)
+int power_rw_threshold(int rw, thrd_t *thr)
 {
     int r;
     power_handle_t *h=&pwrHandle;
@@ -320,16 +325,6 @@ int power_reset_consum(int addr)
 }
 
 
-int power_get_alarm(int addr, int ch, alarm_data_t *alarm)
-{
-    int r;
-    power_handle_t *h=&pwrHandle;
-    
-    
-    return 0;
-}
-
-
 int power_set_ch_switch(int addr, int ch, int on)
 {
     int r;

+ 0 - 4
f407/applications/sys.c

@@ -52,9 +52,6 @@ int sys_get_chip_id(int *id)
 }
 
 
-
-
-
 static void* poll_thread(void *arg)
 {
     thread_handle_t *h=(thread_handle_t*)arg;
@@ -62,7 +59,6 @@ static void* poll_thread(void *arg)
     //wdog_init();
     //tmp_create();
     while(h->quit==0) {
-        
         sleep(1);
     }
     pthread_exit(NULL);

+ 154 - 0
f407/applications/ui/beep.c

@@ -0,0 +1,154 @@
+#include "gpio.h"
+#include "timer.h"
+#include "rtdbg.h"
+#include "beep.h"
+#include "paras.h"
+#include <stdio.h>
+#include <sys/time.h>
+
+
+#if 1
+    #define LOGD  LOG_D
+    #define LOGE  LOG_E
+#else
+    #define LOGD  printf
+    #define LOGE  printf
+#endif
+
+
+#define BEEP_GPIO               103     //PD7=96+7
+#define BEEP_ON_LEVEL           1
+#define BEEP_OFF_LEVEL          0
+
+
+static beep_para_t beep_para[BEEP_MODE_MAX]={
+#if 0
+    {1000, 1000, 5},        //BEEP_MODE_WARN1
+    {1000, 1000, 5},        //BEEP_MODE_WARN1
+    {500,  500,  10},       //BEEP_MODE_ERROR
+    {200,  200,  25},       //BEEP_MODE_FAULT
+    {50,   50,   -1},       //BEEP_MODE_FATAL
+#else
+    {500, 500,   300},      //BEEP_MODE_WARN1
+    {333, 333,   450},      //BEEP_MODE_WARN2
+    {500,  500,  10},       //BEEP_MODE_ERROR
+    {200,  200,  25},       //BEEP_MODE_FAULT
+    {50,   50,   -1},       //BEEP_MODE_FATAL
+#endif
+};
+typedef struct {
+    int             tmr;
+    uint32_t        cnt;
+    beep_para_t     para;
+    int             mode;
+    int             stop_level;
+}beep_handle_t;
+static beep_handle_t bpHandle={0};
+
+
+static void beep_handler(void *arg, int last)
+{
+    beep_handle_t *h=(beep_handle_t*)arg;
+    
+    if(h->para.on_ms>0 && h->para.off_ms>0) {
+        h->cnt++;
+        if(h->cnt%2) {
+            gpio_set(BEEP_GPIO, BEEP_OFF_LEVEL);
+        }
+        else {
+            gpio_set(BEEP_GPIO, BEEP_ON_LEVEL);
+        }
+    }
+    
+    if(last) {
+        timer_stop(h->tmr);
+        gpio_set(BEEP_GPIO, BEEP_OFF_LEVEL);
+    }
+}
+/////////////////////////////////////////////
+
+
+int beep_init(void)
+{
+    beep_handle_t *h=&bpHandle;
+    
+    gpio_init(BEEP_GPIO, GPIO_OUT, BEEP_OFF_LEVEL);
+    h->tmr = timer_init();
+    h->mode = -1;
+
+    //beep_set(BEEP_MODE_FATAL);
+    return 0;
+}
+
+
+int beep_deinit(void)
+{
+    beep_handle_t *h=&bpHandle;
+    
+    gpio_deinit(BEEP_GPIO);
+    timer_deinit(h->tmr);
+    h->tmr = -1;
+    
+    return 0;
+}
+
+
+int beep_set(int mode)
+{
+    beep_handle_t *h=&bpHandle;
+    
+    h->mode = mode;
+    return beep_set_ex(&beep_para[h->mode]);
+}
+
+
+int beep_set_ex(beep_para_t *para)
+{
+    int r = 0;
+    beep_handle_t *h=&bpHandle;
+    misc_data_t *misc=&paras_get()->misc;
+
+    if(!misc->beep || !para || (para->on_ms<=0 && para->off_ms<=0) || para->times==0) {
+        return -1;
+    }
+    
+    h->cnt = 0;
+    h->para = *para;
+    if(h->para.on_ms>0) {
+        gpio_set(BEEP_GPIO, BEEP_ON_LEVEL);
+        if(h->para.off_ms>0) {
+            h->para.times *= 2;
+        }
+        else {
+            h->para.on_ms *= h->para.times;
+            h->para.times = 1;
+        }
+        r = timer_start(h->tmr, h->para.on_ms, h->para.times, beep_handler, h);
+    }
+    else {
+        gpio_set(BEEP_GPIO, BEEP_OFF_LEVEL);
+        if(h->para.off_ms>0) {
+            h->para.off_ms *= h->para.times;
+            h->para.times = 1;
+            r = timer_start(h->tmr, h->para.off_ms, h->para.times, beep_handler, h);
+        }
+    }
+    
+    return r;
+}
+
+
+int beep_reset(void)
+{
+    beep_handle_t *h=&bpHandle;
+
+    if(h->mode==-1) {
+        return -1;
+    }
+
+    h->mode = -1;
+    timer_stop(h->tmr);
+    gpio_set(BEEP_GPIO, BEEP_OFF_LEVEL);
+    return 0;
+}
+

+ 25 - 0
f407/applications/ui/beep.h

@@ -0,0 +1,25 @@
+#ifndef __BEEP_Hx__
+#define __BEEP_Hx__
+
+enum {
+    BEEP_MODE_WARN1=0,
+    BEEP_MODE_WARN2,
+    BEEP_MODE_ERROR,
+    BEEP_MODE_FAULT,
+    BEEP_MODE_FATAL,
+    
+    BEEP_MODE_MAX,
+};
+
+typedef struct {
+    int on_ms;
+    int off_ms;
+    int times;
+}beep_para_t;
+
+int beep_init(void);
+int beep_deinit(void);
+int beep_set(int mode);
+int beep_set_ex(beep_para_t *para);
+int beep_reset(void);
+#endif

+ 723 - 0
f407/applications/ui/font.c

@@ -0,0 +1,723 @@
+#include <string.h>
+#include "font.h"
+
+//Arial Helvetica  Verdana
+
+static const uint8_t font_en_0806[95][6] =
+{
+{0x00,0x00,0x00,0x00,0x00,0x00},/*" ",0*/
+{0x00,0x00,0x00,0x2f,0x00,0x00},/*"!",1*/
+{0x00,0x00,0x07,0x00,0x07,0x00},/*""",2*/
+{0x00,0x14,0x7f,0x14,0x7f,0x14},/*"#",3*/
+{0x00,0x24,0x2a,0x7f,0x2a,0x12},/*"$",4*/
+{0x00,0x62,0x64,0x08,0x13,0x23},/*"%",5*/
+{0x00,0x36,0x49,0x55,0x22,0x50},/*"&",6*/
+{0x00,0x00,0x05,0x03,0x00,0x00},/*"'",7*/
+{0x00,0x00,0x1c,0x22,0x41,0x00},/*"(",8*/
+{0x00,0x00,0x41,0x22,0x1c,0x00},/*")",9*/
+{0x00,0x14,0x08,0x3E,0x08,0x14},/*"*",10*/
+{0x00,0x08,0x08,0x3E,0x08,0x08},/*"+",11*/
+{0x00,0x00,0x00,0xA0,0x60,0x00},/*",",12*/
+{0x00,0x08,0x08,0x08,0x08,0x08},/*"-",13*/
+{0x00,0x00,0x60,0x60,0x00,0x00},/*".",14*/
+{0x00,0x20,0x10,0x08,0x04,0x02},/*"/",15*/
+{0x00,0x3E,0x51,0x49,0x45,0x3E},/*"0",16*/
+{0x00,0x00,0x42,0x7F,0x40,0x00},/*"1",17*/
+{0x00,0x42,0x61,0x51,0x49,0x46},/*"2",18*/
+{0x00,0x21,0x41,0x45,0x4B,0x31},/*"3",19*/
+{0x00,0x18,0x14,0x12,0x7F,0x10},/*"4",20*/
+{0x00,0x27,0x45,0x45,0x45,0x39},/*"5",21*/
+{0x00,0x3C,0x4A,0x49,0x49,0x30},/*"6",22*/
+{0x00,0x01,0x71,0x09,0x05,0x03},/*"7",23*/
+{0x00,0x36,0x49,0x49,0x49,0x36},/*"8",24*/
+{0x00,0x06,0x49,0x49,0x29,0x1E},/*"9",25*/
+{0x00,0x28,0x28,0x00,0x00,0x00},/*":",26*/
+{0x00,0x48,0x28,0x00,0x00,0x00},/*";",27*/
+{0x00,0x08,0x14,0x22,0x41,0x00},/*"<",28*/
+{0x00,0x14,0x14,0x14,0x14,0x14},/*"=",29*/
+{0x00,0x00,0x41,0x22,0x14,0x08},/*">",30*/
+{0x00,0x02,0x01,0x51,0x09,0x06},/*"?",31*/
+{0x00,0x32,0x49,0x59,0x51,0x3E},/*"@",32*/
+{0x00,0x7C,0x12,0x11,0x12,0x7C},/*"A",33*/
+{0x00,0x7F,0x49,0x49,0x49,0x36},/*"B",34*/
+{0x00,0x3E,0x41,0x41,0x41,0x22},/*"C",35*/
+{0x00,0x7F,0x41,0x41,0x22,0x1C},/*"D",36*/
+{0x00,0x7F,0x49,0x49,0x49,0x41},/*"E",37*/
+{0x00,0x7F,0x09,0x09,0x09,0x01},/*"F",38*/
+{0x00,0x3E,0x41,0x49,0x49,0x7A},/*"G",39*/
+{0x00,0x7F,0x08,0x08,0x08,0x7F},/*"H",40*/
+{0x00,0x00,0x41,0x7F,0x41,0x00},/*"I",41*/
+{0x00,0x20,0x40,0x41,0x3F,0x01},/*"J",42*/
+{0x00,0x7F,0x08,0x14,0x22,0x41},/*"K",43*/
+{0x00,0x7F,0x40,0x40,0x40,0x40},/*"L",44*/
+{0x00,0x7F,0x02,0x0C,0x02,0x7F},/*"M",45*/
+{0x00,0x7F,0x04,0x08,0x10,0x7F},/*"N",46*/
+{0x00,0x3E,0x41,0x41,0x41,0x3E},/*"O",47*/
+{0x00,0x7F,0x09,0x09,0x09,0x06},/*"P",48*/
+{0x00,0x3E,0x41,0x51,0x21,0x5E},/*"Q",49*/
+{0x00,0x7F,0x09,0x19,0x29,0x46},/*"R",50*/
+{0x00,0x46,0x49,0x49,0x49,0x31},/*"S",51*/
+{0x00,0x01,0x01,0x7F,0x01,0x01},/*"T",52*/
+{0x00,0x3F,0x40,0x40,0x40,0x3F},/*"U",53*/
+{0x00,0x1F,0x20,0x40,0x20,0x1F},/*"V",54*/
+{0x00,0x3F,0x40,0x38,0x40,0x3F},/*"W",55*/
+{0x00,0x63,0x14,0x08,0x14,0x63},/*"X",56*/
+{0x00,0x07,0x08,0x70,0x08,0x07},/*"Y",57*/
+{0x00,0x61,0x51,0x49,0x45,0x43},/*"Z",58*/
+{0x00,0x00,0x7F,0x41,0x41,0x00},/*"[",59*/
+{0x00,0x55,0x2A,0x55,0x2A,0x55},/*"\",60*/
+{0x00,0x00,0x41,0x41,0x7F,0x00},/*"]",61*/
+{0x00,0x04,0x02,0x01,0x02,0x04},/*"^",62*/
+{0x00,0x40,0x40,0x40,0x40,0x40},/*"_",63*/
+{0x00,0x00,0x01,0x02,0x04,0x00},/*"`",64*/
+{0x00,0x20,0x54,0x54,0x54,0x78},/*"a",65*/
+{0x00,0x7F,0x48,0x44,0x44,0x38},/*"b",66*/
+{0x00,0x38,0x44,0x44,0x44,0x20},/*"c",67*/
+{0x00,0x38,0x44,0x44,0x48,0x7F},/*"d",68*/
+{0x00,0x38,0x54,0x54,0x54,0x18},/*"e",69*/
+{0x00,0x08,0x7E,0x09,0x01,0x02},/*"f",70*/
+{0x00,0x18,0xA4,0xA4,0xA4,0x7C},/*"g",71*/
+{0x00,0x7F,0x08,0x04,0x04,0x78},/*"h",72*/
+{0x00,0x00,0x44,0x7D,0x40,0x00},/*"i",73*/
+{0x00,0x40,0x80,0x84,0x7D,0x00},/*"j",74*/
+{0x00,0x7F,0x10,0x28,0x44,0x00},/*"k",75*/
+{0x00,0x00,0x41,0x7F,0x40,0x00},/*"l",76*/
+{0x00,0x7C,0x04,0x18,0x04,0x78},/*"m",77*/
+{0x00,0x7C,0x08,0x04,0x04,0x78},/*"n",78*/
+{0x00,0x38,0x44,0x44,0x44,0x38},/*"o",79*/
+{0x00,0xFC,0x24,0x24,0x24,0x18},/*"p",80*/
+{0x00,0x18,0x24,0x24,0x18,0xFC},/*"q",81*/
+{0x00,0x7C,0x08,0x04,0x04,0x08},/*"r",82*/
+{0x00,0x48,0x54,0x54,0x54,0x20},/*"s",83*/
+{0x00,0x04,0x3F,0x44,0x40,0x20},/*"t",84*/
+{0x00,0x3C,0x40,0x40,0x20,0x7C},/*"u",85*/
+{0x00,0x1C,0x20,0x40,0x20,0x1C},/*"v",86*/
+{0x00,0x3C,0x40,0x30,0x40,0x3C},/*"w",87*/
+{0x00,0x44,0x28,0x10,0x28,0x44},/*"x",88*/
+{0x00,0x1C,0xA0,0xA0,0xA0,0x7C},/*"y",89*/
+{0x00,0x44,0x64,0x54,0x4C,0x44},/*"z",90*/
+{0x10,0xEE,0x82,0x82,0x00,0x00},/*"{",91*/
+{0x00,0xFE,0x00,0x00,0x00,0x00},/*"|",92*/
+{0x82,0x82,0xEE,0x10,0x00,0x00},/*"}",93*/
+{0x10,0x08,0x08,0x10,0x18,0x00},/*"~",94*/
+};
+static const uint8_t font_en_1206[95][12] =
+{
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*" ",0*/
+{0x00,0x00,0x00,0x00,0x7C,0x02,0x00,0x00,0x00,0x00,0x00,0x00},/*"!",1*/
+{0x00,0x00,0x04,0x00,0x03,0x00,0x04,0x00,0x03,0x00,0x00,0x00},/*""",2*/
+{0x90,0x00,0xFC,0x03,0x90,0x00,0xFC,0x03,0x90,0x00,0x00,0x00},/*"#",3*/
+{0x18,0x01,0x24,0x02,0xFE,0x07,0x44,0x02,0x88,0x01,0x00,0x00},/*"$",4*/
+{0x38,0x00,0x44,0x03,0xF8,0x00,0xD0,0x01,0x2C,0x02,0xC0,0x01},/*"%",5*/
+{0xC0,0x01,0x38,0x02,0xE4,0x02,0x18,0x01,0xE0,0x02,0x20,0x01},/*"&",6*/
+{0x04,0x00,0x03,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"'",7*/
+{0x00,0x00,0x00,0x00,0xF8,0x00,0x06,0x03,0x01,0x04,0x00,0x00},/*"(",8*/
+{0x00,0x00,0x01,0x04,0x06,0x03,0xF8,0x00,0x00,0x00,0x00,0x00},/*")",9*/
+{0x90,0x00,0x60,0x00,0xF8,0x01,0x60,0x00,0x90,0x00,0x00,0x00},/*"*",10*/
+{0x00,0x00,0x20,0x00,0x20,0x00,0xF8,0x00,0x20,0x00,0x20,0x00},/*"+",11*/
+{0x00,0x04,0x00,0x03,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*",",12*/
+{0x20,0x00,0x20,0x00,0x20,0x00,0x20,0x00,0x20,0x00,0x20,0x00},/*"-",13*/
+{0x00,0x00,0x00,0x02,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*".",14*/
+{0x00,0x04,0x00,0x03,0xC0,0x00,0x30,0x00,0x0C,0x00,0x02,0x00},/*"/",15*/
+{0xF8,0x01,0x04,0x02,0x04,0x02,0x04,0x02,0xF8,0x01,0x00,0x00},/*"0",16*/
+{0x00,0x00,0x08,0x02,0xFC,0x03,0x00,0x02,0x00,0x00,0x00,0x00},/*"1",17*/
+{0x18,0x03,0x84,0x02,0x44,0x02,0x24,0x02,0x18,0x02,0x00,0x00},/*"2",18*/
+{0x08,0x01,0x04,0x02,0x24,0x02,0x24,0x02,0xD8,0x01,0x00,0x00},/*"3",19*/
+{0xC0,0x00,0xA0,0x00,0x98,0x02,0xFC,0x03,0x80,0x02,0x00,0x00},/*"4",20*/
+{0x7C,0x01,0x24,0x02,0x24,0x02,0x24,0x02,0xC4,0x01,0x00,0x00},/*"5",21*/
+{0xF0,0x01,0x48,0x02,0x24,0x02,0x24,0x02,0xC8,0x01,0x00,0x00},/*"6",22*/
+{0x00,0x00,0x04,0x00,0xC4,0x03,0x34,0x00,0x0C,0x00,0x00,0x00},/*"7",23*/
+{0xD8,0x01,0x24,0x02,0x24,0x02,0x24,0x02,0xD8,0x01,0x00,0x00},/*"8",24*/
+{0x38,0x01,0x44,0x02,0x44,0x02,0x24,0x01,0xF8,0x00,0x00,0x00},/*"9",25*/
+{0x00,0x00,0x00,0x00,0x10,0x02,0x00,0x00,0x00,0x00,0x00,0x00},/*":",26*/
+{0x00,0x00,0x00,0x00,0x20,0x06,0x00,0x00,0x00,0x00,0x00,0x00},/*";",27*/
+{0x00,0x00,0x60,0x00,0x90,0x00,0x08,0x01,0x04,0x02,0x00,0x00},/*"<",28*/
+{0x50,0x00,0x50,0x00,0x50,0x00,0x50,0x00,0x50,0x00,0x50,0x00},/*"=",29*/
+{0x00,0x00,0x04,0x02,0x08,0x01,0x90,0x00,0x60,0x00,0x00,0x00},/*">",30*/
+{0x18,0x00,0x04,0x00,0xC4,0x02,0x24,0x00,0x18,0x00,0x00,0x00},/*"?",31*/
+{0xF0,0x00,0x08,0x01,0xE4,0x02,0xF4,0x02,0x84,0x02,0x78,0x01},/*"@",32*/
+{0x00,0x02,0xE0,0x03,0x9C,0x00,0xF0,0x00,0x80,0x03,0x00,0x02},/*"A",33*/
+{0x04,0x02,0xFC,0x03,0x24,0x02,0x24,0x02,0xD8,0x01,0x00,0x00},/*"B",34*/
+{0xF8,0x01,0x04,0x02,0x04,0x02,0x04,0x02,0x0C,0x01,0x00,0x00},/*"C",35*/
+{0x04,0x02,0xFC,0x03,0x04,0x02,0x04,0x02,0xF8,0x01,0x00,0x00},/*"D",36*/
+{0x04,0x02,0xFC,0x03,0x24,0x02,0x74,0x02,0x0C,0x03,0x00,0x00},/*"E",37*/
+{0x04,0x02,0xFC,0x03,0x24,0x02,0x74,0x00,0x0C,0x00,0x00,0x00},/*"F",38*/
+{0xF0,0x00,0x08,0x01,0x04,0x02,0x44,0x02,0xCC,0x01,0x40,0x00},/*"G",39*/
+{0x04,0x02,0xFC,0x03,0x20,0x00,0x20,0x00,0xFC,0x03,0x04,0x02},/*"H",40*/
+{0x04,0x02,0x04,0x02,0xFC,0x03,0x04,0x02,0x04,0x02,0x00,0x00},/*"I",41*/
+{0x00,0x0C,0x04,0x08,0x04,0x08,0xFC,0x07,0x04,0x00,0x04,0x00},/*"J",42*/
+{0x04,0x02,0xFC,0x03,0x24,0x02,0x50,0x00,0x8C,0x03,0x04,0x02},/*"K",43*/
+{0x04,0x02,0xFC,0x03,0x04,0x02,0x00,0x02,0x00,0x02,0x00,0x03},/*"L",44*/
+{0xFC,0x03,0x3C,0x00,0xC0,0x03,0x3C,0x00,0xFC,0x03,0x04,0x02},/*"M",45*/
+{0x04,0x02,0xFC,0x03,0x30,0x02,0xC4,0x00,0xFC,0x03,0x04,0x00},/*"N",46*/
+{0xF8,0x01,0x04,0x02,0x04,0x02,0x04,0x02,0xF8,0x01,0x00,0x00},/*"O",47*/
+{0x04,0x02,0xFC,0x03,0x24,0x02,0x24,0x00,0x18,0x00,0x00,0x00},/*"P",48*/
+{0xF8,0x01,0x84,0x02,0x84,0x02,0x04,0x07,0xF8,0x05,0x00,0x00},/*"Q",49*/
+{0x04,0x02,0xFC,0x03,0x24,0x02,0x64,0x00,0x98,0x03,0x00,0x02},/*"R",50*/
+{0x18,0x03,0x24,0x02,0x24,0x02,0x44,0x02,0x8C,0x01,0x00,0x00},/*"S",51*/
+{0x0C,0x00,0x04,0x02,0xFC,0x03,0x04,0x02,0x0C,0x00,0x00,0x00},/*"T",52*/
+{0x04,0x00,0xFC,0x01,0x00,0x02,0x00,0x02,0xFC,0x01,0x04,0x00},/*"U",53*/
+{0x04,0x00,0x7C,0x00,0x80,0x03,0xE0,0x00,0x1C,0x00,0x04,0x00},/*"V",54*/
+{0x3C,0x00,0xC0,0x03,0x7C,0x00,0xC0,0x03,0x3C,0x00,0x00,0x00},/*"W",55*/
+{0x04,0x02,0x9C,0x03,0x60,0x00,0x9C,0x03,0x04,0x02,0x00,0x00},/*"X",56*/
+{0x04,0x00,0x3C,0x02,0xC0,0x03,0x3C,0x02,0x04,0x00,0x00,0x00},/*"Y",57*/
+{0x0C,0x02,0x84,0x03,0x64,0x02,0x1C,0x02,0x04,0x03,0x00,0x00},/*"Z",58*/
+{0x00,0x00,0x00,0x00,0xFF,0x07,0x01,0x04,0x01,0x04,0x00,0x00},/*"[",59*/
+{0x00,0x00,0x06,0x00,0x38,0x00,0xC0,0x01,0x00,0x06,0x00,0x00},/*"\",60*/
+{0x00,0x00,0x01,0x04,0x01,0x04,0xFF,0x07,0x00,0x00,0x00,0x00},/*"]",61*/
+{0x00,0x00,0x02,0x00,0x01,0x00,0x02,0x00,0x00,0x00,0x00,0x00},/*"^",62*/
+{0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08},/*"_",63*/
+{0x00,0x00,0x01,0x00,0x02,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"`",64*/
+{0x00,0x00,0x40,0x01,0xA0,0x02,0xA0,0x02,0xC0,0x03,0x00,0x02},/*"a",65*/
+{0x02,0x00,0xFE,0x03,0x20,0x02,0x20,0x02,0xC0,0x01,0x00,0x00},/*"b",66*/
+{0x00,0x00,0xC0,0x01,0x20,0x02,0x20,0x02,0x60,0x01,0x00,0x00},/*"c",67*/
+{0x00,0x00,0xC0,0x01,0x20,0x02,0x22,0x02,0xFE,0x03,0x00,0x02},/*"d",68*/
+{0x00,0x00,0xC0,0x01,0xA0,0x02,0xA0,0x02,0xC0,0x02,0x00,0x00},/*"e",69*/
+{0x00,0x00,0x20,0x02,0xFC,0x03,0x22,0x02,0x22,0x02,0x04,0x00},/*"f",70*/
+{0x00,0x00,0x40,0x05,0xA0,0x0A,0xA0,0x0A,0x60,0x0A,0x20,0x04},/*"g",71*/
+{0x02,0x02,0xFE,0x03,0x20,0x02,0x20,0x00,0xC0,0x03,0x00,0x02},/*"h",72*/
+{0x00,0x00,0x20,0x02,0xE6,0x03,0x00,0x02,0x00,0x00,0x00,0x00},/*"i",73*/
+{0x00,0x08,0x00,0x08,0x20,0x08,0xE6,0x07,0x00,0x00,0x00,0x00},/*"j",74*/
+{0x02,0x02,0xFE,0x03,0x80,0x00,0x60,0x01,0x20,0x02,0x00,0x00},/*"k",75*/
+{0x02,0x02,0x02,0x02,0xFE,0x03,0x00,0x02,0x00,0x02,0x00,0x00},/*"l",76*/
+{0xE0,0x03,0x20,0x00,0xE0,0x03,0x20,0x00,0xC0,0x03,0x00,0x00},/*"m",77*/
+{0x20,0x02,0xE0,0x03,0x20,0x02,0x20,0x00,0xC0,0x03,0x00,0x02},/*"n",78*/
+{0x00,0x00,0xC0,0x01,0x20,0x02,0x20,0x02,0xC0,0x01,0x00,0x00},/*"o",79*/
+{0x20,0x08,0xE0,0x0F,0x20,0x0A,0x20,0x02,0xC0,0x01,0x00,0x00},/*"p",80*/
+{0x00,0x00,0xC0,0x01,0x20,0x02,0x20,0x0A,0xE0,0x0F,0x00,0x08},/*"q",81*/
+{0x20,0x02,0xE0,0x03,0x40,0x02,0x20,0x00,0x20,0x00,0x00,0x00},/*"r",82*/
+{0x00,0x00,0x60,0x02,0xA0,0x02,0xA0,0x02,0x20,0x03,0x00,0x00},/*"s",83*/
+{0x00,0x00,0x20,0x00,0xF8,0x03,0x20,0x02,0x20,0x02,0x00,0x00},/*"t",84*/
+{0x20,0x00,0xE0,0x01,0x00,0x02,0x20,0x02,0xE0,0x03,0x00,0x02},/*"u",85*/
+{0x20,0x00,0xE0,0x00,0x00,0x03,0xE0,0x00,0x20,0x00,0x00,0x00},/*"v",86*/
+{0x60,0x00,0x80,0x03,0xE0,0x00,0x80,0x03,0x60,0x00,0x00,0x00},/*"w",87*/
+{0x20,0x02,0x60,0x03,0x80,0x00,0x60,0x03,0x20,0x02,0x00,0x00},/*"x",88*/
+{0x20,0x08,0xE0,0x08,0x00,0x05,0x00,0x03,0xE0,0x00,0x20,0x00},/*"y",89*/
+{0x00,0x00,0x20,0x02,0xA0,0x03,0x60,0x02,0x20,0x02,0x00,0x00},/*"z",90*/
+{0x00,0x00,0x00,0x00,0x20,0x00,0xFF,0x07,0x01,0x04,0x00,0x00},/*"{",91*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0xFF,0x0F,0x00,0x00,0x00,0x00},/*"|",92*/
+{0x00,0x00,0x01,0x04,0xDF,0x07,0x20,0x00,0x00,0x00,0x00,0x00},/*"}",93*/
+{0x02,0x00,0x01,0x00,0x01,0x00,0x02,0x00,0x01,0x00,0x00,0x00},/*"~",94*/
+};
+static const uint8_t font_en_1608[95][16] =
+{      
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*" ",0*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0xF8,0x33,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"!",1*/
+{0x00,0x00,0x10,0x00,0x0C,0x00,0x02,0x00,0x10,0x00,0x0C,0x00,0x02,0x00,0x00,0x00},/*""",2*/
+{0x00,0x00,0x40,0x04,0xC0,0x3F,0x78,0x04,0x40,0x04,0xC0,0x3F,0x78,0x04,0x00,0x00},/*"#",3*/
+{0x00,0x00,0x70,0x18,0x88,0x20,0x88,0x20,0xFC,0xFF,0x08,0x21,0x30,0x1E,0x00,0x00},/*"$",4*/
+{0xF0,0x00,0x08,0x31,0xF0,0x0C,0x80,0x03,0x60,0x1E,0x18,0x21,0x00,0x1E,0x00,0x00},/*"%",5*/
+{0x00,0x1E,0xF0,0x21,0x08,0x23,0x88,0x2C,0x70,0x19,0x00,0x27,0x00,0x21,0x00,0x10},/*"&",6*/
+{0x00,0x00,0x12,0x00,0x0E,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"'",7*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0xE0,0x07,0x18,0x18,0x04,0x20,0x02,0x40,0x00,0x00},/*"(",8*/
+{0x00,0x00,0x02,0x40,0x04,0x20,0x18,0x18,0xE0,0x07,0x00,0x00,0x00,0x00,0x00,0x00},/*")",9*/
+{0x40,0x02,0x40,0x02,0x80,0x01,0xF0,0x0F,0x80,0x01,0x40,0x02,0x40,0x02,0x00,0x00},/*"*",10*/
+{0x00,0x00,0x00,0x01,0x00,0x01,0x00,0x01,0xE0,0x0F,0x00,0x01,0x00,0x01,0x00,0x01},/*"+",11*/
+{0x00,0x00,0x00,0x90,0x00,0x70,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*",",12*/
+{0x00,0x00,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x00},/*"-",13*/
+{0x00,0x00,0x00,0x30,0x00,0x30,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*".",14*/
+{0x00,0x00,0x00,0x60,0x00,0x18,0x00,0x07,0xC0,0x00,0x38,0x00,0x04,0x00,0x00,0x00},/*"/",15*/
+{0x00,0x00,0xE0,0x0F,0x10,0x10,0x08,0x20,0x08,0x20,0x10,0x10,0xE0,0x0F,0x00,0x00},/*"0",16*/
+{0x00,0x00,0x00,0x00,0x10,0x20,0x10,0x20,0xF8,0x3F,0x00,0x20,0x00,0x20,0x00,0x00},/*"1",17*/
+{0x00,0x00,0x70,0x30,0x08,0x28,0x08,0x24,0x08,0x22,0x08,0x21,0xF0,0x30,0x00,0x00},/*"2",18*/
+{0x00,0x00,0x30,0x18,0x08,0x20,0x08,0x21,0x08,0x21,0x88,0x22,0x70,0x1C,0x00,0x00},/*"3",19*/
+{0x00,0x00,0x00,0x06,0x80,0x05,0x40,0x24,0x30,0x24,0xF8,0x3F,0x00,0x24,0x00,0x24},/*"4",20*/
+{0x00,0x00,0xF8,0x19,0x88,0x20,0x88,0x20,0x88,0x20,0x08,0x11,0x08,0x0E,0x00,0x00},/*"5",21*/
+{0x00,0x00,0xE0,0x0F,0x10,0x11,0x88,0x20,0x88,0x20,0x90,0x20,0x00,0x1F,0x00,0x00},/*"6",22*/
+{0x00,0x00,0x18,0x00,0x08,0x00,0x08,0x3E,0x88,0x01,0x68,0x00,0x18,0x00,0x00,0x00},/*"7",23*/
+{0x00,0x00,0x70,0x1C,0x88,0x22,0x08,0x21,0x08,0x21,0x88,0x22,0x70,0x1C,0x00,0x00},/*"8",24*/
+{0x00,0x00,0xF0,0x01,0x08,0x12,0x08,0x22,0x08,0x22,0x10,0x11,0xE0,0x0F,0x00,0x00},/*"9",25*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0xC0,0x30,0xC0,0x30,0x00,0x00,0x00,0x00,0x00,0x00},/*":",26*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x80,0xE0,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*";",27*/
+{0x00,0x00,0x00,0x01,0x80,0x02,0x40,0x04,0x20,0x08,0x10,0x10,0x08,0x20,0x00,0x00},/*"<",28*/
+{0x00,0x00,0x40,0x02,0x40,0x02,0x40,0x02,0x40,0x02,0x40,0x02,0x40,0x02,0x00,0x00},/*"=",29*/
+{0x00,0x00,0x08,0x20,0x10,0x10,0x20,0x08,0x40,0x04,0x80,0x02,0x00,0x01,0x00,0x00},/*">",30*/
+{0x00,0x00,0x70,0x00,0x48,0x00,0x08,0x30,0x08,0x37,0x88,0x00,0x70,0x00,0x00,0x00},/*"?",31*/
+{0xC0,0x07,0x30,0x18,0xC8,0x27,0x28,0x28,0xE8,0x2F,0x10,0x28,0xE0,0x17,0x00,0x00},/*"@",32*/
+{0x00,0x20,0x00,0x3C,0xC0,0x23,0x38,0x02,0xE0,0x02,0x00,0x27,0x00,0x38,0x00,0x20},/*"A",33*/
+{0x08,0x20,0xF8,0x3F,0x88,0x20,0x88,0x20,0x88,0x20,0x70,0x11,0x00,0x0E,0x00,0x00},/*"B",34*/
+{0xC0,0x07,0x30,0x18,0x08,0x20,0x08,0x20,0x08,0x20,0x08,0x10,0x38,0x08,0x00,0x00},/*"C",35*/
+{0x08,0x20,0xF8,0x3F,0x08,0x20,0x08,0x20,0x08,0x20,0x10,0x10,0xE0,0x0F,0x00,0x00},/*"D",36*/
+{0x08,0x20,0xF8,0x3F,0x88,0x20,0x88,0x20,0xE8,0x23,0x08,0x20,0x10,0x18,0x00,0x00},/*"E",37*/
+{0x08,0x20,0xF8,0x3F,0x88,0x20,0x88,0x00,0xE8,0x03,0x08,0x00,0x10,0x00,0x00,0x00},/*"F",38*/
+{0xC0,0x07,0x30,0x18,0x08,0x20,0x08,0x20,0x08,0x22,0x38,0x1E,0x00,0x02,0x00,0x00},/*"G",39*/
+{0x08,0x20,0xF8,0x3F,0x08,0x21,0x00,0x01,0x00,0x01,0x08,0x21,0xF8,0x3F,0x08,0x20},/*"H",40*/
+{0x00,0x00,0x08,0x20,0x08,0x20,0xF8,0x3F,0x08,0x20,0x08,0x20,0x00,0x00,0x00,0x00},/*"I",41*/
+{0x00,0xC0,0x00,0x80,0x08,0x80,0x08,0x80,0xF8,0x7F,0x08,0x00,0x08,0x00,0x00,0x00},/*"J",42*/
+{0x08,0x20,0xF8,0x3F,0x88,0x20,0xC0,0x01,0x28,0x26,0x18,0x38,0x08,0x20,0x00,0x00},/*"K",43*/
+{0x08,0x20,0xF8,0x3F,0x08,0x20,0x00,0x20,0x00,0x20,0x00,0x20,0x00,0x30,0x00,0x00},/*"L",44*/
+{0x08,0x20,0xF8,0x3F,0xF8,0x01,0x00,0x3E,0xF8,0x01,0xF8,0x3F,0x08,0x20,0x00,0x00},/*"M",45*/
+{0x08,0x20,0xF8,0x3F,0x30,0x20,0xC0,0x00,0x00,0x07,0x08,0x18,0xF8,0x3F,0x08,0x00},/*"N",46*/
+{0xE0,0x0F,0x10,0x10,0x08,0x20,0x08,0x20,0x08,0x20,0x10,0x10,0xE0,0x0F,0x00,0x00},/*"O",47*/
+{0x08,0x20,0xF8,0x3F,0x08,0x21,0x08,0x01,0x08,0x01,0x08,0x01,0xF0,0x00,0x00,0x00},/*"P",48*/
+{0xE0,0x0F,0x10,0x10,0x08,0x28,0x08,0x28,0x08,0x30,0x10,0x50,0xE0,0x4F,0x00,0x00},/*"Q",49*/
+{0x08,0x20,0xF8,0x3F,0x88,0x20,0x88,0x00,0x88,0x03,0x88,0x0C,0x70,0x30,0x00,0x20},/*"R",50*/
+{0x00,0x00,0x70,0x38,0x88,0x20,0x08,0x21,0x08,0x21,0x08,0x22,0x38,0x1C,0x00,0x00},/*"S",51*/
+{0x18,0x00,0x08,0x00,0x08,0x20,0xF8,0x3F,0x08,0x20,0x08,0x00,0x18,0x00,0x00,0x00},/*"T",52*/
+{0x08,0x00,0xF8,0x1F,0x08,0x20,0x00,0x20,0x00,0x20,0x08,0x20,0xF8,0x1F,0x08,0x00},/*"U",53*/
+{0x08,0x00,0x78,0x00,0x88,0x07,0x00,0x38,0x00,0x0E,0xC8,0x01,0x38,0x00,0x08,0x00},/*"V",54*/
+{0x08,0x00,0xF8,0x03,0x00,0x3E,0xF8,0x01,0x00,0x3E,0xF8,0x03,0x08,0x00,0x00,0x00},/*"W",55*/
+{0x08,0x20,0x18,0x30,0x68,0x2C,0x80,0x03,0x80,0x03,0x68,0x2C,0x18,0x30,0x08,0x20},/*"X",56*/
+{0x08,0x00,0x38,0x00,0xC8,0x20,0x00,0x3F,0xC8,0x20,0x38,0x00,0x08,0x00,0x00,0x00},/*"Y",57*/
+{0x10,0x20,0x08,0x38,0x08,0x26,0x08,0x21,0xC8,0x20,0x38,0x20,0x08,0x18,0x00,0x00},/*"Z",58*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0xFE,0x7F,0x02,0x40,0x02,0x40,0x02,0x40,0x00,0x00},/*"[",59*/
+{0x00,0x00,0x04,0x00,0x38,0x00,0xC0,0x01,0x00,0x06,0x00,0x38,0x00,0xC0,0x00,0x00},/*"\",60*/
+{0x00,0x00,0x02,0x40,0x02,0x40,0x02,0x40,0xFE,0x7F,0x00,0x00,0x00,0x00,0x00,0x00},/*"]",61*/
+{0x00,0x00,0x00,0x00,0x04,0x00,0x02,0x00,0x02,0x00,0x04,0x00,0x00,0x00,0x00,0x00},/*"^",62*/
+{0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80},/*"_",63*/
+{0x00,0x00,0x02,0x00,0x02,0x00,0x04,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"`",64*/
+{0x00,0x00,0x00,0x19,0x80,0x24,0x80,0x24,0x80,0x12,0x00,0x3F,0x00,0x20,0x00,0x00},/*"a",65*/
+{0x10,0x00,0xF0,0x3F,0x00,0x11,0x80,0x20,0x80,0x20,0x00,0x11,0x00,0x0E,0x00,0x00},/*"b",66*/
+{0x00,0x00,0x00,0x0E,0x00,0x11,0x80,0x20,0x80,0x20,0x80,0x20,0x00,0x11,0x00,0x00},/*"c",67*/
+{0x00,0x00,0x00,0x1F,0x80,0x20,0x80,0x20,0x80,0x20,0x90,0x10,0xF0,0x3F,0x00,0x20},/*"d",68*/
+{0x00,0x00,0x00,0x1F,0x80,0x24,0x80,0x24,0x80,0x24,0x80,0x24,0x00,0x17,0x00,0x00},/*"e",69*/
+{0x00,0x00,0x80,0x20,0x80,0x20,0xE0,0x3F,0x90,0x20,0x90,0x20,0x20,0x00,0x00,0x00},/*"f",70*/
+{0x00,0x00,0x00,0x6B,0x80,0x94,0x80,0x94,0x80,0x94,0x80,0x93,0x80,0x60,0x00,0x00},/*"g",71*/
+{0x10,0x20,0xF0,0x3F,0x00,0x21,0x80,0x00,0x80,0x00,0x80,0x20,0x00,0x3F,0x00,0x20},/*"h",72*/
+{0x00,0x00,0x80,0x20,0x98,0x20,0x98,0x3F,0x00,0x20,0x00,0x20,0x00,0x00,0x00,0x00},/*"i",73*/
+{0x00,0x00,0x00,0xC0,0x00,0x80,0x80,0x80,0x98,0x80,0x98,0x7F,0x00,0x00,0x00,0x00},/*"j",74*/
+{0x10,0x20,0xF0,0x3F,0x00,0x24,0x00,0x06,0x80,0x29,0x80,0x30,0x80,0x20,0x00,0x00},/*"k",75*/
+{0x00,0x00,0x10,0x20,0x10,0x20,0xF8,0x3F,0x00,0x20,0x00,0x20,0x00,0x00,0x00,0x00},/*"l",76*/
+{0x80,0x20,0x80,0x3F,0x80,0x20,0x80,0x00,0x80,0x3F,0x80,0x20,0x80,0x00,0x00,0x3F},/*"m",77*/
+{0x80,0x20,0x80,0x3F,0x00,0x21,0x80,0x00,0x80,0x00,0x80,0x20,0x00,0x3F,0x00,0x20},/*"n",78*/
+{0x00,0x00,0x00,0x1F,0x80,0x20,0x80,0x20,0x80,0x20,0x80,0x20,0x00,0x1F,0x00,0x00},/*"o",79*/
+{0x80,0x80,0x80,0xFF,0x00,0x91,0x80,0x20,0x80,0x20,0x00,0x11,0x00,0x0E,0x00,0x00},/*"p",80*/
+{0x00,0x00,0x00,0x0E,0x00,0x11,0x80,0x20,0x80,0x20,0x00,0x91,0x80,0xFF,0x00,0x80},/*"q",81*/
+{0x80,0x20,0x80,0x20,0x80,0x3F,0x00,0x21,0x80,0x20,0x80,0x00,0x80,0x01,0x00,0x00},/*"r",82*/
+{0x00,0x00,0x00,0x33,0x80,0x24,0x80,0x24,0x80,0x24,0x80,0x24,0x80,0x19,0x00,0x00},/*"s",83*/
+{0x00,0x00,0x80,0x00,0x80,0x00,0xE0,0x1F,0x80,0x20,0x80,0x20,0x00,0x10,0x00,0x00},/*"t",84*/
+{0x80,0x00,0x80,0x1F,0x00,0x20,0x00,0x20,0x00,0x20,0x80,0x10,0x80,0x3F,0x00,0x20},/*"u",85*/
+{0x80,0x00,0x80,0x03,0x80,0x0C,0x00,0x30,0x80,0x0C,0x80,0x03,0x80,0x00,0x00,0x00},/*"v",86*/
+{0x80,0x01,0x80,0x0E,0x00,0x30,0x80,0x0C,0x80,0x07,0x00,0x38,0x80,0x06,0x80,0x01},/*"w",87*/
+{0x00,0x00,0x80,0x20,0x80,0x31,0x80,0x0E,0x00,0x2E,0x80,0x31,0x80,0x20,0x00,0x00},/*"x",88*/
+{0x80,0x00,0x80,0x81,0x80,0x86,0x00,0x78,0x00,0x18,0x80,0x06,0x80,0x01,0x80,0x00},/*"y",89*/
+{0x00,0x00,0x80,0x21,0x80,0x30,0x80,0x2C,0x80,0x22,0x80,0x21,0x80,0x30,0x00,0x00},/*"z",90*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x01,0xFC,0x3E,0x02,0x40,0x02,0x40},/*"{",91*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xFF,0xFF,0x00,0x00,0x00,0x00,0x00,0x00},/*"|",92*/
+{0x02,0x40,0x02,0x40,0xFC,0x3E,0x00,0x01,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"}",93*/
+{0x00,0x00,0x02,0x00,0x01,0x00,0x02,0x00,0x02,0x00,0x04,0x00,0x02,0x00,0x00,0x00},/*"~",94*/
+};
+static const uint8_t font_en_2412[95][36] =
+{
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*" ",0*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xF0,0x77,0x1C,0xF0,0x0F,0x1C,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"!",1*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x80,0x00,0x00,0x60,0x00,0x00,0x30,0x00,0x00,0x1C,0x00,0x00,0x8C,0x00,0x00,0x60,0x00,0x00,0x30,0x00,0x00,0x1C,0x00,0x00,0x0C,0x00,0x00,0x00,0x00,0x00},/*""",2*/
+{0x00,0x00,0x00,0x00,0x83,0x01,0x00,0x83,0x1F,0x00,0xFF,0x01,0xF0,0x83,0x01,0x00,0x83,0x01,0x00,0x83,0x01,0x00,0x83,0x01,0x00,0xFB,0x1F,0xF0,0x87,0x01,0x00,0x83,0x01,0x00,0x00,0x00},/*"#",3*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x80,0x03,0x07,0xC0,0x07,0x0F,0x60,0x0C,0x12,0x20,0x18,0x10,0xF8,0xFF,0x7F,0x20,0x71,0x10,0xE0,0xE1,0x0F,0xC0,0x81,0x07,0x00,0x00,0x00,0x00,0x00,0x00},/*"$",4*/
+{0xC0,0x07,0x00,0x30,0x18,0x00,0x10,0x10,0x18,0x30,0x18,0x07,0xC0,0xCF,0x00,0x00,0x38,0x00,0x00,0xC6,0x07,0xC0,0x31,0x18,0x30,0x10,0x10,0x00,0x30,0x18,0x00,0xC0,0x07,0x00,0x00,0x00},/*"%",5*/
+{0x00,0xC0,0x07,0x00,0xE0,0x0F,0xE0,0x17,0x18,0xF0,0x3F,0x10,0x10,0xF8,0x10,0xF0,0xC7,0x13,0xE0,0x03,0x0F,0x00,0x08,0x0E,0x00,0xF8,0x19,0x00,0x08,0x10,0x00,0x08,0x10,0x00,0x00,0x0C},/*"&",6*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x8C,0x00,0x00,0x4C,0x00,0x00,0x38,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"'",7*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xFE,0x00,0x80,0x01,0x03,0x60,0x00,0x0C,0x10,0x00,0x10,0x08,0x00,0x20,0x04,0x00,0x40,0x00,0x00,0x00},/*"(",8*/
+{0x00,0x00,0x00,0x04,0x00,0x40,0x08,0x00,0x20,0x10,0x00,0x10,0x60,0x00,0x0C,0x80,0x01,0x03,0x00,0xFE,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*")",9*/
+{0x00,0x00,0x00,0x00,0x66,0x00,0x00,0x66,0x00,0x00,0x24,0x00,0x00,0x38,0x00,0x00,0x10,0x00,0xC0,0xFF,0x03,0x80,0x18,0x00,0x00,0x3C,0x00,0x00,0x24,0x00,0x00,0x66,0x00,0x00,0x66,0x00},/*"*",10*/
+{0x00,0x00,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x80,0xFF,0x03,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00},/*"+",11*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x8C,0x00,0x00,0x4C,0x00,0x00,0x38,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*",",12*/
+{0x00,0x00,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x00,0x00},/*"-",13*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x1C,0x00,0x00,0x1C,0x00,0x00,0x1C,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*".",14*/
+{0x00,0x00,0x00,0x00,0x00,0x60,0x00,0x00,0x38,0x00,0x00,0x0E,0x00,0x80,0x01,0x00,0x70,0x00,0x00,0x1C,0x00,0x00,0x03,0x00,0xE0,0x00,0x00,0x38,0x00,0x00,0x0C,0x00,0x00,0x00,0x00,0x00},/*"/",15*/
+{0x00,0x00,0x00,0x00,0xFE,0x01,0x80,0xFF,0x07,0xC0,0x01,0x0E,0x60,0x00,0x18,0x20,0x00,0x10,0x20,0x00,0x10,0x60,0x00,0x18,0xC0,0x01,0x0E,0x80,0xFF,0x07,0x00,0xFE,0x01,0x00,0x00,0x00},/*"0",16*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x40,0x00,0x10,0x40,0x00,0x10,0x40,0x00,0x10,0xC0,0xFF,0x1F,0xE0,0xFF,0x1F,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x00,0x00,0x00,0x00},/*"1",17*/
+{0x00,0x00,0x00,0x80,0x03,0x18,0x40,0x03,0x1C,0x20,0x00,0x12,0x20,0x00,0x11,0x20,0xC0,0x10,0x20,0x60,0x10,0x60,0x30,0x10,0xC0,0x1F,0x10,0x80,0x07,0x1E,0x00,0x00,0x00,0x00,0x00,0x00},/*"2",18*/
+{0x00,0x00,0x00,0xC0,0x01,0x0E,0xC0,0x01,0x0E,0x20,0x00,0x10,0x20,0x10,0x10,0x20,0x10,0x10,0x60,0x18,0x10,0xC0,0x2F,0x18,0x80,0xE7,0x0F,0x00,0x80,0x07,0x00,0x00,0x00,0x00,0x00,0x00},/*"3",19*/
+{0x00,0x00,0x00,0x00,0xC0,0x00,0x00,0xA0,0x00,0x00,0x98,0x00,0x00,0x84,0x00,0x00,0x83,0x10,0x80,0x80,0x10,0xE0,0xFF,0x1F,0xE0,0xFF,0x1F,0x00,0x80,0x10,0x00,0x80,0x10,0x00,0x80,0x00},/*"4",20*/
+{0x00,0x00,0x00,0x00,0x00,0x07,0xE0,0x3F,0x0B,0x20,0x10,0x10,0x20,0x08,0x10,0x20,0x08,0x10,0x20,0x08,0x10,0x20,0x18,0x1C,0x20,0xF0,0x0F,0x20,0xE0,0x03,0x00,0x00,0x00,0x00,0x00,0x00},/*"5",21*/
+{0x00,0x00,0x00,0x00,0xFC,0x01,0x80,0xFF,0x07,0xC0,0x21,0x0C,0x40,0x10,0x18,0x20,0x08,0x10,0x20,0x08,0x10,0x20,0x08,0x10,0xE0,0x18,0x08,0xC0,0xF0,0x0F,0x00,0xE0,0x03,0x00,0x00,0x00},/*"6",22*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0xC0,0x01,0x00,0x60,0x00,0x00,0x20,0x00,0x00,0x20,0x00,0x1F,0x20,0xE0,0x1F,0x20,0x18,0x00,0x20,0x07,0x00,0xE0,0x00,0x00,0x60,0x00,0x00,0x00,0x00,0x00},/*"7",23*/
+{0x00,0x00,0x00,0x80,0x83,0x07,0xC0,0xCF,0x0F,0x60,0x6C,0x08,0x20,0x18,0x10,0x20,0x10,0x10,0x20,0x30,0x10,0x20,0x30,0x10,0x60,0x68,0x18,0xC0,0xCF,0x0F,0x80,0x83,0x07,0x00,0x00,0x00},/*"8",24*/
+{0x00,0x00,0x00,0x00,0x1F,0x00,0xC0,0x3F,0x0C,0xC0,0x60,0x1C,0x20,0x40,0x10,0x20,0x40,0x10,0x20,0x40,0x10,0x20,0x20,0x08,0xC0,0x10,0x0F,0x80,0xFF,0x03,0x00,0xFE,0x00,0x00,0x00,0x00},/*"9",25*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x1C,0x1C,0x00,0x1C,0x1C,0x00,0x1C,0x1C,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*":",26*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x0C,0xD8,0x00,0x0C,0x38,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*";",27*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x10,0x00,0x00,0x28,0x00,0x00,0x44,0x00,0x00,0x82,0x00,0x00,0x01,0x01,0x80,0x00,0x02,0x40,0x00,0x04,0x20,0x00,0x08,0x10,0x00,0x10,0x00,0x00,0x00},/*"<",28*/
+{0x00,0x00,0x00,0x00,0x44,0x00,0x00,0x44,0x00,0x00,0x44,0x00,0x00,0x44,0x00,0x00,0x44,0x00,0x00,0x44,0x00,0x00,0x44,0x00,0x00,0x44,0x00,0x00,0x44,0x00,0x00,0x44,0x00,0x00,0x00,0x00},/*"=",29*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x10,0x00,0x10,0x20,0x00,0x08,0x40,0x00,0x04,0x80,0x00,0x02,0x00,0x01,0x01,0x00,0x82,0x00,0x00,0x44,0x00,0x00,0x28,0x00,0x00,0x10,0x00,0x00,0x00,0x00},/*">",30*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x80,0x07,0x00,0x40,0x06,0x00,0x40,0x00,0x00,0x20,0x00,0x1C,0x20,0xE0,0x1C,0x20,0x10,0x1C,0x20,0x18,0x00,0x60,0x08,0x00,0xC0,0x0F,0x00,0x80,0x07,0x00},/*"?",31*/
+{0x00,0x00,0x00,0x00,0xFE,0x00,0xC0,0xFF,0x07,0xE0,0x00,0x0E,0x20,0xF8,0x18,0x10,0xFF,0x11,0x90,0x03,0x11,0x90,0xFC,0x11,0xA0,0x07,0x09,0x60,0x80,0x0C,0x80,0x7F,0x02,0x00,0x00,0x00},/*"@",32*/
+{0x00,0x00,0x10,0x00,0x00,0x1C,0x00,0x80,0x13,0x00,0x78,0x10,0x80,0x47,0x00,0x60,0x40,0x00,0xE0,0x41,0x00,0x00,0x5F,0x00,0x00,0xF0,0x11,0x00,0x80,0x1F,0x00,0x00,0x18,0x00,0x00,0x10},/*"A",33*/
+{0x00,0x00,0x00,0x20,0x00,0x10,0xE0,0xFF,0x1F,0xE0,0xFF,0x1F,0x20,0x10,0x10,0x20,0x10,0x10,0x20,0x10,0x10,0x60,0x18,0x10,0xC0,0x2F,0x18,0xC0,0xE7,0x0F,0x00,0x80,0x07,0x00,0x00,0x00},/*"B",34*/
+{0x00,0x00,0x00,0x00,0xFC,0x01,0x80,0xFF,0x07,0xC0,0x01,0x0E,0x40,0x00,0x18,0x20,0x00,0x10,0x20,0x00,0x10,0x20,0x00,0x10,0x60,0x00,0x08,0xE0,0x00,0x0C,0x80,0x03,0x03,0x00,0x00,0x00},/*"C",35*/
+{0x20,0x00,0x10,0x20,0x00,0x10,0xE0,0xFF,0x1F,0xE0,0xFF,0x1F,0x20,0x00,0x10,0x20,0x00,0x10,0x20,0x00,0x10,0x40,0x00,0x08,0xC0,0x01,0x0E,0x80,0xFF,0x07,0x00,0xFE,0x01,0x00,0x00,0x00},/*"D",36*/
+{0x20,0x00,0x10,0xE0,0xFF,0x1F,0xE0,0xFF,0x1F,0x20,0x10,0x10,0x20,0x10,0x10,0x20,0x10,0x10,0x20,0x10,0x10,0x20,0xFC,0x10,0x60,0x00,0x10,0x60,0x00,0x18,0x80,0x01,0x06,0x00,0x00,0x00},/*"E",37*/
+{0x20,0x00,0x10,0xE0,0xFF,0x1F,0xE0,0xFF,0x1F,0x20,0x10,0x10,0x20,0x10,0x10,0x20,0x10,0x00,0x20,0x10,0x00,0x20,0xFC,0x00,0x60,0x00,0x00,0x60,0x00,0x00,0x80,0x01,0x00,0x00,0x00,0x00},/*"F",38*/
+{0x00,0x00,0x00,0x00,0xFC,0x01,0x80,0xFF,0x07,0xC0,0x01,0x0E,0x60,0x00,0x18,0x20,0x00,0x10,0x20,0x40,0x10,0x20,0x40,0x10,0x40,0xC0,0x0F,0x80,0xC3,0x0F,0x00,0x40,0x00,0x00,0x40,0x00},/*"G",39*/
+{0x20,0x00,0x10,0xE0,0xFF,0x1F,0xE0,0xFF,0x1F,0x20,0x10,0x10,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x20,0x10,0x10,0xE0,0xFF,0x1F,0xE0,0xFF,0x1F,0x20,0x00,0x10},/*"H",40*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x20,0x00,0x10,0x20,0x00,0x10,0x20,0x00,0x10,0xE0,0xFF,0x1F,0xE0,0xFF,0x1F,0x20,0x00,0x10,0x20,0x00,0x10,0x20,0x00,0x10,0x00,0x00,0x00,0x00,0x00,0x00},/*"I",41*/
+{0x00,0x00,0x00,0x00,0x00,0x60,0x00,0x00,0xE0,0x20,0x00,0x80,0x20,0x00,0x80,0x20,0x00,0xC0,0xE0,0xFF,0x7F,0xE0,0xFF,0x3F,0x20,0x00,0x00,0x20,0x00,0x00,0x20,0x00,0x00,0x00,0x00,0x00},/*"J",42*/
+{0x20,0x00,0x10,0xE0,0xFF,0x1F,0xE0,0xFF,0x1F,0x20,0x30,0x10,0x00,0x0C,0x00,0x00,0x3A,0x00,0xA0,0xE1,0x00,0xE0,0x80,0x13,0x60,0x00,0x1E,0x20,0x00,0x18,0x00,0x00,0x10,0x00,0x00,0x00},/*"K",43*/
+{0x20,0x00,0x10,0xE0,0xFF,0x1F,0xE0,0xFF,0x1F,0x20,0x00,0x10,0x20,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x18,0x00,0x00,0x06,0x00,0x00,0x00},/*"L",44*/
+{0x20,0x00,0x10,0xE0,0xFF,0x1F,0xE0,0x0F,0x10,0x00,0xFF,0x00,0x00,0xE0,0x0F,0x00,0x80,0x07,0x00,0x7C,0x00,0xC0,0x03,0x10,0xE0,0xFF,0x1F,0xE0,0xFF,0x1F,0x20,0x00,0x10,0x00,0x00,0x00},/*"M",45*/
+{0x00,0x00,0x10,0x20,0x00,0x10,0xE0,0xFF,0x1F,0xE0,0x01,0x10,0x80,0x07,0x10,0x00,0x1E,0x00,0x00,0x78,0x00,0x20,0xC0,0x03,0x20,0x00,0x0F,0xE0,0xFF,0x1F,0x20,0x00,0x00,0x20,0x00,0x00},/*"N",46*/
+{0x00,0x00,0x00,0x00,0xFE,0x01,0x80,0xFF,0x07,0xC0,0x01,0x0E,0x60,0x00,0x18,0x20,0x00,0x10,0x20,0x00,0x10,0x60,0x00,0x18,0xC0,0x00,0x0C,0x80,0xFF,0x07,0x00,0xFE,0x01,0x00,0x00,0x00},/*"O",47*/
+{0x20,0x00,0x10,0xE0,0xFF,0x1F,0xE0,0xFF,0x1F,0x20,0x20,0x10,0x20,0x20,0x10,0x20,0x20,0x00,0x20,0x20,0x00,0x20,0x30,0x00,0x40,0x10,0x00,0xC0,0x1F,0x00,0x80,0x0F,0x00,0x00,0x00,0x00},/*"P",48*/
+{0x00,0x00,0x00,0x00,0xFE,0x01,0x80,0xFF,0x07,0xC0,0x01,0x0E,0x60,0x00,0x19,0x20,0x00,0x11,0x20,0x00,0x17,0x60,0x00,0x3C,0xC0,0x00,0x6C,0x80,0xFF,0x67,0x00,0xFE,0x21,0x00,0x00,0x00},/*"Q",49*/
+{0x20,0x00,0x10,0xE0,0xFF,0x1F,0xE0,0xFF,0x1F,0x20,0x10,0x10,0x20,0x10,0x00,0x20,0x10,0x00,0x20,0x70,0x00,0x20,0xD0,0x01,0x60,0x08,0x07,0xC0,0x0F,0x1E,0x80,0x07,0x18,0x00,0x00,0x10},/*"R",50*/
+{0x00,0x00,0x00,0x80,0x07,0x07,0xC0,0x0F,0x0C,0x60,0x1C,0x08,0x20,0x18,0x10,0x20,0x38,0x10,0x20,0x30,0x10,0x20,0x70,0x10,0x40,0xE0,0x18,0xE0,0xE1,0x0F,0x00,0x80,0x07,0x00,0x00,0x00},/*"S",51*/
+{0x80,0x01,0x00,0x60,0x00,0x00,0x20,0x00,0x00,0x20,0x00,0x10,0x20,0x00,0x10,0xE0,0xFF,0x1F,0xE0,0xFF,0x1F,0x20,0x00,0x10,0x20,0x00,0x10,0x20,0x00,0x00,0x60,0x00,0x00,0x80,0x01,0x00},/*"T",52*/
+{0x00,0x00,0x00,0x20,0x00,0x00,0xE0,0xFF,0x07,0xE0,0xFF,0x0F,0x20,0x00,0x18,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x20,0x00,0x08,0xE0,0xFF,0x07,0x20,0x00,0x00,0x00,0x00,0x00},/*"U",53*/
+{0x20,0x00,0x00,0x60,0x00,0x00,0xE0,0x07,0x00,0x20,0x7E,0x00,0x00,0xE0,0x07,0x00,0x00,0x1E,0x00,0x80,0x03,0x00,0x78,0x00,0xA0,0x07,0x00,0x60,0x00,0x00,0x20,0x00,0x00,0x00,0x00,0x00},/*"V",54*/
+{0x20,0x00,0x00,0xE0,0x03,0x00,0x20,0xFF,0x00,0x00,0xC0,0x1F,0x20,0xC0,0x03,0x60,0x3C,0x00,0xE0,0x3F,0x00,0x20,0xF0,0x1F,0x00,0x80,0x07,0x20,0x7C,0x00,0xE0,0x03,0x00,0x20,0x00,0x00},/*"W",55*/
+{0x00,0x00,0x00,0x20,0x00,0x10,0x60,0x00,0x18,0xE0,0x01,0x16,0x20,0x87,0x01,0x00,0x7C,0x00,0x00,0xE8,0x00,0x20,0x86,0x13,0xE0,0x01,0x1E,0x20,0x00,0x18,0x20,0x00,0x10,0x00,0x00,0x00},/*"X",56*/
+{0x20,0x00,0x00,0x60,0x00,0x00,0xE0,0x01,0x00,0x20,0x0F,0x10,0x00,0x3C,0x10,0x00,0xF8,0x1F,0x00,0xE0,0x1F,0x00,0x18,0x10,0x20,0x06,0x10,0xA0,0x01,0x00,0x60,0x00,0x00,0x20,0x00,0x00},/*"Y",57*/
+{0x00,0x00,0x00,0x80,0x01,0x10,0xE0,0x00,0x1C,0x60,0x00,0x17,0x20,0x80,0x11,0x20,0x60,0x10,0x20,0x18,0x10,0x20,0x06,0x10,0xA0,0x03,0x10,0xE0,0x00,0x18,0x20,0x00,0x06,0x00,0x00,0x00},/*"Z",58*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xFC,0xFF,0x7F,0x04,0x00,0x40,0x04,0x00,0x40,0x04,0x00,0x40,0x04,0x00,0x40,0x00,0x00,0x00,0x00,0x00,0x00},/*"[",59*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x30,0x00,0x00,0xC0,0x00,0x00,0x00,0x07,0x00,0x00,0x18,0x00,0x00,0xE0,0x00,0x00,0x80,0x03,0x00,0x00,0x0C,0x00,0x00,0x70,0x00,0x00,0x80,0x00,0x00,0x00},/*"\",60*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x04,0x00,0x40,0x04,0x00,0x40,0x04,0x00,0x40,0x04,0x00,0x40,0xFC,0xFF,0x7F,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"]",61*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x08,0x00,0x00,0x04,0x00,0x00,0x02,0x00,0x00,0x02,0x00,0x00,0x04,0x00,0x00,0x08,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"^",62*/
+{0x00,0x00,0x80,0x00,0x00,0x80,0x00,0x00,0x80,0x00,0x00,0x80,0x00,0x00,0x80,0x00,0x00,0x80,0x00,0x00,0x80,0x00,0x00,0x80,0x00,0x00,0x80,0x00,0x00,0x80,0x00,0x00,0x80,0x00,0x00,0x80},/*"_",63*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x04,0x00,0x00,0x04,0x00,0x00,0x08,0x00,0x00,0x08,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"`",64*/
+{0x00,0x00,0x00,0x00,0x00,0x0F,0x00,0x98,0x1F,0x00,0x98,0x19,0x00,0x84,0x10,0x00,0x44,0x10,0x00,0x44,0x10,0x00,0x44,0x08,0x00,0xFC,0x0F,0x00,0xF8,0x1F,0x00,0x00,0x10,0x00,0x00,0x18},/*"a",65*/
+{0x00,0x00,0x00,0x20,0x00,0x00,0xE0,0xFF,0x1F,0xF0,0xFF,0x0F,0x00,0x18,0x08,0x00,0x08,0x10,0x00,0x04,0x10,0x00,0x04,0x10,0x00,0x0C,0x18,0x00,0xF8,0x0F,0x00,0xF0,0x03,0x00,0x00,0x00},/*"b",66*/
+{0x00,0x00,0x00,0x00,0xE0,0x03,0x00,0xF8,0x0F,0x00,0x18,0x0C,0x00,0x04,0x10,0x00,0x04,0x10,0x00,0x04,0x10,0x00,0x3C,0x10,0x00,0x38,0x08,0x00,0x00,0x06,0x00,0x00,0x00,0x00,0x00,0x00},/*"c",67*/
+{0x00,0x00,0x00,0x00,0xE0,0x03,0x00,0xF8,0x0F,0x00,0x1C,0x18,0x00,0x04,0x10,0x00,0x04,0x10,0x20,0x04,0x10,0x20,0x08,0x08,0xE0,0xFF,0x1F,0xF0,0xFF,0x0F,0x00,0x00,0x08,0x00,0x00,0x00},/*"d",68*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xE0,0x03,0x00,0xF8,0x0F,0x00,0x88,0x0C,0x00,0x84,0x10,0x00,0x84,0x10,0x00,0x84,0x10,0x00,0x8C,0x10,0x00,0xF8,0x08,0x00,0xE0,0x04,0x00,0x00,0x00},/*"e",69*/
+{0x00,0x00,0x00,0x00,0x04,0x00,0x00,0x04,0x10,0x00,0x04,0x10,0x80,0xFF,0x1F,0xC0,0xFF,0x1F,0x60,0x04,0x10,0x20,0x04,0x10,0x20,0x04,0x10,0xE0,0x00,0x00,0xC0,0x00,0x00,0x00,0x00,0x00},/*"f",70*/
+{0x00,0x00,0x00,0x00,0x00,0x70,0x00,0x70,0x7E,0x00,0xF8,0xCF,0x00,0x8C,0x85,0x00,0x04,0x85,0x00,0x0C,0x8D,0x00,0xFC,0xCD,0x00,0xF4,0x78,0x00,0x0C,0x78,0x00,0x0C,0x00,0x00,0x00,0x00},/*"g",71*/
+{0x00,0x00,0x00,0x20,0x00,0x10,0xE0,0xFF,0x1F,0xF0,0xFF,0x1F,0x00,0x08,0x10,0x00,0x04,0x00,0x00,0x04,0x00,0x00,0x04,0x10,0x00,0xFC,0x1F,0x00,0xF8,0x1F,0x00,0x00,0x10,0x00,0x00,0x00},/*"h",72*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x04,0x10,0x00,0x04,0x10,0x00,0x04,0x10,0x60,0xFC,0x1F,0x60,0xFE,0x1F,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x00,0x00,0x00,0x00},/*"i",73*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xC0,0x00,0x00,0xC0,0x00,0x04,0x80,0x00,0x04,0x80,0x60,0x04,0xC0,0x60,0xFC,0x7F,0x60,0xFE,0x3F,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"j",74*/
+{0x00,0x00,0x00,0x20,0x00,0x10,0xE0,0xFF,0x1F,0xF0,0xFF,0x1F,0x00,0x80,0x10,0x00,0x40,0x00,0x00,0xE0,0x00,0x00,0x1C,0x13,0x00,0x04,0x1E,0x00,0x04,0x18,0x00,0x00,0x10,0x00,0x00,0x00},/*"k",75*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x20,0x00,0x10,0x20,0x00,0x10,0x20,0x00,0x10,0xE0,0xFF,0x1F,0xF0,0xFF,0x1F,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x00,0x00,0x00,0x00},/*"l",76*/
+{0x00,0x04,0x10,0x00,0xFC,0x1F,0x00,0xFC,0x1F,0x00,0x08,0x10,0x00,0x04,0x10,0x00,0xFC,0x1F,0x00,0xF8,0x1F,0x00,0x08,0x10,0x00,0x04,0x10,0x00,0xFC,0x1F,0x00,0xFC,0x1F,0x00,0x00,0x10},/*"m",77*/
+{0x00,0x00,0x00,0x00,0x04,0x10,0x00,0xFC,0x1F,0x00,0xFC,0x1F,0x00,0x08,0x10,0x00,0x04,0x00,0x00,0x04,0x00,0x00,0x04,0x10,0x00,0xFC,0x1F,0x00,0xF8,0x1F,0x00,0x00,0x10,0x00,0x00,0x00},/*"n",78*/
+{0x00,0x00,0x00,0x00,0xE0,0x03,0x00,0xF0,0x0F,0x00,0x18,0x0C,0x00,0x0C,0x10,0x00,0x04,0x10,0x00,0x04,0x10,0x00,0x0C,0x10,0x00,0x18,0x0C,0x00,0xF0,0x0F,0x00,0xE0,0x03,0x00,0x00,0x00},/*"o",79*/
+{0x00,0x00,0x00,0x00,0x04,0x80,0x00,0xFC,0xFF,0x00,0xFC,0xFF,0x00,0x08,0x88,0x00,0x04,0x90,0x00,0x04,0x10,0x00,0x04,0x10,0x00,0x0C,0x1C,0x00,0xF8,0x0F,0x00,0xF0,0x03,0x00,0x00,0x00},/*"p",80*/
+{0x00,0x00,0x00,0x00,0xE0,0x03,0x00,0xF8,0x0F,0x00,0x1C,0x18,0x00,0x04,0x10,0x00,0x04,0x10,0x00,0x04,0x90,0x00,0x08,0x88,0x00,0xF8,0xFF,0x00,0xFC,0xFF,0x00,0x00,0x80,0x00,0x00,0x00},/*"q",81*/
+{0x00,0x04,0x10,0x00,0x04,0x10,0x00,0x04,0x10,0x00,0xFC,0x1F,0x00,0xFC,0x1F,0x00,0x10,0x10,0x00,0x08,0x10,0x00,0x04,0x10,0x00,0x04,0x00,0x00,0x1C,0x00,0x00,0x18,0x00,0x00,0x00,0x00},/*"r",82*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x38,0x1E,0x00,0x78,0x18,0x00,0xCC,0x10,0x00,0xC4,0x10,0x00,0x84,0x11,0x00,0x84,0x19,0x00,0x0C,0x1F,0x00,0x3C,0x0F,0x00,0x00,0x00,0x00,0x00,0x00},/*"s",83*/
+{0x00,0x00,0x00,0x00,0x04,0x00,0x00,0x04,0x00,0x00,0x04,0x00,0x00,0xFF,0x0F,0xC0,0xFF,0x1F,0x00,0x04,0x10,0x00,0x04,0x10,0x00,0x04,0x10,0x00,0x00,0x0C,0x00,0x00,0x00,0x00,0x00,0x00},/*"t",84*/
+{0x00,0x00,0x00,0x00,0x04,0x00,0x00,0xFC,0x0F,0x00,0xFE,0x1F,0x00,0x00,0x18,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x04,0x08,0x00,0xFC,0x1F,0x00,0xFE,0x0F,0x00,0x00,0x08,0x00,0x00,0x00},/*"u",85*/
+{0x00,0x00,0x00,0x00,0x04,0x00,0x00,0x0C,0x00,0x00,0x7C,0x00,0x00,0xC4,0x03,0x00,0x00,0x1F,0x00,0x00,0x0C,0x00,0x80,0x03,0x00,0x74,0x00,0x00,0x0C,0x00,0x00,0x04,0x00,0x00,0x00,0x00},/*"v",86*/
+{0x00,0x04,0x00,0x00,0x1C,0x00,0x00,0xF4,0x01,0x00,0x80,0x1F,0x00,0x04,0x0F,0x00,0xEC,0x00,0x00,0xFC,0x00,0x00,0x84,0x0F,0x00,0x00,0x0F,0x00,0xE4,0x00,0x00,0x1C,0x00,0x00,0x04,0x00},/*"w",87*/
+{0x00,0x00,0x00,0x00,0x00,0x10,0x00,0x04,0x10,0x00,0x0C,0x1C,0x00,0x3C,0x12,0x00,0xE4,0x01,0x00,0xC0,0x01,0x00,0x24,0x13,0x00,0x1C,0x1C,0x00,0x04,0x18,0x00,0x04,0x10,0x00,0x00,0x00},/*"x",88*/
+{0x00,0x00,0x00,0x00,0x04,0x00,0x00,0x04,0xC0,0x00,0x3C,0x80,0x00,0xC4,0x81,0x00,0x00,0x7F,0x00,0x00,0x0E,0x00,0xC4,0x01,0x00,0x3C,0x00,0x00,0x04,0x00,0x00,0x04,0x00,0x00,0x00,0x00},/*"y",89*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x3C,0x18,0x00,0x04,0x1E,0x00,0x04,0x13,0x00,0xC4,0x11,0x00,0x74,0x10,0x00,0x1C,0x10,0x00,0x0C,0x18,0x00,0x00,0x0E,0x00,0x00,0x00,0x00,0x00,0x00},/*"z",90*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x10,0x00,0x00,0x28,0x00,0xF8,0xC7,0x3F,0x04,0x00,0x40,0x04,0x00,0x40,0x00,0x00,0x00,0x00,0x00,0x00},/*"{",91*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xFF,0xFF,0xFF,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"|",92*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x04,0x00,0x40,0x04,0x00,0x40,0xF8,0xC7,0x3F,0x00,0x28,0x00,0x00,0x10,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"}",93*/
+{0x00,0x00,0x00,0x0C,0x00,0x00,0x02,0x00,0x00,0x02,0x00,0x00,0x02,0x00,0x00,0x04,0x00,0x00,0x08,0x00,0x00,0x18,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x0C,0x00,0x00,0x00,0x00,0x00},/*"~",94*/
+};
+
+//新宋体▶→
+static const char *font_cn_str="→输出入通道状态率耗电压流量功率因素温湿度数据版本日期时间地址模式保存退出取消设置开关主从";
+static const uint8_t font_cn_1212[][24] =
+{
+{0x20,0x00,0x20,0x00,0x20,0x00,0x20,0x00,0x20,0x00,0x20,0x00,0xA8,0x00,0x70,0x00,0x70,0x00,0x20,0x00,0x20,0x00,0x00,0x00},/*"→",0*/
+{0x34,0x01,0x2C,0x01,0xF7,0x0F,0xA4,0x00,0xE8,0x0F,0xA4,0x02,0xEA,0x0F,0x09,0x00,0xCA,0x03,0x04,0x08,0xE8,0x0F,0x00,0x00},/*"输",1*/
+{0x80,0x07,0x1E,0x04,0x10,0x04,0x10,0x04,0x10,0x04,0xFF,0x07,0x10,0x04,0x10,0x04,0x10,0x04,0x1E,0x04,0x80,0x0F,0x00,0x00},/*"出",2*/
+{0x00,0x08,0x00,0x04,0x01,0x02,0x81,0x01,0x72,0x00,0x0C,0x00,0x70,0x00,0x80,0x01,0x00,0x02,0x00,0x04,0x00,0x08,0x00,0x00},/*"入",3*/
+{0x11,0x08,0xF2,0x07,0x00,0x08,0xF9,0x0B,0xA9,0x08,0xAB,0x08,0xFD,0x0B,0xAD,0x08,0xAB,0x0A,0xF8,0x0B,0x00,0x08,0x00,0x00},/*"通",4*/
+{0x10,0x08,0x11,0x04,0xF2,0x03,0x00,0x04,0xFA,0x0B,0xAB,0x0A,0xAE,0x0A,0xAA,0x0A,0xAA,0x0A,0xAB,0x0A,0xFA,0x0B,0x00,0x00},/*"道",5*/
+{0x04,0x01,0x88,0x00,0xFF,0x0F,0x00,0x00,0x10,0x08,0x10,0x06,0xD0,0x01,0x3F,0x00,0xD0,0x01,0x12,0x06,0x14,0x08,0x00,0x00},/*"状",6*/
+{0x44,0x04,0x44,0x03,0x24,0x00,0x14,0x07,0x0C,0x08,0xA7,0x08,0x4C,0x0B,0x14,0x08,0x24,0x0C,0x44,0x01,0x44,0x06,0x00,0x00},/*"态",7*/
+{0x02,0x02,0x8A,0x02,0x52,0x02,0x9A,0x02,0xD6,0x02,0xB3,0x0F,0xD2,0x02,0x8A,0x02,0x52,0x02,0x8A,0x02,0x02,0x02,0x00,0x00},/*"率",8*/
+{0x44,0x02,0x54,0x01,0xFF,0x0F,0x54,0x01,0x44,0x02,0x92,0x00,0x92,0x00,0xFE,0x07,0x49,0x08,0x49,0x08,0x40,0x0E,0x00,0x00},/*"耗",9*/
+{0xFC,0x03,0x24,0x01,0x24,0x01,0x24,0x01,0xFF,0x07,0x24,0x09,0x24,0x09,0x24,0x09,0xFC,0x09,0x00,0x08,0x00,0x0E,0x00,0x00},/*"电",10*/
+{0x00,0x08,0xFE,0x07,0x02,0x08,0x42,0x08,0x42,0x08,0x42,0x08,0xFA,0x0F,0x42,0x08,0x42,0x09,0x42,0x0A,0x02,0x08,0x00,0x00},/*"压",11*/
+{0x22,0x04,0x44,0x02,0x00,0x08,0x24,0x04,0xB4,0x03,0x2C,0x00,0xA5,0x0F,0x26,0x00,0xA4,0x07,0x34,0x08,0x64,0x0E,0x00,0x00},/*"流",12*/
+{0x08,0x08,0xFF,0x0A,0xA9,0x0A,0xA9,0x0A,0xA9,0x0A,0xFB,0x0F,0xAD,0x0A,0xA9,0x0A,0xA9,0x0A,0xFF,0x0A,0x08,0x08,0x00,0x00},/*"量",13*/
+{0x04,0x02,0x04,0x02,0xFC,0x01,0x04,0x09,0x04,0x05,0x08,0x03,0xFF,0x00,0x08,0x00,0x08,0x08,0x08,0x08,0xF8,0x07,0x00,0x00},/*"功",14*/
+{0x02,0x02,0x8A,0x02,0x52,0x02,0x9A,0x02,0xD6,0x02,0xB3,0x0F,0xD2,0x02,0x8A,0x02,0x52,0x02,0x8A,0x02,0x02,0x02,0x00,0x00},/*"率",15*/
+{0xFF,0x0F,0x01,0x04,0x11,0x05,0x91,0x04,0x51,0x04,0x3D,0x04,0x51,0x04,0x91,0x04,0x11,0x05,0x01,0x04,0xFF,0x0F,0x00,0x00},/*"因",16*/
+{0x22,0x00,0x2A,0x0A,0xAA,0x06,0xEA,0x02,0xAA,0x0B,0xBF,0x0E,0xAA,0x02,0x6A,0x02,0x2A,0x07,0x2A,0x0A,0x22,0x00,0x00,0x00},/*"素",17*/
+{0x22,0x04,0x44,0x02,0x00,0x09,0xC0,0x0F,0x5F,0x08,0xD5,0x0F,0x55,0x08,0xD5,0x0F,0x5F,0x08,0xC0,0x0F,0x00,0x08,0x00,0x00},/*"温",18*/
+{0x11,0x04,0x22,0x02,0x80,0x08,0x3E,0x09,0x2A,0x08,0xEA,0x0F,0x2A,0x08,0xEA,0x0F,0x2A,0x08,0x3E,0x09,0x80,0x08,0x00,0x00},/*"湿",19*/
+{0x00,0x08,0xFE,0x07,0x0A,0x00,0x8A,0x08,0xBE,0x09,0xAA,0x0A,0xAB,0x04,0xAA,0x04,0xBE,0x0A,0x8A,0x09,0x0A,0x08,0x00,0x00},/*"度",20*/
+{0x48,0x09,0x2A,0x0B,0x98,0x05,0x7F,0x05,0x28,0x0B,0x4A,0x00,0x10,0x08,0xEF,0x05,0x08,0x02,0xF8,0x05,0x08,0x08,0x00,0x00},/*"数",21*/
+{0x88,0x00,0x88,0x08,0xFF,0x0F,0x48,0x08,0x00,0x06,0xFE,0x01,0xAA,0x0F,0xAA,0x04,0xFA,0x04,0xAA,0x04,0xAE,0x0F,0x00,0x00},/*"据",22*/
+{0x00,0x08,0xFE,0x07,0x90,0x00,0x9F,0x0F,0x10,0x04,0xFE,0x03,0x12,0x08,0xF2,0x05,0x12,0x02,0x91,0x05,0x71,0x08,0x00,0x00},/*"版",23*/
+{0x04,0x02,0x04,0x01,0x84,0x02,0x64,0x02,0x14,0x02,0xFF,0x0F,0x14,0x02,0x64,0x02,0x84,0x02,0x04,0x01,0x04,0x02,0x00,0x00},/*"本",24*/
+{0x00,0x00,0xFE,0x0F,0x22,0x04,0x22,0x04,0x22,0x04,0x22,0x04,0x22,0x04,0x22,0x04,0x22,0x04,0xFE,0x0F,0x00,0x00,0x00,0x00},/*"日",25*/
+{0x04,0x09,0xFF,0x05,0x54,0x01,0x54,0x01,0xFF,0x05,0x04,0x09,0x00,0x08,0xFE,0x07,0x92,0x00,0x92,0x08,0xFE,0x0F,0x00,0x00},/*"期",26*/
+{0xFE,0x07,0x22,0x02,0x22,0x02,0xFE,0x07,0x00,0x00,0x08,0x00,0x48,0x00,0x88,0x09,0x08,0x08,0xFF,0x0F,0x08,0x00,0x00,0x00},/*"时",27*/
+{0x00,0x00,0xF9,0x0F,0x02,0x00,0xF8,0x03,0x49,0x02,0x49,0x02,0x49,0x02,0x49,0x02,0xF9,0x0B,0x01,0x08,0xFF,0x0F,0x00,0x00},/*"间",28*/
+{0x10,0x04,0x10,0x04,0xFF,0x03,0x10,0x02,0x20,0x00,0xFC,0x07,0x10,0x08,0xFF,0x09,0x08,0x08,0x84,0x08,0xFC,0x0E,0x00,0x00},/*"地",29*/
+{0x10,0x04,0x10,0x04,0xFF,0x03,0x10,0x02,0x00,0x08,0xF8,0x0F,0x00,0x08,0x00,0x08,0xFF,0x0F,0x10,0x08,0x10,0x08,0x00,0x00},/*"址",30*/
+{0x88,0x00,0x68,0x00,0xFF,0x0F,0x48,0x00,0x02,0x0A,0xFA,0x0A,0xAF,0x06,0xAA,0x03,0xAF,0x06,0xFA,0x0A,0x02,0x0A,0x00,0x00},/*"模",31*/
+{0x08,0x08,0x48,0x08,0x48,0x08,0xC8,0x07,0x48,0x04,0x48,0x04,0x08,0x04,0xFF,0x00,0x08,0x03,0x09,0x04,0x0A,0x0E,0x00,0x00},/*"式",32*/
+{0x20,0x00,0x10,0x00,0xFC,0x0F,0x03,0x00,0x40,0x04,0x5E,0x02,0x52,0x01,0xF2,0x0F,0x52,0x01,0x5E,0x02,0x40,0x04,0x00,0x00},/*"保",33*/
+{0x84,0x00,0x44,0x00,0xF4,0x0F,0x0C,0x00,0x87,0x00,0x94,0x00,0x94,0x08,0xD4,0x0F,0xB4,0x00,0x94,0x00,0x84,0x00,0x00,0x00},/*"存",34*/
+{0x10,0x08,0x11,0x04,0xF2,0x03,0x00,0x04,0xFF,0x0B,0x15,0x09,0xB5,0x08,0x55,0x08,0x95,0x08,0x5F,0x0B,0x20,0x08,0x00,0x00},/*"退",35*/
+{0x80,0x07,0x1E,0x04,0x10,0x04,0x10,0x04,0x10,0x04,0xFF,0x07,0x10,0x04,0x10,0x04,0x10,0x04,0x1E,0x04,0x80,0x0F,0x00,0x00},/*"出",36*/
+{0x02,0x02,0xFE,0x03,0x52,0x02,0x52,0x02,0xFE,0x0F,0x02,0x01,0x04,0x08,0xFC,0x04,0x04,0x03,0xFC,0x04,0x00,0x08,0x00,0x00},/*"取",37*/
+{0x10,0x04,0x22,0x02,0x04,0x01,0x00,0x00,0xF2,0x0F,0x54,0x01,0x50,0x01,0x5F,0x01,0x50,0x01,0x54,0x09,0xF2,0x0F,0x00,0x00},/*"消",38*/
+{0x10,0x00,0x11,0x00,0xF2,0x07,0x00,0x02,0x50,0x08,0xCF,0x08,0x41,0x05,0x41,0x02,0x4F,0x05,0xD0,0x08,0x10,0x08,0x00,0x00},/*"设",39*/
+{0x10,0x08,0x17,0x08,0xD5,0x0F,0x55,0x08,0x57,0x08,0x7D,0x0E,0x57,0x08,0x55,0x08,0xD5,0x0F,0x17,0x08,0x10,0x08,0x00,0x00},/*"置",40*/
+{0x40,0x00,0x42,0x08,0x42,0x06,0xFE,0x01,0x42,0x00,0x42,0x00,0x42,0x00,0xFE,0x0F,0x42,0x00,0x42,0x00,0x40,0x00,0x00,0x00},/*"开",41*/
+{0x40,0x08,0x48,0x08,0x49,0x04,0x4A,0x02,0x48,0x01,0xF8,0x00,0x48,0x01,0x4A,0x02,0x49,0x04,0x48,0x08,0x40,0x08,0x00,0x00},/*"关",42*/
+{0x00,0x08,0x88,0x08,0x88,0x08,0x88,0x08,0x89,0x08,0xFA,0x0F,0x88,0x08,0x88,0x08,0x88,0x08,0x88,0x08,0x00,0x08,0x00,0x00},/*"主",43*/
+{0x00,0x08,0x00,0x06,0xE0,0x01,0x1F,0x00,0xE0,0x09,0x00,0x06,0xC0,0x01,0x3F,0x00,0xC0,0x01,0x00,0x06,0x00,0x08,0x00,0x00},/*"从",44*/
+};
+static const uint8_t font_cn_1616[][32] =
+{
+{0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x90,0x04,0xA0,0x02,0xE0,0x03,0xC0,0x01,0xC0,0x01,0x80,0x00,0x80,0x00,0x00,0x00},/*"→",0*/
+{0x88,0x09,0x68,0x19,0x1F,0x09,0xC8,0xFF,0x08,0x05,0x10,0x00,0xC8,0xFF,0x54,0x12,0x52,0x92,0xD1,0xFF,0x12,0x00,0x94,0x5F,0x08,0x80,0xD0,0x7F,0x10,0x00,0x00,0x00},/*"输",1*/
+{0x00,0x00,0x00,0x7C,0x7C,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0xFF,0x7F,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0xFC,0x40,0x00,0xFC,0x00,0x00,0x00,0x00},/*"出",2*/
+{0x00,0x80,0x00,0x40,0x00,0x20,0x00,0x10,0x00,0x0C,0x01,0x03,0xE2,0x00,0x1C,0x00,0xE0,0x00,0x00,0x03,0x00,0x0C,0x00,0x30,0x00,0x40,0x00,0x80,0x00,0x80,0x00,0x00},/*"入",3*/
+{0x40,0x80,0x42,0x40,0xCC,0x3F,0x00,0x40,0x00,0x80,0xE2,0xFF,0x22,0x89,0x2A,0x89,0x2A,0x89,0xF2,0xBF,0x2A,0x89,0x26,0xA9,0x22,0xC9,0xE0,0xBF,0x00,0x80,0x00,0x00},/*"通",4*/
+{0x40,0x00,0x40,0x40,0x42,0x20,0xCC,0x1F,0x00,0x20,0x08,0x40,0xE9,0x5F,0xAA,0x4A,0xB8,0x4A,0xA8,0x4A,0xA8,0x4A,0xAA,0x4A,0xE9,0x5F,0x08,0x40,0x00,0x40,0x00,0x00},/*"道",5*/
+{0x00,0x04,0x08,0x04,0x30,0x02,0x00,0x01,0xFF,0xFF,0x20,0x80,0x20,0x40,0x20,0x30,0x20,0x0E,0xFF,0x01,0x20,0x06,0x20,0x18,0x22,0x20,0x2C,0x40,0x20,0x80,0x00,0x00},/*"状",6*/
+{0x00,0x41,0x04,0x39,0x84,0x00,0x84,0x00,0x44,0x3C,0x24,0x40,0x54,0x40,0x8F,0x42,0x14,0x4C,0x24,0x40,0x44,0x40,0x84,0x70,0x84,0x04,0x04,0x09,0x00,0x31,0x00,0x00},/*"态",7*/
+{0x00,0x08,0x14,0x09,0xA4,0x08,0x44,0x08,0x24,0x09,0x34,0x09,0xAD,0x09,0x66,0xFD,0x24,0x09,0x94,0x09,0x04,0x0B,0x44,0x08,0xA4,0x08,0x14,0x09,0x00,0x08,0x00,0x00},/*"率",8*/
+{0x88,0x20,0xA8,0x18,0xA8,0x06,0xFF,0xFF,0xA8,0x02,0xA8,0x0C,0x88,0x00,0x00,0x04,0x44,0x04,0x44,0x04,0xFC,0x7F,0x22,0x82,0x23,0x82,0x22,0x82,0x00,0xF2,0x00,0x00},/*"耗",9*/
+{0x00,0x00,0x00,0x00,0xF8,0x1F,0x88,0x08,0x88,0x08,0x88,0x08,0x88,0x08,0xFF,0x7F,0x88,0x88,0x88,0x88,0x88,0x88,0x88,0x88,0xF8,0x9F,0x00,0x80,0x00,0xF0,0x00,0x00},/*"电",10*/
+{0x00,0x80,0x00,0x60,0xFE,0x1F,0x02,0x40,0x82,0x40,0x82,0x40,0x82,0x40,0x82,0x40,0xFA,0x7F,0x82,0x40,0x82,0x40,0x82,0x44,0x82,0x58,0x82,0x40,0x02,0x40,0x00,0x00},/*"压",11*/
+{0x10,0x04,0x60,0x04,0x02,0x7E,0x8C,0x01,0x00,0x80,0x44,0x40,0x64,0x3E,0x54,0x00,0x4D,0x00,0x46,0xFE,0x44,0x00,0x54,0x00,0x64,0x7E,0xC4,0x80,0x04,0xE0,0x00,0x00},/*"流",12*/
+{0x20,0x00,0x20,0x80,0x20,0x80,0xBE,0xAF,0xAA,0xAA,0xAA,0xAA,0xAA,0xAA,0xAA,0xFF,0xAA,0xAA,0xAA,0xAA,0xAA,0xAA,0xBE,0xAF,0x20,0x80,0x20,0x80,0x20,0x00,0x00,0x00},/*"量",13*/
+{0x08,0x10,0x08,0x30,0x08,0x10,0xF8,0x1F,0x08,0x08,0x08,0x88,0x08,0x48,0x10,0x30,0x10,0x0E,0xFF,0x01,0x10,0x40,0x10,0x80,0x10,0x40,0xF0,0x3F,0x00,0x00,0x00,0x00},/*"功",14*/
+{0x00,0x08,0x14,0x09,0xA4,0x08,0x44,0x08,0x24,0x09,0x34,0x09,0xAD,0x09,0x66,0xFD,0x24,0x09,0x94,0x09,0x04,0x0B,0x44,0x08,0xA4,0x08,0x14,0x09,0x00,0x08,0x00,0x00},/*"率",15*/
+{0x00,0x00,0xFE,0xFF,0x02,0x40,0x42,0x50,0x42,0x48,0x42,0x44,0x42,0x43,0xFA,0x40,0x42,0x41,0x42,0x42,0x42,0x44,0x42,0x58,0x02,0x40,0xFE,0xFF,0x00,0x00,0x00,0x00},/*"因",16*/
+{0x20,0x00,0x20,0x80,0x22,0x48,0x2A,0x29,0x2A,0x09,0xAA,0x4D,0x6A,0x8D,0x3F,0x7B,0x2A,0x0B,0x2A,0x09,0xAA,0x28,0x2A,0x4C,0x22,0x98,0x20,0x00,0x20,0x00,0x00,0x00},/*"素",17*/
+{0x10,0x04,0x60,0x04,0x02,0x7E,0x8C,0x01,0x00,0x40,0x00,0x7E,0xFE,0x42,0x92,0x42,0x92,0x7E,0x92,0x42,0x92,0x7E,0x92,0x42,0xFE,0x42,0x00,0x7E,0x00,0x40,0x00,0x00},/*"温",18*/
+{0x10,0x04,0x60,0x04,0x02,0x7E,0x8C,0x01,0x00,0x44,0xFE,0x48,0x92,0x50,0x92,0x7F,0x92,0x40,0x92,0x40,0x92,0x7F,0x92,0x50,0xFE,0x48,0x00,0x44,0x00,0x40,0x00,0x00},/*"湿",19*/
+{0x00,0x40,0x00,0x30,0xFC,0x8F,0x24,0x80,0x24,0x84,0x24,0x4C,0xFC,0x55,0x25,0x25,0x26,0x25,0x24,0x25,0xFC,0x55,0x24,0x4C,0x24,0x80,0x24,0x80,0x04,0x80,0x00,0x00},/*"度",20*/
+{0x90,0x82,0x52,0x9A,0x34,0x56,0x10,0x63,0xFF,0x22,0x10,0x52,0x34,0x8E,0x52,0x00,0x80,0x80,0x70,0x40,0x8F,0x33,0x08,0x0C,0x08,0x33,0xF8,0x40,0x08,0x80,0x00,0x00},/*"数",21*/
+{0x10,0x42,0x10,0x82,0xFF,0x7F,0x10,0x01,0x90,0x80,0x00,0x60,0xFE,0x1F,0x92,0x00,0x92,0xFC,0x92,0x44,0xF2,0x47,0x92,0x44,0x92,0x44,0x9E,0xFC,0x80,0x00,0x00,0x00},/*"据",22*/
+{0x00,0x80,0xFE,0x7F,0x20,0x01,0x20,0x01,0x3F,0xFF,0x20,0x80,0x00,0x60,0xFC,0x1F,0x24,0x80,0xE4,0x41,0x24,0x26,0x22,0x18,0x23,0x26,0xE2,0x41,0x00,0x80,0x00,0x00},/*"版",23*/
+{0x00,0x10,0x10,0x08,0x10,0x04,0x10,0x02,0x10,0x09,0xD0,0x08,0x30,0x08,0xFF,0xFF,0x30,0x08,0xD0,0x08,0x10,0x09,0x10,0x02,0x10,0x04,0x10,0x08,0x00,0x10,0x00,0x00},/*"本",24*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0xFE,0xFF,0x82,0x40,0x82,0x40,0x82,0x40,0x82,0x40,0x82,0x40,0x82,0x40,0x82,0x40,0xFE,0xFF,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"日",25*/
+{0x00,0x88,0x04,0x48,0xFF,0x2F,0x24,0x09,0x24,0x09,0x24,0x19,0xFF,0xAF,0x04,0x48,0x00,0x30,0xFE,0x0F,0x22,0x02,0x22,0x42,0x22,0x82,0xFE,0x7F,0x00,0x00,0x00,0x00},/*"期",26*/
+{0x00,0x00,0xFC,0x3F,0x84,0x10,0x84,0x10,0x84,0x10,0xFC,0x3F,0x00,0x00,0x10,0x00,0x10,0x01,0x10,0x06,0x10,0x40,0x10,0x80,0xFF,0x7F,0x10,0x00,0x10,0x00,0x00,0x00},/*"时",27*/
+{0x00,0x00,0xF8,0xFF,0x01,0x00,0x06,0x00,0x00,0x00,0xF0,0x1F,0x12,0x11,0x12,0x11,0x12,0x11,0xF2,0x1F,0x02,0x00,0x02,0x40,0x02,0x80,0xFE,0x7F,0x00,0x00,0x00,0x00},/*"间",28*/
+{0x20,0x10,0x20,0x30,0x20,0x10,0xFF,0x0F,0x20,0x08,0x20,0x08,0x80,0x00,0xF8,0x3F,0x80,0x40,0x40,0x40,0xFF,0x5F,0x20,0x42,0x10,0x44,0xF0,0x43,0x00,0x78,0x00,0x00},/*"地",29*/
+{0x20,0x10,0x20,0x30,0x20,0x10,0xFF,0x0F,0x20,0x08,0x20,0x48,0x00,0x40,0xF8,0x7F,0x00,0x40,0x00,0x40,0xFF,0x7F,0x40,0x40,0x40,0x40,0x40,0x40,0x00,0x40,0x00,0x00},/*"址",30*/
+{0x10,0x04,0x10,0x03,0xD0,0x00,0xFF,0xFF,0x90,0x00,0x14,0x89,0xE4,0x4B,0xAF,0x2A,0xA4,0x1A,0xA4,0x0E,0xA4,0x1A,0xAF,0x2A,0xE4,0x4B,0x04,0x88,0x00,0x80,0x00,0x00},/*"模",31*/
+{0x10,0x00,0x10,0x20,0x90,0x60,0x90,0x20,0x90,0x3F,0x90,0x10,0x90,0x10,0x10,0x10,0x10,0x00,0xFF,0x03,0x10,0x0C,0x10,0x10,0x11,0x20,0x16,0x40,0x10,0xF8,0x00,0x00},/*"式",32*/
+{0x00,0x01,0x80,0x00,0x60,0x00,0xF8,0xFF,0x07,0x20,0x00,0x11,0x3E,0x09,0x22,0x05,0x22,0x03,0xE2,0xFF,0x22,0x03,0x22,0x05,0x3E,0x09,0x00,0x11,0x00,0x20,0x00,0x00},/*"保",33*/
+{0x04,0x02,0x04,0x01,0x84,0x00,0xE4,0xFF,0x1C,0x00,0x07,0x02,0x24,0x02,0x24,0x42,0x24,0x82,0x24,0x7F,0xA4,0x02,0x64,0x02,0x24,0x02,0x04,0x02,0x04,0x02,0x00,0x00},/*"存",34*/
+{0x40,0x00,0x40,0x40,0x42,0x20,0xCC,0x1F,0x00,0x20,0x00,0x40,0xFF,0x5F,0x49,0x48,0x49,0x44,0xC9,0x40,0x49,0x41,0x49,0x42,0x7F,0x45,0x80,0x58,0x00,0x40,0x00,0x00},/*"退",35*/
+{0x00,0x00,0x00,0x7C,0x7C,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0xFF,0x7F,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0xFC,0x40,0x00,0xFC,0x00,0x00,0x00,0x00},/*"出",36*/
+{0x02,0x08,0x02,0x18,0xFE,0x0F,0x92,0x08,0x92,0x08,0x92,0x04,0xFE,0xFF,0x02,0x04,0x06,0x84,0xFC,0x40,0x04,0x27,0x04,0x18,0x04,0x27,0xFC,0x40,0x00,0x80,0x00,0x00},/*"取",37*/
+{0x10,0x04,0x60,0x04,0x02,0x7C,0x0C,0x03,0xC0,0x00,0x00,0x00,0xE2,0xFF,0x2C,0x09,0x20,0x09,0x3F,0x09,0x20,0x49,0x28,0x89,0xE6,0x7F,0x00,0x00,0x00,0x00,0x00,0x00},/*"消",38*/
+{0x40,0x00,0x40,0x00,0x42,0x00,0xCC,0x3F,0x00,0x90,0x40,0x88,0xA0,0x40,0x9E,0x43,0x82,0x2C,0x82,0x10,0x82,0x28,0x9E,0x46,0xA0,0x41,0x20,0x80,0x20,0x80,0x00,0x00},/*"设",39*/
+{0x00,0x40,0x17,0x40,0x15,0x40,0xD5,0x7F,0x55,0x55,0x57,0x55,0x55,0x55,0x7D,0x55,0x55,0x55,0x57,0x55,0x55,0x55,0xD5,0x7F,0x15,0x40,0x17,0x40,0x00,0x40,0x00,0x00},/*"置",40*/
+{0x80,0x00,0x82,0x80,0x82,0x40,0x82,0x30,0xFE,0x0F,0x82,0x00,0x82,0x00,0x82,0x00,0x82,0x00,0x82,0x00,0xFE,0xFF,0x82,0x00,0x82,0x00,0x82,0x00,0x80,0x00,0x00,0x00},/*"开",41*/
+{0x00,0x81,0x00,0x81,0x10,0x41,0x11,0x41,0x16,0x21,0x10,0x11,0x10,0x0D,0xF0,0x03,0x10,0x0D,0x10,0x11,0x14,0x21,0x13,0x41,0x10,0x41,0x00,0x81,0x00,0x81,0x00,0x00},/*"关",42*/
+{0x00,0x40,0x08,0x40,0x08,0x41,0x08,0x41,0x08,0x41,0x08,0x41,0x09,0x41,0xFA,0x7F,0x08,0x41,0x08,0x41,0x08,0x41,0x08,0x41,0x08,0x41,0x08,0x40,0x00,0x40,0x00,0x00},/*"主",43*/
+{0x00,0x80,0x00,0x40,0x00,0x30,0x00,0x0E,0xFF,0x01,0x00,0x82,0x00,0x4C,0x00,0x20,0x00,0x18,0x00,0x07,0xFF,0x00,0x00,0x07,0x00,0x18,0x00,0x60,0x00,0x80,0x00,0x00},/*"从",44*/
+};
+static const uint8_t font_cn_2424[][72] =
+{
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x52,0x00,0x00,0x7C,0x00,0x00,0x3C,0x00,0x00,0x38,0x00,0x00,0x38,0x00,0x00,0x18,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"→",0*/
+{0x00,0x00,0x00,0x20,0x08,0x02,0x20,0x0E,0x02,0xE0,0x0B,0x01,0x7C,0x08,0x01,0x2C,0x09,0x71,0x20,0xFF,0x7F,0x20,0x88,0x00,0x20,0x8A,0x00,0x20,0x01,0x00,0x00,0xFD,0x7F,0x80,0x24,0x01,0x60,0x25,0x21,0x38,0x25,0x61,0x0E,0xFD,0x3F,0x0C,0x01,0x00,0x10,0x01,0x00,0xA0,0xF8,0x07,0x40,0x01,0x20,0x80,0x00,0x60,0x80,0xFD,0x3F,0x00,0x01,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"输",1*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x20,0xE0,0x8F,0x3F,0xE0,0x8F,0x20,0x00,0x08,0x20,0x00,0x08,0x20,0x00,0x08,0x20,0x00,0x08,0x20,0x00,0x08,0x20,0xFC,0xFF,0x3F,0xF8,0xFF,0x3F,0x00,0x08,0x20,0x00,0x08,0x20,0x00,0x08,0x20,0x00,0x08,0x20,0x00,0x08,0x20,0xE0,0x1F,0x20,0x20,0x90,0x7F,0x00,0x80,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"出",2*/
+{0x00,0x00,0x00,0x00,0x00,0x40,0x00,0x00,0x20,0x00,0x00,0x10,0x00,0x00,0x08,0x00,0x00,0x0C,0x00,0x00,0x06,0x04,0x80,0x01,0x04,0xC0,0x00,0x08,0x30,0x00,0x18,0x1E,0x00,0xF0,0x03,0x00,0xC0,0x01,0x00,0x00,0x0E,0x00,0x00,0x70,0x00,0x00,0xC0,0x00,0x00,0x80,0x03,0x00,0x00,0x06,0x00,0x00,0x0C,0x00,0x00,0x18,0x00,0x00,0x38,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x00},/*"入",3*/
+{0x00,0x00,0x00,0x00,0x04,0x20,0x00,0x04,0x30,0x08,0x04,0x18,0x70,0x04,0x08,0x60,0xFC,0x07,0x00,0x00,0x08,0x00,0x00,0x10,0x00,0x00,0x30,0x84,0xFF,0x2F,0x84,0x44,0x20,0x84,0x44,0x60,0x94,0x44,0x60,0xA4,0x44,0x60,0xE4,0xFF,0x6F,0xE4,0x44,0x60,0x94,0x44,0x60,0x94,0x44,0x60,0x8C,0x44,0x68,0x88,0x44,0x7C,0x80,0xFF,0x6F,0x00,0x00,0x20,0x00,0x00,0x00,0x00,0x00,0x00},/*"通",4*/
+{0x00,0x00,0x00,0x00,0x02,0x10,0x00,0x02,0x18,0x04,0x02,0x08,0x0C,0x02,0x04,0x18,0xFF,0x07,0x00,0x02,0x08,0x20,0x00,0x10,0x20,0x00,0x10,0x20,0x00,0x20,0x22,0xFF,0x27,0x24,0x49,0x22,0x38,0x49,0x62,0xA0,0x49,0x62,0x60,0x49,0x42,0x20,0x49,0x42,0x30,0x49,0x42,0x2C,0x49,0x42,0x24,0xFF,0x47,0x20,0xFF,0x67,0x20,0x00,0x60,0x20,0x00,0x20,0x00,0x00,0x20,0x00,0x00,0x00},/*"道",5*/
+{0x00,0x00,0x00,0x00,0x00,0x01,0x40,0x80,0x01,0x80,0x81,0x00,0x00,0x43,0x00,0x00,0x20,0x00,0x04,0x10,0x40,0xFC,0xFF,0x3F,0x00,0x02,0x40,0x00,0x02,0x20,0x00,0x02,0x10,0x00,0x02,0x0C,0x00,0x02,0x07,0x00,0xF2,0x01,0xFC,0x3F,0x00,0x00,0x06,0x00,0x00,0x7A,0x00,0x08,0x82,0x03,0x10,0x02,0x0E,0x70,0x02,0x1C,0xE0,0x03,0x38,0x00,0x02,0x30,0x00,0x00,0x00,0x00,0x00,0x00},/*"状",6*/
+{0x00,0x00,0x00,0x00,0x40,0x00,0x20,0x40,0x18,0x20,0x20,0x1C,0x20,0x20,0x0F,0x20,0x10,0x00,0x20,0x10,0x00,0x20,0x08,0x3F,0x20,0x04,0x61,0x20,0x07,0x40,0xF0,0x89,0x40,0x3E,0x98,0x41,0x60,0x30,0x47,0xA0,0x01,0x40,0x20,0x02,0x40,0x20,0x04,0x40,0x20,0x0C,0x7C,0x20,0x18,0x00,0x20,0x18,0x01,0x20,0x30,0x06,0x30,0x30,0x1E,0x20,0x10,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"态",7*/
+{0x00,0x00,0x00,0x00,0x00,0x01,0x10,0x20,0x01,0x10,0x20,0x01,0x90,0x20,0x01,0x90,0x11,0x01,0x10,0x08,0x01,0x10,0x08,0x01,0x10,0x23,0x01,0x90,0x32,0x01,0x52,0x2A,0x01,0x3C,0xE6,0x7F,0x1C,0x62,0x61,0x10,0x29,0x01,0xD0,0x11,0x01,0x90,0x70,0x01,0x10,0x0A,0x01,0x10,0x09,0x01,0x90,0x10,0x01,0x90,0x30,0x01,0x10,0x20,0x01,0x00,0x00,0x01,0x00,0x00,0x00,0x00,0x00,0x00},/*"率",8*/
+{0x00,0x00,0x00,0x00,0x04,0x08,0x90,0x04,0x04,0x90,0x04,0x03,0x90,0xC4,0x00,0x90,0x7C,0x00,0xFE,0xFF,0x7F,0x90,0x24,0x00,0x90,0xC4,0x00,0x90,0x84,0x01,0x10,0x04,0x00,0x00,0x84,0x00,0x20,0x84,0x00,0x20,0x84,0x00,0x10,0x44,0x00,0xF0,0xFF,0x3F,0x10,0x42,0x20,0x08,0x42,0x20,0x08,0x42,0x20,0x0C,0x21,0x20,0x04,0x21,0x20,0x00,0x30,0x3E,0x00,0x20,0x10,0x00,0x00,0x00},/*"耗",9*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xC0,0xFF,0x03,0x40,0x84,0x00,0x40,0x84,0x00,0x40,0x84,0x00,0x40,0x84,0x00,0x40,0x84,0x00,0x40,0x84,0x00,0xFE,0xFF,0x7F,0x40,0x84,0x40,0x40,0x84,0x40,0x40,0x84,0x40,0x40,0x84,0x40,0x40,0x84,0x40,0x40,0x84,0x40,0xC0,0xFF,0x41,0x40,0x00,0x40,0x00,0x00,0x60,0x00,0x00,0x7C,0x00,0x00,0x00,0x00,0x00,0x00},/*"电",10*/
+{0x00,0x00,0x00,0x00,0x00,0x40,0x00,0x00,0x30,0x00,0x00,0x0C,0xF8,0xFF,0x17,0xF8,0x7F,0x10,0x08,0x00,0x10,0x08,0x08,0x10,0x08,0x08,0x10,0x08,0x08,0x10,0x08,0x08,0x10,0x08,0x08,0x10,0xE8,0xFF,0x1F,0xE8,0xFF,0x1F,0x08,0x08,0x10,0x08,0x08,0x10,0x08,0x48,0x10,0x08,0x88,0x11,0x08,0x08,0x17,0x08,0x08,0x12,0x0C,0x00,0x10,0x08,0x00,0x10,0x00,0x00,0x00,0x00,0x00,0x00},/*"压",11*/
+{0x00,0x00,0x00,0x00,0x01,0x01,0x00,0x03,0x01,0x04,0x0E,0x3F,0x08,0x80,0x3F,0x38,0x60,0x40,0x30,0x1C,0x40,0x80,0x03,0x20,0x50,0x00,0x18,0x10,0xF4,0x0F,0x10,0xF6,0x01,0x10,0x05,0x00,0xD2,0x04,0x00,0x74,0xF4,0x7F,0x3C,0x14,0x00,0x10,0x02,0x00,0x10,0x02,0x00,0x90,0xF2,0x3F,0x10,0x13,0x20,0x10,0x0E,0x20,0x18,0x00,0x20,0x10,0x00,0x3C,0x00,0x00,0x10,0x00,0x00,0x00},/*"流",12*/
+{0x00,0x00,0x00,0x00,0x02,0x20,0x00,0x02,0x20,0x00,0x02,0x24,0x00,0x02,0x24,0xFC,0xFB,0x27,0xFC,0x2B,0x25,0x94,0x2A,0x25,0x94,0x2A,0x25,0x94,0x2A,0x25,0x94,0x2A,0x25,0x94,0xFA,0x3F,0x94,0xFA,0x3F,0x94,0x2A,0x25,0x94,0x2A,0x25,0x94,0x2A,0x25,0x94,0x2A,0x25,0xFC,0xFB,0x27,0x00,0xFA,0x27,0x00,0x02,0x24,0x00,0x02,0x20,0x00,0x03,0x30,0x00,0x02,0x00,0x00,0x00,0x00},/*"量",13*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x20,0x00,0x06,0x20,0x00,0x06,0x20,0x00,0x02,0x20,0x00,0x02,0xE0,0xFF,0x01,0x20,0x00,0x41,0x20,0x00,0x21,0x20,0x80,0x20,0x30,0x80,0x10,0xA0,0x00,0x08,0x80,0x00,0x06,0x80,0x00,0x03,0x80,0xF0,0x00,0xFE,0x1F,0x10,0x84,0x00,0x10,0x80,0x00,0x20,0x80,0x00,0x60,0x80,0x00,0x30,0x80,0xFF,0x1F,0x80,0x07,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"功",14*/
+{0x00,0x00,0x00,0x00,0x00,0x01,0x10,0x20,0x01,0x10,0x20,0x01,0x90,0x20,0x01,0x90,0x11,0x01,0x10,0x08,0x01,0x10,0x08,0x01,0x10,0x23,0x01,0x90,0x32,0x01,0x52,0x2A,0x01,0x3C,0xE6,0x7F,0x1C,0x62,0x61,0x10,0x29,0x01,0xD0,0x11,0x01,0x90,0x70,0x01,0x10,0x0A,0x01,0x10,0x09,0x01,0x90,0x10,0x01,0x90,0x30,0x01,0x10,0x20,0x01,0x00,0x00,0x01,0x00,0x00,0x00,0x00,0x00,0x00},/*"率",15*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xFC,0xFF,0x7F,0x04,0x00,0x10,0x04,0x02,0x18,0x04,0x02,0x14,0x04,0x02,0x14,0x04,0x02,0x12,0x04,0x02,0x11,0x04,0xE2,0x10,0xE4,0x3F,0x10,0x24,0x12,0x10,0x04,0x22,0x10,0x04,0x42,0x10,0x04,0x82,0x11,0x04,0x82,0x17,0x04,0x02,0x10,0x04,0x00,0x10,0x04,0x00,0x10,0xFC,0xFF,0x3F,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"因",16*/
+{0x00,0x00,0x00,0x00,0x01,0x00,0x00,0x01,0x40,0x08,0x01,0x20,0x08,0x01,0x10,0x48,0x81,0x19,0x48,0x99,0x0D,0x48,0x95,0x07,0x48,0x55,0x05,0x48,0xD3,0x20,0x48,0xAB,0x60,0xFE,0xA9,0x7F,0xFE,0x91,0x3F,0x48,0x89,0x00,0x48,0x8D,0x00,0x48,0x85,0x02,0x48,0xE1,0x04,0x48,0xC1,0x0C,0x48,0x81,0x19,0x0C,0x01,0x38,0x08,0x01,0x30,0x00,0x01,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"素",17*/
+{0x00,0x00,0x00,0x80,0x00,0x01,0x00,0x01,0x01,0x04,0x07,0x3F,0x08,0x80,0x3F,0x18,0x78,0x20,0x00,0x07,0x20,0xC0,0x00,0x20,0x00,0xE0,0x3F,0xF8,0x2F,0x20,0x48,0x24,0x20,0x48,0x24,0x20,0x48,0xE4,0x3F,0x48,0x24,0x20,0x48,0x24,0x20,0x48,0xE4,0x3F,0x48,0x24,0x20,0x48,0x24,0x20,0xFC,0x2F,0x20,0x00,0xE0,0x3F,0x00,0x20,0x20,0x00,0x00,0x30,0x00,0x00,0x20,0x00,0x00,0x00},/*"温",18*/
+{0x00,0x00,0x00,0x80,0x80,0x00,0x00,0x01,0x11,0x04,0x87,0x3F,0x18,0xC2,0x01,0x38,0x38,0x00,0x00,0x07,0x20,0xC0,0x00,0x20,0x00,0xC0,0x20,0xF8,0x8F,0x27,0xF8,0x0F,0x22,0x48,0x04,0x20,0x48,0xFC,0x3F,0x48,0x04,0x20,0x48,0x04,0x20,0x48,0x04,0x20,0x48,0xFC,0x3F,0x48,0x04,0x24,0x48,0x04,0x23,0xFC,0x8F,0x21,0x08,0xE0,0x20,0x00,0x60,0x30,0x00,0x00,0x20,0x00,0x00,0x00},/*"湿",19*/
+{0x00,0x00,0x00,0x00,0x00,0x20,0x00,0x00,0x18,0x00,0xC0,0x07,0xF0,0xFF,0x00,0x10,0x01,0x40,0x10,0x01,0x40,0x10,0x41,0x40,0x10,0x41,0x20,0x30,0x41,0x20,0xD0,0xDF,0x11,0x12,0x49,0x12,0x1C,0x49,0x0C,0x1C,0x49,0x08,0x10,0x49,0x0C,0x10,0x49,0x12,0xF0,0x5F,0x11,0x50,0xC1,0x30,0x10,0x41,0x20,0x10,0x01,0x20,0x98,0x01,0x60,0x10,0x01,0x20,0x00,0x00,0x20,0x00,0x00,0x00},/*"度",20*/
+{0x00,0x00,0x00,0x00,0x50,0x40,0x40,0x48,0x40,0x44,0x48,0x20,0x78,0x44,0x22,0x50,0xC3,0x13,0xC0,0xE1,0x12,0xFE,0x7F,0x0C,0x40,0x41,0x0C,0x60,0x41,0x06,0x50,0xC6,0x4D,0x4C,0x44,0x38,0x40,0x0C,0x20,0x80,0x03,0x10,0xF0,0x0F,0x18,0x5E,0xF0,0x0C,0x44,0x80,0x07,0x40,0x80,0x07,0x40,0xFC,0x0C,0xC0,0x1F,0x18,0x40,0x00,0x30,0x40,0x00,0x30,0x00,0x00,0x00,0x00,0x00,0x00},/*"数",21*/
+{0x00,0x00,0x00,0x80,0x40,0x00,0x80,0xC0,0x20,0x80,0x40,0x20,0x80,0x20,0x60,0xFC,0xFF,0x7F,0x88,0x10,0x20,0x80,0x08,0x10,0xC0,0x08,0x0C,0x80,0x84,0x03,0xF8,0xFF,0x00,0xF8,0x09,0x00,0x88,0x88,0x7F,0x88,0x88,0x10,0x88,0x88,0x10,0x88,0x88,0x10,0x88,0xFF,0x10,0x88,0x88,0x10,0x88,0x88,0x10,0xF8,0x89,0x7F,0xF8,0x89,0x3F,0x00,0x08,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"据",22*/
+{0x00,0x00,0x00,0x00,0x00,0x60,0x00,0x00,0x1E,0xF8,0xFF,0x03,0x00,0x11,0x00,0x00,0x11,0x00,0xFE,0x11,0x00,0xFC,0xF1,0x1F,0x00,0xF1,0x4F,0x00,0x01,0x30,0x00,0x01,0x4E,0xF0,0xFF,0x21,0x10,0x01,0x20,0x10,0x03,0x10,0x10,0x3D,0x08,0x08,0xC1,0x04,0x08,0x01,0x03,0x08,0x81,0x07,0x08,0x71,0x0C,0x0C,0x1F,0x18,0x0C,0x03,0x30,0x00,0x00,0x30,0x00,0x00,0x00,0x00,0x00,0x00},/*"版",23*/
+{0x00,0x00,0x00,0x00,0x00,0x08,0x40,0x00,0x04,0x40,0x00,0x04,0x40,0x00,0x02,0x40,0x00,0x01,0x40,0xC0,0x02,0x40,0x60,0x02,0x40,0x38,0x02,0x40,0x0E,0x02,0xC0,0x03,0x02,0xFE,0xFF,0xFF,0xFC,0xFF,0xFF,0xC0,0x01,0x02,0x40,0x06,0x02,0x40,0x18,0x02,0x40,0x30,0x03,0x40,0xC0,0x02,0x40,0x80,0x01,0x40,0x00,0x03,0x60,0x00,0x07,0x40,0x00,0x02,0x00,0x00,0x02,0x00,0x00,0x00},/*"本",24*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xFC,0xFF,0x7F,0x08,0x04,0x08,0x08,0x04,0x08,0x08,0x04,0x08,0x08,0x04,0x08,0x08,0x04,0x08,0x08,0x04,0x08,0x08,0x04,0x08,0x08,0x04,0x08,0x08,0x04,0x08,0x08,0x04,0x08,0x08,0x04,0x08,0x08,0x04,0x08,0xFC,0xFF,0x3F,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"日",25*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x20,0x80,0x20,0x20,0x80,0x10,0x20,0x80,0x08,0xFC,0xFF,0x07,0x20,0x89,0x02,0x20,0x89,0x00,0x20,0x89,0x00,0x20,0x89,0x02,0xFC,0xFF,0x44,0x20,0x80,0x2C,0x20,0x80,0x10,0x00,0x80,0x0C,0x18,0xF0,0x07,0xF8,0xFF,0x00,0x08,0x21,0x00,0x08,0x21,0x10,0x08,0x21,0x20,0x08,0x21,0x20,0xF8,0xFF,0x3F,0xF8,0xFF,0x1F,0x00,0x00,0x00,0x00,0x00,0x00},/*"期",26*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0xF0,0xFF,0x0F,0x10,0x04,0x02,0x10,0x04,0x02,0x10,0x04,0x02,0x10,0x04,0x02,0xF0,0xFF,0x0F,0xF0,0xFF,0x07,0x80,0x00,0x00,0x80,0x00,0x00,0x80,0x08,0x00,0x80,0x30,0x00,0x80,0x70,0x10,0x80,0x00,0x20,0x80,0x00,0x20,0x80,0x00,0x60,0xFE,0xFF,0x3F,0x84,0x00,0x00,0x80,0x00,0x00,0x80,0x00,0x00,0x80,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"时",27*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xF0,0xFF,0x7F,0x20,0x00,0x00,0x06,0x00,0x00,0x1C,0x00,0x00,0x18,0x00,0x00,0x80,0xFF,0x03,0x88,0x10,0x01,0x88,0x10,0x01,0x88,0x10,0x01,0x88,0x10,0x01,0x88,0x10,0x01,0x88,0xFF,0x03,0x88,0x80,0x03,0x08,0x00,0x10,0x08,0x00,0x20,0x08,0x00,0x60,0x08,0x00,0x70,0xF8,0xFF,0x3F,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"间",28*/
+{0x00,0x00,0x00,0x00,0x02,0x08,0x00,0x02,0x18,0x00,0x02,0x08,0xFC,0xFF,0x0F,0xFC,0xFF,0x07,0x00,0x02,0x04,0x00,0x0A,0x02,0x00,0x0A,0x02,0x00,0x04,0x02,0xF0,0xFF,0x1F,0xE0,0xFF,0x3F,0x00,0x02,0x20,0x00,0x02,0x20,0x02,0x82,0x23,0xFE,0xFF,0x23,0x00,0x81,0x20,0x80,0x80,0x20,0x80,0x80,0x21,0xC0,0xFF,0x21,0x80,0x00,0x20,0x00,0x00,0x3F,0x00,0x00,0x10,0x00,0x00,0x00},/*"地",29*/
+{0x00,0x00,0x00,0x00,0x01,0x04,0x00,0x01,0x0C,0x00,0x01,0x04,0x00,0x01,0x04,0xFE,0xFF,0x03,0x00,0x01,0x02,0x00,0x01,0x21,0x80,0x01,0x21,0x00,0x01,0x20,0x00,0x00,0x20,0x00,0xFF,0x3F,0x00,0x01,0x20,0x00,0x00,0x20,0x00,0x00,0x20,0xFE,0xFF,0x3F,0xFC,0xFF,0x3F,0x00,0x04,0x20,0x00,0x04,0x20,0x00,0x04,0x20,0x00,0x06,0x30,0x00,0x04,0x20,0x00,0x00,0x00,0x00,0x00,0x00},/*"址",30*/
+{0x00,0x00,0x00,0x40,0x00,0x01,0x40,0xC0,0x00,0x40,0x38,0x00,0x40,0x0F,0x00,0xFE,0xFF,0x7F,0x40,0x02,0x00,0x40,0x0C,0x00,0x70,0x18,0x41,0x10,0x00,0x41,0x10,0x00,0x21,0x90,0x7F,0x21,0xFE,0x24,0x11,0xFC,0x24,0x0D,0x90,0xE4,0x07,0x90,0x64,0x01,0x90,0x24,0x07,0xFE,0x24,0x09,0x90,0x24,0x11,0x90,0x7F,0x31,0x90,0x00,0x21,0x10,0x00,0x21,0x00,0x00,0x20,0x00,0x00,0x00},/*"模",31*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x40,0x08,0x30,0x40,0x08,0x30,0x40,0x08,0x10,0x40,0x08,0x10,0x40,0x08,0x08,0x40,0xF8,0x0F,0x40,0x08,0x08,0x40,0x08,0x04,0x40,0x08,0x04,0x40,0x08,0x04,0x40,0x00,0x04,0xFE,0x01,0x00,0xFC,0x7F,0x00,0x40,0xE0,0x01,0x40,0x00,0x07,0x44,0x00,0x0C,0x58,0x00,0x18,0x78,0x00,0x30,0x60,0x00,0x30,0x40,0x00,0x7E,0x00,0x00,0x40,0x00,0x00,0x00},/*"式",32*/
+{0x00,0x00,0x00,0x00,0x10,0x00,0x00,0x08,0x00,0x00,0x06,0x00,0x80,0x01,0x00,0xE0,0xFF,0x7F,0x3C,0x00,0x00,0x06,0x10,0x20,0x00,0x10,0x10,0x00,0x10,0x08,0xF8,0x13,0x04,0x08,0x11,0x03,0x08,0xD1,0x01,0x08,0x71,0x00,0x08,0xFF,0x7F,0x08,0x11,0x30,0x08,0x71,0x00,0x08,0x91,0x00,0x08,0x11,0x03,0xF8,0x13,0x04,0x08,0x10,0x18,0x00,0x18,0x18,0x00,0x10,0x00,0x00,0x00,0x00},/*"保",33*/
+{0x00,0x00,0x00,0x00,0x00,0x01,0x10,0x80,0x00,0x10,0x40,0x00,0x10,0x20,0x00,0x10,0x18,0x00,0x10,0xFE,0x7F,0x10,0x03,0x00,0x90,0x41,0x00,0x70,0x40,0x00,0xBE,0x40,0x00,0x94,0x40,0x00,0x90,0x40,0x20,0x90,0x40,0x20,0x90,0x40,0x60,0x90,0xF8,0x3F,0x90,0x4C,0x00,0x90,0x42,0x00,0x90,0x41,0x00,0x90,0x41,0x00,0x18,0x40,0x00,0x10,0x40,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"存",34*/
+{0x00,0x00,0x00,0x00,0x02,0x08,0x00,0x02,0x18,0x04,0x02,0x04,0x18,0x02,0x04,0x30,0xFE,0x03,0x00,0x02,0x04,0x00,0x00,0x08,0x00,0x00,0x18,0x00,0x00,0x10,0xF8,0xFF,0x1F,0x48,0x04,0x36,0x48,0x04,0x32,0x48,0x04,0x31,0x48,0x24,0x31,0x48,0x44,0x30,0x48,0x44,0x30,0x48,0xA4,0x30,0xF8,0xA7,0x31,0x08,0x18,0x33,0x00,0x18,0x36,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x00},/*"退",35*/
+{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x20,0xE0,0x8F,0x3F,0xE0,0x8F,0x20,0x00,0x08,0x20,0x00,0x08,0x20,0x00,0x08,0x20,0x00,0x08,0x20,0x00,0x08,0x20,0xFC,0xFF,0x3F,0xF8,0xFF,0x3F,0x00,0x08,0x20,0x00,0x08,0x20,0x00,0x08,0x20,0x00,0x08,0x20,0x00,0x08,0x20,0xE0,0x1F,0x20,0x20,0x90,0x7F,0x00,0x80,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"出",36*/
+{0x00,0x00,0x00,0x08,0x00,0x02,0x08,0x00,0x06,0x08,0x00,0x06,0xF8,0xFF,0x03,0x88,0x10,0x02,0x88,0x10,0x02,0x88,0x10,0x01,0x88,0x10,0x01,0xF8,0xFF,0x7F,0x08,0x00,0x41,0x2C,0x80,0x20,0x20,0x80,0x10,0xE0,0x01,0x18,0x20,0x1E,0x0C,0x20,0xE0,0x02,0x20,0x80,0x01,0x20,0x70,0x06,0x20,0x1E,0x0C,0xE0,0x03,0x18,0x20,0x00,0x38,0x00,0x00,0x10,0x00,0x00,0x10,0x00,0x00,0x00},/*"取",37*/
+{0x00,0x00,0x00,0x80,0x00,0x00,0x00,0x01,0x01,0x00,0x07,0x01,0x0C,0x06,0x3F,0x38,0x80,0x7F,0x30,0x70,0x00,0x00,0x0E,0x00,0xC0,0x01,0x00,0x04,0x00,0x00,0x08,0xFF,0x7F,0x70,0x89,0x00,0x60,0x89,0x00,0x00,0x89,0x00,0x00,0x89,0x00,0xFE,0x89,0x00,0x00,0x89,0x20,0xC0,0x89,0x20,0x20,0x89,0x60,0x18,0xFF,0x3F,0x08,0x01,0x00,0x08,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"消",38*/
+{0x00,0x00,0x00,0x00,0x02,0x00,0x00,0x02,0x00,0x00,0x02,0x00,0x04,0x02,0x00,0x38,0xFE,0x1F,0x30,0x02,0x18,0x00,0x08,0x44,0x00,0x04,0x42,0x00,0x02,0x21,0x00,0x0B,0x20,0xFC,0x18,0x10,0x3C,0x68,0x10,0x04,0x88,0x09,0x04,0x08,0x0E,0x04,0x08,0x06,0x04,0x08,0x0B,0xFC,0xEB,0x18,0x08,0x7E,0x10,0x00,0x0A,0x30,0x00,0x02,0x20,0x00,0x02,0x20,0x00,0x02,0x00,0x00,0x00,0x00},/*"设",39*/
+{0x00,0x00,0x00,0x00,0x00,0x20,0x00,0x00,0x20,0x00,0x02,0x20,0xFC,0x02,0x20,0x44,0x02,0x20,0x44,0xFA,0x3F,0x44,0x4A,0x25,0x44,0x4A,0x25,0x7C,0x4A,0x25,0x44,0x4A,0x25,0xC4,0x4F,0x25,0x44,0x4A,0x25,0x44,0x4A,0x25,0x7C,0x4A,0x25,0x44,0x4A,0x25,0x44,0x4A,0x25,0x44,0xFE,0x3F,0x44,0x0A,0x20,0xFC,0x03,0x20,0x00,0x02,0x20,0x00,0x00,0x30,0x00,0x00,0x20,0x00,0x00,0x00},/*"置",40*/
+{0x00,0x00,0x00,0x00,0x08,0x00,0x08,0x08,0x40,0x08,0x08,0x20,0x08,0x08,0x10,0x08,0x08,0x18,0x08,0x08,0x0C,0x08,0x88,0x03,0xF8,0xFF,0x00,0x08,0x08,0x00,0x08,0x08,0x00,0x08,0x08,0x00,0x08,0x08,0x00,0x08,0x08,0x00,0x08,0x08,0x00,0xF8,0xFF,0x7F,0x08,0x08,0x00,0x08,0x08,0x00,0x08,0x08,0x00,0x0C,0x08,0x00,0x08,0x0C,0x00,0x00,0x08,0x00,0x00,0x00,0x00,0x00,0x00,0x00},/*"开",41*/
+{0x00,0x00,0x00,0x00,0x10,0x00,0x00,0x10,0x40,0x40,0x10,0x20,0x40,0x10,0x20,0x40,0x10,0x10,0x40,0x10,0x10,0x44,0x10,0x08,0x4C,0x10,0x04,0x78,0x10,0x03,0x40,0xD0,0x01,0xC0,0x7F,0x00,0xC0,0x13,0x00,0x40,0x70,0x00,0x70,0x90,0x01,0x4E,0x10,0x03,0x44,0x10,0x04,0x40,0x10,0x08,0x40,0x10,0x18,0x40,0x10,0x30,0x40,0x18,0x70,0x00,0x10,0x20,0x00,0x00,0x20,0x00,0x00,0x00},/*"关",42*/
+{0x00,0x00,0x00,0x00,0x00,0x20,0x00,0x00,0x20,0x80,0x00,0x20,0x80,0x00,0x20,0x80,0x40,0x20,0x80,0x40,0x20,0x80,0x40,0x20,0x80,0x40,0x20,0x84,0x40,0x20,0x88,0x40,0x20,0xB8,0xFF,0x3F,0xF0,0xFF,0x3F,0x80,0x40,0x20,0x80,0x40,0x20,0x80,0x40,0x20,0x80,0x40,0x20,0x80,0x40,0x20,0x80,0x60,0x20,0xC0,0x40,0x20,0x80,0x00,0x30,0x00,0x00,0x20,0x00,0x00,0x00,0x00,0x00,0x00},/*"主",43*/
+{0x00,0x00,0x00,0x00,0x00,0x20,0x00,0x00,0x10,0x00,0x00,0x08,0x00,0x00,0x06,0x00,0xC0,0x01,0x00,0x7F,0x00,0xFC,0x0F,0x40,0x08,0x10,0x20,0x00,0x60,0x10,0x00,0xC0,0x19,0x00,0x00,0x0C,0x00,0x00,0x03,0x00,0xE0,0x01,0xFC,0x7F,0x00,0xF8,0x03,0x00,0x00,0x3C,0x00,0x00,0xC0,0x01,0x00,0x00,0x07,0x00,0x00,0x0C,0x00,0x00,0x38,0x00,0x00,0x30,0x00,0x00,0x00,0x00,0x00,0x00},/*"从",44*/
+};
+
+static inline int utf8_chrlen(uint8_t *str)
+{
+    int len=-1;
+    uint8_t t=((*str)&0x80);
+
+    if(t==0) {
+        len = 1;
+    }
+    else {
+        t = ((*str)&0xf0);
+        if(t==0xc0) {
+            len = 2;
+        }
+        else if(t==0xe0) {
+            len = 3;
+        }
+        else if(t==0xf0) {
+            len = 4;
+        }
+        else {
+            len = -1;
+        }
+    }
+
+    return len;
+}
+static int utf8_strlen(uint8_t *str)
+{
+    int len = 0;
+    while (*str) {
+        if ((*str & 0x80) == 0) {
+            str++;
+        } else {
+            str++;
+            while ((*str & 0xC0) == 0x80) {
+                str++;
+            }
+        }
+        len++;
+    }
+    return len;
+}
+static int is_chinese(uint8_t *c)
+{
+    if (c[0] >= 0xE0 && c[0] <= 0xEF &&
+        c[1] >= 0x80 && c[1] <= 0xBF &&
+        c[2] >= 0x80 && c[2] <= 0xBF) {
+        return 1;
+    }
+    return 0;
+}
+static int chinese_index(uint8_t *s1, uint8_t *s2)
+{
+    uint8_t *p=s1;
+    int idx=0;
+
+    int chrlen = utf8_chrlen(s2);
+    if (chrlen == 0) {
+        return -1;
+    }
+    
+    while (*p) {
+        if (memcmp(p, s2, chrlen) != 0) {
+            p += chrlen;
+            idx++;
+        } else {
+            return idx;
+        }
+    }
+ 
+    return -1;
+}
+
+
+uint8_t* font_next(uint8_t *str)
+{
+    int len = utf8_chrlen(str);
+    if(len<=0) {
+        return (void*)0;
+    }
+    return str+len;
+}
+
+
+int font_width_str(int font, uint8_t *str)
+{
+    int w=0;
+    uint8_t *pstr=str;
+    font_data_t fdat;
+    while(*pstr) {
+        fdat = font_data(font, pstr);
+        w += fdat.width;
+        pstr = font_next(pstr);
+    }
+
+    return w;
+}
+
+
+font_data_t font_data(int font, uint8_t* c)
+{
+    int idx,chinese=0;
+    font_data_t tmp={0};
+    
+    chinese = is_chinese(c);
+    if(chinese) {
+        idx = chinese_index((uint8_t*)font_cn_str, c);
+    }
+    else {
+        idx = c[0]-32;
+    }
+
+    switch(font) {
+        
+        case FONT_08:
+        {
+            if(!chinese) {
+                tmp.data = (uint8_t*)font_en_0806[idx];
+                tmp.dlen = 6;
+                tmp.width = 6;
+                tmp.height = 8;
+            }
+        }
+        break;
+
+        case FONT_12:
+        {
+            if(chinese) {
+                tmp.data = (uint8_t*)font_cn_1212[idx];
+                tmp.dlen = 24;
+                tmp.width = 12;
+                tmp.height = 12;
+            }
+            else {
+                tmp.data = (uint8_t*)font_en_1206[idx];
+                tmp.dlen = 12;
+                tmp.width = 6;
+                tmp.height = 12;
+            }
+        }
+        break;
+        
+        case FONT_16:
+        {
+            if(chinese) {
+                tmp.data = (uint8_t*)font_cn_1616[idx];
+                tmp.dlen = 32;
+                tmp.width = 16;
+                tmp.height = 16;
+            }
+            else {
+                tmp.data = (uint8_t*)font_en_1608[idx];
+                tmp.dlen = 16;
+                tmp.width = 8;
+                tmp.height = 16;
+            }
+        }
+        break;
+        
+        case FONT_24:
+        {
+            if(chinese) {
+                tmp.data = (uint8_t*)font_cn_2424[idx];
+                tmp.dlen = 72;
+                tmp.width = 24;
+                tmp.height = 24;
+            }
+            else {
+                tmp.data = (uint8_t*)font_en_2412[idx];
+                tmp.dlen = 36;
+                tmp.width = 12;
+                tmp.height = 24;
+            }
+        }
+        break;
+    }
+    return tmp;
+}

+ 29 - 0
f407/applications/ui/font.h

@@ -0,0 +1,29 @@
+#ifndef __FONT_Hx__
+#define __FONT_Hx__
+
+#include <stdint.h>
+
+enum {
+    FONT_08=0,
+    FONT_12,
+    FONT_16,
+    FONT_24,
+    
+    FONT_MAX
+};
+
+
+typedef struct {
+    uint8_t width;
+    uint8_t height;
+    uint8_t *data;
+    uint32_t dlen;
+}font_data_t;
+
+
+uint8_t* font_next(uint8_t *str);
+int font_width_str(int font, uint8_t *str);
+font_data_t font_data(int font, uint8_t* c);
+
+#endif
+

+ 47 - 0
f407/applications/ui/gpio.c

@@ -0,0 +1,47 @@
+#include <string.h>
+#include <stdio.h>
+#include "gpio.h"
+#include "rtdbg.h"
+
+
+#if 1
+    #define LOGD  LOG_D
+    #define LOGE  LOG_E
+#else
+    #define LOGD  printf
+    #define LOGE  printf
+#endif
+
+
+
+int gpio_init(int gpio, int io, int hl)
+{
+    if(io==GPIO_IN) {
+        rt_pin_mode(gpio, PIN_MODE_OUTPUT);
+    }
+    else {
+        rt_pin_mode(gpio, PIN_MODE_OUTPUT);
+        rt_pin_write(gpio, (hl>0)?PIN_HIGH:PIN_LOW);
+    }
+    
+    return 0;
+}
+
+
+int gpio_deinit(int fd)
+{
+    return 0;
+}
+
+
+int gpio_set(int gpio, int hl)
+{
+    rt_pin_write(gpio, (hl>0)?PIN_HIGH:PIN_LOW);
+	return 0;
+}
+
+int gpio_get(int gpio)
+{
+    rt_ssize_t r = rt_pin_read(gpio);
+    return (r==PIN_HIGH)?1:0;
+}

+ 17 - 0
f407/applications/ui/gpio.h

@@ -0,0 +1,17 @@
+#ifndef __GPIO_Hx__
+#define __GPIO_Hx__
+
+#include <drv_gpio.h>
+
+enum {
+    GPIO_IN=0,
+    GPIO_OUT,
+};
+
+int gpio_init(int gpio, int io, int hl);
+int gpio_deinit(int fd);
+
+int gpio_get(int gpio);
+int gpio_set(int gpio, int hl);
+
+#endif

+ 174 - 0
f407/applications/ui/key.c

@@ -0,0 +1,174 @@
+#include <stdint.h>
+#include <stdio.h>
+#include <unistd.h>
+#include <sys/time.h>
+#include "key.h"
+#include "gpio.h"
+#include "rtdbg.h"
+
+
+#if 1
+    #define LOGD  LOG_D
+    #define LOGE  LOG_E
+#else
+    #define LOGD  printf
+    #define LOGE  printf
+#endif
+
+
+#define KEY_NUM             3
+#define KEY_LONG_TIME       500
+#define KEY_PRESS_LEVEL     0
+
+#define K1_GPIO             101     //PD5, K1
+#define K2_GPIO             102     //PD6, K2
+#define K3_GPIO             104     //PD8, K3
+
+
+typedef struct {
+    int      gpio;
+    uint16_t key;
+    uint8_t  active_level;
+}io_info_t;
+static io_info_t io_info[KEY_NUM]={
+    {K1_GPIO, KEY_OK,    KEY_PRESS_LEVEL},      //S2
+    {K2_GPIO, KEY_UP,    KEY_PRESS_LEVEL},      //S1
+    {K3_GPIO, KEY_DOWN,  KEY_PRESS_LEVEL},      //S3
+};
+
+typedef struct {
+    int         key;
+    uint64_t    ms;
+}key_info_t;
+typedef struct {
+    key_info_t  k1;
+    key_info_t  k2;
+    int         long_trigged;
+}key_data_t;
+typedef struct {
+    io_info_t   *io;
+    key_data_t  kd[KEY_NUM];
+}key_handle_t;
+static key_handle_t keyHandle={0};
+
+static uint64_t get_ms(void)
+{
+    struct timeval tv;
+    gettimeofday(&tv, NULL);
+    return (uint64_t)(tv.tv_sec)*1000 + (uint64_t)(tv.tv_usec)/1000;
+}
+
+///////////////////////////////////////////////////////////////
+
+int key_init(void)
+{
+    int i;
+    key_handle_t *h=&keyHandle;
+
+    h->io = io_info;
+    for(i=0; i<KEY_NUM; i++) {
+        gpio_init(io_info[i].gpio, GPIO_IN, 0);
+        h->kd[i].k1.key = -1;
+        h->kd[i].k1.ms = 0;
+
+        h->kd[i].k2 = h->kd[i].k1;
+        h->kd[i].long_trigged = 0;
+    }
+    return 0;
+}
+
+int key_deinit(void)
+{
+    int i;
+    key_handle_t *h=&keyHandle;
+
+    for(i=0; i<KEY_NUM; i++) {
+        gpio_deinit(io_info[i].gpio);
+    }
+    return 0;
+}
+
+
+int key_get(key_val_t *kv)
+{
+    int i,r;
+    key_val_t k;
+    uint64_t ms_max=0;
+    key_handle_t *h=&keyHandle;
+
+    if(!kv) {
+        return -1;
+    }
+
+    kv->key = -1;
+    for(i=0; i<KEY_NUM; i++) {
+        key_data_t *p=&h->kd[i];
+        key_info_t *p1=&p->k1;
+        key_info_t *p2=&p->k2;
+
+        r = gpio_get(h->io[i].gpio);
+        if(r==KEY_PRESS_LEVEL) {            //key pressed
+            if(p1->key==-1) {
+                p1->ms = get_ms();
+                p1->key = h->io[i].key;
+            }
+            else {
+                p2->ms = get_ms();
+                p2->key = h->io[i].key;
+
+#if 0
+                if(!p->long_trigged && p2->ms-p1->ms>=KEY_LONG_TIME) {
+                    *p1 = *p2;
+
+                    kv->type = TYPE_LONG;
+                    kv->key = p2->key;
+                    p->long_trigged = 1;
+                    return 0;
+                }
+#endif
+            }
+        }
+        else {     
+            if(p1->key>=0 && p2->key==-1) {
+                p2->ms = get_ms();
+                p2->key = h->io[i].key;
+            }
+                                     //key replease
+            if(p2->key>=0) {
+                kv->key = p2->key;
+                if(p2->ms-p1->ms<KEY_LONG_TIME) {
+                    kv->type = TYPE_SHORT;
+                }
+                else {
+                    kv->type = TYPE_LONG;
+                }
+                p1->key = p2->key = -1;
+                p->long_trigged = 0;
+                
+                return 0;
+            }
+        }
+    }
+    
+    return -1;
+}
+
+
+int key_print(key_val_t *kv)
+{
+    switch(kv->key) {
+        case KEY_UP:
+        printf("____ KEY_UP, %s\n", (kv->type==TYPE_LONG)?"LONG":"SHORT");
+        break;
+
+        case KEY_DOWN:
+        printf("____ KEY_DOWN, %s\n", (kv->type==TYPE_LONG)?"LONG":"SHORT");
+        break;
+
+        case KEY_OK:
+        printf("____ KEY_OK, %s\n", (kv->type==TYPE_LONG)?"LONG":"SHORT");
+        break;
+    }
+    return 0;
+}
+

+ 28 - 0
f407/applications/ui/key.h

@@ -0,0 +1,28 @@
+#ifndef __KEY_Hx__
+#define __KEY_Hx__
+
+enum {
+    KEY_UP=0,
+    KEY_DOWN,
+    KEY_OK,
+    
+    KEY_MAX,
+};
+
+enum {
+    TYPE_SHORT=0,
+    TYPE_LONG,
+};
+
+typedef struct {
+    int type;         //TYPE_SHORT TYPE_LONG
+    int key;
+}key_val_t;
+
+
+int key_init(void);
+int key_deinit(void);
+int key_get(key_val_t *kv);
+int key_print(key_val_t *kv);
+
+#endif

+ 77 - 0
f407/applications/ui/lang.c

@@ -0,0 +1,77 @@
+#include "lang.h"
+#include "datadef.h"
+#include "rtdbg.h"
+
+//--no-multibyte-chars
+//--locale=english
+
+#if 1
+    #define LOGD  LOG_D
+    #define LOGE  LOG_E
+#else
+    #define LOGD  printf
+    #define LOGE  printf
+#endif
+
+const char *lang_str_pool[2][STR_ID_MAX]={
+    {
+        "版本",     //STR_ID_VERSION
+        "时间",     //STR_ID_TIME
+        "地址",     //STR_ID_ADDR
+        "输入",     //STR_ID_INPUT
+        "输出",     //STR_ID_OUTPUT
+        "电压",     //STR_ID_VOLTAGE
+        "电流",     //STR_ID_CURRENT
+        "功率",     //STR_ID_POWER
+        "耗电量",   //STR_ID_CONSUMP
+        "因数",     //STR_ID_FACTOR
+        "开关",     //STR_ID_SWITCH
+        "温度",     //STR_ID_TEMP
+        "湿度",     //STR_ID_HUMI
+        "设置",     //STR_ID_SETT
+        "模式",     //STR_ID_MODE
+        "保存",     //STR_ID_SAVE
+        "退出",     //STR_ID_QUIT
+        "取消",     //STR_ID_CANCLE
+        "开",       //STR_ID_ON
+        "关",       //STR_ID_OFF
+        "主",       //STR_ID_MASTER
+        "从",       //STR_ID_SLAVE
+    },
+    
+    {
+        "Version",  //STR_ID_VERSION
+        "Time",     //STR_ID_TIME
+        "Addr",     //STR_ID_ADDR
+        "INPUT",    //STR_ID_INPUT
+        "OUTPUT",   //STR_ID_OUTPUT
+        "Volt",     //STR_ID_VOLTAGE
+        "Curr",     //STR_ID_CURRENT
+        "Power",    //STR_ID_POWER
+        "Consump",  //STR_ID_CONSUMP
+        "Factor",   //STR_ID_FACTOR
+        "Switch",   //STR_ID_SWITCH
+        "Temp",     //STR_ID_TEMP
+        "Humi",     //STR_ID_HUMI
+        "SETT",     //STR_ID_SETT
+        "Mode",     //STR_ID_MODE
+        "Save",     //STR_ID_SAVE
+        "Quit",     //STR_ID_QUIT
+        "Cancle",   //STR_ID_CANCLE
+        "On",       //STR_ID_ON
+        "Off",      //STR_ID_OFF
+        "Master",   //STR_ID_MASTER
+        "Slave",    //STR_ID_SLAVE
+    },
+};
+
+
+char* lang_get_str(int lang_id, int str_id)
+{
+    if(lang_id>=2 || str_id>=STR_ID_MAX) {
+        return 0;
+    }
+    
+    return (char*)lang_str_pool[lang_id][str_id];
+}
+

+ 34 - 0
f407/applications/ui/lang.h

@@ -0,0 +1,34 @@
+#ifndef __LANG_Hx__
+#define __LANG_Hx__
+
+enum {
+    STR_ID_VER=0,
+    STR_ID_TIME,
+    STR_ID_ADDR,
+    STR_ID_INPUT,
+    STR_ID_OUTPUT,
+    STR_ID_VOLTAGE,
+    STR_ID_CURRENT,
+    STR_ID_POWER,
+    STR_ID_CONSUMP,
+    STR_ID_FACTOR,
+    STR_ID_SWITCH,
+    STR_ID_TEMP,
+    STR_ID_HUMI,
+    STR_ID_SETT,
+    STR_ID_MODE,
+    STR_ID_SAVE,
+    STR_ID_QUIT,
+    STR_ID_CANCLE,
+    STR_ID_ON,
+    STR_ID_OFF,
+    STR_ID_MASTER,
+    STR_ID_SLAVE,
+    
+    
+    STR_ID_MAX,
+};
+
+char* lang_get_str(int lang_id, int str_id);
+
+#endif

+ 462 - 0
f407/applications/ui/lcd.c

@@ -0,0 +1,462 @@
+#include <stdio.h>
+#include <stdlib.h>
+#include <fcntl.h>
+#include <unistd.h>
+#include <string.h>
+#include "gpio.h"
+#include "lcd.h"
+#include "rtdbg.h"
+
+#define BK_GPIO             98      //PD2
+#define DC_GPIO             99      //PD3, 96+3=99
+#define RST_GPIO            100     //PD4, 96+4=100
+
+#if 1
+    #define LOGD  LOG_D
+    #define LOGE  LOG_E
+#else
+    #define LOGD  printf
+    #define LOGE  printf
+#endif
+
+#define BIT(x)              (1<<x)
+#define SWAP16(a)           ((uint16_t)((a<<8)|(a>>8)))
+
+
+#define DEV_PATH        "/dev/spidev1.0"
+
+
+
+typedef struct {
+    int  x;
+    int  y;
+    int  w;
+    int  h;
+}lcd_rect_t;
+typedef struct {
+    int         width;
+    int         height;
+    int         color;
+    int         rotate;
+
+    int         fd;
+    int         io;
+    uint8_t     *buf;
+
+    
+    int         buflen;
+}lcd_handle_t;
+static lcd_handle_t lcdHandle={0};
+static int ssd1309_init(lcd_handle_t *h);
+static void ssd1309_refresh(lcd_handle_t *h);
+
+static int lcd_hw_init(lcd_handle_t *h)
+{
+    h->fd = open(DEV_PATH, O_RDWR);
+    if (h->fd < 0) {
+        LOGE("___ open %s failed\n", DEV_PATH);
+        return -1;
+    }
+
+    gpio_init(DC_GPIO, GPIO_OUT, 0);
+    h->buflen = h->width*h->height/8;
+    h->buf = (uint8_t*)calloc(1, h->buflen);
+    if (!h->buf) {
+        LOGE("malloc buffer falied\n");
+        return -1;
+    }
+    
+    #if 0
+    uint8_t mode = SPI_MODE_0;
+    if (ioctl(fd, SPI_IOC_WR_MODE, &mode) == -1) {
+        LOGE("Can't set SPI mode\n");
+        return -1;
+    }
+    
+    uint32_t speed = 8000000;
+    if (ioctl(fd, SPI_IOC_WR_MAX_SPEED_HZ, &speed) == -1) {
+        LOGE("Can't set max speed\n");
+        return -1;
+    }
+    #endif
+    
+    ssd1309_init(h);
+
+    return 0;
+}
+static int lcd_hw_write(lcd_handle_t *h, void *data, int len)
+{
+    int r;
+    
+    
+    return 0;
+}
+static void lcd_write_reg(lcd_handle_t *h, uint8_t reg)
+{
+    gpio_set(DC_GPIO, 0);
+    lcd_hw_write(h, &reg, 1);
+}
+static int ssd1309_reset(void)
+{
+    gpio_init(RST_GPIO, GPIO_OUT, 0);
+    usleep(100*1000);
+    gpio_set(RST_GPIO, 1);
+    gpio_deinit(RST_GPIO);
+    return 0;
+}
+static void ssd1309_on(lcd_handle_t *h, int flag)
+{
+    if(flag) {
+        lcd_write_reg(h,0x8D);
+	    lcd_write_reg(h,0x14);
+	    lcd_write_reg(h,0xAF);
+    }
+    else {
+        lcd_write_reg(h,0x8D);
+	    lcd_write_reg(h,0x10);
+	    lcd_write_reg(h,0xAE);
+    }
+
+}
+static int ssd1309_init(lcd_handle_t *h)
+{
+    ssd1309_reset();
+
+    lcd_write_reg(h,0xFD);
+	lcd_write_reg(h,0x12);
+	lcd_write_reg(h,0xAE);//--turn off oled panel
+	lcd_write_reg(h,0xd5);//--set display clock divide ratio/oscillator frequency
+	lcd_write_reg(h,0xA0);
+	lcd_write_reg(h,0xA8);//--set multiplex ratio(1 to 64)
+	lcd_write_reg(h,0x3f);//--1/64 duty
+	lcd_write_reg(h,0xD3);//-set display offset	Shift Mapping RAM Counter (0x00~0x3F)
+	lcd_write_reg(h,0x00);//-not offset
+	lcd_write_reg(h,0x40);//--set start line address  Set Mapping RAM Display Start Line (0x00~0x3F)
+	lcd_write_reg(h,0xA1);//--Set SEG/Column Mapping     0xa0左右反置 0xa1正常
+	lcd_write_reg(h,0xC8);//Set COM/Row Scan Direction   0xc0上下反置 0xc8正常
+	lcd_write_reg(h,0xDA);//--set com pins hardware configuration
+	lcd_write_reg(h,0x12);
+	lcd_write_reg(h,0x81);//--set contrast control register
+	lcd_write_reg(h,0x7F);// Set SEG Output Current Brightness
+	lcd_write_reg(h,0xD9);//--set pre-charge period
+	lcd_write_reg(h,0x82);//Set Pre-Charge as 15 Clocks & Discharge as 1 Clock
+	lcd_write_reg(h,0xDB);//--set vcomh
+	lcd_write_reg(h,0x34);//Set VCOM Deselect Level
+	lcd_write_reg(h,0xA4);// Disable Entire Display On (0xa4/0xa5)
+	lcd_write_reg(h,0xA6);// Disable Inverse Display On (0xa6/a7)
+
+    ssd1309_refresh(h);
+    ssd1309_on(h,1);
+	
+	return 0;
+}
+static void ssd1309_refresh(lcd_handle_t *h)
+{
+	int i,n,offset;
+    
+	for(i=0;i<8;i++) {
+	   lcd_write_reg(h,0xb0+i); 			//设置行起始地址
+	   lcd_write_reg(h,0x00);   			//设置低列起始地址
+	   lcd_write_reg(h,0x10);   			//设置高列起始地址
+
+       gpio_set(DC_GPIO, 1);
+       offset = i*128;
+	   for(n=0;n<128;n++) {
+          lcd_hw_write(h, &h->buf[offset+n], 1);
+	   }
+  	}
+}
+static int lcd_hw_deinit(lcd_handle_t *h)
+{
+    gpio_deinit(DC_GPIO);
+    gpio_deinit(RST_GPIO);
+    
+    free(h->buf);
+    close(h->fd);
+    
+    return 0;
+}
+
+static inline int set_point(lcd_handle_t *h, int x, int y, int data)
+{
+    int pos,bit;
+
+    if(h->rotate==180) {
+        x = h->width-1-x;
+        y = h->height-1-y;
+    }
+
+    pos = y / 8;                                            /* get y page */
+    bit = y % 8;                                            /* get y point */
+    if (data) {                                             /* if 1  */
+        h->buf[pos*h->width+x] |= BIT(bit);         		/* set 1 */
+    }
+    else {
+        h->buf[pos*h->width+x] &= ~BIT(bit);        		/* set 0 */
+    }
+	
+	return 0;
+}
+static int get_color_bits(int color)
+{
+    if(color==COLOR_WB) {
+        return 1;
+    }
+    else if(color==COLOR_RGB8) {
+        return 8;
+    }
+    else if(color==COLOR_RGB565) {
+        return 16;
+    }
+    else {
+        return 32;
+    }
+}
+
+////////////////////////////////////////////////////////////
+void lcd_init(int width, int height, int color)
+{
+    lcd_handle_t *h=&lcdHandle;
+    h->width  = width;
+    h->height = height;
+    h->color  = color;
+    h->rotate = 0;
+
+    lcd_hw_init(h);
+}
+
+void lcd_deinit(void)
+{
+    lcd_handle_t *h=&lcdHandle;
+    lcd_hw_deinit(h);
+}
+
+
+void lcd_rotate(int rotate)
+{
+    lcd_handle_t *h=&lcdHandle;
+
+    if(rotate==0 || rotate==180) {
+        h->rotate = rotate;
+    }
+}
+
+
+int lcd_get_rotate(void)
+{
+    lcd_handle_t *h=&lcdHandle;
+    return h->rotate;
+}
+
+
+void lcd_set_backlight(int on)
+{
+    lcd_handle_t *h=&lcdHandle;
+}
+
+
+void lcd_fill(int color)
+{
+    lcd_handle_t *h=&lcdHandle;
+    
+    lcd_fill_rect(0, 0, h->width, h->height, color);
+}
+
+
+void lcd_draw_line(int x1, int y1, int x2, int y2, int color)
+{
+    int incx = 0, incy = 0;
+    int  delta_x = 0, delta_y = 0;
+    int  distance = 0;
+    int  t = 0;
+    int  x = 0, y = 0;
+    int  x_temp = 0, y_temp = 0;
+    lcd_handle_t *h=&lcdHandle;
+
+    /* 画斜线(Bresenham算法) */
+    delta_x = x2 - x1;
+    delta_y = y2 - y1;
+    if(delta_x > 0) {
+        //斜线(从左到右)
+        incx = 1;
+    }
+    else if(delta_x == 0) {
+        //垂直斜线(竖线)
+        incx = 0;
+    }
+    else {
+        //斜线(从右到左)
+        incx = -1;
+        delta_x = -delta_x;
+    }
+    
+    if(delta_y > 0) {
+        //斜线(从左到右)
+        incy = 1;
+    }
+    else if(delta_y == 0) {
+        //水平斜线(水平线)
+        incy = 0;
+    }
+    else {
+        //斜线(从右到左)
+        incy = -1;
+        delta_y = -delta_y;
+    }           
+    
+    /* 计算画笔打点距离(取两个间距中的最大值) */
+    if(delta_x > delta_y) {
+        distance = delta_x;
+    }
+    else {
+        distance = delta_y;
+    }
+    
+    /* 开始打点 */
+    x = x1;
+    y = y1;
+    //第一个点无效,所以t的次数加一
+    for(t = 0; t <= distance + 1;t++) {
+        set_point(h, x, y, color);
+    
+        /* 判断离实际值最近的像素点 */
+        x_temp += delta_x;  
+        if(x_temp > distance) {
+            //x方向越界,减去距离值,为下一次检测做准备
+            x_temp -= distance;     
+            //在x方向递增打点
+            x += incx;
+        }
+        y_temp += delta_y;
+        if(y_temp > distance) {
+            //y方向越界,减去距离值,为下一次检测做准备
+            y_temp -= distance;
+            //在y方向递增打点
+            y += incy;
+        }
+    }
+}
+
+
+
+void lcd_draw_rect(int x, int y, int w, int h, int color)
+{
+    int  x2,y2;
+
+    x2 = x + w;
+    y2 = y + h;
+    lcd_draw_line(x,y,x2,y,color);
+    lcd_draw_line(x,y,x,y2,color);
+    lcd_draw_line(x,y2,x2,y2,color);
+    lcd_draw_line(x,y,x2,y2,color);
+}
+
+
+void lcd_fill_rect(int x, int y, int w, int h, int color)
+{
+    int i,j;
+    lcd_handle_t *h2=&lcdHandle;
+
+    for(i=x; i<x+w; i++) {
+        for(j=y; j<y+h; j++) {
+            set_point(h2, i, j, color);
+        }
+    }
+}
+
+
+void lcd_refresh(void)
+{
+    lcd_handle_t *h=&lcdHandle;
+    ssd1309_refresh(h);
+}
+
+
+int lcd_draw_char(lcd_handle_t *hd, int x, int y, int w, int h, uint8_t *c, int font, int color, int bgcolor, int vert)
+{
+    uint8_t tmp;
+    font_data_t fdata;
+    int i,j,x0=x,y0=y,x1=x+w,y1=y+h;
+    
+    fdata = font_data(font, c);
+    if(h>fdata.height) {
+        if(vert==VERTICAL_CENTER) {
+            y0 += (h-fdata.height)/2;
+        }
+        else if (vert==VERTICAL_BOTTOM) {
+            y0 += h-fdata.height;
+        }
+        y = y0;
+    }
+    
+    for(i=0; i<fdata.dlen; i++)  {
+        tmp = fdata.data[i];
+        for(j=0; j<8; j++)  {
+            if((x<x1 && x<hd->width) && (y<y1 && y<hd->height)) 
+            {
+                if(tmp&0x01) {
+                    set_point(hd, x, y, color);
+                }
+                else {
+                    set_point(hd, x, y, bgcolor);
+                }
+            }
+            tmp >>= 1;
+            y++;
+
+            if((y-y0)>=fdata.height) {
+                y=y0; x++;
+                break;
+            }
+        }
+    }
+
+    return fdata.width;
+}
+
+
+void lcd_draw_string(int x, int y, int w, int h, char *str, int font, int color, int bgcolor, int hori, int vert)
+{
+    int r,sw,xmax=x+w;
+    lcd_rect_t rect;
+    uint8_t *pstr=(uint8_t*)str;
+    lcd_handle_t *h2=&lcdHandle;
+
+   sw = font_width_str(font, pstr);
+    if(sw>w) {
+        sw = w;
+    }
+    
+    if(hori==HORIZONTAL_LEFT) {
+        rect.x = x;
+    }
+    else if(hori==HORIZONTAL_RIGHT) {
+        rect.x = x+w-sw;
+    }
+    else if(hori==HORIZONTAL_CENTER) {
+        rect.x = x+(w-sw)/2;
+    }
+    else {
+        return;
+    }
+    
+    if(rect.x+sw>=h2->width) {
+        rect.w = h2->width-rect.x;
+    }
+    else {
+        rect.w = sw;
+    }
+    rect.y = y;
+    rect.h = h;
+
+    while(*pstr)  {
+        r = lcd_draw_char(h2, rect.x, rect.y, rect.w, rect.h, pstr, font, color, bgcolor, vert);
+        rect.x += r;
+        pstr = font_next(pstr);
+        if(!pstr || x>=xmax) {
+            break;
+        }
+    }
+}
+
+

+ 78 - 0
f407/applications/ui/lcd.h

@@ -0,0 +1,78 @@
+#ifndef __LCD_Hx__
+#define __LCD_Hx__
+
+#include "font.h"
+
+#define LCD_COLOR   COLOR_WB
+#define LCD_WIDTH   128
+#define LCD_HEIGHT  64
+
+/* 颜色 */
+#if (LCD_COLOR==COLOR_WB)
+    #define COLOR_WHITE         	 1
+    #define COLOR_BLACK         	 0	  
+#elif (LCD_COLOR==COLOR_RGB565)
+    #define COLOR_WHITE         	 0xFFFF
+    #define COLOR_BLACK         	 0x0000	  
+    #define COLOR_BLUE               0x001F  
+    #define COLOR_BRED               0XF81F
+    #define COLOR_GRED               0XFFE0
+    #define COLOR_GBLUE              0X07FF
+    #define COLOR_RED           	 0xF800
+    #define COLOR_MAGENTA       	 0xF81F
+    #define COLOR_GREEN         	 0x07E0
+    #define COLOR_CYAN          	 0x7FFF
+    #define COLOR_YELLOW        	 0xFFE0
+    #define COLOR_BROWN 			 0XBC40
+    #define COLOR_BRRED 			 0XFC07
+    #define COLOR_GRAY  			 0X8430
+#elif (LCD_COLOR==COLOR_RGB666)
+    
+#elif (LCD_COLOR==COLOR_RGB888)
+
+#else
+
+
+#endif
+
+
+enum {
+    HORIZONTAL_LEFT=0,
+    HORIZONTAL_CENTER,
+    HORIZONTAL_RIGHT,
+};
+
+enum {
+    VERTICAL_TOP=0,
+    VERTICAL_CENTER,
+    VERTICAL_BOTTOM,
+};
+
+enum {
+    COLOR_WB=0,
+    COLOR_RGB8,
+    COLOR_RGB565,
+    COLOR_RGB666,
+    COLOR_RGB888,
+    COLOR_RGBA,
+};
+
+
+void lcd_init(int width, int height, int color);
+void lcd_deinit(void);
+
+void lcd_rotate(int angle);
+int lcd_get_rotate(void);
+void lcd_set_backlight(int on);
+void lcd_fill(int color);
+void lcd_draw_line(int x1, int y1, int x2, int y2, int color);
+void lcd_draw_rect(int x1, int y1, int w, int h, int color);
+void lcd_fill_rect(int x1, int y1, int w, int h, int color);
+
+void lcd_draw_string(int x, int y, int width, int height, char *str, int font, int color, int bgcolor, int hori, int vert);
+void lcd_refresh(void);
+#endif
+
+
+
+

+ 193 - 0
f407/applications/ui/led.c

@@ -0,0 +1,193 @@
+#include "led.h"
+#include "timer.h"
+#include "gpio.h"
+#include "paras.h"
+#include "rtdbg.h"
+
+
+#if 1
+    #define LOGD  LOG_D
+    #define LOGE  LOG_E
+#else
+    #define LOGD  printf
+    #define LOGE  printf
+#endif
+
+
+#ifdef BOARD_EVB_ATK
+    #define LEDR_GPIO    GET_PIN(F, 9)
+    #define LEDG_GPIO    GET_PIN(F, 10)
+#else
+    #define LEDR_GPIO    GET_PIN(E, 6)
+    #define LEDG_GPIO    -1
+#endif
+
+
+typedef struct {
+    int         gpio;
+    int         on_level;
+    int         off_level;
+}led_info_t;
+static led_info_t led_info[LED_ID_MAX]={
+    {LEDR_GPIO, 0, 1},
+    {LEDG_GPIO, 0, 1},
+};
+typedef struct {
+    int         io;
+    led_para_t  para;
+    led_info_t  *info;
+    uint32_t    cnt;
+    int         tmr;
+}led_data_t;
+typedef struct {
+    int         tmr;
+    int         mode;
+    led_data_t  data[LED_ID_MAX];
+}led_handle_t;
+
+static led_para_t led_para[LED_MODE_MAX]={
+#if 0
+    {LED_ID_GREEN,  1000,0,     -1,   0},     //LED_MODE_NORMAL
+    {LED_ID_GREEN,  300, 300,   -1,   0},     //LED_MODE_UPGRADING
+    {LED_ID_RED,    1000, 1000,  5,   0},     //LED_MODE_WARN1,
+    {LED_ID_RED,    1000, 1000,  10,  0},     //LED_MODE_WARN2,
+    {LED_ID_RED,    500, 500,    10,  0},     //LED_MODE_ERROR,
+    {LED_ID_RED,    200, 200,    25,  0},     //LED_MODE_FAULT
+    {LED_ID_RED,    50,  50,     -1,  0},     //LED_MODE_FATAL
+#else
+    {LED_ID_RED,   0,   1000, -1, 0},      //LED_MODE_NORMAL
+    {LED_ID_RED,   300, 1000,  -1, 0},     //LED_MODE_UPGRADING
+    {LED_ID_RED,   500, 500,  300,  0},    //LED_MODE_WARN1,
+    {LED_ID_RED,   333, 333,  450,  0},    //LED_MODE_WARN2,
+    {LED_ID_RED,   500, 500,  10, 0},      //LED_MODE_ERROR,
+    {LED_ID_RED,   200, 200,  25, 0},      //LED_MODE_FAULT
+    {LED_ID_RED,   50,  50,   -1, 0},      //LED_MODE_FATAL
+#endif
+};
+static led_handle_t ledHandle={0};
+
+
+static void led_handler(void *arg, int last)
+{
+    int level;
+    led_data_t *h=(led_data_t*)arg;
+    
+    if(h->para.on_ms>0 && h->para.off_ms) {
+        h->cnt++;
+        if(h->cnt%2) {
+            gpio_set(h->io, h->info->off_level);
+        }
+        else {
+            gpio_set(h->io, h->info->on_level);
+        }
+    }
+    
+    if(last) {
+        timer_stop(h->tmr);
+        if(h->para.end_on) {
+            gpio_set(h->io, h->info->on_level);
+        }
+        else {
+            gpio_set(h->io, h->info->off_level);
+        }
+
+        led_set(LED_MODE_NORMAL);
+    } 
+}
+//////////////////////////////////////////////////
+int led_init(void)
+{
+    int i;
+    led_handle_t *h=&ledHandle;
+    
+    h->tmr = timer_init();
+    for(i=0; i<LED_ID_MAX; i++) {
+        h->data[i].info = &led_info[i];
+        h->data[i].cnt = 0;
+        h->data[i].tmr = h->tmr;
+        h->data[i].io = led_info[i].gpio;
+        gpio_init(h->data[i].io, GPIO_OUT, led_info[i].off_level);
+    }
+    h->mode = -1;
+    
+    //led_set(LED_MODE_UPGRADING);
+    
+    return 0;
+}
+
+
+int led_deinit(void)
+{
+    int i;
+    led_handle_t *h=&ledHandle;
+    
+    timer_deinit(h->tmr);
+    for(i=0; i<LED_ID_MAX; i++) {
+        gpio_deinit(h->data[i].io);
+        h->data[i].io = -1;
+    }
+    return 0;
+}
+
+
+int led_set(int mode)
+{
+    led_handle_t *h=&ledHandle;
+
+    h->mode = mode;
+    return led_set_ex(&led_para[h->mode]);
+}
+
+
+int led_set_ex(led_para_t *para)
+{
+    int r=0;
+    led_handle_t *h=&ledHandle;
+    misc_data_t *misc=&paras_get()->misc;
+    
+    if(!misc->led || !para || (para->on_ms<=0 && para->off_ms<=0) || para->times==0) {
+        return -1;
+    }
+    led_data_t *ld=&h->data[para->led_id];
+    
+    ld->cnt = 0;
+    ld->para = *para;
+    if(ld->para.on_ms>0) {
+        gpio_set(ld->io, ld->info->on_level);
+        if(ld->para.off_ms>0) {
+            ld->para.times *= 2;
+        }
+        else {
+            ld->para.on_ms *= ld->para.times;
+            ld->para.times = 1;
+        }
+        r = timer_start(h->tmr, ld->para.on_ms, ld->para.times, led_handler, ld);
+    }
+    else {
+        gpio_set(ld->io, ld->info->on_level);
+        if(ld->para.off_ms>0) {
+            ld->para.off_ms *= ld->para.times;
+            ld->para.times = 1;
+            r = timer_start(h->tmr, ld->para.off_ms, ld->para.times, led_handler, ld);
+        }
+    }
+    
+    return r;
+}
+
+
+int led_reset(void)
+{
+    led_handle_t *h=&ledHandle;
+
+    if(h->mode==-1) {
+        return -1;
+    }
+
+    h->mode = -1;
+    timer_stop(h->tmr);
+    gpio_set(h->data[LED_ID_RED].io, led_info[LED_ID_RED].off_level);
+    return 0;
+}
+
+

+ 38 - 0
f407/applications/ui/led.h

@@ -0,0 +1,38 @@
+#ifndef __LED_Hx__
+#define __LED_Hx__
+
+
+enum {
+    LED_ID_RED=0,
+    LED_ID_GREEN,
+    
+    LED_ID_MAX
+};
+
+enum {
+    LED_MODE_NORMAL=0,
+    LED_MODE_UPGRADING,
+    LED_MODE_WARN1,
+    LED_MODE_WARN2,
+    LED_MODE_ERROR,
+    LED_MODE_FAULT,
+    LED_MODE_FATAL,
+    
+    LED_MODE_MAX
+};
+
+typedef struct {
+    int led_id;
+    int on_ms;
+    int off_ms;
+    int times;
+    int end_on;
+}led_para_t;
+
+int led_init(void);
+int led_deinit(void);
+int led_set(int mode);
+int led_set_ex(led_para_t *para);
+int led_reset(void);
+
+#endif

+ 762 - 0
f407/applications/ui/menu.c

@@ -0,0 +1,762 @@
+#include <string.h>
+#include <unistd.h>
+#include "menu.h"
+#include "lcd.h"
+#include "led.h"
+#include "beep.h"
+#include "paras.h"
+#include "rtdbg.h"
+#include "thread.h"
+#include "lang.h"
+#include "timer.h"
+#include "cfg.h"
+
+#define REFRESH_TIME   300
+//#define TEXT_ALIGN
+
+#if 1
+    #define LOGD  LOG_D
+    #define LOGE  LOG_E
+#else
+    #define LOGD  printf
+    #define LOGE  printf
+#endif
+
+enum {
+    MENU_SYSTEM=0,
+    MENU_INPUT,
+    MENU_OUTPUT,
+    MENU_SENSOR,
+    MENU_MODBUS,
+
+    MENU_MAX
+};
+enum {
+    MODBUS_ITEM_ADDR=0,
+    MODBUS_ITEM_MODE,
+    MODBUS_ITEM_SAVE,
+    MODBUS_ITEM_QUIT,
+
+    MODBUS_ITEM_MAX
+};
+enum {
+    UFLAG_KEY=(1<<0),
+    UFLAG_FLIP=(1<<1),
+    UFLAG_TIMER=(1<<2),
+    UFLAG_REFRESH=(1<<3),
+};
+
+typedef struct {
+    int menu_id;
+    int item_id;
+    int item_max;
+}page_data_t;
+typedef struct {
+    int menu_id;
+    int menu_lv;    //level
+    page_data_t page[MENU_MAX];
+}menu_data_t;
+typedef struct {
+    int         fd;
+    int         tmr;
+    int         lang;
+
+    int         ph_in;
+    int         ph_out;
+    int         ch_out;
+    int         ch_out_max;
+    menu_data_t menu;
+    
+    uint64_t    flip_ms;
+    uint64_t    refresh_ms;
+
+    uint16_t    uflag;
+    int         fliptime;
+
+    modbus_data_t mb;
+}menu_handle_t;
+static int lang_id=LANG_ID_CHINESE;
+//static int lang_id=LANG_ID_ENGLISH;
+static menu_handle_t mnHandle={0};
+
+
+
+static uint64_t get_ms(void)
+{
+    struct timeval tv;
+    gettimeofday(&tv, NULL);
+    return (uint64_t)(tv.tv_sec)*1000 + (uint64_t)(tv.tv_usec)/1000;
+}
+static modbus_data_t*get_pmb(menu_handle_t *h)
+{
+    if(h->menu.menu_lv==0) {
+        return &paras_get()->cas;
+    }
+    else {
+        return &h->mb;
+    }
+}
+
+static int get_ch_out_max(menu_handle_t *h)
+{
+    int ch=0;
+    paras_data_t *p=paras_get();
+    
+    return ch;
+}
+static int is_ph3_in(menu_handle_t *h)
+{
+    paras_data_t *p=paras_get();
+    
+    if ((p->prod.pwr_type == PDU_AC_I3O3 ||
+         p->prod.pwr_type == PDU_AC_I3O1  ||
+         p->prod.pwr_type == PDU_AC_I3O3_H)) {
+        return 1;
+    }
+    return 0;
+}
+static int is_ph3_out(menu_handle_t *h)
+{
+    paras_data_t *p=paras_get();
+    if (p->prod.pwr_type == PDU_AC_I3O3) {
+        return 1;
+    }
+    return 0;
+}
+static int get_input(menu_handle_t *h, int ph, power_t *power)
+{
+    int i=0;
+    power_ch_t *pch=NULL;
+
+    if (is_ph3_in(h) && ph>0) {
+        
+    }
+    else {
+        //*pwr = h->dm->_globalPowerManger._PowerInfo;
+    }
+    return 0;
+}
+static int get_output(menu_handle_t *h, int ch, int ph, power_t *power)
+{
+    int i=-1,j=0;
+    
+
+    return -1;
+}
+static void refresh_handler(void *arg, int last)
+{
+    menu_handle_t *h=(menu_handle_t*)arg;
+    h->uflag |= UFLAG_TIMER;
+    
+    if(last) {
+        timer_stop(h->tmr);
+    }
+}
+static void tmr_start(menu_handle_t *h, int ms)
+{
+    if(h->tmr!=-1) {
+        timer_stop(h->tmr);
+    }
+    timer_start(h->tmr, ms, -1, refresh_handler, h);
+}
+static void tmr_stop(menu_handle_t *h)
+{
+    timer_stop(h->tmr);
+    h->tmr = -1;
+}
+
+static void menu_system_paint(menu_handle_t *h, int font1, int font2, int item_h, key_val_t *kv)
+{
+    char time[60],tmp[100];
+
+    lcd_fill(0);
+    sprintf(tmp, "SmartPDU");
+    lcd_draw_string(0, 0, LCD_WIDTH, item_h, tmp, font1, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_CENTER, VERTICAL_CENTER);
+
+    sprintf(tmp, "%s:%s", lang_get_str(h->lang, STR_ID_VER), VERSION);
+    lcd_draw_string(0, item_h, LCD_WIDTH, item_h, tmp, font2, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_LEFT, VERTICAL_CENTER);
+
+    //get_curtime_str2(time, sizeof(time));
+    sprintf(tmp, "%s:%s", lang_get_str(h->lang, STR_ID_TIME), time);
+    lcd_draw_string(0, item_h*2, LCD_WIDTH, item_h, tmp, font2, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_LEFT, VERTICAL_CENTER);
+
+    //sprintf(tmp, "IP:%s", getLocalIpAddress("eth0"));
+    lcd_draw_string(0, item_h*3, LCD_WIDTH, item_h, tmp, font2, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_LEFT, VERTICAL_CENTER);
+    lcd_refresh();
+}
+static void menu_input_paint(menu_handle_t *h, int font1, int font2, int item_h, key_val_t *kv)
+{
+    int r;
+    char tmp[100];
+    power_t *pwr,info={0};
+
+    pwr = &info;
+    sprintf(tmp, "%s", lang_get_str(h->lang, STR_ID_INPUT));
+
+    r = get_input(h, h->ph_in, &info);
+    if(r==0) {
+        if(h->menu.menu_lv==1 && h->ph_in>0) {
+            sprintf(tmp, "%s-L%d", lang_get_str(h->lang, STR_ID_INPUT), h->ph_in);
+        }
+    }
+
+    lcd_fill(0);
+    lcd_draw_string(0, 0, LCD_WIDTH, item_h, tmp, font1, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_CENTER, VERTICAL_CENTER);
+
+#ifdef TEXT_ALIGN
+    sprintf(tmp, "%s:%0.2f", lang_get_str(h->lang, STR_ID_VOLTAGE), pwr->voltage);
+    lcd_draw_string(0, item_h, LCD_WIDTH/2, item_h, tmp, font2, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_LEFT, VERTICAL_CENTER);
+    sprintf(tmp, "%s:%0.2f", lang_get_str(h->lang, STR_ID_CURRENT), pwr->current);
+    lcd_draw_string(LCD_WIDTH/2, item_h, LCD_WIDTH/2, item_h, tmp, font2, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_LEFT, VERTICAL_CENTER);
+
+    sprintf(tmp, "%s:%0.2f", lang_get_str(h->lang, STR_ID_POWER), pwr->power);
+    lcd_draw_string(0, item_h*2, LCD_WIDTH/2, item_h, tmp, font2, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_LEFT, VERTICAL_CENTER);
+    sprintf(tmp, "%s:%0.2f", lang_get_str(h->lang, STR_ID_FACTOR), pwr->factor);
+    lcd_draw_string(LCD_WIDTH/2, item_h*2, LCD_WIDTH/2, item_h, tmp, font2, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_LEFT, VERTICAL_CENTER);
+#else
+    sprintf(tmp, "%s:%0.2f %s:%0.2f", lang_get_str(h->lang, STR_ID_VOLTAGE), pwr->voltage, lang_get_str(h->lang, STR_ID_CURRENT), pwr->current);
+    lcd_draw_string(0, item_h, LCD_WIDTH, item_h, tmp, font2, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_LEFT, VERTICAL_CENTER);
+
+    sprintf(tmp, "%s:%0.2f %s:%0.2f", lang_get_str(h->lang, STR_ID_POWER), pwr->power, lang_get_str(h->lang, STR_ID_FACTOR), pwr->factor);
+    lcd_draw_string(0, item_h*2, LCD_WIDTH, item_h, tmp, font2, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_LEFT, VERTICAL_CENTER);
+#endif
+    sprintf(tmp, "%s:%0.2f", lang_get_str(h->lang, STR_ID_CONSUMP), pwr->consump);
+    lcd_draw_string(0, item_h*3, LCD_WIDTH, item_h, tmp, font2, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_LEFT, VERTICAL_CENTER);
+
+    lcd_refresh();
+    
+}
+static void menu_output_paint(menu_handle_t *h, int font1, int font2, int item_h, key_val_t *kv)
+{
+    int r;
+    char tmp[100];
+    power_t *pwr,info={0};
+
+    pwr = &info;
+    sprintf(tmp, "%s", lang_get_str(h->lang, STR_ID_OUTPUT));
+
+    r = get_output(h, h->ch_out, h->ph_out, &info);
+    if(r==0 && h->ch_out_max>0) {
+        sprintf(tmp, "%s CH%d", lang_get_str(h->lang, STR_ID_OUTPUT), h->ch_out+1);
+    }
+
+    lcd_fill(0);
+    lcd_draw_string(0, 0, LCD_WIDTH, item_h, tmp, font1, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_CENTER, VERTICAL_CENTER);
+
+    char *pon=((pwr->status)?lang_get_str(h->lang, STR_ID_ON):lang_get_str(h->lang, STR_ID_OFF));
+#ifdef TEXT_ALIGN
+    sprintf(tmp, "%s:%s", lang_get_str(h->lang, STR_ID_SWITCH), pon);
+    lcd_draw_string(0, item_h, LCD_WIDTH/2, item_h, tmp, font2, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_LEFT, VERTICAL_CENTER);
+    sprintf(tmp, "%s:%0.2f", lang_get_str(h->lang, STR_ID_CURRENT), pwr->current);
+    lcd_draw_string(LCD_WIDTH/2, item_h, LCD_WIDTH/2, item_h, tmp, font2, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_LEFT, VERTICAL_CENTER);
+
+    sprintf(tmp, "%s:%0.2f ", lang_get_str(h->lang, STR_ID_POWER), pwr->power);
+    lcd_draw_string(0, item_h*2, LCD_WIDTH/2, item_h, tmp, font2, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_LEFT, VERTICAL_CENTER);
+    sprintf(tmp, "%s:%0.2f", lang_get_str(h->lang, STR_ID_FACTOR), pwr->factor);
+    lcd_draw_string(LCD_WIDTH/2, item_h*2, LCD_WIDTH/2, item_h, tmp, font2, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_LEFT, VERTICAL_CENTER);
+#else
+    sprintf(tmp, "%s:%s  %s:%0.2f", lang_get_str(h->lang, STR_ID_SWITCH), pon, lang_get_str(h->lang, STR_ID_CURRENT), pwr->current);
+    lcd_draw_string(0, item_h, LCD_WIDTH, item_h, tmp, font2, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_LEFT, VERTICAL_CENTER);
+
+    sprintf(tmp, "%s:%0.2f %s:%0.2f", lang_get_str(h->lang, STR_ID_POWER), pwr->power, lang_get_str(h->lang, STR_ID_FACTOR), pwr->factor);
+    lcd_draw_string(0, item_h*2, LCD_WIDTH, item_h, tmp, font2, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_LEFT, VERTICAL_CENTER);
+#endif
+    sprintf(tmp, "%s:%0.2f", lang_get_str(h->lang, STR_ID_CONSUMP), pwr->consump);
+    lcd_draw_string(0, item_h*3, LCD_WIDTH, item_h, tmp, font2, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_LEFT, VERTICAL_CENTER);
+
+    lcd_refresh();
+    
+}
+static void menu_sensor_paint(menu_handle_t *h, int font1, int font2, int item_h, key_val_t *kv)
+{
+    char tmp[100];
+
+    lcd_fill(0);
+    sprintf(tmp, "%s/%s", lang_get_str(h->lang, STR_ID_TEMP), lang_get_str(h->lang, STR_ID_HUMI));
+    lcd_draw_string(0, 0, LCD_WIDTH, item_h, tmp, font1, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_CENTER, VERTICAL_CENTER);
+
+#ifdef TEXT_ALIGN
+    sprintf(tmp, "%s:", lang_get_str(h->lang, STR_ID_TEMP));
+    lcd_draw_string(0, item_h, LCD_WIDTH/2, item_h, tmp, font2, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_LEFT, VERTICAL_CENTER);
+    sprintf(tmp, "%0.1f", dm->g_modebus_read.temprature/100.0f);
+    lcd_draw_string(LCD_WIDTH/2, item_h, LCD_WIDTH/2, item_h, tmp, font2, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_LEFT, VERTICAL_CENTER);
+
+    sprintf(tmp, "%s:", lang_get_str(h->lang, STR_ID_HUMI));
+    lcd_draw_string(0, item_h*2, LCD_WIDTH/2, item_h, tmp, font2, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_LEFT, VERTICAL_CENTER);
+    sprintf(tmp, "%0.1f", dm->g_modebus_read.humidity/100.0f);
+    lcd_draw_string(LCD_WIDTH/2, item_h*2, LCD_WIDTH/2, item_h, tmp, font2, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_LEFT, VERTICAL_CENTER);
+#else
+    //sprintf(tmp, " %s: %0.1f", lang_get_str(h->lang, STR_ID_TEMP), h->dm->g_modebus_read.temprature/100.0f);
+    lcd_draw_string(0, item_h, LCD_WIDTH, item_h, tmp, font2, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_LEFT, VERTICAL_CENTER);
+
+    //sprintf(tmp, " %s: %0.1f%%", lang_get_str(h->lang, STR_ID_HUMI), h->dm->g_modebus_read.humidity/100.0f);
+    lcd_draw_string(0, item_h*2, LCD_WIDTH, item_h, tmp, font2, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_LEFT, VERTICAL_CENTER);
+#endif
+
+    lcd_refresh();
+    
+}
+static void menu_modbus_paint(menu_handle_t *h, int font1, int font2, int item_h, key_val_t *kv)
+{
+    int r,font_color;
+    char tmp[100];
+    modbus_data_t *pmb=get_pmb(h);
+    static uint8_t flash_cnt=0;
+    
+    if(h->uflag&UFLAG_TIMER) {
+        flash_cnt++;
+    }
+
+    lcd_fill(0);
+
+    sprintf(tmp, "MODBUS %s", lang_get_str(h->lang, STR_ID_SETT));
+    lcd_draw_string(0, 0, LCD_WIDTH, item_h, tmp, font1, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_CENTER, VERTICAL_CENTER);
+
+    font_color = COLOR_WHITE;
+    if(h->menu.menu_lv && h->menu.page[h->menu.menu_id].item_id==MODBUS_ITEM_ADDR) {
+        if(h->uflag&UFLAG_TIMER && h->menu.menu_lv==2) {
+            font_color = (flash_cnt%2)?COLOR_WHITE:COLOR_BLACK;
+        }
+        sprintf(tmp, ">%s:", lang_get_str(h->lang, STR_ID_ADDR));
+    }
+    else {
+        sprintf(tmp, " %s:", lang_get_str(h->lang, STR_ID_ADDR));
+    }
+    lcd_draw_string(0, item_h, LCD_WIDTH/2, item_h, tmp, font2, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_LEFT, VERTICAL_CENTER);
+    sprintf(tmp, "%d", pmb->addr);
+    lcd_draw_string(LCD_WIDTH/2, item_h, LCD_WIDTH/2, item_h, tmp, font2, font_color, COLOR_BLACK, HORIZONTAL_LEFT, VERTICAL_CENTER);
+
+    font_color = COLOR_WHITE;
+    if(h->menu.menu_lv && h->menu.page[h->menu.menu_id].item_id==MODBUS_ITEM_MODE) {
+        if(h->uflag&UFLAG_TIMER && h->menu.menu_lv==2) {
+            font_color = (flash_cnt%2)?COLOR_WHITE:COLOR_BLACK;
+        }
+        sprintf(tmp, ">%s:", lang_get_str(h->lang, STR_ID_MODE));
+    }
+    else {
+        sprintf(tmp, " %s:", lang_get_str(h->lang, STR_ID_MODE));
+    }
+    lcd_draw_string(0, item_h*2, LCD_WIDTH/2, item_h, tmp, font2, COLOR_WHITE, COLOR_BLACK, HORIZONTAL_LEFT, VERTICAL_CENTER);
+    sprintf(tmp, "%s", (pmb->mode==MODBUS_MASTER)?lang_get_str(h->lang, STR_ID_MASTER):lang_get_str(h->lang, STR_ID_SLAVE));
+    lcd_draw_string(LCD_WIDTH/2, item_h*2, LCD_WIDTH/2, item_h, tmp, font2, font_color, COLOR_BLACK, HORIZONTAL_LEFT, VERTICAL_CENTER);
+
+    font_color = COLOR_WHITE;
+    if(h->menu.menu_lv && h->menu.page[h->menu.menu_id].item_id==MODBUS_ITEM_SAVE) {
+        sprintf(tmp, ">%s", lang_get_str(h->lang, STR_ID_SAVE));
+    }
+    else {
+        sprintf(tmp, " %s", lang_get_str(h->lang, STR_ID_SAVE));
+    }
+    lcd_draw_string(0, item_h*3, LCD_WIDTH/2, item_h, tmp, font2, font_color, COLOR_BLACK, HORIZONTAL_CENTER, VERTICAL_CENTER);
+    
+    font_color = COLOR_WHITE;
+    if(h->menu.menu_lv && h->menu.page[h->menu.menu_id].item_id==MODBUS_ITEM_QUIT) {
+        sprintf(tmp, ">%s", lang_get_str(h->lang, STR_ID_QUIT));
+    }
+    else {
+        sprintf(tmp, " %s", lang_get_str(h->lang, STR_ID_QUIT));
+    }
+    lcd_draw_string(LCD_WIDTH/2, item_h*3, LCD_WIDTH/2, item_h, tmp, font2, font_color, COLOR_BLACK, HORIZONTAL_CENTER, VERTICAL_CENTER);
+
+    lcd_refresh();
+}
+/////////////////////////////////////////////////
+
+int menu_init(void)
+{
+    int i;
+    menu_handle_t *h=&mnHandle;
+    misc_data_t *misc=&paras_get()->misc;
+    
+    memset(h, 0, sizeof(menu_handle_t));
+    h->lang = lang_id;
+    h->tmr = timer_init();
+    h->flip_ms = get_ms();
+    h->refresh_ms = get_ms();
+    h->uflag |= UFLAG_REFRESH;
+    h->fliptime = misc->flip_time*1000;
+    
+    h->ph_in = 0;
+    h->ph_out = 0;
+    h->ch_out = 0;
+    h->ch_out_max = 0;
+    h->menu.menu_id = 0;
+    h->menu.menu_lv = 0;
+    for(i=0; i<MENU_MAX; i++) {
+        h->menu.page[i].menu_id = i;
+        h->menu.page[i].item_id = 0;
+        h->menu.page[i].item_max = 0;
+    }
+    key_init();
+    led_init();
+    beep_init();
+    lcd_init(LCD_WIDTH,LCD_HEIGHT,LCD_COLOR);
+    lcd_rotate(misc->rotate);
+    
+    return 0;
+}
+
+int menu_deinit(void)
+{
+    menu_handle_t *h=&mnHandle;
+    
+    timer_deinit(h->tmr);
+
+    lcd_deinit();
+    key_deinit();
+    led_deinit();
+    beep_deinit();
+    
+    return 0;
+}
+
+
+static void key_remap(key_val_t *kv, int rotate)
+{
+    key_print(kv);
+    if(rotate==180) {
+        if(kv->key==KEY_UP) {
+            kv->key = KEY_DOWN;
+        }
+        else if(kv->key==KEY_DOWN) {
+            kv->key = KEY_UP;
+        }
+    }
+}
+static int menu_modbus_key_handle(menu_handle_t *h, key_val_t *kv)
+{
+    int r=-1;
+    
+    if(h->menu.menu_lv==0) {
+        h->mb = paras_get()->cas;
+    }
+
+    switch(kv->key) {
+        case KEY_UP:
+        {
+            if(h->menu.menu_lv==0) {
+                if(kv->type==TYPE_SHORT) {
+                    h->menu.menu_id--;
+                }
+            }
+            else if(h->menu.menu_lv==1) {
+                if(h->menu.page[h->menu.menu_id].item_id>0) {
+                    h->menu.page[h->menu.menu_id].item_id--;
+                }
+                else {
+                    h->menu.page[h->menu.menu_id].item_id = MODBUS_ITEM_QUIT;
+                }
+            }
+            else if(h->menu.menu_lv==2) {
+                modbus_data_t *pmb=&h->mb;
+                if(h->menu.page[h->menu.menu_id].item_id==MODBUS_ITEM_ADDR) {         //addr
+                    if(pmb->addr<CASCADE_MAX) {
+                        pmb->addr++;
+                    }
+                    else {
+                        pmb->addr = 1;
+                    }
+                }
+                else if(h->menu.page[h->menu.menu_id].item_id==MODBUS_ITEM_MODE) {    //mode
+                    pmb->mode = !pmb->mode;
+                }
+            }
+        }
+        break;
+
+        case KEY_DOWN:
+        {
+            if(h->menu.menu_lv==0) {
+                if(kv->type==TYPE_SHORT) {
+                    h->menu.menu_id = MENU_SYSTEM;
+                }
+            }
+            else if(h->menu.menu_lv==1) {
+                if(h->menu.page[h->menu.menu_id].item_id<MODBUS_ITEM_QUIT) {
+                    h->menu.page[h->menu.menu_id].item_id++;
+                }
+                else {
+                    h->menu.page[h->menu.menu_id].item_id = 0;
+                }
+            }
+            else if(h->menu.menu_lv==2) {
+                modbus_data_t *pmb=&h->mb;
+                if(h->menu.page[h->menu.menu_id].item_id==MODBUS_ITEM_ADDR) {         //addr
+                    if(pmb->addr) {
+                        pmb->addr--;
+                    }
+                    else {
+                        pmb->addr = CASCADE_MAX;
+                    }
+                }
+                else if(h->menu.page[h->menu.menu_id].item_id==MODBUS_ITEM_MODE) {    //mode
+                    pmb->mode = !pmb->mode;
+                }
+            }
+        }
+        break;
+
+        case KEY_OK:
+        {
+            if(h->menu.menu_lv==1) {
+                if(h->menu.page[h->menu.menu_id].item_id==MODBUS_ITEM_SAVE || h->menu.page[h->menu.menu_id].item_id==MODBUS_ITEM_QUIT) {         //save
+                    if(h->menu.page[h->menu.menu_id].item_id==MODBUS_ITEM_SAVE) {
+                        //r = cascade_set_modbus(&h->mb);
+                        if(r==0) {
+                            paras_get()->cas = h->mb;
+                            r = paras_save();
+                        }
+
+                    }
+                    h->menu.page[h->menu.menu_id].item_id = 0;
+                    h->menu.menu_lv = 0;
+                    tmr_stop(h);
+                }
+                else {
+                    h->menu.menu_lv = 2;
+                    tmr_start(h, 500);
+                }
+            }
+            else if(h->menu.menu_lv==2 && kv->type==TYPE_SHORT) {
+                h->menu.menu_lv = 1;
+            }
+            else {
+                if(kv->type==TYPE_LONG) {
+                    h->menu.menu_lv = 1;
+                }
+            }
+        }
+        break;
+
+        default:
+        {
+            if(h->menu.menu_lv==0 && h->uflag&UFLAG_FLIP) {
+                h->menu.menu_id = MENU_SYSTEM;
+            }
+        }
+    }
+    
+    return r;
+}
+static int menu_key_handle(menu_handle_t *h, key_val_t *kv)
+{
+    int r=0;
+
+    h->ch_out_max = get_ch_out_max(h);
+    switch(h->menu.menu_id) {
+        case MENU_SYSTEM:
+        case MENU_SENSOR:
+        {
+            if(h->menu.menu_lv==0) {
+                if(h->uflag&UFLAG_FLIP || ((kv->key==KEY_UP || kv->key==KEY_DOWN) && kv->type==TYPE_SHORT)) {
+                    if(kv->key==KEY_UP) {
+                        h->menu.menu_id = h->menu.menu_id?(h->menu.menu_id-1):MENU_MAX-1;
+                    }
+                    else {
+                        h->menu.menu_id = (h->menu.menu_id==MENU_MAX-1)?0:(h->menu.menu_id+1);
+                    }
+                }
+            }
+        }
+        break;
+
+        case MENU_INPUT:
+        {
+            if(h->menu.menu_lv==0) {
+                if((kv->key==KEY_UP || kv->key==KEY_DOWN) && kv->type==TYPE_SHORT) {
+                    if(kv->key==KEY_UP) {
+                        h->menu.menu_id--;
+                    }
+                    else {
+                        h->menu.menu_id++;
+                    }
+                }
+                else if(kv->key==KEY_OK && kv->type==TYPE_SHORT) {
+                    if(is_ph3_in(h)) {
+                        h->ph_in = 1;
+                        h->menu.menu_lv = 1;
+                    }
+                }
+                else if(h->uflag&UFLAG_FLIP) {
+                    if(is_ph3_in(h)) {
+                        h->ph_in = 1;
+                        h->menu.menu_lv = 1;
+                    }
+                    else {
+                        h->menu.menu_id++;
+                    }
+                }
+            }
+            else if(h->menu.menu_lv==1) {
+                if((kv->key==KEY_UP || kv->key==KEY_DOWN) && kv->type==TYPE_SHORT) {
+                    if(kv->key==KEY_UP) {
+                        if(h->ph_in>1) {
+                            h->ph_in--;
+                        }
+                        else {
+                            h->ph_in = 3;
+                        }
+                    }
+                    else {
+                        if(h->ph_in<3) {
+                            h->ph_in++;
+                        }
+                        else {
+                            h->ph_in = 1;
+                        }
+                    }
+                }
+                else if(h->uflag&UFLAG_FLIP) {
+                    if(h->ph_in<3) {
+                        h->ph_in++;
+                    }
+                    else {
+                        h->ph_in = 0;
+                        h->menu.menu_lv = 0;
+                        h->menu.menu_id++;
+                    }
+                }
+                else if(h->uflag&UFLAG_REFRESH) {
+                    //
+                }
+                else {
+                    h->ph_in = 0;
+                    h->menu.menu_lv = 0;
+                }
+            }
+        }
+        break;
+
+        case MENU_OUTPUT:
+        {
+            if(h->uflag&UFLAG_FLIP || ((kv->key==KEY_UP || kv->key==KEY_DOWN) && kv->type==TYPE_SHORT)) {
+                if(kv->key==KEY_UP) {
+                    if(h->ch_out>0) {
+                        h->ch_out--;
+                    }
+                    else {
+                        h->ch_out = 0;
+                        h->menu.menu_id--;
+                    }
+                }
+                else {
+                    if(h->ch_out<h->ch_out_max-1) {
+                        h->ch_out++;
+                    }
+                    else {
+                        h->ch_out = 0;
+                        h->menu.menu_id++;
+                    }
+                }
+            }
+        }
+        break;
+
+        case MENU_MODBUS:
+        {
+            r = menu_modbus_key_handle(h, kv);
+        }
+        break;
+    }
+
+    return r;
+}
+
+
+int menu_handle(void)
+{
+    int r;
+    uint64_t cur_ms;
+    key_val_t kv;
+    int rotate=lcd_get_rotate();
+    int item_h=LCD_HEIGHT/4;
+    int font1=FONT_12,font2=FONT_12;
+    menu_handle_t *h=&mnHandle;
+    
+    r = key_get(&kv); key_remap(&kv, rotate);
+    switch(kv.key) {
+        case KEY_OK:
+        {
+            if(kv.type==TYPE_SHORT) {
+                if(h->menu.menu_lv==0) {
+            #if 0
+                    if(rotate==0) {
+                        lcd_rotate(180);
+                    }
+                    else {
+                        lcd_rotate(0);
+                    }
+            #endif
+                }
+            }
+        }
+        break;
+
+        case KEY_UP:
+        case KEY_DOWN:
+        {
+            led_reset(); beep_reset();
+        }
+        break;
+
+        default:
+        {
+            cur_ms = get_ms();
+#if 1
+            if(h->fliptime>0) {
+                if((cur_ms-h->flip_ms)>=h->fliptime) {
+                    h->uflag |= UFLAG_FLIP;
+                    h->flip_ms = cur_ms;
+                }
+            }
+#endif
+            if((cur_ms-h->refresh_ms)>=REFRESH_TIME) {
+                h->uflag |= UFLAG_REFRESH;
+                h->refresh_ms = cur_ms;
+            }
+        }
+    }
+    if(h->uflag==0 && kv.key<0) {
+        return -1;
+    }
+    //printf("___ uflag: %d\n", h->uflag);
+
+    menu_key_handle(h, &kv);
+    switch(h->menu.menu_id) {
+        case MENU_SYSTEM:
+        {
+            menu_system_paint(h, font1, font2, item_h, &kv);
+        }
+        break;
+
+        case MENU_INPUT:
+        {
+            menu_input_paint(h, font1, font2, item_h, &kv);
+        }
+        break;
+
+        case MENU_OUTPUT:
+        {
+            menu_output_paint(h, font1, font2, item_h, &kv);
+        }
+        break;
+
+        case MENU_SENSOR:
+        {
+            menu_sensor_paint(h, font1, font2, item_h, &kv);
+        }
+        break;
+
+        case MENU_MODBUS:
+        {
+            menu_modbus_paint(h, font1, font2, item_h, &kv);
+        }
+        break;
+    }
+    h->uflag = 0;
+    //printf("___ menu_id: %d, menu_lv: %d\n", h->menu.menu_id, h->menu.menu_lv);
+    
+    return 0;
+}
+
+

+ 11 - 0
f407/applications/ui/menu.h

@@ -0,0 +1,11 @@
+#ifndef __MENU_Hx__
+#define __MENU_Hx__
+
+#include "key.h"
+
+int menu_init(void);
+int menu_deinit(void);
+int menu_handle(void);
+
+#endif
+

+ 112 - 0
f407/applications/ui/timer.c

@@ -0,0 +1,112 @@
+#include <time.h>
+#include <signal.h>
+#include <stdlib.h>
+#include <rtthread.h>
+#include "timer.h"
+
+typedef struct {
+    rt_timer_t timer;
+    int times;
+    int times_max;
+    
+    timer_fn_t fn;
+    void *arg;
+    int   inited;
+}timer_handle_t;
+
+
+static void timer_callback(void *arg)
+{
+    timer_handle_t *h=(timer_handle_t*)arg;
+    if(h->fn) {
+        if(h->times_max>0 && h->times<h->times_max) {
+            int last=0;
+            h->times++;
+            if(h->times==h->times_max) {
+                last = 1;
+            }
+            h->fn(h->arg, last);
+        }
+        else {
+            h->fn(h->arg, 0);
+        }
+    }
+}
+static int set_time(timer_handle_t *h, int t)
+{
+    rt_timer_delete(h->timer);
+    h->timer = rt_timer_create("timer", timer_callback, h, rt_tick_from_millisecond(t), RT_TIMER_FLAG_PERIODIC);
+    return 0;
+}
+
+
+int timer_init(void)
+{
+    int r;
+    timer_handle_t *h=(timer_handle_t*)malloc(sizeof(timer_handle_t));
+    
+    if(!h) {
+        return -1;
+    }
+    
+    h->timer = NULL;
+    h->times = 0;
+    h->times_max = 0;
+    h->fn  = NULL;
+    h->arg = NULL;
+    h->inited = 1;
+    
+    return (int)h;
+}
+
+
+int timer_deinit(int h)
+{
+    int r;
+    timer_handle_t *th=(timer_handle_t*)h;
+
+    if(h==-1 || !th->inited) {
+        return -1;
+    }
+    rt_timer_delete(th->timer);
+    th->inited = 0;
+    free(th);
+
+    return r;
+}
+
+
+int timer_start(int h, int t, int times, timer_fn_t fn, void *arg)
+{
+    int r;
+    timer_handle_t *th=(timer_handle_t*)h;
+    
+    if(h==-1 || !th->inited) {
+        return -1;
+    }
+    rt_timer_stop(th->timer);
+
+    th->times = 0;
+    th->times_max = times;
+    th->fn  = fn;
+    th->arg = arg;
+    
+    r = set_time(th, t);
+    return rt_timer_start(th->timer);
+}
+
+
+int timer_stop(int h)
+{
+    int r;
+    timer_handle_t *th=(timer_handle_t*)h;
+    
+    if(h==-1 || !th->inited) {
+        return -1;
+    }
+    
+    return rt_timer_stop(th->timer);
+}
+
+
+

+ 17 - 0
f407/applications/ui/timer.h

@@ -0,0 +1,17 @@
+#ifndef __TIMER_Hx__
+#define __TIMER_Hx__
+
+
+typedef void (*timer_fn_t)(void *arg, int last);
+
+int timer_init(void);
+int timer_deinit(int h);
+
+int timer_start(int h, int t, int times, timer_fn_t fn, void *arg);
+int timer_stop(int h);
+
+#endif
+
+
+
+

+ 60 - 0
f407/applications/ui/ui.c

@@ -0,0 +1,60 @@
+#include "ui.h"
+#include <unistd.h>
+#include <stdlib.h>
+#include "menu.h"
+#include "sys.h"
+#include "thread.h"
+#include "cfg.h"
+
+
+#if 1
+    #define LOGD  log_d
+    #define LOGE  log_e
+#else
+    #define LOGD  printf
+    #define LOGE  printf
+#endif
+
+
+typedef struct {
+    int fd;
+    
+}ui_handle_t;
+static ui_handle_t uiHandle={0};
+
+
+static void msleep(int ms)
+{
+    usleep(ms*1000);
+}
+static void *ui_thread(void *arg)
+{
+    int r;
+    thread_handle_t *th=(thread_handle_t*)arg;
+    ui_handle_t *h=(ui_handle_t*)th->arg;
+    
+    menu_init();
+    while(th->quit==0) {
+        menu_handle();
+        msleep(50);
+    }
+    menu_deinit();
+    
+    pthread_exit(NULL);
+}
+/////////////////////////////////////////////////////
+
+int ui_init(void)
+{
+    ui_handle_t *h=&uiHandle;
+
+#ifdef USE_UI
+    thread_start(THREAD_ID_UI, ui_thread, h);
+#endif
+
+    return 0;
+}
+
+
+
+

+ 7 - 0
f407/applications/ui/ui.h

@@ -0,0 +1,7 @@
+#ifndef __UI_Hx__
+#define __UI_Hx__
+
+int ui_init(void);
+
+#endif
+

+ 73 - 11
f407/applications/web.c

@@ -1,8 +1,12 @@
 #include "web.h"
 #include "mongoose.h"
 #include "thread.h"
+#include "list.h"
 #include "cfg.h"
+#include <stdio.h>
+#include "datadef.h"
 
+#define TIMER_INTERVAL     1000
 typedef void (*http_fn_t)(void *arg);
 
 
@@ -29,14 +33,64 @@ typedef struct {
     mg_opts_t       opts;
 #endif
     
+    handle_t        list;
     char            rootDir[MG_PATH_MAX];
 }web_handle_t;
 static web_handle_t webHandle={0};
 
+static void set_timer(struct mg_connection *c, int ms)
+{
+    mg_set_timer(c, mg_time()+ms/1000.0f);
+}
+
+static int ws_send(struct mg_connection *c, void *data, int len, int isbin)
+{
+    pkt_hdr_t *h=(pkt_hdr_t*)malloc(len+sizeof(pkt_hdr_t));
+    if(!h) {
+        return -1;
+    }
+    h->magic = PKT_MAGIC;
+    h->type  = PKT_TYPE_POWER_TOTAL;
+    h->nack  = 0;
+    h->dlen  = len;
+    memcpy(h->data, data, len);
+    mg_send_websocket_frame(c, isbin?WEBSOCKET_OP_BINARY:WEBSOCKET_OP_TEXT, h, len+sizeof(pkt_hdr_t));
+    free(h);
+    return 0;
+}
+static int ws_handle(pkt_hdr_t *hdr)
+{
+    switch(hdr->type) {
+        case PKT_TYPE_PARAS:
+        {
+            
+        }
+        break;
+        
+        case PKT_TYPE_POWER_CH:
+        {
+            
+        }
+        break;
+        
+        case PKT_TYPE_SENSOR:
+        {
+            
+        }
+        break;
+        
+        case PKT_TYPE_BREAKER:
+        {
+            
+        }
+        break;
+        
+    }
+}
 
 static void http_fn(struct mg_connection *c, int ev, void *ev_data)
 {
-    int i,j,flag=0;
+    int r,flag=0;
     web_handle_t *h=&webHandle;
     mg_stream_t s={c,ev,ev_data};
 
@@ -54,17 +108,22 @@ static void http_fn(struct mg_connection *c, int ev, void *ev_data)
     if (ev == MG_EV_HTTP_REQUEST) {
         mg_serve_http(c, (struct http_message *)ev_data, h->opts);
     }
+    else if(ev == MG_EV_WEBSOCKET_HANDSHAKE_DONE) {
+        set_timer(c, TIMER_INTERVAL);
+    }
     else if(ev == MG_EV_WEBSOCKET_FRAME) {
-        static int cnt=0;
-        char tmp[30];
         struct websocket_message *wm = (struct websocket_message *) ev_data;
-        
-        sprintf(tmp, "hello %d\n", cnt++);
-        //web_send(wm->data, wm->size, 1);
-        web_send(tmp, strlen(tmp)+1, 1);
+        pkt_hdr_t *pkt=(pkt_hdr_t*)wm->data;
+        ws_handle(pkt);
     }
-    else {
-        //
+    else if(ev==MG_EV_TIMER) {
+        list_node_t *ln=NULL;
+        r = list_take_node(h->list, &ln, 0);
+        if(r==0) {
+            node_t *n=&ln->data;
+            ws_send(c, n->buf, n->dlen, 1);
+            list_back_node(list_append, ln);
+        }
     }
 #endif
 }
@@ -118,20 +177,23 @@ static void *web_thread(void *arg)
 
 int web_init(void)
 {
+    list_cfg_t lc={0,0,10};
     web_handle_t *h=&webHandle;
     
+    h->list = list_init(&lc);
     thread_start(THREAD_ID_WEB, web_thread, h);
     return 0;
 }
 
 
-int web_send(void *data, int len, int is_bin)
+
+int web_send(void *data, int len, int isbin)
 {
     struct mg_connection *c;
     web_handle_t *h=&webHandle;
     
     for (c = mg_next(&h->mgr, NULL); c != NULL; c = mg_next(&h->mgr, c)) {
-        mg_send_websocket_frame(c, is_bin?WEBSOCKET_OP_BINARY:WEBSOCKET_OP_TEXT, data, len);
+        ws_send(c, data, len, isbin);
     }
     
     return 0;

Plik diff jest za duży
+ 1031 - 843
f407/project/app/app.uvoptx


Plik diff jest za duży
+ 57 - 2
f407/project/app/app.uvprojx