Initial commit

This commit is contained in:
icyqwq 2020-11-12 16:52:21 +08:00
commit cd4b3e21a8
62 changed files with 81865 additions and 0 deletions

2
.gitattributes vendored Normal file
View File

@ -0,0 +1,2 @@
# Auto detect text files and perform LF normalization
* text=auto

35
.gitignore vendored Normal file
View File

@ -0,0 +1,35 @@
# Prerequisites
*.d
# Compiled Object files
*.slo
*.lo
*.o
*.obj
# Precompiled Headers
*.gch
*.pch
# Compiled Dynamic libraries
*.so
*.dylib
*.dll
# Fortran module files
*.mod
*.smod
# Compiled Static libraries
*.lai
*.la
*.a
*.lib
# Executables
*.exe
*.out
*.app
.pio
.vscode

67
.travis.yml Normal file
View File

@ -0,0 +1,67 @@
# Continuous Integration (CI) is the practice, in software
# engineering, of merging all developer working copies with a shared mainline
# several times a day < https://docs.platformio.org/page/ci/index.html >
#
# Documentation:
#
# * Travis CI Embedded Builds with PlatformIO
# < https://docs.travis-ci.com/user/integration/platformio/ >
#
# * PlatformIO integration with Travis CI
# < https://docs.platformio.org/page/ci/travis.html >
#
# * User Guide for `platformio ci` command
# < https://docs.platformio.org/page/userguide/cmd_ci.html >
#
#
# Please choose one of the following templates (proposed below) and uncomment
# it (remove "# " before each line) or use own configuration according to the
# Travis CI documentation (see above).
#
#
# Template #1: General project. Test it using existing `platformio.ini`.
#
# language: python
# python:
# - "2.7"
#
# sudo: false
# cache:
# directories:
# - "~/.platformio"
#
# install:
# - pip install -U platformio
# - platformio update
#
# script:
# - platformio run
#
# Template #2: The project is intended to be used as a library with examples.
#
# language: python
# python:
# - "2.7"
#
# sudo: false
# cache:
# directories:
# - "~/.platformio"
#
# env:
# - PLATFORMIO_CI_SRC=path/to/test/file.c
# - PLATFORMIO_CI_SRC=examples/file.ino
# - PLATFORMIO_CI_SRC=path/to/test/directory
#
# install:
# - pip install -U platformio
# - platformio update
#
# script:
# - platformio ci --lib="." --board=ID_1 --board=ID_2 --board=ID_N

21
LICENSE Normal file
View File

@ -0,0 +1,21 @@
MIT License
Copyright (c) 2020 icyqwq
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.

6
default_16MB.csv Normal file
View File

@ -0,0 +1,6 @@
# Name, Type, SubType, Offset, Size, Flags
nvs, data, nvs, 0x9000, 0x5000,
otadata, data, ota, 0xe000, 0x2000,
app0, app, ota_0, 0x10000, 0x640000,
app1, app, ota_1, 0x650000,0x640000,
spiffs, data, spiffs, 0xc90000,0x370000,
1 # Name Type SubType Offset Size Flags
2 nvs data nvs 0x9000 0x5000
3 otadata data ota 0xe000 0x2000
4 app0 app ota_0 0x10000 0x640000
5 app1 app ota_1 0x650000 0x640000
6 spiffs data spiffs 0xc90000 0x370000

39
include/README Normal file
View File

@ -0,0 +1,39 @@
This directory is intended for project header files.
A header file is a file containing C declarations and macro definitions
to be shared between several project source files. You request the use of a
header file in your project source file (C, C++, etc) located in `src` folder
by including it, with the C preprocessing directive `#include'.
```src/main.c
#include "header.h"
int main (void)
{
...
}
```
Including a header file produces the same results as copying the header file
into each source file that needs it. Such copying would be time-consuming
and error-prone. With a header file, the related declarations appear
in only one place. If they need to be changed, they can be changed in one
place, and programs that include the header file will automatically use the
new version when next recompiled. The header file eliminates the labor of
finding and changing all the copies as well as the risk that a failure to
find one copy will result in inconsistencies within a program.
In C, the usual convention is to give header files names that end with `.h'.
It is most portable to use only letters, digits, dashes, and underscores in
header file names, and at most one dot.
Read more about using header files in official GCC documentation:
* Include Syntax
* Include Operation
* Once-Only Headers
* Computed Includes
https://gcc.gnu.org/onlinedocs/cpp/Header-Files.html

46
lib/README Normal file
View File

@ -0,0 +1,46 @@
This directory is intended for project specific (private) libraries.
PlatformIO will compile them to static libraries and link into executable file.
The source code of each library should be placed in a an own separate directory
("lib/your_library_name/[here are source files]").
For example, see a structure of the following two libraries `Foo` and `Bar`:
|--lib
| |
| |--Bar
| | |--docs
| | |--examples
| | |--src
| | |- Bar.c
| | |- Bar.h
| | |- library.json (optional, custom build options, etc) https://docs.platformio.org/page/librarymanager/config.html
| |
| |--Foo
| | |- Foo.c
| | |- Foo.h
| |
| |- README --> THIS FILE
|
|- platformio.ini
|--src
|- main.c
and a contents of `src/main.c`:
```
#include <Foo.h>
#include <Bar.h>
int main (void)
{
...
}
```
PlatformIO Library Dependency Finder will find automatically dependent
libraries scanning project source files.
More information about PlatformIO Library Dependency Finder
- https://docs.platformio.org/page/librarymanager/ldf.html

0
log.txt Normal file
View File

21
platformio.ini Normal file
View File

@ -0,0 +1,21 @@
; PlatformIO Project Configuration File
;
; Build options: build flags, source filter
; Upload options: custom upload port, speed and extra flags
; Library options: dependencies, extra library storages
; Advanced options: extra scripting
;
; Please visit documentation for the other options and examples
; https://docs.platformio.org/page/projectconf.html
[env:m5stack-fire]
platform = espressif32
board = m5stack-fire
framework = arduino
upload_speed = 2000000
monitor_speed = 115200
board_build.partitions = default_16MB.csv
build_flags =
-DCORE_DEBUG_LEVEL=4
-DBOARD_HAS_PSRAM
-mfix-esp32-psram-cache-issue

213
src/epdgui/epdgui.cpp Normal file
View File

@ -0,0 +1,213 @@
#include <stack>
#include <map>
#include <list>
#include "epdgui.h"
typedef struct
{
Frame_Base* frame;
epdgui_args_vector_t args;
}frame_struct_t;
std::list<EPDGUI_Base*> epdgui_object_list;
uint32_t obj_id = 1;
Frame_Base* wait_for_delete = NULL;
std::stack <Frame_Base*> frame_stack;
std::map<String, frame_struct_t> frame_map;
uint8_t frame_switch_count = 0;
bool _is_auto_update = true;
uint16_t _last_pos_x = 0xFFFF, _last_pos_y = 0xFFFF;
void EPDGUI_AddObject(EPDGUI_Base* object)
{
object->SetID(obj_id);
obj_id++;
epdgui_object_list.push_back(object);
}
void EPDGUI_Draw(m5epd_update_mode_t mode)
{
for(std::list<EPDGUI_Base*>::iterator p = epdgui_object_list.begin(); p != epdgui_object_list.end(); p++)
{
(*p)->Draw(mode);
}
}
void EPDGUI_Process(void)
{
for(std::list<EPDGUI_Base*>::iterator p = epdgui_object_list.begin(); p != epdgui_object_list.end(); p++)
{
(*p)->UpdateState(-1, -1);
}
}
void EPDGUI_Process(int16_t x, int16_t y)
{
for(std::list<EPDGUI_Base*>::iterator p = epdgui_object_list.begin(); p != epdgui_object_list.end(); p++)
{
// log_d("%d, %d -> %d, %d, %d, %d", x, y, (*p)->getX(), (*p)->getY(), (*p)->getRX(), (*p)->getBY());
(*p)->UpdateState(x, y);
}
}
void EPDGUI_Clear(void)
{
epdgui_object_list.clear();
}
void EPDGUI_Run(Frame_Base* frame)
{
uint32_t last_active_time = 0;
if(frame->isRun() == 0)
{
frame->exit();
log_d("Exit %s", frame->GetFrameName().c_str());
if(wait_for_delete != NULL)
{
delete wait_for_delete;
wait_for_delete = NULL;
}
return;
}
EPDGUI_Draw(UPDATE_MODE_NONE);
if((frame->GetFrameID() == 1) || (frame_switch_count > 3))
{
frame_switch_count = 0;
M5.EPD.UpdateFull(UPDATE_MODE_GC16);
}
else
{
M5.EPD.UpdateFull(UPDATE_MODE_GL16);
frame_switch_count++;
}
while (1)
{
if((frame->isRun() == 0) || (frame->run() == 0))
{
frame->exit();
// M5.EPD.Clear();
log_d("Exit %s", frame->GetFrameName().c_str());
if(wait_for_delete != NULL)
{
log_d("delete %s", wait_for_delete->GetFrameName().c_str());
delete wait_for_delete;
wait_for_delete = NULL;
}
return;
}
if (M5.TP.avaliable())
{
M5.TP.update();
bool is_finger_up = M5.TP.isFingerUp();
if(is_finger_up || (_last_pos_x != M5.TP.readFingerX(0)) || (_last_pos_y != M5.TP.readFingerY(0)))
{
_last_pos_x = M5.TP.readFingerX(0);
_last_pos_y = M5.TP.readFingerY(0);
if(is_finger_up)
{
EPDGUI_Process();
last_active_time = millis();
}
else
{
EPDGUI_Process(M5.TP.readFingerX(0), M5.TP.readFingerY(0));
last_active_time = 0;
}
}
M5.TP.flush();
}
if((last_active_time != 0) && (millis() - last_active_time > 2000))
{
if(M5.EPD.UpdateCount() > 4)
{
M5.EPD.ResetUpdateCount();
if(_is_auto_update)
{
M5.EPD.UpdateFull(UPDATE_MODE_GL16);
}
}
last_active_time = 0;
}
}
}
void EPDGUI_MainLoop(void)
{
if((!frame_stack.empty()) && (frame_stack.top() != NULL))
{
Frame_Base *frame = frame_stack.top();
log_d("Run %s", frame->GetFrameName().c_str());
EPDGUI_Clear();
_is_auto_update = true;
frame->init(frame_map[frame->GetFrameName()].args);
EPDGUI_Run(frame);
}
}
void EPDGUI_AddFrame(String name, Frame_Base* frame)
{
frame_struct_t f;
f.frame = frame;
frame_map.insert(std::pair<String, frame_struct_t>(name, f));
}
void EPDGUI_AddFrameArg(String name, int n, void* arg)
{
if(frame_map.count(name) == 0)
{
return;
}
if(frame_map[name].args.size() > n)
{
frame_map[name].args[n] = arg;
}
else
{
frame_map[name].args.push_back(arg);
}
log_d("%d", frame_map[name].args.size());
}
Frame_Base* EPDGUI_GetFrame(String name)
{
if(frame_map.count(name) > 0)
{
return frame_map[name].frame;
}
return NULL;
}
void EPDGUI_PushFrame(Frame_Base* frame)
{
frame_stack.push(frame);
}
void EPDGUI_PopFrame(bool isDelete)
{
if(isDelete)
{
wait_for_delete = frame_stack.top();
}
frame_stack.pop();
}
void EPDGUI_OverwriteFrame(Frame_Base* frame)
{
while(!frame_stack.empty())
{
frame_stack.pop();
}
frame_stack.push(frame);
}
void EPDGUI_SetAutoUpdate(bool isAuto)
{
_is_auto_update = isAuto;
}

27
src/epdgui/epdgui.h Normal file
View File

@ -0,0 +1,27 @@
#ifndef __EPDGUI_H
#define __EPDGUI_H
#include "epdgui_base.h"
#include "epdgui_button.h"
#include "epdgui_switch.h"
#include "epdgui_keyboard.h"
#include "epdgui_textbox.h"
#include "epdgui_mutexswitch.h"
#include "../frame/frame_base.h"
void EPDGUI_AddObject(EPDGUI_Base* object);
void EPDGUI_Draw(m5epd_update_mode_t mode = UPDATE_MODE_GC16);
void EPDGUI_Process(void);
void EPDGUI_Process(int16_t x, int16_t y);
void EPDGUI_Clear(void);
void EPDGUI_Run(Frame_Base* frame);
void EPDGUI_MainLoop(void);
void EPDGUI_PushFrame(Frame_Base* frame);
void EPDGUI_PopFrame(bool isDelete = false);
void EPDGUI_OverwriteFrame(Frame_Base* frame);
void EPDGUI_AddFrame(String name, Frame_Base* frame);
void EPDGUI_AddFrameArg(String name, int n, void* arg);
Frame_Base* EPDGUI_GetFrame(String name);
void EPDGUI_SetAutoUpdate(bool isAuto);
#endif //__EPDGUI_H

View File

@ -0,0 +1,70 @@
#include "epdgui_base.h"
EPDGUI_Base::EPDGUI_Base(int16_t x, int16_t y, int16_t w, int16_t h)
{
x = (x + 3) & 0xFFFC;
w = (w + 3) & 0xFFFC;
this->_x = x;
this->_y = y;
this->_w = w;
this->_h = h;
_rx = _x + _w;
_by = _y + _h;
}
EPDGUI_Base::EPDGUI_Base()
{
}
bool EPDGUI_Base::isSelected(void)
{
return _issel;
}
bool EPDGUI_Base::isInBox(int16_t x, int16_t y)
{
if (x == -1 || y == -1)
{
return false;
}
if ((x > _x) && (x < _rx) && (y > _y) && (y < _by))
{
_issel = true;
return 1;
}
_issel = false;
return 0;
}
void EPDGUI_Base::SetHide(bool ishide)
{
this->_ishide = ishide;
}
void EPDGUI_Base::SetEnable(bool isenable)
{
this->_isenable = isenable;
}
void EPDGUI_Base::SetGeometry(int16_t x, int16_t y, int16_t w, int16_t h)
{
x = (x + 3) & 0xFFFC;
w = (w + 3) & 0xFFFC;
this->_x = x;
this->_y = y;
this->_w = w;
this->_h = h;
}
void EPDGUI_Base::SetPos(int16_t x, int16_t y)
{
x = (x + 3) & 0xFFFC;
this->_x = x;
this->_y = y;
}
void EPDGUI_Base::UpdateGram(m5epd_update_mode_t mode)
{
M5.EPD.UpdateArea(_x, _y, _w, _h, mode);
}

53
src/epdgui/epdgui_base.h Normal file
View File

@ -0,0 +1,53 @@
#ifndef __EPDGUI_BASE_H
#define __EPDGUI_BASE_H
#include <M5EPD.h>
#include <vector>
#include "../global_setting.h"
#include "../resources/ImageResource.h"
typedef std::vector<void*> epdgui_args_vector_t;
class EPDGUI_Base
{
public:
EPDGUI_Base(int16_t x, int16_t y, int16_t w, int16_t h);
EPDGUI_Base();
virtual ~EPDGUI_Base() {};
virtual void Draw(m5epd_update_mode_t mode) = 0;
virtual void Bind(int16_t event, void (* func_cb)(epdgui_args_vector_t&)) = 0;
virtual void UpdateState(int16_t x, int16_t y) = 0;
virtual void Draw(M5EPD_Canvas* canvas) = 0;
bool isInBox(int16_t x, int16_t y);
virtual bool isSelected(void);
void SetHide(bool ishide);
void SetEnable(bool isenable);
void SetGeometry(int16_t x, int16_t y, int16_t w, int16_t h);
void SetPos(int16_t x, int16_t y);
void UpdateGram(m5epd_update_mode_t mode = UPDATE_MODE_DU4);
uint32_t GetID(void) { return _id;}
uint32_t* GetID_P(void) { return &_id;}
void SetID(uint32_t id) { _id = id;}
void SetCustomString(String s) {_user_custom_str = s;}
String GetCustomString(void) {return _user_custom_str;}
inline int16_t getX() {return _x;}
inline int16_t getY() {return _y;}
inline int16_t getW() {return _w;}
inline int16_t getH() {return _h;}
inline int16_t getRX() {return _rx;}
inline int16_t getBY() {return _by;}
protected:
String _user_custom_str;
int16_t _x, _y, _w, _h;
int16_t _rx, _by;
uint32_t _id;
bool _issel = false;
bool _ishide = false;
bool _isenable = true;
};
#endif //__EPDGUI_BASE_H

View File

@ -0,0 +1,226 @@
#include "epdgui_button.h"
EPDGUI_Button::EPDGUI_Button(int16_t x, int16_t y, int16_t w, int16_t h):
EPDGUI_Base(x, y, w, h)
{
this->_CanvasNormal = new M5EPD_Canvas(&M5.EPD);
this->_CanvasPressed = new M5EPD_Canvas(&M5.EPD);
this->_CanvasNormal->createCanvas(_w, _h);
this->_CanvasPressed->createCanvas(_w, _h);
}
EPDGUI_Button::EPDGUI_Button(String label, int16_t x, int16_t y, int16_t w, int16_t h, uint32_t style):
EPDGUI_Base(x, y, w, h)
{
if(style & STYLE_INVISABLE)
{
_is_invisable = true;
return;
}
this->_label = label;
this->_CanvasNormal = new M5EPD_Canvas(&M5.EPD);
this->_CanvasPressed = new M5EPD_Canvas(&M5.EPD);
// log_d("[%s] %d, %d", label.c_str(), _x, _y);
this->_CanvasNormal->createCanvas(_w, _h);
this->_CanvasPressed->createCanvas(_w, _h);
this->_CanvasNormal->fillCanvas(0);
this->_CanvasNormal->setTextSize(26);
this->_CanvasNormal->setTextColor(15);
this->_CanvasPressed->fillCanvas(15);
this->_CanvasPressed->setTextSize(26);
this->_CanvasPressed->setTextColor(0);
if(style & STYLE_SOLIDBORDER)
{
this->_CanvasNormal->drawRect(0, 0, _w, _h, 15);
}
if(style & STYLE_ALIGN_LEFT)
{
this->_CanvasNormal->setTextDatum(CL_DATUM);
this->_CanvasPressed->setTextDatum(CL_DATUM);
this->_CanvasNormal->drawString(_label, 5, _h / 2 + 3);
this->_CanvasPressed->drawString(_label, 5, _h / 2 + 3);
}
else if(style & STYLE_ALIGN_RIGHT)
{
this->_CanvasNormal->setTextDatum(CR_DATUM);
this->_CanvasPressed->setTextDatum(CR_DATUM);
this->_CanvasNormal->drawString(_label, _w - 5, _h / 2 + 3);
this->_CanvasPressed->drawString(_label, _w - 5, _h / 2 + 3);
}
else if(style & STYLE_ALIGN_CENTER)
{
this->_CanvasNormal->setTextDatum(CC_DATUM);
this->_CanvasPressed->setTextDatum(CC_DATUM);
this->_CanvasNormal->drawString(_label, _w / 2, _h / 2 + 3);
this->_CanvasPressed->drawString(_label, _w / 2, _h / 2 + 3);
}
}
EPDGUI_Button::~EPDGUI_Button()
{
delete this->_CanvasNormal;
delete this->_CanvasPressed;
}
M5EPD_Canvas* EPDGUI_Button::CanvasNormal()
{
return this->_CanvasNormal;
}
M5EPD_Canvas* EPDGUI_Button::CanvasPressed()
{
return this->_CanvasPressed;
}
void EPDGUI_Button::Draw(m5epd_update_mode_t mode)
{
if(_ishide || _is_invisable)
{
return;
}
if(_state == EVENT_NONE || _state == EVENT_RELEASED)
{
this->_CanvasNormal->pushCanvas(_x, _y, mode);
}
else if(_state == EVENT_PRESSED)
{
this->_CanvasPressed->pushCanvas(_x, _y, mode);
}
}
void EPDGUI_Button::Draw(M5EPD_Canvas* canvas)
{
if(_ishide)
{
return;
}
if(_state == EVENT_NONE || _state == EVENT_RELEASED)
{
_CanvasNormal->pushToCanvas(_x, _y, canvas);
}
else if(_state == EVENT_PRESSED)
{
_CanvasPressed->pushToCanvas(_x, _y, canvas);
}
}
void EPDGUI_Button::Bind(int16_t event, void (* func_cb)(epdgui_args_vector_t&))
{
if(event == EVENT_PRESSED)
{
_pressed_cb = func_cb;
}
else if(event == EVENT_RELEASED)
{
_released_cb = func_cb;
}
}
void EPDGUI_Button::UpdateState(int16_t x, int16_t y)
{
if(!_isenable || _ishide)
{
return;
}
bool is_in_area = isInBox(x, y);
if(is_in_area)
{
if(_state == EVENT_NONE)
{
_state = EVENT_PRESSED;
// Serial.printf("%s Pressed ", _label.c_str());
Draw();
if(_pressed_cb != NULL)
{
_pressed_cb(_pressed_cb_args);
}
}
}
else
{
if(_state == EVENT_PRESSED)
{
_state = EVENT_NONE;
Draw();
if(_released_cb != NULL)
{
_released_cb(_released_cb_args);
}
}
}
}
void EPDGUI_Button::setBMPButton(String label_l, String label_r, const uint8_t *bmp32x32)
{
_CanvasNormal->fillCanvas(0);
_CanvasNormal->drawRect(0, 0, _w, _h, 15);
_CanvasNormal->setTextSize(26);
_CanvasNormal->setTextColor(15);
if(label_l.length())
{
_CanvasNormal->setTextDatum(CL_DATUM);
_CanvasNormal->drawString(label_l, 47 + 8, (_h >> 1) + 5);
}
if(label_r.length())
{
_CanvasNormal->setTextDatum(CR_DATUM);
_CanvasNormal->drawString(label_r, _w - 15, (_h >> 1) + 5);
}
_CanvasNormal->pushImage(15, (_h >> 1) - 16, 32, 32, bmp32x32);
*(_CanvasPressed) = *(_CanvasNormal);
_CanvasPressed->ReverseColor();
}
void EPDGUI_Button::setLabel(String label)
{
_label = label;
this->_CanvasNormal->fillCanvas(0);
this->_CanvasNormal->drawRect(0, 0, _w, _h, 15);
this->_CanvasNormal->setTextSize(26);
this->_CanvasNormal->setTextDatum(CC_DATUM);
this->_CanvasNormal->setTextColor(15);
this->_CanvasNormal->drawString(_label, _w / 2, _h / 2 + 3);
this->_CanvasPressed->fillCanvas(15);
this->_CanvasPressed->setTextSize(26);
this->_CanvasPressed->setTextDatum(CC_DATUM);
this->_CanvasPressed->setTextColor(0);
this->_CanvasPressed->drawString(_label, _w / 2, _h / 2 + 3);
}
void EPDGUI_Button::AddArgs(int16_t event, uint16_t n, void* arg)
{
if(event == EVENT_PRESSED)
{
if(_pressed_cb_args.size() > n)
{
_pressed_cb_args[n] = arg;
}
else
{
_pressed_cb_args.push_back(arg);
}
}
else if(event == EVENT_RELEASED)
{
if(_released_cb_args.size() > n)
{
_released_cb_args[n] = arg;
}
else
{
_released_cb_args.push_back(arg);
}
}
}

View File

@ -0,0 +1,52 @@
#ifndef __EPDGUI_BUTTON_H
#define __EPDGUI_BUTTON_H
#include "epdgui_base.h"
class EPDGUI_Button: public EPDGUI_Base
{
public:
static const int16_t EVENT_NONE = 0;
static const int16_t EVENT_PRESSED = 1;
static const int16_t EVENT_RELEASED = 2;
static const uint32_t STYLE_BORDERLESS = 0x00000001;
static const uint32_t STYLE_SOLIDBORDER = 0x00000002;
static const uint32_t STYLE_ALIGN_LEFT = 0x00000004;
static const uint32_t STYLE_ALIGN_RIGHT = 0x00000008;
static const uint32_t STYLE_ALIGN_CENTER = 0x00000010;
static const uint32_t STYLE_INVISABLE = 0x00000020;
static const uint32_t STYLE_DEFAULT = STYLE_SOLIDBORDER | STYLE_ALIGN_CENTER;
public:
EPDGUI_Button(int16_t x, int16_t y, int16_t w, int16_t h);
EPDGUI_Button(String label, int16_t x, int16_t y, int16_t w, int16_t h, uint32_t style = STYLE_DEFAULT);
~EPDGUI_Button();
void Draw(m5epd_update_mode_t mode = UPDATE_MODE_DU4);
void Draw(M5EPD_Canvas* canvas);
void Bind(int16_t event, void (* func_cb)(epdgui_args_vector_t&));
void UpdateState(int16_t x, int16_t y);
void setLabel(String label);
String getLabel(void) {return _label;}
void AddArgs(int16_t event, uint16_t n, void* arg);
void setBMPButton(String label_l, String label_r, const uint8_t *bmp32x32);
M5EPD_Canvas* CanvasNormal();
M5EPD_Canvas* CanvasPressed();
private:
void (*_pressed_cb)(epdgui_args_vector_t& args) = NULL;
void (*_released_cb)(epdgui_args_vector_t& args) = NULL;
epdgui_args_vector_t _pressed_cb_args;
epdgui_args_vector_t _released_cb_args;
int16_t _state = EVENT_NONE;
String _label;
bool _is_invisable = false;
public:
M5EPD_Canvas* _CanvasNormal = NULL;
M5EPD_Canvas* _CanvasPressed = NULL;
};
#endif //__EPDGUI_BUTTON_H

