#include "app.h" namespace { String serial_line; constexpr lv_display_rotation_t kDisplayRotation = LV_DISPLAY_ROTATION_180; void handleSerialCommand(const String &command) { if (command.equalsIgnoreCase("tare")) { performTare(); return; } if (command.equalsIgnoreCase("reset")) { clearCalibration(); return; } if (command.equalsIgnoreCase("status")) { Serial.printf("online=%d raw=%ld offset=%ld scale=%f has_offset=%d wifi_status=%d\n", sensor_online ? 1 : 0, static_cast(last_raw), static_cast(calibration.offset), calibration.scale, calibration.has_offset ? 1 : 0, static_cast(WiFi.status())); return; } if (command.startsWith("cal ")) { const float grams = command.substring(4).toFloat(); performCalibration(grams); return; } if (command.startsWith("scale ")) { const float scale = command.substring(6).toFloat(); if (scale > 0.0f) { calibration.scale = scale; saveCalibration(); displayed_weight_valid = false; refreshUi(); setCalibrationNote("Manual scale factor saved."); } else { setCalibrationNote("Invalid scale factor."); } return; } setCalibrationNote("Unknown serial command. Use: tare | cal | scale | reset | status"); } void handleSerial() { while (Serial.available() > 0) { const char ch = static_cast(Serial.read()); if (ch == '\r') { continue; } if (ch == '\n') { serial_line.trim(); if (!serial_line.isEmpty()) { handleSerialCommand(serial_line); } serial_line = ""; continue; } serial_line += ch; } } } // namespace void setup() { #ifdef ARDUINO_USB_CDC_ON_BOOT delay(5000); #endif Serial.begin(115200); Serial.setDebugOutput(true); log_i("Board: %s", BOARD_NAME); log_i("CPU: %s rev%d, %d MHz, %d core(s)", ESP.getChipModel(), ESP.getChipRevision(), getCpuFrequencyMhz(), ESP.getChipCores()); log_i("Free heap: %d bytes", ESP.getFreeHeap()); log_i("Free PSRAM: %d bytes", ESP.getPsramSize()); log_i("SDK version: %s", ESP.getSdkVersion()); prefs.begin(kPrefsNamespace, false); loadCalibration(); loadWifiConfig(); loadInventreeConfig(); hx711.begin(HX711_DOUT_PIN, HX711_SCK_PIN); log_i("Initializing smart display..."); smartdisplay_init(); lv_display_t *display = lv_display_get_default(); if (display != nullptr) { lv_display_set_rotation(display, kDisplayRotation); } log_i("Building UI..."); buildUi(); log_i("UI ready."); lv_tick_inc(1); lv_timer_handler(); delay(20); lv_tick_inc(20); lv_timer_handler(); WiFi.mode(WIFI_OFF); if (!wifi_data.ssid.isEmpty()) { connectWifi(wifi_data.ssid, wifi_data.password, false); setWifiNote("Auto-connecting to saved Wi-Fi..."); } last_lv_tick_ms = millis(); next_ui_refresh_ms = millis(); log_i("HX711 pins: SCK=%d DOUT=%d", HX711_SCK_PIN, HX711_DOUT_PIN); log_i("Setup complete."); } void loop() { const uint32_t now = millis(); sampleSensor(); handleSerial(); handleWifi(); if (now >= next_ui_refresh_ms) { next_ui_refresh_ms = now + kUiRefreshMs; refreshUi(); } lv_tick_inc(now - last_lv_tick_ms); last_lv_tick_ms = now; lv_timer_handler(); delay(5); }