batterie.ino
The Plus2 has no PMIC: battery voltage is inferred, and the HOLD pin (G4) latches the power. This sketch shows the level and switches the stick off cleanly by dropping HOLD.
Hardware required
An M5StickC Plus2 (ESP32-PICO-V3-02, 135×240 display, A/B/C buttons, passive buzzer on G2, IR + red LED on G19, MPU6886 IMU, microphone, 200 mAh battery). None; USB to see the charging state.
Wiring
No wiring. G4 (HOLD) must stay high in operation; the firmware holds it, the sketch forces it low to power off.
How it works
Power.getBatteryLevel estimates percentage from voltage; gpio_set_level(4,0) cuts the power latch — the software twin of the firmware's long Power press. In the Arduino IDE (esp32 package), board « M5StickCPlus2 »; « M5StickCPlus2 » or M5Unified library. On the PMIC-less v2, hold button C for >2 s to power on; HOLD (G4) latches the power.
Going further
Log the discharge hourly before shutdown, to trace the pack's real capacity.
batterie.ino
// Batterie 200 mAh : niveau via ADC interne (Plus2 sans PMIC) et HOLD.
#include <M5Unified.h>
void setup() {
auto cfg = M5.config();
M5.begin(cfg);
M5.Power.begin();
M5.Display.setRotation(1);
M5.Display.setTextSize(2);
}
void loop() {
M5.update();
int niveau = M5.Power.getBatteryLevel(); // 0-100 (estime)
bool charge = M5.Power.isCharging();
M5.Display.fillRect(0, 0, 240, 135, TFT_BLACK);
M5.Display.setCursor(6, 10);
M5.Display.printf("Batterie %d %%\n", niveau);
M5.Display.printf("%s\n", charge ? "en charge" : "sur batterie");
M5.Display.drawRect(6, 70, 200, 40, TFT_WHITE);
M5.Display.fillRect(8, 72, 196 * niveau / 100, 36,
niveau < 15 ? TFT_RED : TFT_GREEN);
M5.Display.drawString("B long = HOLD off", 6, 118, 1);
if (M5.BtnB.wasHold(2000)) {
M5.Display.drawString("Arret: HOLD bas", 6, 90, 2);
delay(1500);
gpio_set_level((gpio_num_t)4, 0); // HOLD G4 a 0 = coupure alim
}
delay(500);
}