View File

@ -0,0 +1,370 @@
#include "epdgui_keyboard.h"
static const char* kKeyAlphaMapLowerCase[26] = {
"q", "w", "e", "r", "t", "y", "u", "i", "o", "p", //10
"a", "s", "d", "f", "g", "h", "j", "k", "l", //9
"z", "x", "c", "v", "b", "n", "m", //7
};
static const char* kKeyAlphaMapUpperCase[26] = {
"Q", "W", "E", "R", "T", "Y", "U", "I", "O", "P", //10
"A", "S", "D", "F", "G", "H", "J", "K", "L", //9
"Z", "X", "C", "V", "B", "N", "M", //7
};
static const char* kKeyAlphaMapNumber[26] = {
"1", "2", "3", "4", "5", "6", "7", "8", "9", "0", //10
"-", "/", ":", ";", "(", ")", "$", "&", "@", //9
"_", "\"", ".", ",", "?", "!", "'", //7
};
static const char* kKeyAlphaMapSymbol[26] = {
"[", "]", "{", "}", "#", "%", "^", "*", "+", "=", //10
"_", "\\", "|", "~", "<", ">", "", "£", "¥", //9
"", "", "\u221A", "\u221E", "\u2103", "\u2109", "\u2116", //7
};
// static const char* kRomaSpell[] = {
// "あアぁァ"
// "ばバびビぶブべべぼボびゃビャびゅビュびょビョ"
// };
enum
{
kKeySpace = 26,
kKeyBackspace,
kKeyWrap,
kKeyCase,
kKeySwitch,
kKeyNumber
};
enum
{
kSWCase = 0,
kSWSwitch,
kSWNumber
};
enum
{
kLayoutLowerAlpha = 0,
kLayoutUpperAlpha,
kLayoutNumber,
kLayoutSymbol
};
EPDGUI_Keyboard::EPDGUI_Keyboard(int16_t dir, uint32_t style): EPDGUI_Base()
{
uint8_t language = GetLanguage();
if(dir) // Horizontal
{
const uint16_t kKeyWidth = 72;
const uint16_t kKeyHeight = 44;
const uint16_t kKeyInterval = 8;
const uint16_t kFirstLineY = 302;
const uint16_t kSecondLineY = 356;
const uint16_t kThirdLineY = 410;
const uint16_t k4thLineY = 464;
const uint16_t kBaseX = 84;
for(int i = 0; i < 10; i++)
{
_btn[i] = new EPDGUI_Button(kKeyAlphaMapLowerCase[i], kBaseX + (kKeyInterval + kKeyWidth) * i, kFirstLineY, kKeyWidth, kKeyHeight);
}
for(int i = 10; i < 19; i++)
{
_btn[i] = new EPDGUI_Button(kKeyAlphaMapLowerCase[i], kBaseX + 40 + (kKeyInterval + kKeyWidth) * (i - 10), kSecondLineY, kKeyWidth, kKeyHeight);
}
for(int i = 19; i < 26; i++)
{
_btn[i] = new EPDGUI_Button(kKeyAlphaMapLowerCase[i], kBaseX + 118 + (kKeyInterval + kKeyWidth) * (i - 19), kThirdLineY, kKeyWidth, kKeyHeight);
}
_btn[kKeyBackspace] = new EPDGUI_Button("", kBaseX + 792 - 96, kThirdLineY, 96, kKeyHeight);
_btn[kKeyBackspace]->CanvasNormal()->pushImage(_btn[kKeyBackspace]->getW() / 2 - 16, _btn[kKeyBackspace]->getH() / 2 - 16, 32, 32, ImageResource_backspace_32x32);
_btn[kKeyBackspace]->CanvasPressed()->fillCanvas(0);
_btn[kKeyBackspace]->CanvasPressed()->pushImage(_btn[kKeyBackspace]->getW() / 2 - 16, _btn[kKeyBackspace]->getH() / 2 - 16, 32, 32, ImageResource_backspace_32x32);
_btn[kKeyBackspace]->CanvasPressed()->ReverseColor();
if(language == LANGUAGE_JA)
{
_btn[kKeySpace] = new EPDGUI_Button("空白", kBaseX + 162, k4thLineY, 468, kKeyHeight);
if(style & STYLE_INPUTMODE_NORMALTEXT)
_btn[kKeyWrap] = new EPDGUI_Button("改行", kBaseX + 792 - 152, k4thLineY, 152, kKeyHeight);
else if(style & STYLE_INPUTMODE_NEEDCONFIRM)
_btn[kKeyWrap] = new EPDGUI_Button("確認", kBaseX + 792 - 152, k4thLineY, 152, kKeyHeight);
}
else if(language == LANGUAGE_ZH)
{
_btn[kKeySpace] = new EPDGUI_Button("空格", kBaseX + 162, k4thLineY, 468, kKeyHeight);
if(style & STYLE_INPUTMODE_NORMALTEXT)
_btn[kKeyWrap] = new EPDGUI_Button("换行", kBaseX + 792 - 152, k4thLineY, 152, kKeyHeight);
else if(style & STYLE_INPUTMODE_NEEDCONFIRM)
_btn[kKeyWrap] = new EPDGUI_Button("确认", kBaseX + 792 - 152, k4thLineY, 152, kKeyHeight);
}
else
{
_btn[kKeySpace] = new EPDGUI_Button("Space", kBaseX + 162, k4thLineY, 468, kKeyHeight);
if(style & STYLE_INPUTMODE_NORMALTEXT)
_btn[kKeyWrap] = new EPDGUI_Button("Wrap", kBaseX + 792 - 152, k4thLineY, 152, kKeyHeight);
else if(style & STYLE_INPUTMODE_NEEDCONFIRM)
_btn[kKeyWrap] = new EPDGUI_Button("Confirm", kBaseX + 792 - 152, k4thLineY, 152, kKeyHeight);
}
// function key
_sw[kSWCase] = new EPDGUI_Switch(2, kBaseX, kThirdLineY, 96, kKeyHeight);
_sw[kSWSwitch] = new EPDGUI_Switch(2, kBaseX, k4thLineY, 68, kKeyHeight);
_sw[kSWNumber] = new EPDGUI_Switch(2, kBaseX + 162 - kKeyInterval - 68, k4thLineY, 68, kKeyHeight);
}
else
{
const uint16_t kBaseX = 16;
const uint16_t kBaseY = 700;
const uint16_t kKeyWidth = 44;
const uint16_t kKeyHeight = 52;
const uint16_t kKeyInterval = 8;
const uint16_t kFirstLineY = kBaseY;
const uint16_t kSecondLineY = kBaseY + 64;
const uint16_t kThirdLineY = kSecondLineY + 64;
const uint16_t k4thLineY = kThirdLineY + 64;
for(int i = 0; i < 10; i++)
{
_btn[i] = new EPDGUI_Button(kKeyAlphaMapLowerCase[i], kBaseX + (kKeyInterval + kKeyWidth) * i, kFirstLineY, kKeyWidth, kKeyHeight);
}
for(int i = 10; i < 19; i++)
{
_btn[i] = new EPDGUI_Button(kKeyAlphaMapLowerCase[i], kBaseX + 28 + (kKeyInterval + kKeyWidth) * (i - 10), kSecondLineY, kKeyWidth, kKeyHeight);
}
for(int i = 19; i < 26; i++)
{
_btn[i] = new EPDGUI_Button(kKeyAlphaMapLowerCase[i], kBaseX + 80 + (kKeyInterval + kKeyWidth) * (i - 19), kThirdLineY, kKeyWidth, kKeyHeight);
}
_btn[kKeyBackspace] = new EPDGUI_Button("", kBaseX + 512 - 60, kThirdLineY, 60, kKeyHeight);
_btn[kKeyBackspace]->CanvasNormal()->pushImage(_btn[kKeyBackspace]->getW() / 2 - 16, _btn[kKeyBackspace]->getH() / 2 - 16, 32, 32, ImageResource_backspace_32x32);
_btn[kKeyBackspace]->CanvasPressed()->fillCanvas(0);
_btn[kKeyBackspace]->CanvasPressed()->pushImage(_btn[kKeyBackspace]->getW() / 2 - 16, _btn[kKeyBackspace]->getH() / 2 - 16, 32, 32, ImageResource_backspace_32x32);
_btn[kKeyBackspace]->CanvasPressed()->ReverseColor();
if(language == LANGUAGE_JA)
{
_btn[kKeySpace] = new EPDGUI_Button("空白", kBaseX + 132, k4thLineY, 244, kKeyHeight);
if(style & STYLE_INPUTMODE_NORMALTEXT)
_btn[kKeyWrap] = new EPDGUI_Button("改行", kBaseX + 512 - 128, k4thLineY, 128, kKeyHeight);
else if(style & STYLE_INPUTMODE_NEEDCONFIRM)
_btn[kKeyWrap] = new EPDGUI_Button("確認", kBaseX + 512 - 128, k4thLineY, 128, kKeyHeight);
}
else if(language == LANGUAGE_ZH)
{
_btn[kKeySpace] = new EPDGUI_Button("空格", kBaseX + 132, k4thLineY, 244, kKeyHeight);
if(style & STYLE_INPUTMODE_NORMALTEXT)
_btn[kKeyWrap] = new EPDGUI_Button("换行", kBaseX + 512 - 128, k4thLineY, 128, kKeyHeight);
else if(style & STYLE_INPUTMODE_NEEDCONFIRM)
_btn[kKeyWrap] = new EPDGUI_Button("确认", kBaseX + 512 - 128, k4thLineY, 128, kKeyHeight);
}
else
{
_btn[kKeySpace] = new EPDGUI_Button("Space", kBaseX + 132, k4thLineY, 244, kKeyHeight);
if(style & STYLE_INPUTMODE_NORMALTEXT)
_btn[kKeyWrap] = new EPDGUI_Button("Wrap", kBaseX + 512 - 128, k4thLineY, 128, kKeyHeight);
else if(style & STYLE_INPUTMODE_NEEDCONFIRM)
_btn[kKeyWrap] = new EPDGUI_Button("Confirm", kBaseX + 512 - 128, k4thLineY, 128, kKeyHeight);
}
// function key
_sw[kSWCase] = new EPDGUI_Switch(2, kBaseX, kThirdLineY, 60, kKeyHeight);
_sw[kSWSwitch] = new EPDGUI_Switch(2, kBaseX, k4thLineY, 56, kKeyHeight);
_sw[kSWNumber] = new EPDGUI_Switch(2, kBaseX + 56 + kKeyInterval, k4thLineY, 60, kKeyHeight);
}
_sw[kSWCase]->Canvas(0)->pushImage(_sw[kSWCase]->getW() / 2 - 16, _sw[kSWCase]->getH() / 2 - 16, 32, 32, ImageResource_upper_32x32);
_sw[kSWCase]->Canvas(1)->pushImage(_sw[kSWCase]->getW() / 2 - 16, _sw[kSWCase]->getH() / 2 - 16, 32, 32, ImageResource_upper_32x32);
_sw[kSWCase]->Canvas(1)->ReverseColor();
_sw[kSWSwitch]->SetLabel(0, ""); //TODO: Support for kana input
_sw[kSWSwitch]->SetLabel(1, "Aa");
_sw[kSWNumber]->SetLabel(0, "123");
_sw[kSWNumber]->SetLabel(1, "Abc");
for(int i = 0; i < 29; i++)
{
_key[i] = _btn[i];
}
_key[kKeyCase] = _sw[kSWCase];
_key[kKeySwitch] = _sw[kSWSwitch];
_key[kKeyNumber] = _sw[kSWNumber];
// _sw[kSWSwitch]->SetHide(true);
_layout = kLayoutLowerAlpha;
}
EPDGUI_Keyboard::~EPDGUI_Keyboard()
{
for(int i = 0; i < 29; i++)
{
delete _btn[i];
}
for(int i = 0; i < 3; i++)
{
delete _sw[i];
}
}
void EPDGUI_Keyboard::Draw(m5epd_update_mode_t mode)
{
if(_ishide)
{
return;
}
for(int i = 0; i < 32; i++)
{
_key[i]->Draw(mode);
}
}
void EPDGUI_Keyboard::Draw(M5EPD_Canvas* canvas)
{
if(_ishide)
{
return;
}
for(int i = 0; i < 32; i++)
{
_key[i]->Draw(canvas);
}
}
void EPDGUI_Keyboard::Bind(int16_t state, void (* func_cb)(epdgui_args_vector_t&))
{
}
void EPDGUI_Keyboard::UpdateState(int16_t x, int16_t y)
{
if(!_isenable)
{
return;
}
// log_d("UpdateState %d, %d", x, y);
for(int i = 0; i < 32; i++)
{
bool keypressed = _key[i]->isInBox(x, y);
_key[i]->UpdateState(x, y);
if(keypressed)
{
if(i < 26)
{
switch(_layout)
{
case kLayoutLowerAlpha: _data += kKeyAlphaMapLowerCase[i]; break;
case kLayoutUpperAlpha: _data += kKeyAlphaMapUpperCase[i]; break;
case kLayoutNumber: _data += kKeyAlphaMapNumber[i]; break;
case kLayoutSymbol: _data += kKeyAlphaMapSymbol[i]; break;
}
}
switch(i)
{
case kKeyBackspace: _data += "\u0008"; break;
case kKeySpace: _data += " "; break;
case kKeyWrap: _data += "\n"; break;
case kKeyCase:
{
if(_layout == kLayoutNumber || _layout == kLayoutSymbol)
{
if(_sw[kSWCase]->getState() == 1)
{
for(int j = 0; j < 26; j++)
{
_btn[j]->setLabel(kKeyAlphaMapNumber[j]);
_layout = kLayoutNumber;
}
}
else
{
for(int j = 0; j < 26; j++)
{
_btn[j]->setLabel(kKeyAlphaMapSymbol[j]);
_layout = kLayoutSymbol;
}
}
_sw[kSWCase]->UpdateState(-1, -1);
Draw(UPDATE_MODE_NONE);
M5.EPD.UpdateFull(UPDATE_MODE_GL16);
}
else
{
if(_sw[kSWCase]->getState() == 1)
{
for(int j = 0; j < 26; j++)
{
_btn[j]->setLabel(kKeyAlphaMapLowerCase[j]);
_layout = kLayoutLowerAlpha;
}
}
else
{
for(int j = 0; j < 26; j++)
{
_btn[j]->setLabel(kKeyAlphaMapUpperCase[j]);
_layout = kLayoutUpperAlpha;
}
}
_sw[kSWCase]->UpdateState(-1, -1);
Draw(UPDATE_MODE_NONE);
M5.EPD.UpdateFull(UPDATE_MODE_GL16);
}
break;
}
case kKeyNumber:
{
if(_sw[kSWNumber]->getState() == 1)
{
_sw[kSWCase]->setState(0);
_sw[kSWCase]->Canvas(0)->fillCanvas(0);
_sw[kSWCase]->Canvas(1)->fillCanvas(0);
_sw[kSWCase]->Canvas(0)->drawRect(0, 0, _sw[kSWCase]->getW(), _sw[kSWCase]->getH(), 15);
_sw[kSWCase]->Canvas(1)->drawRect(0, 0, _sw[kSWCase]->getW(), _sw[kSWCase]->getH(), 15);
_sw[kSWCase]->Canvas(0)->pushImage(_sw[kSWCase]->getW() / 2 - 16, _sw[kSWCase]->getH() / 2 - 16, 32, 32, ImageResource_upper_32x32);
_sw[kSWCase]->Canvas(1)->pushImage(_sw[kSWCase]->getW() / 2 - 16, _sw[kSWCase]->getH() / 2 - 16, 32, 32, ImageResource_upper_32x32);
_sw[kSWCase]->Canvas(1)->ReverseColor();
for(int j = 0; j < 26; j++)
{
_btn[j]->setLabel(kKeyAlphaMapLowerCase[j]);
_layout = kLayoutLowerAlpha;
}
}
else
{
_sw[kSWCase]->setState(0);
_sw[kSWCase]->SetLabel(0, "#+-");
_sw[kSWCase]->SetLabel(1, "123");
for(int j = 0; j < 26; j++)
{
_btn[j]->setLabel(kKeyAlphaMapNumber[j]);
_layout = kLayoutNumber;
}
}
_sw[kSWNumber]->UpdateState(-1, -1);
Draw(UPDATE_MODE_NONE);
M5.EPD.UpdateFull(UPDATE_MODE_GL16);
break;
}
}
}
}
}
String EPDGUI_Keyboard::getData(void)
{
String data = _data;
_data = "";
return data;
}

View File

@ -0,0 +1,35 @@
#ifndef __EPDGUI_KEYBOARD_H
#define __EPDGUI_KEYBOARD_H
#include "epdgui_button.h"
#include "epdgui_switch.h"
class EPDGUI_Keyboard: public EPDGUI_Base
{
public:
static const uint32_t STYLE_INPUTMODE_NORMALTEXT = 0x00000001;
static const uint32_t STYLE_INPUTMODE_NEEDCONFIRM = 0x00000002;
static const uint32_t STYLE_DEFAULT = STYLE_INPUTMODE_NORMALTEXT;
public:
EPDGUI_Keyboard(int16_t dir = 1, uint32_t style = STYLE_DEFAULT);
~EPDGUI_Keyboard();
void Draw(m5epd_update_mode_t mode = UPDATE_MODE_DU4);
void Draw(M5EPD_Canvas* canvas);
void Bind(int16_t event, void (* func_cb)(epdgui_args_vector_t&));
void UpdateState(int16_t x, int16_t y);
String getData(void);
private:
EPDGUI_Button *_btn[29];
EPDGUI_Switch *_sw[3];
EPDGUI_Base *_key[32];
String _data;
uint8_t _layout = 0;
public:
};
#endif //__EPDGUI_KEYBOARD_H

View File

@ -0,0 +1,110 @@
#include "epdgui_mutexswitch.h"
EPDGUI_MutexSwitch::EPDGUI_MutexSwitch()
{
}
void EPDGUI_MutexSwitch::Draw(m5epd_update_mode_t mode)
{
if(_ishide)
{
return;
}
for(std::list<EPDGUI_Switch*>::iterator p = _object_list.begin(); p != _object_list.end(); p++)
{
(*p)->Draw(mode);
}
}
void EPDGUI_MutexSwitch::Draw(M5EPD_Canvas* canvas)
{
if(_ishide)
{
return;
}
for(std::list<EPDGUI_Switch*>::iterator p = _object_list.begin(); p != _object_list.end(); p++)
{
(*p)->Draw(canvas);
}
}
void EPDGUI_MutexSwitch::Bind(int16_t event, void (* func_cb)(epdgui_args_vector_t&))
{
}
void EPDGUI_MutexSwitch::UpdateState(int16_t x, int16_t y)
{
if(!_isenable)
{
return;
}
std::list<EPDGUI_Switch*>::iterator pressed_sw = _object_list.end();
for(std::list<EPDGUI_Switch*>::iterator p = _object_list.begin(); p != _object_list.end(); p++)
{
if(_last_pressed == p)
{
(*p)->UpdateState(-1, -1);
continue;
}
if((*p)->isInBox(x, y))
{
_last_pressed = p;
pressed_sw = p;
}
(*p)->UpdateState(x, y);
}
if(!_is_exclusive)
{
return;
}
if(pressed_sw == _object_list.end())
{
return;
}
for(std::list<EPDGUI_Switch*>::iterator p = _object_list.begin(); p != _object_list.end(); p++)
{
if(pressed_sw == p)
{
continue;
}
if((*p)->getState() != 0)
{
(*p)->setState(0);
(*p)->Draw(UPDATE_MODE_GL16);
}
}
}
void EPDGUI_MutexSwitch::SetDefault(uint16_t idx)
{
if(idx < _object_list.size())
{
_default_idx = idx;
}
int i = 0;
for(std::list<EPDGUI_Switch*>::iterator p = _object_list.begin(); p != _object_list.end(); p++)
{
if(i == _default_idx)
{
_last_pressed = p;
(*p)->setState(1);
// (*p)->Draw(UPDATE_MODE_GL16);
}
else
{
(*p)->setState(0);
// (*p)->Draw(UPDATE_MODE_GL16);
}
i++;
}
}

View File

@ -0,0 +1,30 @@
#ifndef _EPDGUI_MUTEXSWITCH_H
#define _EPDGUI_MUTEXSWITCH_H
#include "epdgui_switch.h"
#include <list>
class EPDGUI_MutexSwitch : public EPDGUI_Base
{
public:
EPDGUI_MutexSwitch();
void Draw(m5epd_update_mode_t mode);
void Draw(M5EPD_Canvas* canvas);
void Bind(int16_t event, void (* func_cb)(epdgui_args_vector_t&));
void UpdateState(int16_t x, int16_t y);
void Add(EPDGUI_Switch* object) {_object_list.push_back(object);}
void SetExclusive(bool isExclusive) {_is_exclusive = isExclusive;}
void SetDefault(uint16_t idx);
private:
bool _is_exclusive = true;
uint16_t _default_idx = 0;
std::list<EPDGUI_Switch*> _object_list;
std::list<EPDGUI_Switch*>::iterator _last_pressed;
};
#endif

View File

@ -0,0 +1,169 @@
#include "epdgui_switch.h"
EPDGUI_Switch::EPDGUI_Switch(int16_t state_num, int16_t x, int16_t y, int16_t w, int16_t h):
EPDGUI_Base(x, y, w, h)
{
if(state_num > EPDGUI_SWITCH_MAX_STATE)
{
state_num = EPDGUI_SWITCH_MAX_STATE;
}
this->_state_num = state_num;
for(int i = 0; i < _state_num; i++)
{
this->_canvas[i] = new M5EPD_Canvas(&M5.EPD);
this->_canvas[i]->createCanvas(_w, _h);
// this->_canvas[i]->fillCanvas(i & 0x01 ? 0 : 15);
this->_canvas[i]->setTextSize(26);
this->_canvas[i]->fillCanvas(0);
this->_canvas[i]->drawRect(0, 0, _w, _h, 15);
}
_canvas_pressed = new M5EPD_Canvas(&M5.EPD);
_canvas_pressed->createCanvas(_w, _h);
_canvas_pressed->fillCanvas(15);
}
EPDGUI_Switch::~EPDGUI_Switch()
{
for(int i = 0; i < _state_num; i++)
{
delete this->_canvas[i];
}
}
M5EPD_Canvas* EPDGUI_Switch::Canvas(int16_t state)
{
if(state == -1)
{
return _canvas_pressed;
}
return _canvas[state];
}
void EPDGUI_Switch::SetLabel(int16_t state, String label)
{
if(state > EPDGUI_SWITCH_MAX_STATE || state < 0)
{
return;
}
this->_canvas[state]->fillCanvas(0);
this->_canvas[state]->drawRect(0, 0, _w, _h, 15);
this->_canvas[state]->setTextSize(26);
this->_canvas[state]->setTextDatum(CC_DATUM);
// this->_canvas[state]->setTextColor(state & 0x01 ? 15 : 0);
this->_canvas[state]->setTextColor(15);
this->_canvas[state]->drawString(label, _w / 2, _h / 2 + 5);
this->_label_array[state] = label;
}
void EPDGUI_Switch::Draw(m5epd_update_mode_t mode)
{
if(_ishide)
{
return;
}
if(_event == EVENT_PRESSED)
{
_canvas_pressed->pushCanvas(_x, _y, mode);
return;
}
this->_canvas[_state]->pushCanvas(_x, _y, mode);
}
void EPDGUI_Switch::Draw(M5EPD_Canvas* canvas)
{
if(_ishide)
{
return;
}
if(_event == EVENT_PRESSED)
{
_canvas_pressed->pushToCanvas(_x, _y, canvas);
return;
}
this->_canvas[_state]->pushToCanvas(_x, _y, canvas);
}
void EPDGUI_Switch::Bind(int16_t state, void (* func_cb)(epdgui_args_vector_t&))
{
if(state > EPDGUI_SWITCH_MAX_STATE || state < 0)
{
return;
}
this->_func_cb_array[state] = func_cb;
}
void EPDGUI_Switch::UpdateState(int16_t x, int16_t y)
{
if(!_isenable || _ishide)
{
return;
}
bool is_in_area = isInBox(x, y);
if(is_in_area)
{
if(_event == EVENT_NONE)
{
_event = EVENT_PRESSED;
Draw();
}
}
else
{
if(_event == EVENT_PRESSED)
{
_event = EVENT_NONE;
_state++;
if(_state == _state_num)
{
_state = 0;
}
Draw();
if(this->_func_cb_array[_state] != NULL)
{
this->_func_cb_array[_state](this->_func_cb_param_array[_state]);
}
}
}
}
void EPDGUI_Switch::setState(int16_t state)
{
if(state >= _state_num || state < 0)
{
return;
}
_state = state;
Draw(UPDATE_MODE_NONE);
}
int16_t EPDGUI_Switch::getState(void)
{
return _state;
}
void EPDGUI_Switch::AddArgs(int16_t state, uint16_t n, void* arg)
{
if(state > EPDGUI_SWITCH_MAX_STATE || state < 0)
{
return;
}
if(this->_func_cb_param_array[state].size() > n)
{
this->_func_cb_param_array[state][n] = arg;
}
else
{
this->_func_cb_param_array[state].push_back(arg);
}
}

