├── .gitignore ├── .vscode └── extensions.json ├── LICENSE ├── README.md ├── include └── README ├── interface.jpg ├── lib └── README ├── platformio.ini ├── src ├── M5Cardputer-Pager.cpp ├── MenuFunctions.cpp ├── MenuFunctions.h ├── StatusBar.cpp └── StatusBar.h └── test └── README /.gitignore: -------------------------------------------------------------------------------- 1 | .pio 2 | .vscode/.browse.c_cpp.db* 3 | .vscode/c_cpp_properties.json 4 | .vscode/launch.json 5 | .vscode/ipch 6 | -------------------------------------------------------------------------------- /.vscode/extensions.json: -------------------------------------------------------------------------------- 1 | { 2 | // See http://go.microsoft.com/fwlink/?LinkId=827846 3 | // for the documentation about the extensions.json format 4 | "recommendations": [ 5 | "platformio.platformio-ide" 6 | ], 7 | "unwantedRecommendations": [ 8 | "ms-vscode.cpptools-extension-pack" 9 | ] 10 | } 11 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2024 Gabriel Kleemann Duarte 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # M5Cardputer-Pager 2 | 3 | A simple Pager firmware for M5Stack Cardputer (IN DEVELOPMENT) 4 | 5 | ![Interface](./interface.jpg) 6 | 7 | To-do: 8 | - [ ] fix the buggy menu -------------------------------------------------------------------------------- /include/README: -------------------------------------------------------------------------------- 1 | 2 | This directory is intended for project header files. 3 | 4 | A header file is a file containing C declarations and macro definitions 5 | to be shared between several project source files. You request the use of a 6 | header file in your project source file (C, C++, etc) located in `src` folder 7 | by including it, with the C preprocessing directive `#include'. 8 | 9 | ```src/main.c 10 | 11 | #include "header.h" 12 | 13 | int main (void) 14 | { 15 | ... 16 | } 17 | ``` 18 | 19 | Including a header file produces the same results as copying the header file 20 | into each source file that needs it. Such copying would be time-consuming 21 | and error-prone. With a header file, the related declarations appear 22 | in only one place. If they need to be changed, they can be changed in one 23 | place, and programs that include the header file will automatically use the 24 | new version when next recompiled. The header file eliminates the labor of 25 | finding and changing all the copies as well as the risk that a failure to 26 | find one copy will result in inconsistencies within a program. 27 | 28 | In C, the usual convention is to give header files names that end with `.h'. 29 | It is most portable to use only letters, digits, dashes, and underscores in 30 | header file names, and at most one dot. 31 | 32 | Read more about using header files in official GCC documentation: 33 | 34 | * Include Syntax 35 | * Include Operation 36 | * Once-Only Headers 37 | * Computed Includes 38 | 39 | https://gcc.gnu.org/onlinedocs/cpp/Header-Files.html 40 | -------------------------------------------------------------------------------- /interface.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dduartee/M5Cardputer-Pager/50fc24cd83e1c1d9e8f04532738d4b3718b70e9d/interface.jpg -------------------------------------------------------------------------------- /lib/README: -------------------------------------------------------------------------------- 1 | 2 | This directory is intended for project specific (private) libraries. 3 | PlatformIO will compile them to static libraries and link into executable file. 4 | 5 | The source code of each library should be placed in a an own separate directory 6 | ("lib/your_library_name/[here are source files]"). 7 | 8 | For example, see a structure of the following two libraries `Foo` and `Bar`: 9 | 10 | |--lib 11 | | | 12 | | |--Bar 13 | | | |--docs 14 | | | |--examples 15 | | | |--src 16 | | | |- Bar.c 17 | | | |- Bar.h 18 | | | |- library.json (optional, custom build options, etc) https://docs.platformio.org/page/librarymanager/config.html 19 | | | 20 | | |--Foo 21 | | | |- Foo.c 22 | | | |- Foo.h 23 | | | 24 | | |- README --> THIS FILE 25 | | 26 | |- platformio.ini 27 | |--src 28 | |- main.c 29 | 30 | and a contents of `src/main.c`: 31 | ``` 32 | #include 33 | #include 34 | 35 | int main (void) 36 | { 37 | ... 38 | } 39 | 40 | ``` 41 | 42 | PlatformIO Library Dependency Finder will find automatically dependent 43 | libraries scanning project source files. 44 | 45 | More information about PlatformIO Library Dependency Finder 46 | - https://docs.platformio.org/page/librarymanager/ldf.html 47 | -------------------------------------------------------------------------------- /platformio.ini: -------------------------------------------------------------------------------- 1 | ; PlatformIO Project Configuration File 2 | ; 3 | ; Build options: build flags, source filter 4 | ; Upload options: custom upload port, speed and extra flags 5 | ; Library options: dependencies, extra library storages 6 | ; Advanced options: extra scripting 7 | ; 8 | ; Please visit documentation for the other options and examples 9 | ; https://docs.platformio.org/page/projectconf.html 10 | 11 | [env:m5stack-stamps3] 12 | platform = espressif32 13 | board = m5stack-stamps3 14 | framework = arduino 15 | lib_extra_dirs = ~/Documents/Arduino/libraries 16 | lib_deps = m5stack/M5Cardputer@^1.0.3 17 | -------------------------------------------------------------------------------- /src/M5Cardputer-Pager.cpp: -------------------------------------------------------------------------------- 1 | #include "M5Cardputer.h" 2 | #include "MenuFunctions.h" 3 | #include "StatusBar.h" 4 | #define Display M5Cardputer.Display 5 | 6 | int retroDelay = 10; 7 | void buildInterface(int time) 8 | { 9 | for (int h = 0; h < Display.height(); h += 5) 10 | { 11 | Display.fillRect(0, 0, Display.width(), h, 0x18E4); 12 | delay(time); 13 | } 14 | for (int h = 0; h > -20; h -= 4) 15 | { 16 | Display.fillRect(0, 135, Display.width(), h, PURPLE); 17 | delay(time); 18 | } 19 | } 20 | 21 | void setup() 22 | { 23 | auto cfg = M5.config(); 24 | M5Cardputer.begin(cfg); 25 | Display.setBrightness(50); 26 | Display.setRotation(1); 27 | Display.fillScreen(BLACK); 28 | Display.setTextColor(GREEN, BLACK); 29 | Display.setFont(&fonts::Font0); 30 | Display.setCursor(0, 10); 31 | Display.println("Starting up...\n"); 32 | delay(500); 33 | Display.println("Display resolution: " + String(Display.width()) + "x" + String(Display.height()) + "\n"); 34 | delay(250); 35 | Display.println("Display brightness: " + String(Display.getBrightness()) + "\n"); 36 | delay(250); 37 | Display.println("Ready! \nPress ANY key to continue...\n"); 38 | bool exitLoop = true; 39 | while (exitLoop) 40 | { 41 | M5Cardputer.update(); 42 | if (M5Cardputer.Keyboard.isPressed()) 43 | exitLoop = false; 44 | } 45 | Display.clearDisplay(); 46 | buildInterface(retroDelay); 47 | } 48 | 49 | void loop() 50 | { 51 | M5Cardputer.update(); 52 | MenuFunctions::handleNavigation(); 53 | if(MenuFunctions::handleConfirm()) { 54 | buildInterface(0); 55 | } 56 | MenuFunctions::handleScreens(); 57 | StatusBar::update(); 58 | delay(30); 59 | } -------------------------------------------------------------------------------- /src/MenuFunctions.cpp: -------------------------------------------------------------------------------- 1 | #include "MenuFunctions.h" 2 | #define Display M5Cardputer.Display 3 | namespace MenuFunctions 4 | { 5 | char *mainMenuItems[] = {"Settings", "About", "Exit"}; 6 | int mainMenuSize = 2; 7 | char *settingsMenuItems[] = {"Back", "Wi-Fi", "Bluetooth", "Interface"}; 8 | int settingsMenuSize = 3; 9 | int screen = -1; 10 | int menuSelection = 0; 11 | bool confirm = 0; 12 | void initMainMenu() 13 | { 14 | Display.setTextColor(WHITE, 0x18E4); 15 | Display.setCursor(0, 10); 16 | Display.setFont(&fonts::Font0); 17 | for (int i = 0; i <= mainMenuSize; i++) 18 | { 19 | Display.setCursor(0, 30 + (i * 15)); 20 | Display.setTextColor(i == menuSelection ? GREEN : WHITE, 0x18E4); 21 | Display.print(i == menuSelection ? "> " : " "); 22 | Display.println(mainMenuItems[i]); 23 | } 24 | } 25 | void initSettingsMenu() 26 | { 27 | Display.setTextColor(WHITE, 0x18E4); 28 | Display.setFont(&fonts::Font0); 29 | for (int i = 0; i <= settingsMenuSize; i++) 30 | { 31 | Display.setCursor(0, 30 + (i * 15)); 32 | Display.setTextColor(i == menuSelection ? GREEN : WHITE, 0x18E4); 33 | Display.print(i == menuSelection ? "> " : " "); 34 | Display.println(settingsMenuItems[i]); 35 | } 36 | } 37 | /** 38 | * Lida com a navegação do menu 39 | */ 40 | void handleNavigation() 41 | { 42 | if (M5Cardputer.Keyboard.isChange()) 43 | { 44 | if (M5Cardputer.Keyboard.isKeyPressed('.')) 45 | { 46 | if (menuSelection < mainMenuSize) 47 | menuSelection++; 48 | else 49 | menuSelection = 0; 50 | } 51 | else if (M5Cardputer.Keyboard.isKeyPressed(';')) 52 | { 53 | if (menuSelection > 0) 54 | menuSelection--; 55 | else 56 | menuSelection = mainMenuSize; 57 | } 58 | else if (M5Cardputer.Keyboard.isKeyPressed(KEY_ENTER)) 59 | { 60 | confirm = true; 61 | } 62 | } 63 | } 64 | 65 | /** 66 | * Lida com a tecla de confirmação ENTER 67 | */ 68 | int handleConfirm() 69 | { 70 | if (confirm) 71 | { 72 | screen = menuSelection; 73 | confirm = false; 74 | menuSelection = 0; 75 | return 1; 76 | } 77 | return 0; 78 | } 79 | 80 | /** 81 | * Lida com a exibição de telas a partir do menu principal 82 | */ 83 | void handleScreens() 84 | { 85 | if (screen == 0) 86 | initSettingsMenu(); 87 | else if (screen == 1) 88 | { 89 | // initAbout(); 90 | } 91 | else 92 | initMainMenu(); 93 | } 94 | } 95 | -------------------------------------------------------------------------------- /src/MenuFunctions.h: -------------------------------------------------------------------------------- 1 | #ifndef MENU_FUNCTIONS_H 2 | #define MENU_FUNCTIONS_H 3 | #include "M5Cardputer.h" 4 | 5 | namespace MenuFunctions 6 | { 7 | void initMainMenu(); 8 | void handleNavigation(); 9 | int handleConfirm(); 10 | void handleScreens(); 11 | void initSettingsMenu(); 12 | 13 | } 14 | #endif 15 | -------------------------------------------------------------------------------- /src/StatusBar.cpp: -------------------------------------------------------------------------------- 1 | #include "StatusBar.h" 2 | #define Display M5Cardputer.Display 3 | namespace StatusBar 4 | { 5 | 6 | float getBatteryVoltage() 7 | { 8 | float batteryADCValue = analogRead(G10) * 2.0f; 9 | float batteryVoltage = (batteryADCValue / 4095.0) * 3300.0; 10 | return batteryVoltage; 11 | } 12 | void showBatteryVoltage() 13 | { 14 | float batteryVoltage = getBatteryVoltage(); 15 | Display.setTextColor(GREEN, PURPLE); 16 | Display.setCursor(200, 123); 17 | Display.print(batteryVoltage / 1000); 18 | Display.print("v"); 19 | } 20 | void showIPv4() 21 | { 22 | Display.setTextColor(GREEN, PURPLE); 23 | Display.setCursor(10, 123); 24 | Display.println("10.0.0.148/24"); // fake ipv4, for now 25 | } 26 | void update() 27 | { 28 | showBatteryVoltage(); 29 | showIPv4(); 30 | } 31 | 32 | } -------------------------------------------------------------------------------- /src/StatusBar.h: -------------------------------------------------------------------------------- 1 | #ifndef STATUSBAR_FUNCTION_H 2 | #define STATUSBAR_FUNCTION_H 3 | #include "M5Cardputer.h" 4 | 5 | namespace StatusBar 6 | { 7 | 8 | float getBatteryVoltage(); 9 | void showBatteryVoltage(); 10 | void showIPv4(); 11 | void update(); 12 | } 13 | 14 | #endif -------------------------------------------------------------------------------- /test/README: -------------------------------------------------------------------------------- 1 | 2 | This directory is intended for PlatformIO Test Runner and project tests. 3 | 4 | Unit Testing is a software testing method by which individual units of 5 | source code, sets of one or more MCU program modules together with associated 6 | control data, usage procedures, and operating procedures, are tested to 7 | determine whether they are fit for use. Unit testing finds problems early 8 | in the development cycle. 9 | 10 | More information about PlatformIO Unit Testing: 11 | - https://docs.platformio.org/en/latest/advanced/unit-testing/index.html 12 | --------------------------------------------------------------------------------