View File

@ -0,0 +1,44 @@
#ifndef __EPDGUI_SWITCH_H
#define __EPDGUI_SWITCH_H
#include "epdgui_base.h"
#define EPDGUI_SWITCH_MAX_STATE 5
class EPDGUI_Switch: public EPDGUI_Base
{
public:
static const int16_t EVENT_NONE = 0;
static const int16_t EVENT_PRESSED = 1;
static const int16_t EVENT_RELEASED = 2;
public:
EPDGUI_Switch(int16_t state_num, int16_t x, int16_t y, int16_t w, int16_t h);
~EPDGUI_Switch();
void Draw(m5epd_update_mode_t mode = UPDATE_MODE_DU4);
void Draw(M5EPD_Canvas* canvas);
void Bind(int16_t state, void (* func_cb)(epdgui_args_vector_t&));
void UpdateState(int16_t x, int16_t y);
void AddArgs(int16_t state, uint16_t n, void* arg);
int16_t getState(void);
void setState(int16_t state);
void SetLabel(int16_t state, String label);
M5EPD_Canvas* Canvas(int16_t state);
private:
int16_t _state_num;
void (*_func_cb_array[EPDGUI_SWITCH_MAX_STATE])(epdgui_args_vector_t &args) = {NULL};
epdgui_args_vector_t _func_cb_param_array[EPDGUI_SWITCH_MAX_STATE];
int16_t _state = 0;
int16_t _event = EVENT_NONE;
String _label_array[EPDGUI_SWITCH_MAX_STATE];
public:
M5EPD_Canvas* _canvas[EPDGUI_SWITCH_MAX_STATE] = {NULL};
M5EPD_Canvas* _canvas_pressed = NULL;
};
#endif //__EPDGUI_BUTTON_H

View File

@ -0,0 +1,233 @@
#include "epdgui_textbox.h"
uint32_t EPDGUI_Textbox::_textbox_touching_id = 0;
EPDGUI_Textbox::EPDGUI_Textbox(int16_t x, int16_t y, int16_t w, int16_t h) : EPDGUI_Base(x, y, w, h)
{
_canvas = new M5EPD_Canvas(&M5.EPD);
_size = 26;
_thiscreat = false;
_canvas->createCanvas(_w, _h);
_canvas->fillCanvas(15);
_canvas->drawRect(0, 0, _w, _h, 15);
if (!_canvas->isRenderExist(_size))
{
_canvas->createRender(_size, 60);
_thiscreat = true;
}
_canvas->setTextSize(_size);
_canvas->setTextDatum(TL_DATUM);
_canvas->setTextColor(15);
for (int i = 0; i < 26; i++)
{
_canvas->preRender('a' + i);
_canvas->preRender('A' + i);
}
_margin_left = 8;
_margin_right = 8;
_margin_top = 8;
_margin_bottom = 8;
_state = EVENT_NONE;
}
EPDGUI_Textbox::~EPDGUI_Textbox()
{
delete _canvas;
}
void EPDGUI_Textbox::SetTextMargin(int16_t left, int16_t top, int16_t right, int16_t bottom)
{
_margin_left = left;
_margin_top = top;
_margin_right = right + left;
_margin_bottom = bottom + top;
}
void EPDGUI_Textbox::SetTextSize(uint16_t size)
{
if (_thiscreat)
{
_canvas->destoryRender(_size);
}
_size = size;
if (!_canvas->isRenderExist(_size))
{
_canvas->createRender(_size, 60);
_thiscreat = true;
}
else
{
_thiscreat = false;
}
_canvas->setTextSize(_size);
for (int i = 0; i < 26; i++)
{
_canvas->preRender('a' + i);
_canvas->preRender('A' + i);
}
Draw(UPDATE_MODE_GC16);
}
void EPDGUI_Textbox::Draw(m5epd_update_mode_t mode)
{
if (_ishide)
{
return;
}
if (_state == EVENT_NONE)
{
_canvas->setTextSize(_size);
_canvas->fillCanvas(0);
_canvas->drawRect(0, 0, _w, _h, 15);
_canvas->setTextArea(_margin_left, _margin_top, _w - _margin_right, _h - _margin_bottom);
_canvas->print(_data);
_canvas->pushCanvas(_x, _y, mode);
}
else
{
_canvas->setTextSize(_size);
_canvas->fillCanvas(0);
_canvas->drawRect(0, 0, _w, _h, 15);
_canvas->drawRect(1, 1, _w - 2, _h - 2, 15);
_canvas->drawRect(2, 2, _w - 4, _h - 4, 15);
_canvas->setTextArea(_margin_left, _margin_top, _w - _margin_right, _h - _margin_bottom);
_canvas->print(_data);
_canvas->pushCanvas(_x, _y, mode);
}
}
void EPDGUI_Textbox::Draw(M5EPD_Canvas* canvas)
{
if (_ishide)
{
return;
}
if (_state == EVENT_NONE)
{
_canvas->setTextSize(_size);
_canvas->fillCanvas(0);
_canvas->drawRect(0, 0, _w, _h, 15);
_canvas->setTextArea(_margin_left, _margin_top, _w - _margin_right, _h - _margin_bottom);
_canvas->print(_data);
_canvas->pushToCanvas(_x, _y, canvas);
}
else
{
_canvas->setTextSize(_size);
_canvas->fillCanvas(0);
_canvas->drawRect(0, 0, _w, _h, 15);
_canvas->drawRect(1, 1, _w - 2, _h - 2, 15);
_canvas->drawRect(2, 2, _w - 4, _h - 4, 15);
_canvas->setTextArea(_margin_left, _margin_top, _w - _margin_right, _h - _margin_bottom);
_canvas->print(_data);
_canvas->pushToCanvas(_x, _y, canvas);
}
}
void EPDGUI_Textbox::Bind(int16_t event, void (*func_cb)(epdgui_args_vector_t &))
{
}
void EPDGUI_Textbox::UpdateState(int16_t x, int16_t y)
{
if (!_isenable)
{
return;
}
int16_t state = _state;
if ((_state == EVENT_PRESSED) && (_textbox_touching_id != _id))
{
state = EVENT_NONE;
}
if (isInBox(x, y))
{
_textbox_touching_id = _id;
state = EVENT_PRESSED;
}
SetState(state);
}
void EPDGUI_Textbox::SetState(int16_t state)
{
if (state != _state)
{
if(state == EVENT_PRESSED)
{
_textbox_touching_id = _id;
}
_state = state;
}
}
void EPDGUI_Textbox::SetText(String text)
{
if (text != _data)
{
_data = text;
Draw(UPDATE_MODE_A2);
}
}
void EPDGUI_Textbox::Remove(int16_t idx)
{
uint16_t n = 0, last_n = 0;
uint8_t* buf = (uint8_t *)_data.c_str();
uint16_t len = strlen((char*)buf);
uint16_t cnt = 0;
while (n < len)
{
last_n = n;
_canvas->decodeUTF8(buf, &n, len - n);
if(cnt == idx)
{
_data.remove(last_n, n - last_n);
return;
}
cnt++;
}
if(idx == -1)
{
_data.remove(last_n, n - last_n);
}
}
void EPDGUI_Textbox::AddText(String text)
{
if(text.length() == 0)
{
return;
}
uint8_t* buf = (uint8_t *)text.c_str();
uint16_t len = strlen((char*)buf);
uint16_t n = 0, last_n = 0;
while (n < len)
{
last_n = n;
uint16_t uniCode = _canvas->decodeUTF8(buf, &n, len - n);
if(uniCode == 0x0008)
{
Remove(-1);
}
else
{
_data += text.substring(last_n, n);
}
}
Draw(UPDATE_MODE_A2);
}

View File

@ -0,0 +1,40 @@
#ifndef __EPDGUI_TEXTBOX_H
#define __EPDGUI_TEXTBOX_H
#include "epdgui_base.h"
class EPDGUI_Textbox : public EPDGUI_Base
{
public:
static const int16_t EVENT_NONE = 0;
static const int16_t EVENT_PRESSED = 1;
public:
EPDGUI_Textbox(int16_t x, int16_t y, int16_t w, int16_t h);
~EPDGUI_Textbox();
void Draw(m5epd_update_mode_t mode = UPDATE_MODE_DU4);
void Draw(M5EPD_Canvas* canvas);
void Bind(int16_t event, void (*func_cb)(epdgui_args_vector_t &));
void UpdateState(int16_t x, int16_t y);
void SetState(int16_t state);
void SetText(String text);
String GetText(void) {return _data;}
void AddText(String text);
void Remove(int16_t idx);
void SetTextSize(uint16_t size);
bool isSelected(void) {return _state;}
void SetTextMargin(int16_t left, int16_t top, int16_t right, int16_t bottom);
private:
M5EPD_Canvas *_canvas = NULL;
String _data;
uint16_t _size;
bool _thiscreat;
int16_t _state;
int16_t _margin_left, _margin_right, _margin_top, _margin_bottom;
static uint32_t _textbox_touching_id;
public:
};
#endif //__EPDGUI_KEYBOARD_H

1
src/frame/frame.cpp Normal file
View File

@ -0,0 +1 @@
#include "frame.h"

19
src/frame/frame.h Normal file
View File

@ -0,0 +1,19 @@
#ifndef _FRAME_H_
#define _FRAME_H_
#include "frame_main.h"
#include "frame_setting.h"
#include "frame_setting_language.h"
#include "frame_setting_wallpaper.h"
#include "frame_keyboard.h"
#include "frame_factorytest.h"
#include "frame_wifiscan.h"
#include "frame_wifipassword.h"
#include "frame_lifegame.h"
#include "frame_fileindex.h"
#include "frame_txtreader.h"
#include "frame_compare.h"
#include "frame_pictureviewer.h"
#include "frame_home.h"
#endif

54
src/frame/frame_base.cpp Normal file
View File

@ -0,0 +1,54 @@
#include "frame_base.h"
#include "../epdgui/epdgui.h"
Frame_Base::Frame_Base(bool _has_title)
{
if(_has_title)
{
_canvas_title = new M5EPD_Canvas(&M5.EPD);
_canvas_title->createCanvas(540, 64);
_canvas_title->drawFastHLine(0, 64, 540, 15);
_canvas_title->drawFastHLine(0, 63, 540, 15);
_canvas_title->drawFastHLine(0, 62, 540, 15);
_canvas_title->setTextSize(26);
_canvas_title->setTextDatum(CC_DATUM);
}
_frame_id = 0;
_frame_name = "Frame_Base";
}
Frame_Base::~Frame_Base()
{
if(_key_exit != NULL)
delete _key_exit;
if(_canvas_title != NULL)
delete _canvas_title;
}
void Frame_Base::exitbtn(String title, uint16_t width)
{
_key_exit = new EPDGUI_Button(8, 12, width, 48);
_key_exit->CanvasNormal()->fillCanvas(0);
_key_exit->CanvasNormal()->setTextSize(26);
_key_exit->CanvasNormal()->setTextDatum(CL_DATUM);
_key_exit->CanvasNormal()->setTextColor(15);
_key_exit->CanvasNormal()->drawString(title, 47 + 13, 28);
_key_exit->CanvasNormal()->pushImage(15, 8, 32, 32, ImageResource_item_icon_arrow_l_32x32);
*(_key_exit->CanvasPressed()) = *(_key_exit->CanvasNormal());
_key_exit->CanvasPressed()->ReverseColor();
}
int Frame_Base::run(void)
{
return _is_run;
}
void Frame_Base::exit(void)
{
}
void Frame_Base::exit_cb(epdgui_args_vector_t &args)
{
EPDGUI_PopFrame();
*((int*)(args[0])) = 0;
}

33
src/frame/frame_base.h Normal file
View File

@ -0,0 +1,33 @@
#ifndef _FRAME_BASE_H_
#define _FRAME_BASE_H_
#include <M5EPD.h>
#include "../epdgui/epdgui_button.h"
#include "../global_setting.h"
#include "../resources/ImageResource.h"
class Frame_Base
{
public:
Frame_Base(bool _has_title = true);
void exitbtn(String title, uint16_t width = 150);
virtual ~Frame_Base();
virtual int run();
virtual void exit();
virtual int init(epdgui_args_vector_t &args) = 0;
String GetFrameName() {return _frame_name;}
int isRun() {return _is_run;}
void SetFrameID(uint32_t id) {_frame_id = id;}
uint32_t GetFrameID() {return _frame_id;}
protected:
static void exit_cb(epdgui_args_vector_t &args);
String _frame_name;
int _is_run = 1;
M5EPD_Canvas *_canvas_title = NULL;
EPDGUI_Button *_key_exit = NULL;
uint32_t _frame_id;
};
#endif

177
src/frame/frame_compare.cpp Normal file
View File

@ -0,0 +1,177 @@
#include "frame_compare.h"
void UpdateCompareCanvasDraw(uint8_t mode, M5EPD_Canvas *update_canvas)
{
update_canvas->fillCanvas(0);
for(int i = 0; i < 16; i++)
{
update_canvas->fillRect(i * 27, 0, 27, 50, i);
}
switch(mode)
{
case UPDATE_MODE_INIT :
{
update_canvas->drawString("Display initialization", 8, 60);
break;
}
case UPDATE_MODE_DU :
{
update_canvas->drawString("Monochrome menu, text input ", 8, 60);
break;
}
case UPDATE_MODE_GC16 :
{
update_canvas->drawString("High quality images", 8, 60);
break;
}
case UPDATE_MODE_GL16 :
{
update_canvas->drawString("Text with white background", 8, 60);
break;
}
case UPDATE_MODE_GLR16:
{
update_canvas->drawString("Text with white background", 8, 60);
break;
}
case UPDATE_MODE_GLD16:
{
update_canvas->drawString("Graphics with white background", 8, 60);
break;
}
case UPDATE_MODE_DU4 :
{
update_canvas->drawString("Fast page flipping", 8, 60);
break;
}
case UPDATE_MODE_A2 :
{
update_canvas->drawString("Anti-aliased text in menus", 8, 60);
break;
}
}
update_canvas->drawRect(0, 0, 432, 100, 15);
}
void key_update_mode_cb(epdgui_args_vector_t &args)
{
EPDGUI_Button *btn = (EPDGUI_Button*)(args[0]);
M5EPD_Canvas *canvas = (M5EPD_Canvas*)(args[1]);
M5EPD_Canvas *canvas_time = (M5EPD_Canvas*)(args[2]);
int mode = btn->GetCustomString().toInt();
UpdateCompareCanvasDraw(mode, canvas);
canvas_time->fillCanvas(0);
uint32_t time = millis();
canvas->pushCanvas(104, 168 + (mode-1) * 108, (m5epd_update_mode_t)mode);
M5.EPD.CheckAFSR();
char buf[30];
sprintf(buf, "%lu ms", millis() - time);
canvas_time->drawString(buf, 200, 15);
canvas_time->pushCanvas(330, 925, UPDATE_MODE_GL16);
}
void key_update_reset_cb(epdgui_args_vector_t &args)
{
M5.EPD.FillPartGram4bpp(104, 168, 432, 748, 0xFFFF);
M5.EPD.UpdateArea(104, 168, 432, 748, UPDATE_MODE_INIT);
}
Frame_Compare::Frame_Compare(void)
{
_frame_name = "Frame_Compare";
_canvas_time = new M5EPD_Canvas(&M5.EPD);
_canvas = new M5EPD_Canvas(&M5.EPD);
_canvas->createCanvas(432, 100);
_canvas_time->createCanvas(200, 30);
_canvas->setTextSize(26);
_canvas_time->setTextSize(26);
_canvas_time->setTextDatum(CR_DATUM);
uint8_t language = GetLanguage();
if(language == LANGUAGE_JA)
{
exitbtn("ホーム");
_canvas_title->drawString("比較", 270, 34);
_key_updatemode[UPDATE_MODE_INIT] = new EPDGUI_Button("リセット", 4, 88, 532, 60);
}
else if(language == LANGUAGE_ZH)
{
exitbtn("主页");
_canvas_title->drawString("比较", 270, 34);
_key_updatemode[UPDATE_MODE_INIT] = new EPDGUI_Button("全部重置", 4, 88, 532, 60);
}
else
{
exitbtn("Home");
_canvas_title->drawString("Compare", 270, 34);
_key_updatemode[UPDATE_MODE_INIT] = new EPDGUI_Button("Reset all", 4, 88, 532, 60);
}
_key_updatemode[UPDATE_MODE_INIT]->Bind(EPDGUI_Button::EVENT_RELEASED, key_update_reset_cb);
for(int i = 1; i < 8; i++)
{
_key_updatemode[i] = new EPDGUI_Button(0, 168 + (i-1) * 108, 100, 100);
char buf[10];
sprintf(buf, "%d", i);
_key_updatemode[i]->SetCustomString(buf);
_key_updatemode[i]->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, _key_updatemode[i]);
_key_updatemode[i]->AddArgs(EPDGUI_Button::EVENT_RELEASED, 1, _canvas);
_key_updatemode[i]->AddArgs(EPDGUI_Button::EVENT_RELEASED, 2, _canvas_time);
_key_updatemode[i]->Bind(EPDGUI_Button::EVENT_RELEASED, key_update_mode_cb);
}
_key_updatemode[UPDATE_MODE_DU ]->setLabel("DU");
_key_updatemode[UPDATE_MODE_GC16 ]->setLabel("GC16");
_key_updatemode[UPDATE_MODE_GL16 ]->setLabel("GL16");
_key_updatemode[UPDATE_MODE_GLR16]->setLabel("GLR16");
_key_updatemode[UPDATE_MODE_GLD16]->setLabel("GLD16");
_key_updatemode[UPDATE_MODE_DU4 ]->setLabel("DU4");
_key_updatemode[UPDATE_MODE_A2 ]->setLabel("A2");
_key_exit->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, (void*)(&_is_run));
_key_exit->Bind(EPDGUI_Button::EVENT_RELEASED, &Frame_Base::exit_cb);
}
Frame_Compare::~Frame_Compare(void)
{
for(int i = 0; i < 8; i++)
{
delete _key_updatemode[i];
}
delete _canvas;
}
int Frame_Compare::run()
{
switch(_update_flag)
{
case 1:
{
_update_flag = 0;
for(int i = 1; i < 8; i++)
{
UpdateCompareCanvasDraw(i, _canvas);
_canvas->pushCanvas(104, 168 + (i-1) * 108, (m5epd_update_mode_t)i);
}
break;
}
}
return 1;
}
int Frame_Compare::init(epdgui_args_vector_t &args)
{
_is_run = 1;
_update_flag = 1;
M5.EPD.Clear();
_canvas_title->pushCanvas(0, 8, UPDATE_MODE_NONE);
EPDGUI_AddObject(_key_exit);
for(int i = 0; i < 8; i++)
{
EPDGUI_AddObject(_key_updatemode[i]);
}
EPDGUI_SetAutoUpdate(false);
return 3;
}

22
src/frame/frame_compare.h Normal file
View File

@ -0,0 +1,22 @@
#ifndef _FRAME_COMPARE_H_
#define _FRAME_COMPARE_H_
#include "frame_base.h"
#include "../epdgui/epdgui.h"
class Frame_Compare : public Frame_Base
{
public:
Frame_Compare();
~Frame_Compare();
int init(epdgui_args_vector_t &args);
int run();
private:
EPDGUI_Button *_key_updatemode[8];
uint8_t _update_flag;
M5EPD_Canvas *_canvas;
M5EPD_Canvas *_canvas_time;
};
#endif //_FRAME_COMPARE_H_

View File

@ -0,0 +1,506 @@
#include "frame_factorytest.h"
#include "WiFi.h"
#define POS_LX (15)
#define POS_RX (240 - 15)
const uint8_t kPins[6] = {32, 25, 33, 26, 19, 18};
void frame_factorytest_exit_cb(epdgui_args_vector_t &args)
{
EPDGUI_PopFrame();
*((int *)(args[0])) = 0;
}
Frame_FactoryTest::Frame_FactoryTest(void)
{
//TODO: Voltage WiFi Psram touch pos
_frame_name = "Frame_FactoryTest";
_canvas_base = new M5EPD_Canvas(&M5.EPD);
_canvas_data = new M5EPD_Canvas(&M5.EPD);
_canvas_pos = new M5EPD_Canvas(&M5.EPD);
_canvas_btn = new M5EPD_Canvas(&M5.EPD);
_canvas_pass = new M5EPD_Canvas(&M5.EPD);
_canvas_base->createCanvas(300, 600);
_canvas_data->createCanvas(240, 480);
_canvas_pos->createCanvas(240, 60);
_canvas_btn->createCanvas(240, 60);
_canvas_pass->createCanvas(150, 32);
_canvas_base->setTextSize(26);
_canvas_data->setTextSize(26);
_canvas_pos->setTextSize(26);
_canvas_btn->setTextSize(26);
_canvas_pass->setTextSize(26);
_canvas_base->setTextDatum(CL_DATUM);
_canvas_data->setTextDatum(CR_DATUM);
_canvas_pos->setTextDatum(CR_DATUM);
_canvas_btn->setTextDatum(CR_DATUM);
_canvas_pass->setTextDatum(CR_DATUM);
_language = GetLanguage();
if (_language == LANGUAGE_JA)
{
exitbtn("ホーム");
_canvas_title->drawString("工場テスト", 270, 34);
}
else if (_language == LANGUAGE_ZH)
{
exitbtn("主页");
_canvas_title->drawString("出厂测试", 270, 34);
}
else
{
exitbtn("Home");
_canvas_title->drawString("Factory Test", 270, 34);
}
_key_exit->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, (void *)(&_is_run));
_key_exit->Bind(EPDGUI_Button::EVENT_RELEASED, &Frame_Base::exit_cb);
for (int i = 0; i < 6; i++)
{
pinMode(kPins[i], OUTPUT);
digitalWrite(kPins[i], HIGH);
}
M5.SHT30.Begin();
M5.RTC.begin();
rtc_time_t time_struct;
rtc_date_t date_struct;
M5.RTC.getTime(&time_struct);
M5.RTC.getDate(&date_struct);
if ((isTimeSynced() == 0) || (date_struct.year < 2010))
{
rtc_time_t time_struct;
time_struct.hour = 23;
time_struct.min = 33;
time_struct.sec = 33;
M5.RTC.setTime(&time_struct);
rtc_date_t date_struct;
date_struct.week = 4;
date_struct.mon = 9;
date_struct.day = 24;
date_struct.year = 2020;
M5.RTC.setDate(&date_struct);
}
_time = 0;
_btn = 0;
_psram_success = false;
_isfirst = true;
_pass_flag = 0;
_pass_flag |= GetInitStatus(0) ? 0x0080 : 0;
}
Frame_FactoryTest::~Frame_FactoryTest(void)
{
delete _canvas_base;
delete _canvas_data;
delete _canvas_pos;
delete _canvas_btn;
delete _canvas_pass;
}
void Frame_FactoryTest::drawItem(uint16_t flag, const char* str, int y)
{
String prefix_pass("[PASS] ");
String prefix_none("");
if(_pass_flag & flag)
{
_canvas_base->drawString(prefix_pass + str, POS_LX, y);
}
else
{
_canvas_base->drawString(str, POS_LX, y);
_canvas_base->ReversePartColor(0, y - 30, 300, 60);
}
}
void Frame_FactoryTest::drawItem(m5epd_update_mode_t mode)
{
_canvas_base->fillCanvas(0);
if (_language == LANGUAGE_JA)
{
drawItem(0x0001, "1.期日", 30);
drawItem(0x0002, "2.時間", 90);
drawItem(0x0004, "3.温度", 150);
drawItem(0x0008, "4.湿度", 210);
drawItem(0x0010, "5.電池", 270);
drawItem(0x0020, "6.Wi-Fi", 330);
drawItem(0x0040, "7.PSRAM", 390);
drawItem(0x0080, "8.SDカード", 450);
drawItem(0x0100, "9.ボタン", 510);
drawItem(0x0200, "10.タッチパッド", 570);
}
else if (_language == LANGUAGE_ZH)
{
drawItem(0x0001, "1.日期", 30);
drawItem(0x0002, "2.时间", 90);
drawItem(0x0004, "3.温度", 150);
drawItem(0x0008, "4.湿度", 210);
drawItem(0x0010, "5.电池", 270);
drawItem(0x0020, "6.Wi-Fi", 330);
drawItem(0x0040, "7.PSRAM", 390);
drawItem(0x0080, "8.SD卡", 450);
drawItem(0x0100, "9.按键", 510);
drawItem(0x0200, "10.触屏", 570);
}
else
{
drawItem(0x0001, "1.day", 30);
drawItem(0x0002, "2.Time", 90);
drawItem(0x0004, "3.Temperature", 150);
drawItem(0x0008, "4.Humidity", 210);
drawItem(0x0010, "5.Battery", 270);
drawItem(0x0020, "6.Wi-Fi", 330);
drawItem(0x0040, "7.PSRAM", 390);
drawItem(0x0080, "8.SD Card", 450);
drawItem(0x0100, "9.Button", 510);
drawItem(0x0200, "10.TouchPad", 570);
}
_canvas_base->pushCanvas(0, 100, mode);
}
void Frame_FactoryTest::drawGrove(m5epd_update_mode_t mode)
{
M5.EPD.WritePartGram4bpp(428, 916, 100, 40, (_pass_flag & 0x0400) ? ImageResource_factory_pass_h_100x40 : ImageResource_factory_port_a_100x40);
M5.EPD.WritePartGram4bpp(4, 848, 40, 100, (_pass_flag & 0x0800) ? ImageResource_factory_pass_v_40x100 : ImageResource_factory_port_b_40x100);
M5.EPD.WritePartGram4bpp(4, 720, 40, 100, (_pass_flag & 0x1000) ? ImageResource_factory_pass_v_40x100 : ImageResource_factory_port_c_40x100);
M5.EPD.UpdateArea(0, 720, 540, 240, mode);
}
bool Frame_FactoryTest::checkGrove(int sda, int scl)
{
Wire1.begin(sda, scl, 10000);
bool groveCheck = true;
Wire1.beginTransmission(0x76);
Wire1.write(0xD0);
if (Wire1.endTransmission() != 0)
{
groveCheck = false;
}
else
{
Wire1.requestFrom(0x76, 1);
uint8_t chipID = Wire1.read();
if (chipID != 0x58)
{
groveCheck = false;
}
}
return groveCheck;
}
void Frame_FactoryTest::drawPassCount(m5epd_update_mode_t mode)
{
uint16_t x = _pass_flag, n = 0;
for (; x; x >>= 1)
n += x & 1;
char buf[20];
sprintf(buf, "PASS %d/13", n);
_canvas_pass->fillCanvas(0);
_canvas_pass->drawString(buf, 150, 14);
_canvas_pass->pushCanvas(375, 28, mode);
}
void Frame_FactoryTest::scan(String *ssid, int32_t *rssi)
{
WiFi.mode(WIFI_STA);
WiFi.disconnect();
WiFi.scanNetworks(true);
int wifi_num;
while (1)
{
wifi_num = WiFi.scanComplete();
if (wifi_num >= 0)
{
break;
}
}
*ssid = WiFi.SSID(0);
*rssi = WiFi.RSSI(0);
WiFi.scanDelete();
}
int Frame_FactoryTest::run()
{
uint16_t pass_flag = _pass_flag;
char buf[100];
// POS
if ((M5.TP.readFingerX(0) != _last_x) || (M5.TP.readFingerY(0) != _last_y))
{
pass_flag |= 0x0200;
_last_x = M5.TP.readFingerX(0);
_last_y = M5.TP.readFingerY(0);
sprintf(buf, "X %d, Y %d", _last_x, _last_y);
_canvas_pos->fillCanvas(0);
_canvas_pos->drawString(buf, POS_RX, 30);
_canvas_pos->pushCanvas(300, 640, UPDATE_MODE_A2);
}
// BTN
M5.update();
int ptr = 0;
bool ispressed = false;
if (_btn == 0x07)
{
_btn |= 0x08;
pass_flag |= 0x0100;
}
if (M5.BtnL.isPressed())
{
_btn |= 0x01;
buf[ptr++] = 'L';
ispressed = true;
}
if (M5.BtnP.isPressed())
{
_btn |= 0x02;
buf[ptr++] = 'P';
ispressed = true;
}
if (M5.BtnR.isPressed())
{
_btn |= 0x04;
buf[ptr++] = 'R';
ispressed = true;
}
buf[ptr] = '\0';
if(ptr == 0)
{
strcpy(buf, "Waiting...");
}
if (ispressed)
{
_canvas_btn->fillCanvas(0);
_canvas_btn->drawString(buf, POS_RX, 30);
_canvas_btn->pushCanvas(300, 580, UPDATE_MODE_A2);
}
if (millis() - _time > 1000)
{
_time = millis();
rtc_time_t time_struct;
rtc_date_t date_struct;
M5.RTC.getTime(&time_struct);
M5.RTC.getDate(&date_struct);
if ((date_struct.year > 2010) && (time_struct.hour <= 24) && (time_struct.min <= 60) && (time_struct.sec <= 60))
{
pass_flag |= 0x01;
}
if (_prev_sec == 255)
{
_prev_sec = time_struct.sec;
}
if (time_struct.sec != _prev_sec)
{
pass_flag |= 0x02;
}
_canvas_data->fillCanvas(0);
_canvas_data->setTextSize(26);
// RTC
sprintf(buf, "%04d - %02d - %02d", date_struct.year, date_struct.mon, date_struct.day);
_canvas_data->drawString(buf, POS_RX, 30);
sprintf(buf, "%02d : %02d : %02d", time_struct.hour, time_struct.min, time_struct.sec);
_canvas_data->drawString(buf, POS_RX, 90);
// SHT30
M5.SHT30.UpdateData();
if(M5.SHT30.GetError() == 0)
{
float ctemp = M5.SHT30.GetTemperature();
float chumi = M5.SHT30.GetRelHumidity();
if (!(pass_flag & 0x04))
{
if (_prev_temp > 100)
{
_prev_temp = ctemp;
}
if ((ctemp < 40) && (ctemp > 0) && (_prev_temp != ctemp))
{
pass_flag |= 0x04;
}
}
if (!(pass_flag & 0x08))
{
if (_prev_hum > 100)
{
_prev_hum = chumi;
}
if ((chumi >= 0) && (chumi <= 100) && (_prev_hum != chumi))
{
pass_flag |= 0x08;
}
}
sprintf(buf, "%.2f ℃", ctemp);
_canvas_data->drawString(buf, POS_RX, 150);
sprintf(buf, "%d %%", (int)chumi);
_canvas_data->drawString(buf, POS_RX, 210);
}
else
{
_canvas_data->drawString("[FAILED]", POS_RX, 150);
_canvas_data->drawString("[FAILED]", POS_RX, 210);
}
// Battery
uint32_t vol = M5.getBatteryVoltage();
if (_prev_vol == 0)
{
_prev_vol = vol;
}
if (_prev_vol != vol)
{
pass_flag |= 0x10;
}
float vol_f = vol / 1000.0f;
sprintf(buf, "%.2f V", vol_f);
_canvas_data->drawString(buf, POS_RX, 270);
// WiFi
if (_isfirst)
{
String ssid;
int32_t rssi;
scan(&ssid, &rssi);
sprintf(buf, "%s (%d db)", ssid.c_str(), rssi);
_wifistr = String(buf);
if (rssi > -55)
{
pass_flag |= 0x20;
}
}
_canvas_data->drawString(_wifistr, POS_RX, 330);
// PSRAM
if (_isfirst)
{
uint8_t *test_p = (uint8_t *)ps_malloc(16);
if (test_p != NULL)
{
free(test_p);
_psram_success = true;
sprintf(buf, "Free %.2f KiB", ESP.getFreePsram() / 1024.0f);
_canvas_data->drawString(buf, POS_RX, 390);
pass_flag |= 0x40;
}
else
{
_psram_success = false;
sprintf(buf, "[FAILED]");
_canvas_data->drawString(buf, POS_RX, 390);
}
}
else
{
if (_psram_success)
{
sprintf(buf, "Free %.2f KiB", ESP.getFreePsram() / 1024.0f);
_canvas_data->drawString(buf, POS_RX, 390);
}
else
{
_canvas_data->drawString("[FAILED]", POS_RX, 390);
}
}
// SD
if (GetInitStatus(0))
{
sprintf(buf, "%.2f MiB", SD.cardSize() / 1024.0f / 1024.0f);
_canvas_data->drawString(buf, POS_RX, 450);
}
else
{
_canvas_data->drawString("[FAILED]", POS_RX, 450);
}
_canvas_data->pushCanvas(300, 100, UPDATE_MODE_A2);
}
// grove
uint16_t temp = pass_flag;
if (!(pass_flag & 0x0400))
{
pass_flag |= checkGrove(M5EPD_PORTA_Y_PIN, M5EPD_PORTA_W_PIN) ? 0x0400 : 0x0000;
}
if (!(pass_flag & 0x0800))
{
pass_flag |= checkGrove(M5EPD_PORTB_Y_PIN, M5EPD_PORTB_W_PIN) ? 0x0800 : 0x0000;
}
if (!(pass_flag & 0x1000))
{
pass_flag |= checkGrove(M5EPD_PORTC_Y_PIN, M5EPD_PORTC_W_PIN) ? 0x1000 : 0x0000;
}
bool update_flag = false;
if(temp != pass_flag)
{
if(pass_flag != _pass_flag)
{
update_flag = true;
}
_pass_flag = pass_flag;
drawGrove(UPDATE_MODE_GL16);
update_flag = true;
}
else if (update_flag || (pass_flag != _pass_flag))
{
_pass_flag = pass_flag;
drawItem(UPDATE_MODE_GL16);
update_flag = true;
}
if(update_flag)
{
drawPassCount(UPDATE_MODE_GL16);
}
if (_isfirst)
{
_isfirst = false;
}
return 1;
}
int Frame_FactoryTest::init(epdgui_args_vector_t &args)
{
_is_run = 1;
M5.EPD.Clear();
_canvas_title->pushCanvas(0, 8, UPDATE_MODE_NONE);
_canvas_base->pushCanvas(0, 100, UPDATE_MODE_NONE);
drawItem(UPDATE_MODE_NONE);
drawGrove(UPDATE_MODE_NONE);
drawPassCount(UPDATE_MODE_NONE);
EPDGUI_AddObject(_key_exit);
_time = 0;
_btn = 0;
_psram_success = false;
_isfirst = true;
_last_x = 0;
_last_y = 0;
_prev_sec = 255;
_prev_temp = 255;
_prev_hum = 255;
_prev_vol = 0;
return 3;
}

View File

@ -0,0 +1,44 @@
#ifndef _FRAME_FACTORYTEST_H_
#define _FRAME_FACTORYTEST_H_
#include "frame_base.h"
#include "../epdgui/epdgui.h"
class Frame_FactoryTest : public Frame_Base
{
public:
Frame_FactoryTest();
~Frame_FactoryTest();
int run();
void scan(String *ssid, int32_t *rssi);
int init(epdgui_args_vector_t &args);
private:
void drawItem(m5epd_update_mode_t mode);
void drawItem(uint16_t flag, const char* str, int y);
void drawGrove(m5epd_update_mode_t mode);
bool checkGrove(int sda, int scl);
void drawPassCount(m5epd_update_mode_t mode);
private:
M5EPD_Canvas *_canvas_base;
M5EPD_Canvas *_canvas_data;
M5EPD_Canvas *_canvas_pos;
M5EPD_Canvas *_canvas_btn;
M5EPD_Canvas *_canvas_pass;
uint8_t _language;
uint32_t _time;
uint8_t _btn;
bool _psram_success;
bool _isfirst;
String _wifistr;
uint32_t _last_x, _last_y;
uint16_t _pass_flag;
uint8_t _prev_sec;
float _prev_temp;
float _prev_hum;
uint16_t _prev_vol;
};
#endif //_FRAME_FACTORYTEST_H_

View File

@ -0,0 +1,229 @@
#include "frame_fileindex.h"
#include "frame_txtreader.h"
#include "frame_pictureviewer.h"
#define MAX_BTN_NUM 14
void key_fileindex_floder_cb(epdgui_args_vector_t &args)
{
Frame_Base *frame = new Frame_FileIndex(((EPDGUI_Button*)(args[0]))->GetCustomString());
EPDGUI_PushFrame(frame);
*((int*)(args[1])) = 0;
log_d("%s", ((EPDGUI_Button*)(args[0]))->GetCustomString().c_str());
}
void key_fileindex_image_cb(epdgui_args_vector_t &args)
{
Frame_Base *frame = new Frame_PictureViewer(((EPDGUI_Button*)(args[0]))->GetCustomString());
EPDGUI_PushFrame(frame);
*((int*)(args[1])) = 0;
log_d("%s", ((EPDGUI_Button*)(args[0]))->GetCustomString().c_str());
}
void key_fileindex_text_cb(epdgui_args_vector_t &args)
{
Frame_Base *frame = new Frame_txtReader(((EPDGUI_Button*)(args[0]))->GetCustomString());
EPDGUI_PushFrame(frame);
*((int*)(args[1])) = 0;
log_d("%s", ((EPDGUI_Button*)(args[0]))->GetCustomString().c_str());
}
void key_fileindex_exit_cb(epdgui_args_vector_t &args)
{
EPDGUI_PopFrame(true);
*((int*)(args[0])) = 0;
}
Frame_FileIndex::Frame_FileIndex(String path)
{
_frame_name = "Frame_FileIndex";
_path = path;
uint8_t language = GetLanguage();
_canvas_title->setTextDatum(CR_DATUM);
if (path == "/")
{
if (language == LANGUAGE_JA)
{
exitbtn("ホーム");
}
else if (language == LANGUAGE_ZH)
{
exitbtn("主页");
}
else
{
exitbtn("Home");
}
_canvas_title->drawString("SD/", 540 - 15, 34);
}
else
{
String parent_directory = path.substring(0, path.lastIndexOf("/"));
exitbtn("/..");
String subpath = path;
if(path.length() > 20)
{
subpath = path.substring(0, 20) + "...";
}
_canvas_title->drawString("SD" + subpath, 540 - 15, 34);
}
_key_exit->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, (void *)(&_is_run));
_key_exit->Bind(EPDGUI_Button::EVENT_RELEASED, &key_fileindex_exit_cb);
}
void Frame_FileIndex::listDir(fs::FS &fs, const char *dirname)
{
File root = fs.open(dirname);
if (!root)
{
log_d("Failed to open directory");
return;
}
if (!root.isDirectory())
{
log_d("Not a directory");
return;
}
std::vector<File> floders;
std::vector<File> files;
File file = root.openNextFile();
while (file)
{
if (file.isDirectory())
{
floders.push_back(file);
}
else
{
files.push_back(file);
}
file = root.openNextFile();
}
for(int n = 0; n < floders.size(); n++)
{
if(_key_files.size() > MAX_BTN_NUM)
{
break;
}
File file = floders[n];
EPDGUI_Button *btn = new EPDGUI_Button(4, 100 + _key_files.size() * 60, 532, 61);
_key_files.push_back(btn);
String filename(file.name());
filename = filename.substring(filename.lastIndexOf("/"));
if(filename.length() > 19)
{
filename = filename.substring(0, 19) + "...";
}
btn->CanvasNormal()->fillCanvas(0);
btn->CanvasNormal()->drawRect(0, 0, 532, 61, 15);
btn->CanvasNormal()->setTextSize(26);
btn->CanvasNormal()->setTextDatum(CL_DATUM);
btn->CanvasNormal()->setTextColor(15);
btn->CanvasNormal()->drawString(filename, 47 + 13, 35);
btn->SetCustomString(file.name());
btn->CanvasNormal()->setTextDatum(CR_DATUM);
btn->CanvasNormal()->pushImage(15, 14, 32, 32, ImageResource_item_icon_file_floder_32x32);
btn->CanvasNormal()->pushImage(532 - 15 - 32, 14, 32, 32, ImageResource_item_icon_arrow_r_32x32);
*(btn->CanvasPressed()) = *(btn->CanvasNormal());
btn->CanvasPressed()->ReverseColor();
btn->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, btn);
btn->AddArgs(EPDGUI_Button::EVENT_RELEASED, 1, (void*)(&_is_run));
btn->Bind(EPDGUI_Button::EVENT_RELEASED, key_fileindex_floder_cb);
}
for(int n = 0; n < files.size(); n++)
{
if(_key_files.size() > MAX_BTN_NUM)
{
break;
}
File file = files[n];
EPDGUI_Button *btn = new EPDGUI_Button(4, 100 + _key_files.size() * 60, 532, 61);
_key_files.push_back(btn);
String filename(file.name());
filename = filename.substring(filename.lastIndexOf("/"));
if(filename.length() > 19)
{
filename = filename.substring(0, 19) + "...";
}
btn->CanvasNormal()->fillCanvas(0);
btn->CanvasNormal()->drawRect(0, 0, 532, 61, 15);
btn->CanvasNormal()->setTextSize(26);
btn->CanvasNormal()->setTextDatum(CL_DATUM);
btn->CanvasNormal()->setTextColor(15);
btn->CanvasNormal()->drawString(filename, 47 + 13, 35);
btn->SetCustomString(file.name());
btn->CanvasNormal()->setTextDatum(CR_DATUM);
String suffix = filename.substring(filename.lastIndexOf("."));
if(suffix.indexOf("txt") >= 0)
{
btn->CanvasNormal()->pushImage(15, 14, 32, 32, ImageResource_item_icon_file_text_32x32);
btn->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, btn);
btn->AddArgs(EPDGUI_Button::EVENT_RELEASED, 1, (void*)(&_is_run));
btn->Bind(EPDGUI_Button::EVENT_RELEASED, key_fileindex_text_cb);
}
else if((suffix.indexOf("bmp") >= 0)
|| (suffix.indexOf("BMP") >= 0)
|| (suffix.indexOf("png") >= 0)
|| (suffix.indexOf("PNG") >= 0)
|| (suffix.indexOf("jpg") >= 0)
|| (suffix.indexOf("JPG") >= 0))
{
btn->CanvasNormal()->pushImage(15, 14, 32, 32, ImageResource_item_icon_file_image_32x32);
btn->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, btn);
btn->AddArgs(EPDGUI_Button::EVENT_RELEASED, 1, (void*)(&_is_run));
btn->Bind(EPDGUI_Button::EVENT_RELEASED, key_fileindex_image_cb);
}
else
{
btn->CanvasNormal()->pushImage(15, 14, 32, 32, ImageResource_item_icon_file_unknow_32x32);
btn->SetEnable(false);
}
char buf[50];
sprintf(buf, "%.2f KiB", file.size() / 1024.0f);
btn->CanvasNormal()->drawString(buf, 532 - 15, 35);
*(btn->CanvasPressed()) = *(btn->CanvasNormal());
btn->CanvasPressed()->ReverseColor();
}
}
Frame_FileIndex::~Frame_FileIndex(void)
{
for(int i = 0; i < _key_files.size(); i++)
{
delete _key_files[i];
}
}
int Frame_FileIndex::init(epdgui_args_vector_t &args)
{
_is_run = 1;
if(_key_files.size() == 0)
{
listDir(SD, _path.c_str());
}
M5.EPD.WriteFullGram4bpp(GetWallpaper());
_canvas_title->pushCanvas(0, 8, UPDATE_MODE_NONE);
EPDGUI_AddObject(_key_exit);
for(int i = 0; i < _key_files.size(); i++)
{
EPDGUI_AddObject(_key_files[i]);
}
return 3;
}

View File

@ -0,0 +1,21 @@
#ifndef _FRAME_FILEINDEX_H_
#define _FRAME_FILEINDEX_H_
#include "frame_base.h"
#include "../epdgui/epdgui.h"
#include <SD.h>
class Frame_FileIndex : public Frame_Base
{
public:
Frame_FileIndex(String path);
~Frame_FileIndex();
void listDir(fs::FS &fs, const char *dirname);
int init(epdgui_args_vector_t &args);
private:
std::vector<EPDGUI_Button*> _key_files;
String _path;
};
#endif //_FRAME_FILEINDEX_H_

259
src/frame/frame_home.cpp Normal file
View File

@ -0,0 +1,259 @@
#include "frame_home.h"
void Frame_Home::InitSwitch(EPDGUI_Switch* sw, String title, String subtitle, const uint8_t *img1, const uint8_t *img2)
{
memcpy(sw->Canvas(0)->frameBuffer(), ImageResource_home_button_background_228x228, 228 * 228 / 2);
sw->Canvas(0)->setTextSize(36);
sw->Canvas(0)->setTextDatum(TC_DATUM);
sw->Canvas(0)->drawString(title, 114, 136);
sw->Canvas(0)->setTextSize(26);
sw->Canvas(0)->drawString(subtitle, 114, 183);
memcpy(sw->Canvas(1)->frameBuffer(), sw->Canvas(0)->frameBuffer(), 228 * 228 / 2);
sw->Canvas(0)->pushImage(68, 20, 92, 92, img1);
sw->Canvas(1)->pushImage(68, 20, 92, 92, img2);
}
void key_home_air_adjust_cb(epdgui_args_vector_t &args)
{
int operation = ((EPDGUI_Button*)(args[0]))->GetCustomString().toInt();
EPDGUI_Switch *sw = ((EPDGUI_Switch*)(args[1]));
if(sw->getState() == 0)
{
return;
}
int temp = sw->GetCustomString().toInt();
char buf[10];
if(operation == 1)
{
temp++;
}
else
{
temp--;
}
sprintf(buf, "%d", temp);
sw->SetCustomString(buf);
sprintf(buf, "%d℃", temp);
sw->Canvas(1)->setTextSize(36);
sw->Canvas(1)->setTextDatum(TC_DATUM);
sw->Canvas(1)->fillRect(114 - 100, 108, 200, 38, 0);
sw->Canvas(1)->drawString(buf, 114, 108);
sw->Canvas(1)->pushCanvas(sw->getX(), sw->getY(), UPDATE_MODE_A2);
}
void key_home_air_state0_cb(epdgui_args_vector_t &args)
{
EPDGUI_Button *b1 = ((EPDGUI_Button*)(args[0]));
EPDGUI_Button *b2 = ((EPDGUI_Button*)(args[1]));
b1->SetEnable(false);
b2->SetEnable(false);
}
void key_home_air_state1_cb(epdgui_args_vector_t &args)
{
EPDGUI_Button *b1 = ((EPDGUI_Button*)(args[0]));
EPDGUI_Button *b2 = ((EPDGUI_Button*)(args[1]));
b1->SetEnable(true);
b2->SetEnable(true);
}
Frame_Home::Frame_Home(void)
{
_frame_name = "Frame_Home";
_sw_light1 = new EPDGUI_Switch(2, 20, 44 + 72, 228, 228);
_sw_light2 = new EPDGUI_Switch(2, 288, 44 + 72, 228, 228);
_sw_socket1 = new EPDGUI_Switch(2, 20, 324 + 72, 228, 228);
_sw_socket2 = new EPDGUI_Switch(2, 288, 324 + 72, 228, 228);
_sw_air_1 = new EPDGUI_Switch(2, 20, 604 + 72, 228, 184);
_sw_air_2 = new EPDGUI_Switch(2, 288, 604 + 72, 228, 184);
_key_air_1_plus = new EPDGUI_Button(20 + 116, 604 + 72 + 184, 112, 44);
_key_air_1_minus = new EPDGUI_Button(20, 604 + 72 + 184, 116, 44);
_key_air_2_plus = new EPDGUI_Button(288 + 116, 604 + 72 + 184, 112, 44);
_key_air_2_minus = new EPDGUI_Button(288, 604 + 72 + 184, 116, 44);
_key_air_1_plus ->SetCustomString("1");
_key_air_1_minus->SetCustomString("0");
_key_air_2_plus ->SetCustomString("1");
_key_air_2_minus->SetCustomString("0");
_key_air_1_plus->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, _key_air_1_plus);
_key_air_1_plus->AddArgs(EPDGUI_Button::EVENT_RELEASED, 1, _sw_air_1);
_key_air_1_plus->Bind(EPDGUI_Button::EVENT_RELEASED, key_home_air_adjust_cb);
_key_air_1_minus->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, _key_air_1_minus);
_key_air_1_minus->AddArgs(EPDGUI_Button::EVENT_RELEASED, 1, _sw_air_1);
_key_air_1_minus->Bind(EPDGUI_Button::EVENT_RELEASED, key_home_air_adjust_cb);
_key_air_2_plus->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, _key_air_2_plus);
_key_air_2_plus->AddArgs(EPDGUI_Button::EVENT_RELEASED, 1, _sw_air_2);
_key_air_2_plus->Bind(EPDGUI_Button::EVENT_RELEASED, key_home_air_adjust_cb);
_key_air_2_minus->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, _key_air_2_minus);
_key_air_2_minus->AddArgs(EPDGUI_Button::EVENT_RELEASED, 1, _sw_air_2);
_key_air_2_minus->Bind(EPDGUI_Button::EVENT_RELEASED, key_home_air_adjust_cb);
M5EPD_Canvas canvas_temp(&M5.EPD);
canvas_temp.createRender(36);
uint8_t language = GetLanguage();
if(language == LANGUAGE_JA)
{
InitSwitch(_sw_light1, "ランプ", "客間", ImageResource_home_icon_light_off_92x92, ImageResource_home_icon_light_on_92x92);
InitSwitch(_sw_light2, "ランプ", "寝室", ImageResource_home_icon_light_off_92x92, ImageResource_home_icon_light_on_92x92);
InitSwitch(_sw_socket1, "炊飯器", "厨房", ImageResource_home_icon_socket_off_92x92, ImageResource_home_icon_socket_on_92x92);
InitSwitch(_sw_socket2, "パソコン", "寝室", ImageResource_home_icon_socket_off_92x92, ImageResource_home_icon_socket_on_92x92);
}
else if(language == LANGUAGE_ZH)
{
InitSwitch(_sw_light1, "吸顶灯", "客厅", ImageResource_home_icon_light_off_92x92, ImageResource_home_icon_light_on_92x92);
InitSwitch(_sw_light2, "台灯", "卧室", ImageResource_home_icon_light_off_92x92, ImageResource_home_icon_light_on_92x92);
InitSwitch(_sw_socket1, "电饭煲", "厨房", ImageResource_home_icon_socket_off_92x92, ImageResource_home_icon_socket_on_92x92);
InitSwitch(_sw_socket2, "电脑", "卧室", ImageResource_home_icon_socket_off_92x92, ImageResource_home_icon_socket_on_92x92);
}
else
{
InitSwitch(_sw_light1, "Ceiling Light", "Living Room", ImageResource_home_icon_light_off_92x92, ImageResource_home_icon_light_on_92x92);
InitSwitch(_sw_light2, "Table Lamp", "Bedroom", ImageResource_home_icon_light_off_92x92, ImageResource_home_icon_light_on_92x92);
InitSwitch(_sw_socket1, "Rice Cooker", "Kitchen", ImageResource_home_icon_socket_off_92x92, ImageResource_home_icon_socket_on_92x92);
InitSwitch(_sw_socket2, "Computer", "Bedroom", ImageResource_home_icon_socket_off_92x92, ImageResource_home_icon_socket_on_92x92);
}
memcpy(_sw_air_1->Canvas(0)->frameBuffer(), ImageResource_home_air_background_228x184, 228 * 184 / 2);
_sw_air_1->Canvas(0)->setTextDatum(TC_DATUM);
_sw_air_1->Canvas(0)->setTextSize(26);
if(language == LANGUAGE_JA)
{
_sw_air_1->Canvas(0)->drawString("寝室", 114, 152);
}
else if(language == LANGUAGE_ZH)
{
_sw_air_1->Canvas(0)->drawString("卧室", 114, 152);
}
else
{
_sw_air_1->Canvas(0)->drawString("Bedroom", 114, 152);
}
memcpy(_sw_air_1->Canvas(1)->frameBuffer(), _sw_air_1->Canvas(0)->frameBuffer(), 228 * 184 / 2);
_sw_air_1->Canvas(0)->setTextSize(36);
_sw_air_1->Canvas(0)->drawString("OFF", 114, 108);
_sw_air_1->Canvas(1)->setTextSize(36);
_sw_air_1->Canvas(1)->setTextDatum(TC_DATUM);
_sw_air_1->Canvas(1)->drawString("26℃", 114, 108);
_sw_air_1->SetCustomString("26");
memcpy(_sw_air_2->Canvas(0)->frameBuffer(), ImageResource_home_air_background_228x184, 228 * 184 / 2);
_sw_air_2->Canvas(0)->setTextDatum(TC_DATUM);
_sw_air_2->Canvas(0)->setTextSize(26);
if(language == LANGUAGE_JA)
{
_sw_air_2->Canvas(0)->drawString("客間", 114, 152);
}
else if(language == LANGUAGE_ZH)
{
_sw_air_2->Canvas(0)->drawString("客厅", 114, 152);
}
else
{
_sw_air_2->Canvas(0)->drawString("Living Room", 114, 152);
}
memcpy(_sw_air_2->Canvas(1)->frameBuffer(), _sw_air_2->Canvas(0)->frameBuffer(), 228 * 184 / 2);
_sw_air_2->Canvas(0)->setTextSize(36);
_sw_air_2->Canvas(0)->drawString("OFF", 114, 108);
_sw_air_2->Canvas(1)->setTextSize(36);
_sw_air_2->Canvas(1)->setTextDatum(TC_DATUM);
_sw_air_2->Canvas(1)->drawString("26℃", 114, 108);
_sw_air_2->SetCustomString("26");
memcpy(_key_air_1_plus->CanvasNormal()->frameBuffer(), ImageResource_home_air_background_r_112x44, 112 * 44 / 2);
memcpy(_key_air_1_plus->CanvasPressed()->frameBuffer(), _key_air_1_plus->CanvasNormal()->frameBuffer(), 112 * 44 / 2);
_key_air_1_plus->CanvasPressed()->ReverseColor();
memcpy(_key_air_2_plus->CanvasNormal()->frameBuffer(), ImageResource_home_air_background_r_112x44, 112 * 44 / 2);
memcpy(_key_air_2_plus->CanvasPressed()->frameBuffer(), _key_air_2_plus->CanvasNormal()->frameBuffer(), 112 * 44 / 2);
_key_air_2_plus->CanvasPressed()->ReverseColor();
memcpy(_key_air_1_minus->CanvasNormal()->frameBuffer(), ImageResource_home_air_background_l_116x44, 116 * 44 / 2);
memcpy(_key_air_1_minus->CanvasPressed()->frameBuffer(), _key_air_1_minus->CanvasNormal()->frameBuffer(), 116 * 44 / 2);
_key_air_1_minus->CanvasPressed()->ReverseColor();
memcpy(_key_air_2_minus->CanvasNormal()->frameBuffer(), ImageResource_home_air_background_l_116x44, 116 * 44 / 2);
memcpy(_key_air_2_minus->CanvasPressed()->frameBuffer(), _key_air_2_minus->CanvasNormal()->frameBuffer(), 116 * 44 / 2);
_key_air_2_minus->CanvasPressed()->ReverseColor();
_key_air_1_plus->SetEnable(false);
_key_air_2_plus->SetEnable(false);
_key_air_1_minus->SetEnable(false);
_key_air_2_minus->SetEnable(false);
_sw_air_1->Canvas(0)->pushImage(68, 12, 92, 92, ImageResource_home_icon_conditioner_off_92x92);
_sw_air_1->Canvas(1)->pushImage(68, 12, 92, 92, ImageResource_home_icon_conditioner_on_92x92);
_sw_air_2->Canvas(0)->pushImage(68, 12, 92, 92, ImageResource_home_icon_conditioner_off_92x92);
_sw_air_2->Canvas(1)->pushImage(68, 12, 92, 92, ImageResource_home_icon_conditioner_on_92x92);
_sw_air_1->AddArgs(0, 0, _key_air_1_plus);
_sw_air_1->AddArgs(0, 1, _key_air_1_minus);
_sw_air_1->AddArgs(0, 2, _sw_air_1);
_sw_air_1->Bind(0, key_home_air_state0_cb);
_sw_air_1->AddArgs(1, 0, _key_air_1_plus);
_sw_air_1->AddArgs(1, 1, _key_air_1_minus);
_sw_air_1->AddArgs(1, 2, _sw_air_1);
_sw_air_1->Bind(1, key_home_air_state1_cb);
_sw_air_2->AddArgs(0, 0, _key_air_2_plus);
_sw_air_2->AddArgs(0, 1, _key_air_2_minus);
_sw_air_2->AddArgs(0, 2, _sw_air_2);
_sw_air_2->Bind(0, key_home_air_state0_cb);
_sw_air_2->AddArgs(1, 0, _key_air_2_plus);
_sw_air_2->AddArgs(1, 1, _key_air_2_minus);
_sw_air_2->AddArgs(1, 2, _sw_air_2);
_sw_air_2->Bind(1, key_home_air_state1_cb);
if(language == LANGUAGE_JA)
{
exitbtn("ホーム");
_canvas_title->drawString("コントロールパネル", 270, 34);
}
else if(language == LANGUAGE_ZH)
{
exitbtn("主页");
_canvas_title->drawString("控制面板", 270, 34);
}
else
{
exitbtn("Home");
_canvas_title->drawString("Control Panel", 270, 34);
}
_key_exit->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, (void*)(&_is_run));
_key_exit->Bind(EPDGUI_Button::EVENT_RELEASED, &Frame_Base::exit_cb);
}
Frame_Home::~Frame_Home(void)
{
delete _sw_light1;
delete _sw_light2;
delete _sw_socket1;
delete _sw_socket2;
delete _sw_air_1;
delete _sw_air_2;
delete _key_air_1_plus;
delete _key_air_1_minus;
delete _key_air_2_plus;
delete _key_air_2_minus;
}
int Frame_Home::init(epdgui_args_vector_t &args)
{
_is_run = 1;
M5.EPD.Clear();
_canvas_title->pushCanvas(0, 8, UPDATE_MODE_NONE);
EPDGUI_AddObject(_sw_light1);
EPDGUI_AddObject(_sw_light2);
EPDGUI_AddObject(_sw_socket1);
EPDGUI_AddObject(_sw_socket2);
EPDGUI_AddObject(_sw_air_1);
EPDGUI_AddObject(_sw_air_2);
EPDGUI_AddObject(_key_air_1_plus);
EPDGUI_AddObject(_key_air_1_minus);
EPDGUI_AddObject(_key_air_2_plus);
EPDGUI_AddObject(_key_air_2_minus);
EPDGUI_AddObject(_key_exit);
return 3;
}

27
src/frame/frame_home.h Normal file
View File

@ -0,0 +1,27 @@
#ifndef _FRAME_HOME_H_
#define _FRAME_HOME_H_
#include "frame_base.h"
#include "../epdgui/epdgui.h"
class Frame_Home : public Frame_Base
{
public:
Frame_Home();
~Frame_Home();
int init(epdgui_args_vector_t &args);
void InitSwitch(EPDGUI_Switch* sw, String title, String subtitle, const uint8_t *img1, const uint8_t *img2);
private:
EPDGUI_Switch *_sw_light1;
EPDGUI_Switch *_sw_light2;
EPDGUI_Switch *_sw_socket1;
EPDGUI_Switch *_sw_socket2;
EPDGUI_Switch *_sw_air_1;
EPDGUI_Switch *_sw_air_2;
EPDGUI_Button *_key_air_1_plus;
EPDGUI_Button *_key_air_1_minus;
EPDGUI_Button *_key_air_2_plus;
EPDGUI_Button *_key_air_2_minus;
};
#endif //_FRAME_HOME_H_

View File

@ -0,0 +1,147 @@
#include "frame_keyboard.h"
uint16_t textsize = 26;
void key_textclear_cb(epdgui_args_vector_t &args)
{
((EPDGUI_Textbox*)(args[0]))->SetText("");
}
void key_textsize_plus_cb(epdgui_args_vector_t &args)
{
textsize += 4;
if(textsize > 96)
{
textsize = 96;
}
char buf[10];
sprintf(buf, "%d", textsize);
((EPDGUI_Button*)(args[1]))->setLabel(buf);
((EPDGUI_Button*)(args[1]))->Draw(UPDATE_MODE_GL16);
((EPDGUI_Textbox*)(args[0]))->SetTextSize(textsize);
}
void key_textsize_minus_cb(epdgui_args_vector_t &args)
{
textsize -= 4;
if(textsize < 12)
{
textsize = 12;
}
char buf[10];
sprintf(buf, "%d", textsize);
((EPDGUI_Button*)(args[1]))->setLabel(buf);
((EPDGUI_Button*)(args[1]))->Draw(UPDATE_MODE_GL16);
((EPDGUI_Textbox*)(args[0]))->SetTextSize(textsize);
}
void key_textsize_reset_cb(epdgui_args_vector_t &args)
{
textsize = 26;
char buf[10];
sprintf(buf, "%d", textsize);
((EPDGUI_Button*)(args[1]))->setLabel(buf);
((EPDGUI_Button*)(args[1]))->Draw(UPDATE_MODE_GL16);
((EPDGUI_Textbox*)(args[0]))->SetTextSize(textsize);
}
Frame_Keyboard::Frame_Keyboard(bool isHorizontal) : Frame_Base()
{
_frame_name = "Frame_Keyboard";
uint8_t language = GetLanguage();
if(isHorizontal)
{
inputbox = new EPDGUI_Textbox(84, 25, 712, 250);
if(language == LANGUAGE_JA)
key_textclear = new EPDGUI_Button("削除", 804, 25, 72, 120);
else if(language == LANGUAGE_ZH)
key_textclear = new EPDGUI_Button("清屏", 804, 25, 72, 120);
else
key_textclear = new EPDGUI_Button("CLR", 804, 25, 72, 120);
key_textsize_plus = new EPDGUI_Button("+", 804, 157, 72, 40);
key_textsize_reset = new EPDGUI_Button("26", 804, 196, 72, 40);
key_textsize_minus = new EPDGUI_Button("-", 804, 235, 72, 40);
}
else
{
const uint16_t kKeyBaseY = 628;
inputbox = new EPDGUI_Textbox(4, 100, 532, 512);
if(language == LANGUAGE_JA)
key_textclear = new EPDGUI_Button("削除", 4, kKeyBaseY, 260, 52);
else if(language == LANGUAGE_ZH)
key_textclear = new EPDGUI_Button("清屏", 4, kKeyBaseY, 260, 52);
else
key_textclear = new EPDGUI_Button("CLR", 4, kKeyBaseY, 260, 52);
key_textsize_plus = new EPDGUI_Button("+", 448, kKeyBaseY, 88, 52);
key_textsize_reset = new EPDGUI_Button("26", 360, kKeyBaseY, 88, 52);
key_textsize_minus = new EPDGUI_Button("-", 272, kKeyBaseY, 88, 52);
}
inputbox->SetState(EPDGUI_Textbox::EVENT_PRESSED);
keyboard = new EPDGUI_Keyboard(isHorizontal);
key_textclear->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, (void*)inputbox);
key_textclear->Bind(EPDGUI_Button::EVENT_RELEASED, key_textclear_cb);
key_textsize_plus->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, (void*)inputbox);
key_textsize_plus->AddArgs(EPDGUI_Button::EVENT_RELEASED, 1, (void*)key_textsize_reset);
key_textsize_plus->Bind(EPDGUI_Button::EVENT_RELEASED, key_textsize_plus_cb);
key_textsize_reset->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, (void*)inputbox);
key_textsize_reset->AddArgs(EPDGUI_Button::EVENT_RELEASED, 1, (void*)key_textsize_reset);
key_textsize_reset->Bind(EPDGUI_Button::EVENT_RELEASED, key_textsize_reset_cb);
key_textsize_minus->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, (void*)inputbox);
key_textsize_minus->AddArgs(EPDGUI_Button::EVENT_RELEASED, 1, (void*)key_textsize_reset);
key_textsize_minus->Bind(EPDGUI_Button::EVENT_RELEASED, key_textsize_minus_cb);
if(language == LANGUAGE_JA)
{
exitbtn("ホーム");
_canvas_title->drawString("鍵盤", 270, 34);
}
else if(language == LANGUAGE_ZH)
{
exitbtn("主页");
_canvas_title->drawString("键盘", 270, 34);
}
else
{
exitbtn("Home");
_canvas_title->drawString("Keyboard", 270, 34);
}
_key_exit->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, (void*)(&_is_run));
_key_exit->Bind(EPDGUI_Button::EVENT_RELEASED, &Frame_Base::exit_cb);
}
Frame_Keyboard::~Frame_Keyboard()
{
delete inputbox;
delete keyboard;
delete key_textclear;
delete key_textsize_plus;
delete key_textsize_reset;
delete key_textsize_minus;
}
int Frame_Keyboard::init(epdgui_args_vector_t &args)
{
_is_run = 1;
M5.EPD.Clear();
_canvas_title->pushCanvas(0, 8, UPDATE_MODE_NONE);
EPDGUI_AddObject(inputbox);
EPDGUI_AddObject(keyboard);
EPDGUI_AddObject(_key_exit);
EPDGUI_AddObject(key_textclear);
EPDGUI_AddObject(key_textsize_plus);
EPDGUI_AddObject(key_textsize_reset);
EPDGUI_AddObject(key_textsize_minus);
return 6;
}
int Frame_Keyboard::run(void)
{
inputbox->AddText(keyboard->getData());
return 1;
}

View File

@ -0,0 +1,24 @@
#ifndef _FRAME_KEYBOARD_H_
#define _FRAME_KEYBOARD_H_
#include "frame_base.h"
#include "../epdgui/epdgui.h"
class Frame_Keyboard : public Frame_Base
{
public:
Frame_Keyboard(bool isHorizontal = false);
~Frame_Keyboard();
int run();
int init(epdgui_args_vector_t &args);
private:
EPDGUI_Textbox *inputbox;
EPDGUI_Keyboard *keyboard;
EPDGUI_Button *key_textclear;
EPDGUI_Button *key_textsize_plus;
EPDGUI_Button *key_textsize_reset;
EPDGUI_Button *key_textsize_minus;
};
#endif //_FRAME_KEYBOARD_H_

View File

@ -0,0 +1,250 @@
#include "frame_lifegame.h"
// #define CELL_W 10
// #define CELL_H 10
// #define CELL_X 54 + 2
// #define CELL_Y 88 + 2
#define CELL_W 4
#define CELL_H 4
#define CELL_X 135 + 2
#define CELL_Y 222 + 2
// #define CELL_W 2
// #define CELL_H 2
// #define CELL_X 270 + 2
// #define CELL_Y 444 + 2
static uint8_t lifegame_cells_flag = 0;
M5EPD_Canvas lifegame_cells_0(&M5.EPD);
M5EPD_Canvas lifegame_cells_1(&M5.EPD);
M5EPD_Canvas lifegame_canvas_0(&M5.EPD);
M5EPD_Canvas lifegame_canvas_1(&M5.EPD);
void LifeGame_RandomCell()
{
lifegame_cells_flag = 0;
uint8_t randbuf[CELL_X];
for (int y = 0; y < CELL_Y; y++)
{
esp_fill_random(randbuf, CELL_X);
for (int x = 0; x < CELL_X; x++)
{
lifegame_cells_0.drawPixel(x, y, randbuf[x] & 0x01 ? 15 : 0);
}
}
lifegame_cells_1.fillCanvas(0);
}
uint8_t LifeGame_Count3x3_0(uint8_t x, uint8_t y)
{
uint8_t count = 0;
for(int j = y - 1; j < y + 2; j++)
{
for(int i = x - 1; i < x + 2; i++)
{
if(lifegame_cells_0.readPixel(i, j))
{
count++;
}
}
}
if(lifegame_cells_0.readPixel(x, y))
{
count--;
}
return count;
}
uint8_t LifeGame_Count3x3_1(uint8_t x, uint8_t y)
{
uint8_t count = 0;
for(int j = y - 1; j < y + 2; j++)
{
for(int i = x - 1; i < x + 2; i++)
{
if(lifegame_cells_1.readPixel(i, j))
{
count++;
}
}
}
if(lifegame_cells_1.readPixel(x, y))
{
count--;
}
return count;
}
void LifeGame_CellProcess_0(uint8_t x, uint8_t y)
{
uint8_t count = LifeGame_Count3x3_0(x, y);
if(lifegame_cells_0.readPixel(x, y))
{
//dead
if(count < 2 || count > 3)
{
lifegame_cells_1.drawPixel(x, y, 0);
}
else
{
lifegame_cells_1.drawPixel(x, y, 15);
}
}
else
{
//new life
if(count == 3)
{
lifegame_cells_1.drawPixel(x, y, 15);
}
else
{
lifegame_cells_1.drawPixel(x, y, 0);
}
}
}
void LifeGame_CellProcess_1(uint8_t x, uint8_t y)
{
uint8_t count = LifeGame_Count3x3_1(x, y);
if(lifegame_cells_1.readPixel(x, y))
{
//dead
if(count < 2 || count > 3)
{
lifegame_cells_0.drawPixel(x, y, 0);
}
else
{
lifegame_cells_0.drawPixel(x, y, 15);
}
}
else
{
//new life
if(count == 3)
{
lifegame_cells_0.drawPixel(x, y, 15);
}
else
{
lifegame_cells_0.drawPixel(x, y, 0);
}
}
}
void LifeGame_RoundProcess()
{
if(lifegame_cells_flag == 0)
{
for (int y = 1; y < CELL_Y - 1; y++)
{
for (int x = 1; x < CELL_X - 1; x++)
{
LifeGame_CellProcess_0(x, y);
lifegame_canvas_0.fillRect((x - 1) * CELL_W, (y - 1) * CELL_H, CELL_W, CELL_H, lifegame_cells_1.readPixel(x, y));
}
}
lifegame_cells_flag = 1;
}
else
{
for (int y = 1; y < CELL_Y - 1; y++)
{
for (int x = 1; x < CELL_X - 1; x++)
{
LifeGame_CellProcess_1(x, y);
lifegame_canvas_1.fillRect((x - 1) * CELL_W, (y - 1) * CELL_H, CELL_W, CELL_H, lifegame_cells_0.readPixel(x, y));
}
}
lifegame_cells_flag = 0;
}
}
void LifeGame_NextGen(void *pvParameters)
{
LifeGame_RoundProcess();
vTaskDelete(NULL);
}
int Frame_Lifegame::run()
{
M5.update();
if(M5.BtnP.wasReleased())
{
LifeGame_RandomCell();
}
xTaskCreatePinnedToCore(LifeGame_NextGen, "LifeGame_NextGen", 4096, NULL, 1, NULL, 0);
if(lifegame_cells_flag == 0)
{
lifegame_canvas_1.pushCanvas(0, 72, UPDATE_MODE_DU4);
}
else
{
lifegame_canvas_0.pushCanvas(0, 72, UPDATE_MODE_DU4);
}
log_d("");
return 1;
}
void Frame_Lifegame::exit()
{
lifegame_cells_0.deleteCanvas();
lifegame_cells_1.deleteCanvas();
lifegame_canvas_0.deleteCanvas();
lifegame_canvas_1.deleteCanvas();
}
Frame_Lifegame::Frame_Lifegame(void)
{
_frame_name = "Frame_Lifegame";
uint8_t language = GetLanguage();
if(language == LANGUAGE_JA)
{
exitbtn("ホーム");
_canvas_title->drawString("ライフゲーム", 270, 34);
}
else if(language == LANGUAGE_ZH)
{
exitbtn("主页");
_canvas_title->drawString("生命游戏", 270, 34);
}
else
{
exitbtn("Home");
_canvas_title->drawString("Life Game", 270, 34);
}
_key_exit->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, (void*)(&_is_run));
_key_exit->Bind(EPDGUI_Button::EVENT_RELEASED, &Frame_Base::exit_cb);
}
Frame_Lifegame::~Frame_Lifegame(void)
{
}
int Frame_Lifegame::init(epdgui_args_vector_t &args)
{
_is_run = 1;
lifegame_cells_0.createCanvas(CELL_X, CELL_Y);
lifegame_cells_1.createCanvas(CELL_X, CELL_Y);
lifegame_canvas_0.createCanvas(540, 888);
lifegame_canvas_1.createCanvas(540, 888);
lifegame_cells_0.fillCanvas(0);
lifegame_cells_1.fillCanvas(0);
lifegame_canvas_0.fillCanvas(0);
lifegame_canvas_1.fillCanvas(0);
lifegame_cells_0.pushImage(2, 2, 132, 120, ImageResource_lifegame_seeder_132x120);
lifegame_cells_flag = 0;
M5.EPD.Clear();
_canvas_title->pushCanvas(0, 8, UPDATE_MODE_NONE);
EPDGUI_AddObject(_key_exit);
return 3;
}

View File

@ -0,0 +1,23 @@
#ifndef _FRAME_LIFEGAME_H_
#define _FRAME_LIFEGAME_H_
#include "frame_base.h"
#include "../epdgui/epdgui.h"
class Frame_Lifegame : public Frame_Base
{
public:
Frame_Lifegame();
~Frame_Lifegame();
int init(epdgui_args_vector_t &args);
int run();
void exit();
private:
M5EPD_Canvas *cells_0;
M5EPD_Canvas *cells_1;
M5EPD_Canvas *canvas_0;
M5EPD_Canvas *canvas_1;
};
#endif //_FRAME_LIFEGAME_H_

332
src/frame/frame_main.cpp Normal file
View File

@ -0,0 +1,332 @@
#include "frame_main.h"
#include "frame_setting.h"
#include "frame_keyboard.h"
#include "frame_factorytest.h"
#include "frame_wifiscan.h"
#include "frame_lifegame.h"
#include "frame_fileindex.h"
#include "frame_compare.h"
#include "frame_home.h"
enum
{
kKeyFactoryTest = 0,
kKeySetting,
kKeyKeyboard,
kKeyWifiScan,
kKeySDFile,
kKeyCompare,
kKeyHome,
kKeyLifeGame
};
#define KEY_W 92
#define KEY_H 92
void key_setting_cb(epdgui_args_vector_t &args)
{
Frame_Base *frame = EPDGUI_GetFrame("Frame_Setting");
if(frame == NULL)
{
frame = new Frame_Setting();
EPDGUI_AddFrame("Frame_Setting", frame);
}
EPDGUI_PushFrame(frame);
*((int*)(args[0])) = 0;
}
void key_keyboard_cb(epdgui_args_vector_t &args)
{
Frame_Base *frame = EPDGUI_GetFrame("Frame_Keyboard");
if(frame == NULL)
{
frame = new Frame_Keyboard(0);
EPDGUI_AddFrame("Frame_Keyboard", frame);
}
EPDGUI_PushFrame(frame);
*((int*)(args[0])) = 0;
}
void key_factorytest_cb(epdgui_args_vector_t &args)
{
Frame_Base *frame = EPDGUI_GetFrame("Frame_FactoryTest");
if(frame == NULL)
{
frame = new Frame_FactoryTest();
EPDGUI_AddFrame("Frame_FactoryTest", frame);
}
EPDGUI_PushFrame(frame);
*((int*)(args[0])) = 0;
}
void key_wifiscan_cb(epdgui_args_vector_t &args)
{
Frame_Base *frame = EPDGUI_GetFrame("Frame_WifiScan");
if(frame == NULL)
{
frame = new Frame_WifiScan();
EPDGUI_AddFrame("Frame_WifiScan", frame);
}
EPDGUI_PushFrame(frame);
*((int*)(args[0])) = 0;
}
void key_lifegame_cb(epdgui_args_vector_t &args)
{
Frame_Base *frame = EPDGUI_GetFrame("Frame_Lifegame");
if(frame == NULL)
{
frame = new Frame_Lifegame();
EPDGUI_AddFrame("Frame_Lifegame", frame);
}
EPDGUI_PushFrame(frame);
*((int*)(args[0])) = 0;
}
void key_sdfile_cb(epdgui_args_vector_t &args)
{
Frame_Base *frame = new Frame_FileIndex("/");
EPDGUI_PushFrame(frame);
*((int*)(args[0])) = 0;
}
void key_compare_cb(epdgui_args_vector_t &args)
{
Frame_Base *frame = EPDGUI_GetFrame("Frame_Compare");
if(frame == NULL)
{
frame = new Frame_Compare();
EPDGUI_AddFrame("Frame_Compare", frame);
}
EPDGUI_PushFrame(frame);
*((int*)(args[0])) = 0;
}
void key_home_cb(epdgui_args_vector_t &args)
{
Frame_Base *frame = EPDGUI_GetFrame("Frame_Home");
if(frame == NULL)
{
frame = new Frame_Home();
EPDGUI_AddFrame("Frame_Home", frame);
}
EPDGUI_PushFrame(frame);
*((int*)(args[0])) = 0;
}
Frame_Main::Frame_Main(void): Frame_Base(false)
{
_frame_name = "Frame_Main";
_frame_id = 1;
_bar = new M5EPD_Canvas(&M5.EPD);
_bar->createCanvas(540, 44);
_bar->setTextSize(26);
_names = new M5EPD_Canvas(&M5.EPD);
_names->createCanvas(540, 32);
_names->setTextDatum(CC_DATUM);
for(int i = 0; i < 4; i++)
{
_key[i] = new EPDGUI_Button("测试", 20 + i * 136, 90, KEY_W, KEY_H);
}
for(int i = 0; i < 4; i++)
{
_key[i + 4] = new EPDGUI_Button("测试", 20 + i * 136, 240, KEY_W, KEY_H);
}
_key[8] = new EPDGUI_Button(20, 390, KEY_W, KEY_H);
_key[kKeySetting]->CanvasNormal()->pushImage(0, 0, 92, 92, ImageResource_main_icon_setting_92x92);
*(_key[kKeySetting]->CanvasPressed()) = *(_key[kKeySetting]->CanvasNormal());
_key[kKeySetting]->CanvasPressed()->ReverseColor();
_key[kKeySetting]->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, (void*)(&_is_run));
_key[kKeySetting]->Bind(EPDGUI_Button::EVENT_RELEASED, key_setting_cb);
_key[kKeyKeyboard]->CanvasNormal()->pushImage(0, 0, 92, 92, ImageResource_main_icon_keyboard_92x92);
*(_key[kKeyKeyboard]->CanvasPressed()) = *(_key[kKeyKeyboard]->CanvasNormal());
_key[kKeyKeyboard]->CanvasPressed()->ReverseColor();
_key[kKeyKeyboard]->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, (void*)(&_is_run));
_key[kKeyKeyboard]->Bind(EPDGUI_Button::EVENT_RELEASED, key_keyboard_cb);
_key[kKeyFactoryTest]->CanvasNormal()->pushImage(0, 0, 92, 92, ImageResource_main_icon_factorytest_92x92);
*(_key[kKeyFactoryTest]->CanvasPressed()) = *(_key[kKeyFactoryTest]->CanvasNormal());
_key[kKeyFactoryTest]->CanvasPressed()->ReverseColor();
_key[kKeyFactoryTest]->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, (void*)(&_is_run));
_key[kKeyFactoryTest]->Bind(EPDGUI_Button::EVENT_RELEASED, key_factorytest_cb);
_key[kKeyWifiScan]->CanvasNormal()->pushImage(0, 0, 92, 92, ImageResource_main_icon_wifi_92x92);
*(_key[kKeyWifiScan]->CanvasPressed()) = *(_key[kKeyWifiScan]->CanvasNormal());
_key[kKeyWifiScan]->CanvasPressed()->ReverseColor();
_key[kKeyWifiScan]->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, (void*)(&_is_run));
_key[kKeyWifiScan]->Bind(EPDGUI_Button::EVENT_RELEASED, key_wifiscan_cb);
_key[kKeyLifeGame]->CanvasNormal()->pushImage(0, 0, 92, 92, ImageResource_main_icon_lifegame_92x92);
*(_key[kKeyLifeGame]->CanvasPressed()) = *(_key[kKeyLifeGame]->CanvasNormal());
_key[kKeyLifeGame]->CanvasPressed()->ReverseColor();
_key[kKeyLifeGame]->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, (void*)(&_is_run));
_key[kKeyLifeGame]->Bind(EPDGUI_Button::EVENT_RELEASED, key_lifegame_cb);
_key[kKeySDFile]->CanvasNormal()->pushImage(0, 0, 92, 92, ImageResource_main_icon_sdcard_92x92);
*(_key[kKeySDFile]->CanvasPressed()) = *(_key[kKeySDFile]->CanvasNormal());
_key[kKeySDFile]->CanvasPressed()->ReverseColor();
_key[kKeySDFile]->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, (void*)(&_is_run));
_key[kKeySDFile]->Bind(EPDGUI_Button::EVENT_RELEASED, key_sdfile_cb);
_key[kKeyCompare]->CanvasNormal()->pushImage(0, 0, 92, 92, ImageResource_main_icon_compare_92x92);
*(_key[kKeyCompare]->CanvasPressed()) = *(_key[kKeyCompare]->CanvasNormal());
_key[kKeyCompare]->CanvasPressed()->ReverseColor();
_key[kKeyCompare]->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, (void*)(&_is_run));
_key[kKeyCompare]->Bind(EPDGUI_Button::EVENT_RELEASED, key_compare_cb);
_key[kKeyHome]->CanvasNormal()->pushImage(0, 0, 92, 92, ImageResource_main_icon_home_92x92);
*(_key[kKeyHome]->CanvasPressed()) = *(_key[kKeyHome]->CanvasNormal());
_key[kKeyHome]->CanvasPressed()->ReverseColor();
_key[kKeyHome]->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, (void*)(&_is_run));
_key[kKeyHome]->Bind(EPDGUI_Button::EVENT_RELEASED, key_home_cb);
_time = 0;
_next_update_time = 0;
}
Frame_Main::~Frame_Main(void)
{
for(int i = 0; i < 8; i++)
{
delete _key[i];
}
}
void Frame_Main::AppName(m5epd_update_mode_t mode)
{
if(!_names->isRenderExist(20))
{
_names->createRender(20, 26);
}
_names->setTextSize(20);
_names->fillCanvas(0);
uint8_t language = GetLanguage();
_names->drawString("WLAN", 20 + 46 + 3 * 136, 16);
if(language == LANGUAGE_JA)
{
_names->drawString("工場テスト", 20 + 46, 16);
_names->drawString("設定", 20 + 46 + 136, 16);
_names->drawString("鍵盤", 20 + 46 + 2 * 136, 16);
}
else if(language == LANGUAGE_ZH)
{
_names->drawString("出厂测试", 20 + 46, 16);
_names->drawString("设定", 20 + 46 + 136, 16);
_names->drawString("键盘", 20 + 46 + 2 * 136, 16);
}
else
{
_names->drawString("Test", 20 + 46, 16);
_names->drawString("Setting", 20 + 46 + 136, 16);
_names->drawString("Keyboard", 20 + 46 + 2 * 136, 16);
}
_names->pushCanvas(0, 186, mode);
_names->fillCanvas(0);
if(language == LANGUAGE_JA)
{
_names->drawString("メモリー", 20 + 46, 16);
_names->drawString("刷新比較", 20 + 46 + 136, 16);
_names->drawString("", 20 + 46 + 2 * 136, 16);
_names->drawString("ライフゲーム", 20 + 46 + 3 * 136, 16);
}
else if(language == LANGUAGE_ZH)
{
_names->drawString("存储", 20 + 46, 16);
_names->drawString("刷新比较", 20 + 46 + 136, 16);
_names->drawString("", 20 + 46 + 2 * 136, 16);
_names->drawString("生命游戏", 20 + 46 + 3 * 136, 16);
}
else
{
_names->drawString("Storage", 20 + 46, 16);
_names->drawString("Compare", 20 + 46 + 136, 16);
_names->drawString("Home", 20 + 46 + 2 * 136, 16);
_names->drawString("LifeGame", 20 + 46 + 3 * 136, 16);
}
_names->pushCanvas(0, 337, mode);
}
void Frame_Main::StatusBar(m5epd_update_mode_t mode)
{
if((millis() - _time) < _next_update_time)
{
return;
}
char buf[20];
_bar->fillCanvas(0);
_bar->drawFastHLine(0, 43, 540, 15);
_bar->setTextDatum(CL_DATUM);
_bar->drawString("M5Paper", 10, 27);
// Battery
_bar->setTextDatum(CR_DATUM);
_bar->pushImage(498, 8, 32, 32, ImageResource_status_bar_battery_32x32);
uint32_t vol = M5.getBatteryVoltage();
if(vol < 3300)
{
vol = 3300;
}
else if(vol > 4350)
{
vol = 4350;
}
float battery = (float)(vol - 3300) / (float)(4350 - 3300);
if(battery <= 0.01)
{
battery = 0.01;
}
if(battery > 1)
{
battery = 1;
}
uint8_t px = battery * 25;
sprintf(buf, "%d%%", (int)(battery * 100));
_bar->drawString(buf, 498 - 10, 27);
_bar->fillRect(498 + 3, 8 + 10, px, 13, 15);
// Time
rtc_time_t time_struct;
rtc_date_t date_struct;
M5.RTC.getTime(&time_struct);
M5.RTC.getDate(&date_struct);
sprintf(buf, "%2d:%02d", time_struct.hour, time_struct.min);
_bar->setTextDatum(CC_DATUM);
_bar->drawString(buf, 270, 27);
_bar->pushCanvas(0, 0, mode);
_time = millis();
_next_update_time = (60 - time_struct.sec) * 1000;
}
int Frame_Main::init(epdgui_args_vector_t &args)
{
_is_run = 1;
M5.EPD.WriteFullGram4bpp(GetWallpaper());
for(int i = 0; i < 8; i++)
{
EPDGUI_AddObject(_key[i]);
}
_time = 0;
_next_update_time = 0;
StatusBar(UPDATE_MODE_NONE);
AppName(UPDATE_MODE_NONE);
return 9;
}
int Frame_Main::run()
{
StatusBar(UPDATE_MODE_GL16);
return 1;
}

24
src/frame/frame_main.h Normal file
View File

@ -0,0 +1,24 @@
#ifndef _FRAME_MAIN_H_
#define _FRAME_MAIN_H_
#include "frame_base.h"
class Frame_Main : public Frame_Base
{
public:
Frame_Main();
~Frame_Main();
int run();
int init(epdgui_args_vector_t &args);
void StatusBar(m5epd_update_mode_t mode);
void AppName(m5epd_update_mode_t mode);
private:
EPDGUI_Button *_key[9];
M5EPD_Canvas *_bar;
M5EPD_Canvas *_names;
uint32_t _next_update_time;
uint32_t _time;
};
#endif //_FRAME_MAIN_H_

View File

@ -0,0 +1,101 @@
#include "frame_pictureviewer.h"
#include "SD.h"
void key_pictureviewer_exit_cb(epdgui_args_vector_t &args)
{
EPDGUI_PopFrame(true);
*((int*)(args[0])) = 0;
}
Frame_PictureViewer::Frame_PictureViewer(String path)
{
_frame_name = "Frame_PictureViewer";
_pic_path = path;
_canvas_picture = new M5EPD_Canvas(&M5.EPD);
_canvas_picture->createCanvas(540, 888);
_canvas_picture->setTextSize(26);
_canvas_picture->setTextColor(0);
_canvas_picture->setTextDatum(CC_DATUM);
uint8_t language = GetLanguage();
if(language == LANGUAGE_JA)
{
exitbtn("戻る");
}
else if(language == LANGUAGE_ZH)
{
exitbtn("返回");
}
else
{
exitbtn("Back");
}
_canvas_title->drawString(path.substring(path.lastIndexOf("/") + 1, path.lastIndexOf(".")), 270, 34);
_key_exit->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, (void*)(&_is_run));
_key_exit->Bind(EPDGUI_Button::EVENT_RELEASED, &key_pictureviewer_exit_cb);
_is_first = true;
}
Frame_PictureViewer::~Frame_PictureViewer(void)
{
delete _canvas_picture;
}
void Frame_PictureViewer::err(String info)
{
_canvas_picture->fillCanvas(0);
_canvas_picture->fillRect(254 - 150, 500 - 50, 300, 100, 15);
_canvas_picture->drawString(info, 150, 55);
}
int Frame_PictureViewer::run()
{
if(_is_first)
{
_is_first = false;
LoadingAnime_32x32_Start(254, 500);
String suffix = _pic_path.substring(_pic_path.lastIndexOf("."));
if((suffix.indexOf("bmp") >= 0) || (suffix.indexOf("BMP") >= 0))
{
bool ret = _canvas_picture->drawBmpFile(SD, _pic_path.c_str(), 0, 0);
if(ret == 0)
{
err("Error opening " + _pic_path.substring(_pic_path.lastIndexOf("/")));
}
}
else if ((suffix.indexOf("png") >= 0) || (suffix.indexOf("PNG") >= 0))
{
bool ret = _canvas_picture->drawPngFile(SD, _pic_path.c_str());
if(ret == 0)
{
err("Error opening " + _pic_path.substring(_pic_path.lastIndexOf("/")));
}
}
else if ((suffix.indexOf("jpg") >= 0) || (suffix.indexOf("JPG") >= 0))
{
bool ret = _canvas_picture->drawJpgFile(SD, _pic_path.c_str());
if(ret == 0)
{
err("Error opening " + _pic_path.substring(_pic_path.lastIndexOf("/")));
}
}
LoadingAnime_32x32_Stop();
_canvas_picture->pushCanvas(0, 72, UPDATE_MODE_GC16);
}
return 1;
}
int Frame_PictureViewer::init(epdgui_args_vector_t &args)
{
_is_run = 1;
M5.EPD.Clear();
_canvas_title->pushCanvas(0, 8, UPDATE_MODE_NONE);
EPDGUI_AddObject(_key_exit);
return 3;
}

View File

@ -0,0 +1,22 @@
#ifndef _FRAME_PICTUREVIEWER_H_
#define _FRAME_PICTUREVIEWER_H_
#include "frame_base.h"
#include "../epdgui/epdgui.h"
class Frame_PictureViewer : public Frame_Base
{
public:
Frame_PictureViewer(String path);
~Frame_PictureViewer();
int init(epdgui_args_vector_t &args);
int run();
void err(String info);
private:
M5EPD_Canvas *_canvas_picture;
String _pic_path;
bool _is_first;
};
#endif //_FRAME_PICTUREVIEWER_H_

203
src/frame/frame_setting.cpp Normal file
View File

@ -0,0 +1,203 @@
#include "frame_setting.h"
#include "frame_setting_language.h"
#include "frame_setting_wallpaper.h"
#include "WiFi.h"
#define KEY_W 92
#define KEY_H 92
void key_shutdown_cb(epdgui_args_vector_t &args)
{
M5.EPD.WriteFullGram4bpp(GetWallpaper());
M5.EPD.UpdateFull(UPDATE_MODE_GC16);
M5.EPD.UpdateFull(UPDATE_MODE_GC16);
delay(600);
M5.disableEPDPower();
M5.disableEXTPower();
M5.disableMainPower();
esp_deep_sleep_start();
while(1);
}
void key_restart_cb(epdgui_args_vector_t &args)
{
esp_restart();
}
void key_language_cb(epdgui_args_vector_t &args)
{
Frame_Base *frame = EPDGUI_GetFrame("Frame_Setting_Language");
if(frame == NULL)
{
frame = new Frame_Setting_Language();
EPDGUI_AddFrame("Frame_Setting_Language", frame);
}
EPDGUI_PushFrame(frame);
*((int*)(args[0])) = 0;
}
void key_wallpaper_cb(epdgui_args_vector_t &args)
{
Frame_Base *frame = EPDGUI_GetFrame("Frame_Setting_Wallpaper");
if(frame == NULL)
{
frame = new Frame_Setting_Wallpaper();
EPDGUI_AddFrame("Frame_Setting_Wallpaper", frame);
}
EPDGUI_PushFrame(frame);
*((int*)(args[0])) = 0;
}
void key_synctime_cb(epdgui_args_vector_t &args)
{
M5EPD_Canvas info(&M5.EPD);
M5EPD_Canvas *title = (M5EPD_Canvas*)(args[0]);
info.createCanvas(300, 100);
info.fillCanvas(15);
info.setTextSize(26);
info.setTextColor(0);
info.setTextDatum(CC_DATUM);
uint8_t language = GetLanguage();
if(WiFi.status() != WL_CONNECTED)
{
if(language == LANGUAGE_JA)
{
info.drawString("WLANが接続いません", 150, 55);
}
else if(language == LANGUAGE_ZH)
{
info.drawString("WLAN未连接", 150, 55);
}
else
{
info.drawString("WLAN not connected", 150, 55);
}
info.pushCanvas(120, 430, UPDATE_MODE_GL16);
M5.EPD.WriteFullGram4bpp(GetWallpaper());
title->pushCanvas(0, 8, UPDATE_MODE_NONE);
EPDGUI_Draw(UPDATE_MODE_NONE);
while(!M5.TP.avaliable());
M5.EPD.UpdateFull(UPDATE_MODE_GL16);
return;
}
LoadingAnime_32x32_Start(532 - 15 - 32, 220 + 14);
bool ret = SyncNTPTime();
LoadingAnime_32x32_Stop();
if(ret == 0)
{
if(language == LANGUAGE_JA)
{
info.drawString("シンクロが失敗しました", 150, 55);
}
else if(language == LANGUAGE_ZH)
{
info.drawString("同步失败", 150, 55);
}
else
{
info.drawString("Time sync failed", 150, 55);
}
info.pushCanvas(120, 430, UPDATE_MODE_GL16);
}
else
{
if(language == LANGUAGE_JA)
{
info.drawString("成功", 150, 55);
}
else if(language == LANGUAGE_ZH)
{
info.drawString("成功", 150, 55);
}
else
{
info.drawString("Success", 150, 55);
}
info.pushCanvas(120, 430, UPDATE_MODE_GL16);
}
M5.EPD.WriteFullGram4bpp(GetWallpaper());
title->pushCanvas(0, 8, UPDATE_MODE_NONE);
EPDGUI_Draw(UPDATE_MODE_NONE);
while(!M5.TP.avaliable());
M5.EPD.UpdateFull(UPDATE_MODE_GL16);
}
Frame_Setting::Frame_Setting(void)
{
_frame_name = "Frame_Setting";
uint8_t language = GetLanguage();
_key_wallpaper = new EPDGUI_Button(4, 100, 532, 61);
_key_language = new EPDGUI_Button(4, 160, 532, 61);
_key_syncntp = new EPDGUI_Button(4, 220, 532, 61);
_key_restart = new EPDGUI_Button(4, 340, 532, 61);
_key_shutdown = new EPDGUI_Button(4, 400, 532, 61);
if(language == LANGUAGE_JA)
{
_key_wallpaper->setBMPButton(" 壁紙", "\u25B6", ImageResource_item_icon_wallpaper_32x32);
_key_language->setBMPButton(" 言語", "\u25B6", ImageResource_item_icon_language_32x32);
_key_syncntp->setBMPButton(" 時間シンクロ", "", ImageResource_item_icon_ntptime_32x32);
_key_restart->setBMPButton(" 再起動", "", ImageResource_item_icon_restart_32x32);
_key_shutdown->setBMPButton(" 電源オフ", "", ImageResource_item_icon_shutdown_32x32);
exitbtn("ホーム");
_canvas_title->drawString("設定", 270, 34);
}
else if(language == LANGUAGE_ZH)
{
_key_wallpaper->setBMPButton(" 壁纸", "\u25B6", ImageResource_item_icon_wallpaper_32x32);
_key_language->setBMPButton(" 语言", "\u25B6", ImageResource_item_icon_language_32x32);
_key_syncntp->setBMPButton(" 同步时间", "", ImageResource_item_icon_ntptime_32x32);
_key_restart->setBMPButton(" 重启", "", ImageResource_item_icon_restart_32x32);
_key_shutdown->setBMPButton(" 关机", "", ImageResource_item_icon_shutdown_32x32);
exitbtn("主页");
_canvas_title->drawString("设置", 270, 34);
}
else
{
_key_wallpaper->setBMPButton(" Wallpaper", "\u25B6", ImageResource_item_icon_wallpaper_32x32);
_key_language->setBMPButton(" Language", "\u25B6", ImageResource_item_icon_language_32x32);
_key_syncntp->setBMPButton(" Sync Time", "", ImageResource_item_icon_ntptime_32x32);
_key_restart->setBMPButton(" Restart", "", ImageResource_item_icon_restart_32x32);
_key_shutdown->setBMPButton(" Shutdown", "", ImageResource_item_icon_shutdown_32x32);
exitbtn("Home");
_canvas_title->drawString("Setting", 270, 34);
}
_key_exit->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, (void*)(&_is_run));
_key_exit->Bind(EPDGUI_Button::EVENT_RELEASED, &Frame_Base::exit_cb);
_key_language->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, (void*)(&_is_run));
_key_language->Bind(EPDGUI_Button::EVENT_RELEASED, &key_language_cb);
_key_wallpaper->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, (void*)(&_is_run));
_key_wallpaper->Bind(EPDGUI_Button::EVENT_RELEASED, &key_wallpaper_cb);
_key_shutdown->Bind(EPDGUI_Button::EVENT_RELEASED, &key_shutdown_cb);
_key_restart->Bind(EPDGUI_Button::EVENT_RELEASED, &key_restart_cb);
_key_syncntp->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, _canvas_title);
_key_syncntp->Bind(EPDGUI_Button::EVENT_RELEASED, &key_synctime_cb);
}
Frame_Setting::~Frame_Setting(void)
{
delete _key_wallpaper;
delete _key_language;
delete _key_shutdown;
delete _key_restart;
delete _key_syncntp;
}
int Frame_Setting::init(epdgui_args_vector_t &args)
{
_is_run = 1;
M5.EPD.WriteFullGram4bpp(GetWallpaper());
_canvas_title->pushCanvas(0, 8, UPDATE_MODE_NONE);
EPDGUI_AddObject(_key_wallpaper);
EPDGUI_AddObject(_key_language);
EPDGUI_AddObject(_key_shutdown);
EPDGUI_AddObject(_key_restart);
EPDGUI_AddObject(_key_syncntp);
EPDGUI_AddObject(_key_exit);
return 3;
}

23
src/frame/frame_setting.h Normal file
View File

@ -0,0 +1,23 @@
#ifndef _FRAME_SETTING_H_
#define _FRAME_SETTING_H_
#include "frame_base.h"
#include "../epdgui/epdgui.h"
class Frame_Setting : public Frame_Base
{
public:
Frame_Setting();
~Frame_Setting();
int init(epdgui_args_vector_t &args);
private:
EPDGUI_Button *_key_wallpaper;
EPDGUI_Button *_key_language;
EPDGUI_Button *_key_shutdown;
EPDGUI_Button *_key_restart;
EPDGUI_Button *_key_syncntp;
};
#endif //_FRAME_SETTING_H_

View File

@ -0,0 +1,103 @@
#include "frame_setting_language.h"
void sw_en_cb(epdgui_args_vector_t &args)
{
SetLanguage(LANGUAGE_EN);
}
void sw_zh_cb(epdgui_args_vector_t &args)
{
SetLanguage(LANGUAGE_ZH);
}
void sw_ja_cb(epdgui_args_vector_t &args)
{
SetLanguage(LANGUAGE_JA);
}
Frame_Setting_Language::Frame_Setting_Language(void)
{
_frame_name = "Frame_Setting_Language";
_sw_en = new EPDGUI_Switch(2, 4, 100, 532, 61);
_sw_zh = new EPDGUI_Switch(2, 4, 160, 532, 61);
_sw_ja = new EPDGUI_Switch(2, 4, 220, 532, 61);
if(isTTFLoaded())
{
_sw_en->SetLabel(0, "English");
_sw_en->SetLabel(1, "English");
_sw_en->Canvas(1)->ReverseColor();
_sw_en->Bind(1, &sw_en_cb);
_sw_zh->SetLabel(0, "中文");
_sw_zh->SetLabel(1, "中文");
_sw_zh->Canvas(1)->ReverseColor();
_sw_zh->Bind(1, &sw_zh_cb);
_sw_ja->SetLabel(0, "日本語");
_sw_ja->SetLabel(1, "日本語");
_sw_ja->Canvas(1)->ReverseColor();
_sw_ja->Bind(1, &sw_ja_cb);
}
else
{
_sw_en->SetLabel(0, "English");
_sw_en->SetLabel(1, "English");
_sw_en->Canvas(1)->ReverseColor();
_sw_en->Bind(1, &sw_en_cb);
_sw_zh->SetLabel(0, "Chinese (Need .ttf file)");
_sw_zh->SetLabel(1, "Chinese (Need .ttf file)");
_sw_zh->Canvas(1)->ReverseColor();
_sw_zh->Bind(1, &sw_zh_cb);
_sw_ja->SetLabel(0, "Japanese (Need .ttf file)");
_sw_ja->SetLabel(1, "Japanese (Need .ttf file)");
_sw_ja->Canvas(1)->ReverseColor();
_sw_ja->Bind(1, &sw_ja_cb);
}
_sw_mutex_group = new EPDGUI_MutexSwitch();
_sw_mutex_group->Add(_sw_en);
_sw_mutex_group->Add(_sw_zh);
_sw_mutex_group->Add(_sw_ja);
uint8_t language = GetLanguage();
if(language == LANGUAGE_JA)
{
exitbtn("設定");
_canvas_title->drawString("言語", 270, 34);
_sw_ja->setState(1);
}
else if(language == LANGUAGE_ZH)
{
exitbtn("设置");
_canvas_title->drawString("语言", 270, 34);
_sw_zh->setState(1);
}
else
{
exitbtn("Setting");
_canvas_title->drawString("Language", 270, 34);
_sw_en->setState(1);
}
_key_exit->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, (void*)(&_is_run));
_key_exit->Bind(EPDGUI_Button::EVENT_RELEASED, &Frame_Base::exit_cb);
}
Frame_Setting_Language::~Frame_Setting_Language(void)
{
delete _sw_en;
delete _sw_zh;
delete _sw_ja;
delete _sw_mutex_group;
}
int Frame_Setting_Language::init(epdgui_args_vector_t &args)
{
_is_run = 1;
M5.EPD.WriteFullGram4bpp(GetWallpaper());
_canvas_title->pushCanvas(0, 8, UPDATE_MODE_NONE);
EPDGUI_AddObject(_sw_mutex_group);
EPDGUI_AddObject(_key_exit);
return 2;
}

View File

@ -0,0 +1,21 @@
#ifndef _FRAME_LANGUAGE_H_
#define _FRAME_LANGUAGE_H_
#include "frame_base.h"
#include "../epdgui/epdgui.h"
class Frame_Setting_Language : public Frame_Base
{
public:
Frame_Setting_Language();
~Frame_Setting_Language();
int init(epdgui_args_vector_t &args);
private:
EPDGUI_Switch* _sw_en;
EPDGUI_Switch* _sw_zh;
EPDGUI_Switch* _sw_ja;
EPDGUI_MutexSwitch* _sw_mutex_group;
};
#endif //_FRAME_LANGUAGE_H_

View File

@ -0,0 +1,65 @@
#include "frame_setting_wallpaper.h"
void sw_wallpapers_cb(epdgui_args_vector_t &args)
{
SetWallpaper(*((uint32_t*)(args[0])));
}
Frame_Setting_Wallpaper::Frame_Setting_Wallpaper(void)
{
_frame_name = "Frame_Setting_Wallpaper";
_sw_mutex_group = new EPDGUI_MutexSwitch();
for(int i = 0; i < WALLPAPER_NUM; i++)
{
_sw_wallpapers[i] = new EPDGUI_Switch(2, 4, 100 + i * 60, 532, 61);
_sw_mutex_group->Add(_sw_wallpapers[i]);
_sw_wallpapers[i]->SetLabel(0, GetWallpaperName(i));
_sw_wallpapers[i]->SetLabel(1, GetWallpaperName(i));
_sw_wallpapers[i]->Canvas(1)->ReverseColor();
_sw_wallpapers[i]->SetID(i);
_sw_wallpapers[i]->AddArgs(1, 0, (void*)(_sw_wallpapers[i]->GetID_P()));
_sw_wallpapers[i]->Bind(1, &sw_wallpapers_cb);
}
_sw_wallpapers[GetWallpaperID()]->setState(1);
uint8_t language = GetLanguage();
if(language == LANGUAGE_JA)
{
exitbtn("設定");
_canvas_title->drawString("壁紙", 270, 34);
}
else if(language == LANGUAGE_ZH)
{
exitbtn("设置");
_canvas_title->drawString("壁纸", 270, 34);
}
else
{
exitbtn("Setting");
_canvas_title->drawString("Wallpaper", 270, 34);
}
_key_exit->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, (void*)(&_is_run));
_key_exit->Bind(EPDGUI_Button::EVENT_RELEASED, &Frame_Base::exit_cb);
}
Frame_Setting_Wallpaper::~Frame_Setting_Wallpaper(void)
{
for(int i = 0; i < WALLPAPER_NUM; i++)
{
delete _sw_wallpapers[i];
}
delete _sw_mutex_group;
}
int Frame_Setting_Wallpaper::init(epdgui_args_vector_t &args)
{
_is_run = 1;
M5.EPD.WriteFullGram4bpp(GetWallpaper());
_canvas_title->pushCanvas(0, 8, UPDATE_MODE_NONE);
EPDGUI_AddObject(_sw_mutex_group);
EPDGUI_AddObject(_key_exit);
return 2;
}

View File

@ -0,0 +1,19 @@
#ifndef _FRAME_WALLPAPER_H_
#define _FRAME_WALLPAPER_H_
#include "frame_base.h"
#include "../epdgui/epdgui.h"
class Frame_Setting_Wallpaper : public Frame_Base
{
public:
Frame_Setting_Wallpaper();
~Frame_Setting_Wallpaper();
int init(epdgui_args_vector_t &args);
private:
EPDGUI_Switch* _sw_wallpapers[WALLPAPER_NUM];
EPDGUI_MutexSwitch* _sw_mutex_group;
};
#endif //_FRAME_WALLPAPER_H_

View File

@ -0,0 +1,209 @@
#include "frame_txtreader.h"
void key_txtreader_exit_cb(epdgui_args_vector_t &args)
{
EPDGUI_PopFrame(true);
*((int*)(args[0])) = 0;
}
int8_t _key_operation = 0;
void key_nextpage_released_cb(epdgui_args_vector_t &args)
{
_key_operation = 1;
// *((int8_t*)(args[0])) = 1;
}
void key_prevpage_released_cb(epdgui_args_vector_t &args)
{
_key_operation = -1;
// *((int8_t*)(args[0])) = -1;
}
Frame_txtReader::Frame_txtReader(String path)
{
_frame_name = "Frame_txtReader";
_txt_path = path;
_text_size = GetTextSize();
_canvas_prev = new M5EPD_Canvas(&M5.EPD);
_canvas_current = new M5EPD_Canvas(&M5.EPD);
_canvas_next = new M5EPD_Canvas(&M5.EPD);
_canvas_page = new M5EPD_Canvas(&M5.EPD);
_key_next = new EPDGUI_Button("", 270, 72, 270, 888, EPDGUI_Button::STYLE_INVISABLE);
_key_prev = new EPDGUI_Button("", 0, 72, 270, 888, EPDGUI_Button::STYLE_INVISABLE);
// _key_next->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, &_key_operation);
_key_next->Bind(EPDGUI_Button::EVENT_RELEASED, key_nextpage_released_cb);
// _key_prev->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, &_key_operation);
_key_prev->Bind(EPDGUI_Button::EVENT_RELEASED, key_prevpage_released_cb);
_language = GetLanguage();
if(_language == LANGUAGE_JA)
{
exitbtn("戻る");
}
else if(_language == LANGUAGE_ZH)
{
exitbtn("返回");
}
else
{
exitbtn("Back");
}
_canvas_title->drawString(path.substring(path.lastIndexOf("/") + 1, path.lastIndexOf(".")), 270, 34);
_key_exit->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, (void*)(&_is_run));
_key_exit->Bind(EPDGUI_Button::EVENT_RELEASED, &key_txtreader_exit_cb);
}
Frame_txtReader::~Frame_txtReader(void)
{
if(_text_size != 26)
{
_canvas_prev->destoryRender(_text_size);
}
delete _canvas_prev;
delete _canvas_current;
delete _canvas_next;
delete _canvas_page;
delete _key_next;
delete _key_prev;
_txt_file.close();
}
uint32_t Frame_txtReader::renderText(uint32_t cursor, uint32_t length, M5EPD_Canvas *canvas)
{
canvas->fillCanvas(0);
canvas->setTextArea(10, 10, 520, 868);
canvas->setTextSize(_text_size);
char buf[length + 1];
_txt_file.seek(cursor, SeekSet);
uint32_t readlen = _txt_file.readBytes(buf, length);
buf[readlen] = '\0';
canvas->print(buf);
return canvas->getExceedOffset();
}
int Frame_txtReader::run()
{
if(_is_first)
{
LoadingAnime_32x32_Start(254, 500);
_is_first = false;
uint32_t cursor;
_page_cursor.insert(std::pair<uint32_t, uint32_t>(0, 0));
cursor = renderText(0, _render_len, _canvas_current);
if(cursor == 0)
{
_page_end = 0;
_end_accessed = true;
}
else
{
_page_end = _page + 1;
_page_cursor.insert(std::pair<uint32_t, uint32_t>(1, cursor));
uint32_t offset = renderText(_page_cursor[1], _render_len, _canvas_next);
if(offset == 0)
{
_page_end = 1;
_end_accessed = true;
}
else
{
_page_cursor.insert(std::pair<uint32_t, uint32_t>(2, cursor + offset));
}
}
LoadingAnime_32x32_Stop();
_canvas_current->pushCanvas(0, 72, UPDATE_MODE_GC16);
}
else
{
M5.update();
if(M5.BtnR.wasReleased() || (_key_operation == 1))
{
_key_operation = 0;
if(_page != _page_end)
{
_page++;
_canvas_next->pushCanvas(0, 72, UPDATE_MODE_GC16);
memcpy(_canvas_prev->frameBuffer(), _canvas_current->frameBuffer(), _canvas_current->getBufferSize());
memcpy(_canvas_current->frameBuffer(), _canvas_next->frameBuffer(), _canvas_next->getBufferSize());
if((_end_accessed == false) || (_page != _page_end))
{
uint32_t offset = renderText(_page_cursor[_page + 1], _render_len, _canvas_next);
if(offset != 0)
{
if(_page_cursor.count(_page + 2) == 0)
{
_page_cursor.insert(std::pair<uint32_t, uint32_t>(_page + 2, _page_cursor[_page + 1] + offset));
}
}
else if(_end_accessed == false)
{
_page_end = _page + 1;
_end_accessed = true;
}
if(!_end_accessed)
{
_page_end = _page + 1;
}
}
}
}
else if(M5.BtnL.wasReleased() || (_key_operation == -1))
{
_key_operation = 0;
if(_page > 0)
{
_page--;
_canvas_prev->pushCanvas(0, 72, UPDATE_MODE_GC16);
memcpy(_canvas_next->frameBuffer(), _canvas_current->frameBuffer(), _canvas_current->getBufferSize());
memcpy(_canvas_current->frameBuffer(), _canvas_prev->frameBuffer(), _canvas_prev->getBufferSize());
if(_page != 0)
{
renderText(_page_cursor[_page - 1], _render_len, _canvas_prev);
}
}
}
}
if(_last_page != _page)
{
_last_page = _page;
_canvas_page->setTextSize(26);
_canvas_page->fillCanvas(0);
char buf[5];
sprintf(buf, "%d", _page + 1);
_canvas_page->drawString(buf, 100, 42);
_canvas_page->pushCanvas(440 - 15, 0, UPDATE_MODE_GL16);
}
return 1;
}
int Frame_txtReader::init(epdgui_args_vector_t &args)
{
_is_run = 1;
M5.EPD.Clear();
_canvas_title->pushCanvas(0, 8, UPDATE_MODE_NONE);
_canvas_prev->createCanvas(540, 888);
_canvas_current->createCanvas(540, 888);
_canvas_next->createCanvas(540, 888);
_canvas_page->createCanvas(100, 60);
_canvas_page->setTextDatum(CR_DATUM);
if(!_canvas_prev->isRenderExist(_text_size))
{
_canvas_prev->createRender(_text_size, 128);
}
EPDGUI_AddObject(_key_exit);
EPDGUI_AddObject(_key_next);
EPDGUI_AddObject(_key_prev);
_txt_file = SD.open(_txt_path);
_last_page = 0;
return 3;
}

View File

@ -0,0 +1,40 @@
#ifndef _FRAME_TXTREADER_H_
#define _FRAME_TXTREADER_H_
#include "frame_base.h"
#include "../epdgui/epdgui.h"
#include "SD.h"
class Frame_txtReader : public Frame_Base
{
public:
Frame_txtReader(String path);
~Frame_txtReader();
int init(epdgui_args_vector_t &args);
uint32_t renderText(uint32_t cursor, uint32_t length, M5EPD_Canvas *canvas);
int run();
private:
EPDGUI_Button *_key_next;
EPDGUI_Button *_key_prev;
uint8_t _language;
uint16_t _text_size = 32;
M5EPD_Canvas *_canvas_prev;
M5EPD_Canvas *_canvas_current;
M5EPD_Canvas *_canvas_next;
M5EPD_Canvas *_canvas_page;
uint32_t _cursor_prev = 0;
uint32_t _cursor_current = 0;
uint32_t _cursor_next = 0;
uint32_t _render_len = 1000;
uint32_t _page = 0;
uint32_t _last_page = 0xFFFFFFFF;
String _txt_path;
File _txt_file;
std::map<uint32_t, uint32_t> _page_cursor;
uint32_t _page_end = 0;
bool _end_accessed = false;
bool _is_first = true;
};
#endif //_FRAME_TXTREADER_H_

View File

@ -0,0 +1,97 @@
#include "frame_wifipassword.h"
void key_passwordclear_cb(epdgui_args_vector_t &args)
{
((EPDGUI_Textbox*)(args[0]))->SetText("");
}
Frame_WifiPassword::Frame_WifiPassword(bool isHorizontal) : Frame_Base()
{
_frame_name = "Frame_WifiPassword";
uint8_t language = GetLanguage();
if(isHorizontal)
{
inputbox = new EPDGUI_Textbox(84, 25, 712, 250);
if(language == LANGUAGE_JA)
key_textclear = new EPDGUI_Button("削除", 804, 25, 72, 120);
else if(language == LANGUAGE_ZH)
key_textclear = new EPDGUI_Button("清除", 804, 25, 72, 120);
else
key_textclear = new EPDGUI_Button("CLR", 804, 25, 72, 120);
}
else
{
const uint16_t kKeyBaseY = 176;
inputbox = new EPDGUI_Textbox(4, 100, 532, 60);
if(language == LANGUAGE_JA)
key_textclear = new EPDGUI_Button("削除", 4, kKeyBaseY, 260, 52);
else if(language == LANGUAGE_ZH)
key_textclear = new EPDGUI_Button("清除", 4, kKeyBaseY, 260, 52);
else
key_textclear = new EPDGUI_Button("CLR", 4, kKeyBaseY, 260, 52);
}
inputbox->SetTextMargin(8, 15, 8, 8);
inputbox->SetState(EPDGUI_Textbox::EVENT_PRESSED);
keyboard = new EPDGUI_Keyboard(isHorizontal, EPDGUI_Keyboard::STYLE_INPUTMODE_NEEDCONFIRM);
key_textclear->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, (void*)inputbox);
key_textclear->Bind(EPDGUI_Button::EVENT_RELEASED, key_passwordclear_cb);
if(language == LANGUAGE_JA)
{
exitbtn("WLAN");
_canvas_title->drawString("パスワード", 270, 34);
}
else if(language == LANGUAGE_ZH)
{
exitbtn("无线局域网", 200);
_canvas_title->drawString("密码", 270, 34);
}
else
{
exitbtn("WLAN");
_canvas_title->drawString("Password", 270, 34);
}
_key_exit->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, (void*)(&_is_run));
_key_exit->Bind(EPDGUI_Button::EVENT_RELEASED, &Frame_Base::exit_cb);
}
Frame_WifiPassword::~Frame_WifiPassword()
{
delete inputbox;
delete keyboard;
delete key_textclear;
}
int Frame_WifiPassword::init(epdgui_args_vector_t &args)
{
_is_run = 1;
M5.EPD.Clear();
_canvas_title->pushCanvas(0, 8, UPDATE_MODE_NONE);
EPDGUI_AddObject(inputbox);
EPDGUI_AddObject(keyboard);
EPDGUI_AddObject(_key_exit);
EPDGUI_AddObject(key_textclear);
return 6;
}
int Frame_WifiPassword::run(void)
{
String data = keyboard->getData();
if(data.indexOf("\n") >= 0)
{
String *pswd = new String(inputbox->GetText());
EPDGUI_AddFrameArg("Frame_WifiScan", 0, pswd);
inputbox->SetText("");
EPDGUI_PopFrame();
_is_run = 0;
return 0;
}
inputbox->AddText(data);
return 1;
}

View File

@ -0,0 +1,21 @@
#ifndef _FRAME_WIFIPASSWORD_H_
#define _FRAME_WIFIPASSWORD_H_
#include "frame_base.h"
#include "../epdgui/epdgui.h"
class Frame_WifiPassword : public Frame_Base
{
public:
Frame_WifiPassword(bool isHorizontal = false);
~Frame_WifiPassword();
int run();
int init(epdgui_args_vector_t &args);
private:
EPDGUI_Textbox *inputbox;
EPDGUI_Keyboard *keyboard;
EPDGUI_Button *key_textclear;
};
#endif //_FRAME_WIFIPASSWORD_H_

View File

@ -0,0 +1,373 @@
#include "frame_wifiscan.h"
#include "frame_wifipassword.h"
#include <WiFi.h>
#define MAX_BTN_NUM 14
#define MAX_WIFI_NUM (MAX_BTN_NUM - 1)
bool _update_flag = false;
EPDGUI_Button *_connect_key = NULL;
const uint8_t *kIMGWifiLevel[4] = {
NULL,
ImageResource_item_icon_wifi_1_32x32,
ImageResource_item_icon_wifi_2_32x32,
ImageResource_item_icon_wifi_3_32x32
};
void key_wifi_cb(epdgui_args_vector_t &args)
{
if(((EPDGUI_Button*)(args[0]))->GetCustomString() == "_$refresh$_")
{
_update_flag = true;
}
else
{
_connect_key = (EPDGUI_Button*)(args[0]);
Frame_Base *frame = EPDGUI_GetFrame("Frame_WifiPassword");
if(frame == NULL)
{
frame = new Frame_WifiPassword(false);
EPDGUI_AddFrame("Frame_WifiPassword", frame);
}
EPDGUI_PushFrame(frame);
*((int*)(args[1])) = 0;
}
}
Frame_WifiScan::Frame_WifiScan(void)
{
_frame_name = "Frame_WifiScan";
for(int i = 0; i < MAX_BTN_NUM; i++)
{
_key_wifi[i] = new EPDGUI_Button(4, 100 + i * 60, 532, 61);
_key_wifi[i]->SetHide(true);
_key_wifi[i]->CanvasNormal()->setTextSize(26);
_key_wifi[i]->CanvasNormal()->setTextDatum(CL_DATUM);
_key_wifi[i]->CanvasNormal()->setTextColor(15);
_key_wifi[i]->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, _key_wifi[i]);
_key_wifi[i]->AddArgs(EPDGUI_Button::EVENT_RELEASED, 1, (void*)(&_is_run));
_key_wifi[i]->Bind(EPDGUI_Button::EVENT_RELEASED, key_wifi_cb);
}
_language = GetLanguage();
if(_language == LANGUAGE_JA)
{
exitbtn("ホーム");
_canvas_title->drawString("WLAN", 270, 34);
}
else if(_language == LANGUAGE_ZH)
{
exitbtn("主页");
_canvas_title->drawString("无线局域网", 270, 34);
}
else
{
exitbtn("Home");
_canvas_title->drawString("WLAN", 270, 34);
}
_key_exit->AddArgs(EPDGUI_Button::EVENT_RELEASED, 0, (void*)(&_is_run));
_key_exit->Bind(EPDGUI_Button::EVENT_RELEASED, &Frame_Base::exit_cb);
_update_flag = true;
_connected = 0;
}
Frame_WifiScan::~Frame_WifiScan(void)
{
for(int i = 0; i < MAX_BTN_NUM; i++)
{
delete _key_wifi[i];
}
}
void Frame_WifiScan::DrawItem(EPDGUI_Button *btn, String ssid, int rssi)
{
int level = 0;
if(rssi > -55)
{
level = 3;
}
else if(rssi > -88)
{
level = 2;
}
else
{
level = 1;
}
if(ssid.length() > 22)
{
ssid = ssid.substring(0, 22) + "...";
}
btn->SetHide(false);
btn->CanvasNormal()->fillCanvas(0);
btn->CanvasNormal()->drawRect(0, 0, 532, 61, 15);
btn->CanvasNormal()->drawString(ssid, 15, 35);
btn->SetCustomString(ssid);
btn->CanvasNormal()->pushImage(532 - 15 - 32, 14, 32, 32, kIMGWifiLevel[level]);
*(btn->CanvasPressed()) = *(btn->CanvasNormal());
btn->CanvasPressed()->ReverseColor();
}
int Frame_WifiScan::run()
{
if(_connect)
{
_connect = false;
Connect();
}
if(_update_flag)
{
_update_flag = false;
scan();
}
return 1;
}
int Frame_WifiScan::scan()
{
WiFi.mode(WIFI_STA);
// WiFi.disconnect();
WiFi.scanNetworks(true);
if(_scan_count > 0)
{
M5.EPD.WriteFullGram4bpp(GetWallpaper());
_canvas_title->pushCanvas(0, 8, UPDATE_MODE_NONE);
_key_exit->Draw(UPDATE_MODE_NONE);
M5.EPD.UpdateFull(UPDATE_MODE_GC16);
}
_scan_count++;
int wifi_num;
while(1)
{
wifi_num = WiFi.scanComplete();
if(wifi_num >= 0)
{
break;
}
}
int connect_wifi_idx = -1;
if(_connected)
{
for(int i = 0; i < wifi_num; i++)
{
String ssid = WiFi.SSID(i);
if(ssid == _connect_ssid)
{
connect_wifi_idx = i;
if(WiFi.RSSI(i) < -90)
{
connect_wifi_idx = -1;
}
break;
}
}
if(connect_wifi_idx == -1)
{
WiFi.disconnect();
_key_wifi[0]->SetEnable(true);
_connected = 0;
for(int i = 1; i < MAX_BTN_NUM; i++)
{
_key_wifi[i]->SetPos(_key_wifi[i]->getX(), _key_wifi[i]->getY() - 32);
}
}
}
wifi_num = wifi_num > MAX_WIFI_NUM ? MAX_WIFI_NUM : wifi_num;
wifi_num -= _connected;
for(int i = _connected; i < MAX_BTN_NUM; i++)
{
_key_wifi[i]->SetHide(true);
}
if(_connected)
{
_key_wifi[0]->Draw(UPDATE_MODE_A2);
}
int idx = 0, cnt = _connected;
while(1)
{
if(idx == connect_wifi_idx)
{
idx++;
continue;
}
String ssid = WiFi.SSID(idx);
DrawItem(_key_wifi[cnt], ssid, WiFi.RSSI(idx));
_key_wifi[cnt]->Draw(UPDATE_MODE_A2);
idx++;
if(idx == wifi_num)
{
break;
}
cnt++;
}
_key_wifi[wifi_num]->SetCustomString("_$refresh$_");
_key_wifi[wifi_num]->SetHide(false);
_key_wifi[wifi_num]->CanvasNormal()->fillCanvas(0);
_key_wifi[wifi_num]->CanvasNormal()->drawRect(0, 0, 532, 61, 15);
_key_wifi[wifi_num]->CanvasNormal()->pushImage(15, 14, 32, 32, ImageResource_item_icon_refresh_32x32);
if(_language == LANGUAGE_JA)
{
_key_wifi[wifi_num]->CanvasNormal()->drawString("刷新", 58, 35);
}
else if(_language == LANGUAGE_ZH)
{
_key_wifi[wifi_num]->CanvasNormal()->drawString("刷新", 58, 35);
}
else
{
_key_wifi[wifi_num]->CanvasNormal()->drawString("Refresh", 58, 35);
}
*(_key_wifi[wifi_num]->CanvasPressed()) = *(_key_wifi[wifi_num]->CanvasNormal());
_key_wifi[wifi_num]->CanvasPressed()->ReverseColor();
_key_wifi[wifi_num]->Draw(UPDATE_MODE_A2);
M5.EPD.UpdateFull(UPDATE_MODE_GL16);
// M5.EPD.UpdateArea(0, 64, 540, 72, UPDATE_MODE_GL16);
WiFi.scanDelete();
return 0;
}
void Frame_WifiScan::Connect()
{
int anime_cnt = 0;
int x = 532 - 15 - 32;
int y = _connect_key->getY() + 14;
M5EPD_Canvas loading(&M5.EPD);
loading.createCanvas(32, 32);
loading.fillCanvas(0);
loading.pushCanvas(x, y, UPDATE_MODE_GL16);
_connect_ssid = _connect_key->GetCustomString();
log_d("SSID = [%s]\n", _connect_ssid.c_str());
log_d("PSWD = [%s]\n", _connect_password.c_str());
WiFi.disconnect();
WiFi.begin(_connect_ssid.c_str(), _connect_password.c_str());
uint32_t start_time = millis();
while (WiFi.status() != WL_CONNECTED)
{
loading.pushImage(0, 0, 32, 32, GetLoadingIMG_32x32(anime_cnt));
loading.pushCanvas(x, y, UPDATE_MODE_DU4);
anime_cnt++;
if(anime_cnt == 16)
{
anime_cnt = 0;
}
if (millis() - start_time > 10000)
{
M5EPD_Canvas err(&M5.EPD);
err.createCanvas(300, 100);
err.fillCanvas(15);
err.setTextSize(26);
err.setTextColor(0);
err.setTextDatum(CC_DATUM);
if(_language == LANGUAGE_JA)
{
err.drawString("パスワードが違います", 150, 55);
}
else if(_language == LANGUAGE_ZH)
{
err.drawString("密码错误", 150, 55);
}
else
{
err.drawString("Wrong password", 150, 55);
}
err.pushCanvas(120, 430, UPDATE_MODE_GL16);
return;
}
}
for(int i = 1; i < MAX_BTN_NUM; i++)
{
_key_wifi[i]->SetPos(_key_wifi[i]->getX(), _key_wifi[i]->getY() + 32);
}
_connect_key->CanvasNormal()->pushImage(532 - 15 - 32, 14, 32, 32, ImageResource_item_icon_success_32x32);
_key_wifi[0]->SetEnable(false);
_key_wifi[0]->SetHide(false);
if(_connect_key != _key_wifi[0])
{
*(_key_wifi[0]->CanvasNormal()) = *(_connect_key->CanvasNormal());
*(_key_wifi[0]->CanvasPressed()) = *(_connect_key->CanvasNormal());
_key_wifi[0]->CanvasPressed()->ReverseColor();
}
loading.pushImage(0, 0, 32, 32, ImageResource_item_icon_success_32x32);
loading.pushCanvas(x, y, UPDATE_MODE_GL16);
_connected = 1;
SetWifi(_connect_ssid, _connect_password);
// SyncNTPTime();
scan();
}
void Frame_WifiScan::SetConnected(String ssid, int rssi)
{
_connect_ssid = ssid;
DrawItem(_key_wifi[0], ssid, rssi);
for(int i = 1; i < MAX_BTN_NUM; i++)
{
_key_wifi[i]->SetPos(_key_wifi[i]->getX(), _key_wifi[i]->getY() + 32);
}
_key_wifi[0]->SetEnable(false);
_key_wifi[0]->SetHide(false);
_connected = 1;
}
int Frame_WifiScan::init(epdgui_args_vector_t &args)
{
_is_run = 1;
_connect = false;
M5.EPD.WriteFullGram4bpp(GetWallpaper());
_canvas_title->pushCanvas(0, 8, UPDATE_MODE_NONE);
if(args.size() > 0)
{
String *password = (String*)(args[0]);
_connect_password = *password;
delete password;
args.pop_back();
for(int i = 0; i < MAX_BTN_NUM; i++)
{
EPDGUI_AddObject(_key_wifi[i]);
}
_update_flag = false;
_connect = true;
}
else
{
for(int i = 0; i < MAX_BTN_NUM; i++)
{
_key_wifi[i]->SetHide(true);
EPDGUI_AddObject(_key_wifi[i]);
}
if(_connected)
{
_key_wifi[0]->SetHide(false);
}
_update_flag = true;
_scan_count = 0;
_connect = false;
}
EPDGUI_AddObject(_key_exit);
return 3;
}

View File

@ -0,0 +1,29 @@
#ifndef _FRAME_WIFISCAN_H_
#define _FRAME_WIFISCAN_H_
#include "frame_base.h"
#include "../epdgui/epdgui.h"
class Frame_WifiScan : public Frame_Base
{
public:
Frame_WifiScan();
~Frame_WifiScan();
int init(epdgui_args_vector_t &args);
int scan();
int run();
void Connect();
void DrawItem(EPDGUI_Button *btn, String ssid, int rssi);
void SetConnected(String ssid, int rssi);
private:
EPDGUI_Button *_key_wifi[14];
uint8_t _language;
uint32_t _scan_count = 0;
bool _connect;
uint8_t _connected;
String _connect_ssid;
String _connect_password;
};
#endif //_FRAME_SETTING_H_

301
src/global_setting.cpp Normal file
View File

@ -0,0 +1,301 @@
#include "global_setting.h"
#include "./resources/ImageResource.h"
#include "esp32-hal-log.h"
#include <WiFi.h>
#define DEFAULT_WALLPAPER 2
SemaphoreHandle_t _xSemaphore_LoadingAnime = NULL;
static uint8_t _loading_anime_eixt_flag = false;
esp_err_t __espret__;
#define NVS_CHECK(x) \
__espret__ = x; \
if (__espret__ != ESP_OK) \
{ \
nvs_close(nvs_arg); \
log_e("Check Err"); \
return __espret__; \
}
const uint8_t *wallpapers[] = {
ImageResource_wallpaper_m5stack_540x960,
ImageResource_wallpaper_engine_540x960,
ImageResource_wallpaper_penrose_triangle_540x960
};
const uint8_t *kIMGLoading[16] = {
ImageResource_item_loading_01_32x32,
ImageResource_item_loading_02_32x32,
ImageResource_item_loading_03_32x32,
ImageResource_item_loading_04_32x32,
ImageResource_item_loading_05_32x32,
ImageResource_item_loading_06_32x32,
ImageResource_item_loading_07_32x32,
ImageResource_item_loading_08_32x32,
ImageResource_item_loading_09_32x32,
ImageResource_item_loading_10_32x32,
ImageResource_item_loading_11_32x32,
ImageResource_item_loading_12_32x32,
ImageResource_item_loading_13_32x32,
ImageResource_item_loading_14_32x32,
ImageResource_item_loading_15_32x32,
ImageResource_item_loading_16_32x32
};
const char *wallpapers_name_en[] = {
"M5Paper",
"Engine",
"Penrose Triangle"
};
const char *wallpapers_name_zh[] = {
"M5Paper",
"引擎",
"彭罗斯三角"
};
const char *wallpapers_name_ja[] = {
"M5Paper",
"エンジン",
"ペンローズの三角形"
};
uint16_t global_wallpaper = DEFAULT_WALLPAPER;
uint8_t global_language = LANGUAGE_EN;
String global_wifi_ssid;
String global_wifi_password;
uint8_t global_wifi_configed = false;
uint16_t global_reader_textsize = 32;
uint8_t global_time_synced = false;
uint8_t global_ttf_file_loaded = false;
uint8_t global_init_status = 0xFF;
void SetInitStatus(uint8_t idx, uint8_t val)
{
global_init_status &= ~(1 << idx);
global_init_status |= (val << idx);
}
uint8_t GetInitStatus(uint8_t idx)
{
return (global_init_status & (1 << idx)) ? true : false;
}
void SetTTFLoaded(uint8_t val)
{
global_ttf_file_loaded = val;
}
uint8_t isTTFLoaded()
{
return global_ttf_file_loaded;
}
uint8_t isTimeSynced(void)
{
return global_time_synced;
}
void SetTimeSynced(uint8_t val)
{
global_time_synced = val;
SaveSetting();
}
void SetLanguage(uint8_t language)
{
if (language >= LANGUAGE_EN && language <= LANGUAGE_ZH)
{
global_language = language;
}
SaveSetting();
}
uint8_t GetLanguage(void)
{
return global_language;
}
void SetWallpaper(uint16_t wallpaper_id)
{
global_wallpaper = wallpaper_id;
SaveSetting();
}
uint16_t GetWallpaperID(void)
{
return global_wallpaper;
}
const uint8_t *GetWallpaper(void)
{
return wallpapers[global_wallpaper];
}
const char *GetWallpaperName(uint16_t wallpaper_id)
{
switch (global_language)
{
case LANGUAGE_ZH:
return wallpapers_name_zh[wallpaper_id];
case LANGUAGE_JA:
return wallpapers_name_ja[wallpaper_id];
default:
return wallpapers_name_en[wallpaper_id];
}
}
esp_err_t LoadSetting(void)
{
nvs_handle nvs_arg;
NVS_CHECK(nvs_open("Setting", NVS_READONLY, &nvs_arg));
NVS_CHECK(nvs_get_u16(nvs_arg, "Wallpaper", &global_wallpaper));
NVS_CHECK(nvs_get_u8(nvs_arg, "Language", &global_language));
NVS_CHECK(nvs_get_u8(nvs_arg, "Timesync", &global_time_synced));
if(global_wallpaper >= WALLPAPER_NUM)
{
global_wallpaper = DEFAULT_WALLPAPER;
}
size_t length = 128;
char buf[128];
NVS_CHECK(nvs_get_str(nvs_arg, "ssid", buf, &length));
global_wifi_ssid = String(buf);
length = 128;
NVS_CHECK(nvs_get_str(nvs_arg, "pswd", buf, &length));
global_wifi_password = String(buf);
global_wifi_configed = true;
nvs_close(nvs_arg);
return ESP_OK;
}
esp_err_t SaveSetting(void)
{
nvs_handle nvs_arg;
NVS_CHECK(nvs_open("Setting", NVS_READWRITE, &nvs_arg));
NVS_CHECK(nvs_set_u16(nvs_arg, "Wallpaper", global_wallpaper));
NVS_CHECK(nvs_set_u8(nvs_arg, "Language", global_language));
NVS_CHECK(nvs_set_u8(nvs_arg, "Timesync", global_time_synced));
NVS_CHECK(nvs_set_str(nvs_arg, "ssid", global_wifi_ssid.c_str()));
NVS_CHECK(nvs_set_str(nvs_arg, "pswd", global_wifi_password.c_str()));
NVS_CHECK(nvs_commit(nvs_arg));
nvs_close(nvs_arg);
return ESP_OK;
}
void SetWifi(String ssid, String password)
{
global_wifi_ssid = ssid;
global_wifi_password = password;
SaveSetting();
}
uint8_t isWiFiConfiged(void)
{
return global_wifi_configed;
}
String GetWifiSSID(void)
{
return global_wifi_ssid;
}
String GetWifiPassword(void)
{
return global_wifi_password;
}
bool SyncNTPTime(void)
{
const char *ntpServer = "time.cloudflare.com";
configTime(8 * 3600, 0, ntpServer);
struct tm timeInfo;
if (getLocalTime(&timeInfo))
{
rtc_time_t time_struct;
time_struct.hour = timeInfo.tm_hour;
time_struct.min = timeInfo.tm_min;
time_struct.sec = timeInfo.tm_sec;
M5.RTC.setTime(&time_struct);
rtc_date_t date_struct;
date_struct.week = timeInfo.tm_wday;
date_struct.mon = timeInfo.tm_mon + 1;
date_struct.day = timeInfo.tm_mday;
date_struct.year = timeInfo.tm_year + 1900;
M5.RTC.setDate(&date_struct);
SetTimeSynced(1);
return 1;
}
log_d("Time Sync failed");
return 0;
}
uint16_t GetTextSize()
{
return global_reader_textsize;
}
void SetTextSize(uint16_t size)
{
global_reader_textsize = size;
}
const uint8_t* GetLoadingIMG_32x32(uint8_t id)
{
return kIMGLoading[id];
}
void __LoadingAnime_32x32(void *pargs)
{
uint16_t *args = (uint16_t *)pargs;
uint16_t x = args[0];
uint16_t y = args[1];
free(pargs);
M5EPD_Canvas loading(&M5.EPD);
loading.createCanvas(32, 32);
loading.fillCanvas(0);
loading.pushCanvas(x, y, UPDATE_MODE_GL16);
int anime_cnt = 0;
uint32_t time = 0;
while (1)
{
if(millis() - time > 200)
{
time = millis();
loading.pushImage(0, 0, 32, 32, GetLoadingIMG_32x32(anime_cnt));
loading.pushCanvas(x, y, UPDATE_MODE_DU4);
anime_cnt++;
if(anime_cnt == 16)
{
anime_cnt = 0;
}
}
xSemaphoreTake(_xSemaphore_LoadingAnime, portMAX_DELAY);
if(_loading_anime_eixt_flag == true)
{
xSemaphoreGive(_xSemaphore_LoadingAnime);
break;
}
xSemaphoreGive(_xSemaphore_LoadingAnime);
}
vTaskDelete(NULL);
}
void LoadingAnime_32x32_Start(uint16_t x, uint16_t y)
{
if(_xSemaphore_LoadingAnime == NULL)
{
_xSemaphore_LoadingAnime = xSemaphoreCreateMutex();
}
_loading_anime_eixt_flag = false;
uint16_t *pos = (uint16_t*)calloc(2, sizeof(uint16_t));
pos[0] = x;
pos[1] = y;
xTaskCreatePinnedToCore(__LoadingAnime_32x32, "__LoadingAnime_32x32", 16 * 1024, pos, 1, NULL, 0);
}
void LoadingAnime_32x32_Stop()
{
xSemaphoreTake(_xSemaphore_LoadingAnime, portMAX_DELAY);
_loading_anime_eixt_flag = true;
xSemaphoreGive(_xSemaphore_LoadingAnime);
delay(200);
}

47
src/global_setting.h Normal file
View File

@ -0,0 +1,47 @@
#ifndef _GLOBAL_SETTING_H_
#define _GLOBAL_SETTING_H_
#include <M5EPD.h>
#include <nvs.h>
#define WALLPAPER_NUM 3
enum
{
LANGUAGE_EN = 0, // default, English
LANGUAGE_JA, // Japanese
LANGUAGE_ZH // Simplified Chinese
};
void SetLanguage(uint8_t language);
uint8_t GetLanguage(void);
void SetWallpaper(uint16_t wallpaper_id);
uint16_t GetWallpaperID(void);
const uint8_t* GetWallpaper(void);
const char* GetWallpaperName(uint16_t wallpaper_id);
esp_err_t LoadSetting(void);
esp_err_t SaveSetting(void);
void SetWifi(String ssid, String password);
String GetWifiSSID(void);
String GetWifiPassword(void);
uint8_t isWiFiConfiged(void);
bool SyncNTPTime(void);
uint16_t GetTextSize();
void SetTextSize(uint16_t size);
const uint8_t* GetLoadingIMG_32x32(uint8_t id);
void LoadingAnime_32x32_Start(uint16_t x, uint16_t y);
void LoadingAnime_32x32_Stop();
uint8_t isTimeSynced(void);
void SetTimeSynced(uint8_t val);
void SetTTFLoaded(uint8_t val);
uint8_t isTTFLoaded(void);
void SetInitStatus(uint8_t idx, uint8_t val);
uint8_t GetInitStatus(uint8_t idx);
#endif //_GLOBAL_SETTING_H_

18
src/main.cpp Normal file
View File

@ -0,0 +1,18 @@
#include <M5EPD.h>
#include "epdgui/epdgui.h"
#include "frame/frame.h"
#include "systeminit.h"
void setup()
{
pinMode(M5EPD_MAIN_PWR_PIN, OUTPUT);
M5.enableMainPower();
SysInit_Start();
}
void loop()
{
EPDGUI_MainLoop();
}

71914
src/resources/ImageResource.h Normal file

File diff suppressed because it is too large Load Diff

3881
src/resources/binaryttf.h Normal file

File diff suppressed because it is too large Load Diff

266
src/systeminit.cpp Normal file
View File

@ -0,0 +1,266 @@
#include "systeminit.h"
#include "epdgui/epdgui.h"
#include "frame/frame.h"
#include "Free_Fonts.h"
#include "global_setting.h"
#include "resources/binaryttf.h"
#include <WiFi.h>
QueueHandle_t xQueue_Info = xQueueCreate(20, sizeof(uint32_t));
void WaitForUser(void)
{
SysInit_UpdateInfo("$ERR");
while(1)
{
M5.update();
if(M5.BtnP.wasReleased())
{
SysInit_UpdateInfo("$RESUME");
return;
}
}
}
void SysInit_Start(void)
{
bool ret = false;
Serial.begin(115200);
Serial.flush();
delay(50);
Serial.print("M5EPD initializing...");
pinMode(M5EPD_EXT_PWR_EN_PIN, OUTPUT);
pinMode(M5EPD_EPD_PWR_EN_PIN, OUTPUT);
pinMode(M5EPD_KEY_RIGHT_PIN, INPUT);
pinMode(M5EPD_KEY_PUSH_PIN, INPUT);
pinMode(M5EPD_KEY_LEFT_PIN, INPUT);
delay(100);
M5.enableEXTPower();
// M5.disableEPDPower();
// delay(500);
M5.enableEPDPower();
delay(1000);
M5.EPD.begin(M5EPD_SCK_PIN, M5EPD_MOSI_PIN, M5EPD_MISO_PIN, M5EPD_CS_PIN, M5EPD_BUSY_PIN);
M5.EPD.Clear(true);
M5.EPD.SetRotation(M5EPD_Driver::ROTATE_90);
M5.TP.SetRotation(GT911::ROTATE_90);
disableCore0WDT();
xTaskCreatePinnedToCore(SysInit_Loading, "SysInit_Loading", 4096, NULL, 1, NULL, 0);
// SysInit_UpdateInfo("Initializing SD card...");
bool is_factory_test;
SPI.begin(14, 13, 12, 4);
ret = SD.begin(4, SPI, 20000000);
if(ret == false)
{
is_factory_test = true;
SetInitStatus(0, 0);
// log_e("Failed to initialize SD card.");
// SysInit_UpdateInfo("[ERROR] Failed to initialize SD card.");
// WaitForUser();
}
else
{
is_factory_test = SD.exists("/__factory_test_flag__");
}
SysInit_UpdateInfo("Initializing Touch pad...");
if(M5.TP.begin(21, 22, 36) != ESP_OK)
{
SetInitStatus(1, 0);
log_e("Touch pad initialization failed.");
SysInit_UpdateInfo("[ERROR] Failed to initialize Touch pad.");
WaitForUser();
}
M5.BatteryADCBegin();
LoadSetting();
M5EPD_Canvas _initcanvas(&M5.EPD);
if((!is_factory_test) && SD.exists("/font.ttf"))
{
_initcanvas.loadFont("/font.ttf", SD);
SetTTFLoaded(true);
}
else
{
_initcanvas.loadFont(binaryttf, sizeof(binaryttf));
SetTTFLoaded(false);
SetLanguage(LANGUAGE_EN);
is_factory_test = true;
}
if(is_factory_test)
{
SysInit_UpdateInfo("$OK");
}
else
{
SysInit_UpdateInfo("Initializing system...");
}
_initcanvas.createRender(26, 128);
Frame_Main *frame_main = new Frame_Main();
EPDGUI_PushFrame(frame_main);
Frame_FactoryTest *frame_factorytest = new Frame_FactoryTest();
EPDGUI_AddFrame("Frame_FactoryTest", frame_factorytest);
if(!is_factory_test)
{
Frame_Setting *frame_setting = new Frame_Setting();
EPDGUI_AddFrame("Frame_Setting", frame_setting);
Frame_Setting_Wallpaper *frame_wallpaper = new Frame_Setting_Wallpaper();
EPDGUI_AddFrame("Frame_Setting_Wallpaper", frame_wallpaper);
Frame_Setting_Language *frame_language = new Frame_Setting_Language();
EPDGUI_AddFrame("Frame_Setting_Language", frame_language);
Frame_Keyboard *frame_keyboard = new Frame_Keyboard(0);
EPDGUI_AddFrame("Frame_Keyboard", frame_keyboard);
Frame_WifiScan *frame_wifiscan = new Frame_WifiScan();
EPDGUI_AddFrame("Frame_WifiScan", frame_wifiscan);
Frame_WifiPassword *frame_wifipassword = new Frame_WifiPassword();
EPDGUI_AddFrame("Frame_WifiPassword", frame_wifipassword);
Frame_Lifegame *frame_lifegame = new Frame_Lifegame();
EPDGUI_AddFrame("Frame_Lifegame", frame_lifegame);
Frame_Compare *frame_compare = new Frame_Compare();
EPDGUI_AddFrame("Frame_Compare", frame_compare);
Frame_Home *frame_home = new Frame_Home();
EPDGUI_AddFrame("Frame_Home", frame_home);
if(isWiFiConfiged())
{
SysInit_UpdateInfo("Connect to " + GetWifiSSID() + "...");
WiFi.begin(GetWifiSSID().c_str(), GetWifiPassword().c_str());
uint32_t t = millis();
while (1)
{
if(millis() - t > 8000)
{
break;
}
if(WiFi.status() == WL_CONNECTED)
{
frame_wifiscan->SetConnected(GetWifiSSID(), WiFi.RSSI());
break;
}
}
}
}
log_d("done");
while(uxQueueMessagesWaiting(xQueue_Info));
if(!is_factory_test)
{
SysInit_UpdateInfo("$OK");
}
Serial.println("OK");
delay(500);
}
void SysInit_Loading(void *pvParameters)
{
const uint16_t kPosy = 548;
const uint8_t *kLD[] = {
ImageResource_loading_01_96x96,
ImageResource_loading_02_96x96,
ImageResource_loading_03_96x96,
ImageResource_loading_04_96x96,
ImageResource_loading_05_96x96,
ImageResource_loading_06_96x96,
ImageResource_loading_07_96x96,
ImageResource_loading_08_96x96,
ImageResource_loading_09_96x96,
ImageResource_loading_10_96x96,
ImageResource_loading_11_96x96,
ImageResource_loading_12_96x96,
ImageResource_loading_13_96x96,
ImageResource_loading_14_96x96,
ImageResource_loading_15_96x96,
ImageResource_loading_16_96x96};
M5EPD_Canvas LoadingIMG(&M5.EPD);
M5EPD_Canvas Info(&M5.EPD);
LoadingIMG.createCanvas(96, 96);
Info.createCanvas(540, 50);
Info.setFreeFont(FF18);
Info.setTextSize(1);
Info.setTextDatum(CC_DATUM);
Info.setTextColor(15);
M5.EPD.WritePartGram4bpp(92, 182, 356, 300, ImageResource_logo_356x300);
M5.EPD.UpdateFull(UPDATE_MODE_GC16);
int i = 0;
char *p;
uint32_t time = 0;
while (1)
{
if(millis() - time > 250)
{
time = millis();
LoadingIMG.pushImage(0, 0, 96, 96, kLD[i]);
LoadingIMG.pushCanvas(220, kPosy + 80, UPDATE_MODE_DU4);
i++;
if (i == 16)
{
i = 0;
}
}
if(xQueueReceive(xQueue_Info, &p, 0))
{
String str(p);
free(p);
if(str.indexOf("$OK") >= 0)
{
LoadingIMG.pushImage(0, 0, 96, 96, ImageResource_loading_success_96x96);
LoadingIMG.pushCanvas(220, kPosy + 80, UPDATE_MODE_GL16);
break;
}
else if(str.indexOf("$ERR") >= 0)
{
LoadingIMG.pushImage(0, 0, 96, 96, ImageResource_loading_error_96x96);
LoadingIMG.pushCanvas(220, kPosy + 80, UPDATE_MODE_GL16);
LoadingIMG.fillCanvas(0);
while(1)
{
if(xQueueReceive(xQueue_Info, &p, 0))
{
String str(p);
free(p);
if(str.indexOf("$RESUME") >= 0)
{
LoadingIMG.pushCanvas(220, kPosy + 80, UPDATE_MODE_GC16);
break;
}
}
}
}
else
{
Info.fillCanvas(0);
Info.drawString(str, 270, 20);
Info.pushCanvas(0, kPosy, UPDATE_MODE_DU);
}
}
}
vTaskDelete(NULL);
}
void SysInit_UpdateInfo(String info)
{
char *p = (char*)malloc(info.length() + 1);
memcpy(p, info.c_str(), info.length());
p[info.length()] = '\0';
if(xQueueSend(xQueue_Info, &p, 0) == 0)
{
free(p);
}
}

11
src/systeminit.h Normal file
View File

@ -0,0 +1,11 @@
#ifndef __SYSTEMINIT_H
#define __SYSTEMINIT_H
#include <M5EPD.h>
void SysInit_Start(void);
void SysInit_Loading(void *pvParameters);
void SysInit_UpdateInfo(String info);
#endif //__SYSTEMINIT_H