Compare commits

..

2 Commits

Author SHA1 Message Date
admin
4f574fb65c refactor(printer): remove controller residue and coex hooks
- rename printer protocol helpers to driver-centric names\n- remove image download coex preference code and config\n- drop esp_coex dependency from domain\n- remove unused set_black helper to keep build warning-free
2026-03-01 15:07:13 +08:00
admin
742cff63bb refactor(printer): replace direct_printer with printer naming 2026-03-01 14:49:50 +08:00
19 changed files with 248 additions and 575 deletions

View File

@@ -6,7 +6,7 @@ business REST endpoints (`/v1/*`).
## Features
- Thermal printer driver (single printer path)
- Auto-connect printer during startup
- Auto-initialize printer driver during startup
- Async print queue and worker lifecycle management
- Printer precheck (paper / battery / temperature)
- MIC key push-to-talk voice flow (button-triggered, no HTTP trigger)
@@ -52,7 +52,6 @@ In `menuconfig -> TQ Printer Config`:
- `TQ_WIFI_PROV_SOFTAP_CHANNEL`
- `TQ_WIFI_PROV_SOFTAP_MAX_CONN`
- Thermal printer runtime and safety policy:
- `TQ_DIRECT_PRINTER_*`
- `TQ_PRINTER_*`
- Z-Image HTTP fields:
- `TQ_Z_IMAGE_API_KEY` (optional, empty means fallback to `TQ_VOICE_API_KEY`)

View File

@@ -29,7 +29,6 @@ idf_component_register(
espressif__libpng
json
mbedtls
esp_coex
EMBED_FILES
"assets/fonts/cn16_index.bin"
"assets/fonts/cn16_glyphs.bin"

View File

@@ -25,10 +25,6 @@ bool domain_policy_is_retryable_error(esp_err_t err);
uint32_t domain_policy_printer_stop_timeout_ms(void);
uint32_t domain_policy_printer_connect_timeout_ms(void);
uint32_t domain_policy_printer_connect_timeout_min_ms(void);
uint32_t domain_policy_printer_connect_timeout_max_ms(void);
uint32_t domain_policy_image_generation_timeout_default_ms(void);
uint32_t domain_policy_image_generation_timeout_min_ms(void);
uint32_t domain_policy_image_generation_timeout_max_ms(void);
@@ -192,7 +188,7 @@ typedef struct {
typedef struct {
// Printer-only option: bypass paper/temp/battery precheck for this print job.
bool direct_ignore_precheck;
bool ignore_precheck;
} printer_print_options_t;
typedef struct {
@@ -205,10 +201,9 @@ typedef struct {
uint16_t override_strobe_interval_us;
uint16_t override_motor_step_us;
uint8_t override_steps_per_line;
} printer_direct_debug_config_t;
} printer_debug_config_t;
typedef struct {
bool connected;
bool busy;
bool has_paper;
int8_t paper_gpio_level;
@@ -224,10 +219,10 @@ typedef uint32_t printer_status_poll_pause_token_t;
esp_err_t printer_protocol_init(void);
esp_err_t printer_protocol_stop(uint32_t timeout_ms);
esp_err_t printer_protocol_get_direct_debug_config(printer_direct_debug_config_t *out_config,
esp_err_t printer_protocol_get_debug_config(printer_debug_config_t *out_config,
char *err,
size_t err_len);
esp_err_t printer_protocol_set_direct_debug_config(const printer_direct_debug_config_t *config,
esp_err_t printer_protocol_set_debug_config(const printer_debug_config_t *config,
bool reset_defaults,
char *err,
size_t err_len);

View File

@@ -26,7 +26,7 @@
typedef struct {
bool used;
bool cancel_requested;
bool direct_ignore_precheck;
bool ignore_precheck;
uint32_t id;
print_job_state_t state;
uint8_t progress;
@@ -64,9 +64,6 @@ extern TaskHandle_t s_status_poll_task_handle;
extern bool s_protocol_initialized;
extern bool s_protocol_stopping;
bool printer_protocol_acquire_control_lane(uint32_t timeout_ms, char *err, size_t err_len);
void printer_protocol_release_control_lane(void);
int printer_protocol_find_job_idx_locked(uint32_t id);
int printer_protocol_alloc_job_slot_locked(void);
bool printer_protocol_is_terminal_state(print_job_state_t state);

View File

@@ -76,18 +76,6 @@ uint32_t domain_policy_printer_stop_timeout_ms(void) {
return runtime_policy_printer_stop_timeout_ms();
}
uint32_t domain_policy_printer_connect_timeout_ms(void) {
return runtime_policy_printer_connect_timeout_ms();
}
uint32_t domain_policy_printer_connect_timeout_min_ms(void) {
return 1000;
}
uint32_t domain_policy_printer_connect_timeout_max_ms(void) {
return 60000;
}
uint32_t domain_policy_image_generation_timeout_default_ms(void) {
return runtime_policy_image_generation_timeout_default_ms();
}

View File

@@ -6,7 +6,6 @@
#include <string.h>
#include "cJSON.h"
#include "esp_coexist.h"
#include "esp_crt_bundle.h"
#include "esp_heap_caps.h"
#include "esp_http_client.h"
@@ -80,36 +79,6 @@ static SemaphoreHandle_t s_prewarm_lock;
static bool s_prewarm_running;
static char s_last_oss_origin[160] = "https://dashscope-result-bj.oss-cn-beijing.aliyuncs.com/";
static bool image_generation_boost_coex_for_download(void) {
#if CONFIG_ESP_COEX_SW_COEXIST_ENABLE && CONFIG_TQ_Z_IMAGE_COEX_PREFER_WIFI_DURING_DOWNLOAD
esp_err_t rc = esp_coex_preference_set(ESP_COEX_PREFER_WIFI);
if (rc != ESP_OK) {
ESP_LOGW(TAG, "failed to prefer Wi-Fi coexist mode, rc=0x%x", (unsigned)rc);
return false;
}
ESP_LOGI(TAG, "coexist prefer Wi-Fi enabled for image download");
return true;
#else
return false;
#endif
}
static void image_generation_restore_coex_after_download(bool boosted) {
#if CONFIG_ESP_COEX_SW_COEXIST_ENABLE && CONFIG_TQ_Z_IMAGE_COEX_PREFER_WIFI_DURING_DOWNLOAD
if (!boosted) {
return;
}
esp_err_t rc = esp_coex_preference_set(ESP_COEX_PREFER_BALANCE);
if (rc != ESP_OK) {
ESP_LOGW(TAG, "failed to restore coexist balance mode, rc=0x%x", (unsigned)rc);
return;
}
ESP_LOGI(TAG, "coexist preference restored to balance");
#else
(void)boosted;
#endif
}
static void image_generation_fill_err(char *err, size_t err_len, const char *msg) {
if (err != NULL && err_len > 0) {
snprintf(err, err_len, "%s", msg != NULL ? msg : "unknown error");
@@ -791,7 +760,6 @@ static esp_err_t image_generation_download_png(image_generation_result_t *out_re
char *err,
size_t err_len) {
ESP_LOGI(TAG, "generated image download start, timeout_ms=%u", (unsigned)timeout_ms);
bool coex_boosted = image_generation_boost_coex_for_download();
esp_http_client_config_t config = {
.url = out_result->image_url,
@@ -822,7 +790,6 @@ static esp_err_t image_generation_download_png(image_generation_result_t *out_re
(unsigned)rc,
(err != NULL && err[0] != '\0') ? err : "download failed");
bytes_buffer_free(&resp);
image_generation_restore_coex_after_download(coex_boosted);
return rc;
}
@@ -831,7 +798,6 @@ static esp_err_t image_generation_download_png(image_generation_result_t *out_re
if (rc != ESP_OK) {
bytes_buffer_free(&resp);
image_generation_fill_err(err, err_len, "image download failed");
image_generation_restore_coex_after_download(coex_boosted);
return ESP_FAIL;
}
extract_remote_error_message((const char *)resp.data, http_status, err, err_len);
@@ -840,7 +806,6 @@ static esp_err_t image_generation_download_png(image_generation_result_t *out_re
http_status,
(err != NULL && err[0] != '\0') ? err : "image download failed");
bytes_buffer_free(&resp);
image_generation_restore_coex_after_download(coex_boosted);
return ESP_FAIL;
}
@@ -851,14 +816,12 @@ static esp_err_t image_generation_download_png(image_generation_result_t *out_re
bytes_buffer_free(&resp);
image_generation_fill_err(err, err_len, "downloaded image is not png");
ESP_LOGW(TAG, "generated image download invalid png signature");
image_generation_restore_coex_after_download(coex_boosted);
return ESP_FAIL;
}
out_result->png = resp.data;
out_result->png_len = resp.len;
ESP_LOGI(TAG, "generated image download done, png_bytes=%u", (unsigned)out_result->png_len);
image_generation_restore_coex_after_download(coex_boosted);
return ESP_OK;
}

View File

@@ -1,7 +1,6 @@
#include "domain.h"
#include "printer_protocol_internal.h"
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
@@ -43,16 +42,13 @@ static const char *TAG = "printer_protocol";
#define PRINT_WORKER_CORE_ID 1
#endif
static esp_err_t ensure_direct_backend_ready(void) {
if (!runtime_policy_direct_printer_enabled()) {
return ESP_ERR_NOT_SUPPORTED;
}
return platform_direct_printer_init();
static esp_err_t ensure_printer_driver_ready(void) {
return platform_printer_init();
}
static void refresh_direct_status_locked(void) {
static void refresh_printer_status_locked(void) {
platform_printer_sensors_t sensors = {0};
if (platform_direct_printer_get_sensors(&sensors) == ESP_OK) {
if (platform_printer_get_sensors(&sensors) == ESP_OK) {
s_status.has_paper = sensors.has_paper;
s_status.paper_gpio_level = sensors.paper_gpio_level;
s_status.paper_present_level = sensors.paper_present_level;
@@ -210,57 +206,6 @@ void printer_protocol_status_poll_pause_release(printer_status_poll_pause_token_
*token = 0;
}
bool printer_protocol_acquire_control_lane(uint32_t timeout_ms, char *err, size_t err_len) {
if (!s_protocol_initialized || s_mutex == NULL) {
if (err != NULL && err_len > 0) {
snprintf(err, err_len, "printer protocol not initialized");
}
return false;
}
if (xSemaphoreTake(s_mutex, pdMS_TO_TICKS(timeout_ms)) != pdTRUE) {
if (err != NULL && err_len > 0) {
snprintf(err, err_len, "lock timeout");
}
return false;
}
if (s_protocol_stopping) {
xSemaphoreGive(s_mutex);
if (err != NULL && err_len > 0) {
snprintf(err, err_len, "printer protocol stopping");
}
return false;
}
if (s_busy_refcnt != 0) {
xSemaphoreGive(s_mutex);
if (err != NULL && err_len > 0) {
snprintf(err, err_len, "printer busy");
}
return false;
}
s_busy_refcnt = 1;
xSemaphoreGive(s_mutex);
return true;
}
void printer_protocol_release_control_lane(void) {
if (s_mutex == NULL) {
return;
}
if (xSemaphoreTake(s_mutex, pdMS_TO_TICKS(1000)) != pdTRUE) {
return;
}
if (s_busy_refcnt > 0) {
--s_busy_refcnt;
}
xSemaphoreGive(s_mutex);
}
static void status_poll_task(void *arg) {
(void)arg;
@@ -278,9 +223,8 @@ static void status_poll_task(void *arg) {
break;
}
if (can_poll && platform_direct_printer_is_connected() &&
xSemaphoreTake(s_mutex, pdMS_TO_TICKS(100)) == pdTRUE) {
refresh_direct_status_locked();
if (can_poll && xSemaphoreTake(s_mutex, pdMS_TO_TICKS(100)) == pdTRUE) {
refresh_printer_status_locked();
xSemaphoreGive(s_mutex);
}
@@ -343,28 +287,18 @@ esp_err_t printer_protocol_init(void) {
s_protocol_initialized = true;
s_protocol_stopping = false;
esp_err_t err = ensure_direct_backend_ready();
esp_err_t err = ensure_printer_driver_ready();
if (err != ESP_OK) {
s_protocol_initialized = false;
destroy_runtime_objects();
return err;
}
uint32_t connect_timeout_ms = domain_policy_printer_connect_timeout_ms();
err = platform_direct_printer_connect(connect_timeout_ms);
if (err != ESP_OK) {
s_protocol_initialized = false;
platform_direct_printer_disconnect();
platform_direct_printer_deinit();
destroy_runtime_objects();
return err;
}
if (xSemaphoreTake(s_mutex, pdMS_TO_TICKS(200)) == pdTRUE) {
refresh_direct_status_locked();
refresh_printer_status_locked();
xSemaphoreGive(s_mutex);
}
ESP_LOGI(TAG, "printer auto connected at startup");
ESP_LOGI(TAG, "printer driver ready at startup");
BaseType_t ok = printer_create_task_prefer_psram(printer_protocol_worker_task,
"print_worker",
@@ -423,8 +357,6 @@ esp_err_t printer_protocol_stop(uint32_t timeout_ms) {
(void)xQueueSend(s_job_queue, &sentinel, 0);
}
platform_direct_printer_disconnect();
bool worker_done = (s_worker_task == NULL);
bool poll_done = (s_status_poll_task_handle == NULL);
@@ -468,7 +400,7 @@ esp_err_t printer_protocol_stop(uint32_t timeout_ms) {
runtime_diag_set_gauge(RUNTIME_DIAG_GAUGE_STATUS_POLL_PAUSE_DEPTH, 0);
runtime_diag_set_gauge(RUNTIME_DIAG_GAUGE_PRINTER_QUEUE_DEPTH, 0);
platform_direct_printer_deinit();
platform_printer_deinit();
ESP_LOGI(TAG, "printer protocol stopped");
return (worker_done && poll_done) ? ESP_OK : ESP_ERR_TIMEOUT;
@@ -482,10 +414,8 @@ void printer_protocol_get_runtime_status(printer_runtime_status_t *out_status) {
memset(out_status, 0, sizeof(*out_status));
out_status->paper_gpio_level = -1;
out_status->connected = platform_direct_printer_is_connected();
platform_printer_sensors_t sensors = {0};
if (platform_direct_printer_get_sensors(&sensors) == ESP_OK &&
if (platform_printer_get_sensors(&sensors) == ESP_OK &&
s_mutex != NULL &&
xSemaphoreTake(s_mutex, pdMS_TO_TICKS(100)) == pdTRUE) {
s_status.has_paper = sensors.has_paper;

View File

@@ -10,26 +10,18 @@ static void write_err(char *err, size_t err_len, const char *msg) {
}
esp_err_t printer_protocol_gap_move(uint32_t timeout_ms, char *err, size_t err_len) {
if (!runtime_policy_direct_printer_enabled()) {
write_err(err, err_len, "printer driver disabled");
return ESP_ERR_NOT_SUPPORTED;
}
return platform_direct_printer_gap_move(timeout_ms, err, err_len);
return platform_printer_gap_move(timeout_ms, err, err_len);
}
esp_err_t printer_protocol_get_direct_debug_config(printer_direct_debug_config_t *out_config,
esp_err_t printer_protocol_get_debug_config(printer_debug_config_t *out_config,
char *err,
size_t err_len) {
if (out_config == NULL) {
write_err(err, err_len, "invalid args");
return ESP_ERR_INVALID_ARG;
}
if (!runtime_policy_direct_printer_enabled()) {
write_err(err, err_len, "printer driver disabled");
return ESP_ERR_NOT_SUPPORTED;
}
esp_err_t rc = platform_direct_printer_get_debug_config(&out_config->shift_clock_high_us,
esp_err_t rc = platform_printer_get_debug_config(&out_config->shift_clock_high_us,
&out_config->shift_clock_low_us,
&out_config->latch_pulse_us,
&out_config->strobe_active_high,
@@ -45,7 +37,7 @@ esp_err_t printer_protocol_get_direct_debug_config(printer_direct_debug_config_t
return ESP_OK;
}
esp_err_t printer_protocol_set_direct_debug_config(const printer_direct_debug_config_t *config,
esp_err_t printer_protocol_set_debug_config(const printer_debug_config_t *config,
bool reset_defaults,
char *err,
size_t err_len) {
@@ -53,12 +45,8 @@ esp_err_t printer_protocol_set_direct_debug_config(const printer_direct_debug_co
write_err(err, err_len, "invalid args");
return ESP_ERR_INVALID_ARG;
}
if (!runtime_policy_direct_printer_enabled()) {
write_err(err, err_len, "printer driver disabled");
return ESP_ERR_NOT_SUPPORTED;
}
return platform_direct_printer_set_debug_config(config != NULL,
return platform_printer_set_debug_config(config != NULL,
config != NULL ? config->shift_clock_high_us : 0,
config != NULL ? config->shift_clock_low_us : 0,
config != NULL ? config->latch_pulse_us : 0,

View File

@@ -135,11 +135,11 @@ esp_err_t printer_protocol_submit_raster_job_ex(const uint8_t *raster,
s_jobs[idx].width = width;
s_jobs[idx].height = height;
s_jobs[idx].data_len = raster_len;
s_jobs[idx].direct_ignore_precheck = (options != NULL && options->direct_ignore_precheck);
s_jobs[idx].ignore_precheck = (options != NULL && options->ignore_precheck);
s_jobs[idx].created_ms = esp_timer_get_time() / 1000;
s_jobs[idx].data = copy;
strlcpy(s_jobs[idx].density, density != NULL ? density : "中等", sizeof(s_jobs[idx].density));
bool ignore_precheck = s_jobs[idx].direct_ignore_precheck;
bool ignore_precheck = s_jobs[idx].ignore_precheck;
xSemaphoreGive(s_mutex);

View File

@@ -31,13 +31,13 @@ static uint16_t density_to_hot_time(const char *density) {
return 2000;
}
static bool precheck_printer_ready(bool direct_ignore_precheck, char *err, size_t err_len) {
if (direct_ignore_precheck) {
static bool precheck_printer_ready(bool ignore_precheck, char *err, size_t err_len) {
if (ignore_precheck) {
return true;
}
platform_printer_sensors_t sensors = {0};
if (platform_direct_printer_get_sensors(&sensors) != ESP_OK) {
if (platform_printer_get_sensors(&sensors) != ESP_OK) {
snprintf(err, err_len, "sensor read failed");
return false;
}
@@ -46,8 +46,8 @@ static bool precheck_printer_ready(bool direct_ignore_precheck, char *err, size_
return false;
}
float temp_min = runtime_policy_direct_printer_temp_min_c();
float temp_max = runtime_policy_direct_printer_temp_max_c();
float temp_min = runtime_policy_printer_temp_min_c();
float temp_max = runtime_policy_printer_temp_max_c();
if (temp_max <= temp_min) {
temp_max = temp_min + 1.0f;
}
@@ -56,36 +56,31 @@ static bool precheck_printer_ready(bool direct_ignore_precheck, char *err, size_
return false;
}
if (sensors.battery_percent < runtime_policy_direct_printer_battery_min_percent()) {
if (sensors.battery_percent < runtime_policy_printer_battery_min_percent()) {
snprintf(err, err_len, "battery too low");
return false;
}
return true;
}
static bool run_print_job_direct(job_slot_t *job) {
if (!platform_direct_printer_is_connected()) {
snprintf(job->error, sizeof(job->error), "printer not connected");
return false;
}
static bool run_print_job_printer_driver(job_slot_t *job) {
char check_err[96];
if (!precheck_printer_ready(job->direct_ignore_precheck, check_err, sizeof(check_err))) {
if (!precheck_printer_ready(job->ignore_precheck, check_err, sizeof(check_err))) {
snprintf(job->error, sizeof(job->error), "%s", check_err);
return false;
}
platform_direct_print_request_t req = {
platform_printer_print_request_t req = {
.width = job->width,
.height = job->height,
.raster = job->data,
.raster_len = job->data_len,
.strobe_on_time_us = density_to_hot_time(job->density),
.strobe_interval_us = runtime_policy_direct_printer_strobe_interval_us(),
.motor_step_delay_us = runtime_policy_direct_printer_motor_step_us(),
.motor_steps_per_line = runtime_policy_direct_printer_steps_per_line(),
.timeout_ms = runtime_policy_direct_printer_operation_timeout_ms(),
.ignore_precheck = job->direct_ignore_precheck,
.strobe_interval_us = runtime_policy_printer_strobe_interval_us(),
.motor_step_delay_us = runtime_policy_printer_motor_step_us(),
.motor_steps_per_line = runtime_policy_printer_steps_per_line(),
.timeout_ms = runtime_policy_printer_operation_timeout_ms(),
.ignore_precheck = job->ignore_precheck,
.cancel_flag = &job->cancel_requested,
};
@@ -94,11 +89,11 @@ static bool run_print_job_direct(job_slot_t *job) {
xSemaphoreGive(s_mutex);
}
char direct_err[96] = {0};
esp_err_t rc = platform_direct_printer_print(&req, direct_err, sizeof(direct_err));
char print_err[96] = {0};
esp_err_t rc = platform_printer_print(&req, print_err, sizeof(print_err));
if (rc != ESP_OK) {
if (direct_err[0] != 0) {
snprintf(job->error, sizeof(job->error), "%s", direct_err);
if (print_err[0] != 0) {
snprintf(job->error, sizeof(job->error), "%s", print_err);
} else if (rc == ESP_ERR_TIMEOUT) {
snprintf(job->error, sizeof(job->error), "print timeout");
} else if (rc == ESP_ERR_INVALID_STATE && job->cancel_requested) {
@@ -118,20 +113,20 @@ static bool run_print_job_direct(job_slot_t *job) {
static bool run_print_job(job_slot_t *job) {
ESP_LOGI(TAG,
"job %u print start, mode=printer, raster_bytes=%u, size=%ux%u, density=%s, ignore_precheck=%d",
"job %u print start, raster_bytes=%u, size=%ux%u, density=%s, ignore_precheck=%d",
(unsigned)job->id,
(unsigned)job->data_len,
(unsigned)job->width,
(unsigned)job->height,
job->density,
job->direct_ignore_precheck);
job->ignore_precheck);
if (printer_protocol_is_stopping()) {
snprintf(job->error, sizeof(job->error), "protocol stopping");
return false;
}
return run_print_job_direct(job);
return run_print_job_printer_driver(job);
}
void printer_protocol_worker_task(void *arg) {

View File

@@ -15,16 +15,6 @@
static const uint8_t s_bit_mask[8] = {0x80u, 0x40u, 0x20u, 0x10u, 0x08u, 0x04u, 0x02u, 0x01u};
static void set_black(uint8_t *buf, uint16_t width, uint16_t x, uint16_t y) {
if (x >= width) {
return;
}
uint16_t bpr = width / 8;
size_t idx = (size_t)y * bpr + (x / 8);
uint8_t bit = (uint8_t)(7 - (x % 8));
buf[idx] |= (uint8_t)(1u << bit);
}
static void *alloc_prefer_psram(size_t size) {
void *ptr = heap_caps_malloc(size, MALLOC_CAP_SPIRAM | MALLOC_CAP_8BIT);
if (ptr == NULL) {

View File

@@ -316,7 +316,7 @@ static esp_err_t voice_submit_marker_generated_image(const voice_image_generatio
uint32_t job_id = 0;
char submit_err[128] = {0};
printer_print_options_t print_opt = {
.direct_ignore_precheck = true,
.ignore_precheck = true,
};
esp_err_t submit_rc = printer_protocol_submit_raster_job_ex(raster,
raster_len,

View File

@@ -2,7 +2,7 @@ idf_component_register(
SRCS
"src/platform_bootstrap.c"
"src/wifi_manager.c"
"src/direct_thermal_printer.c"
"src/thermal_printer.c"
"src/display_st7789.c"
"src/display_lcd_module.c"
"src/display_lcd_decode_image.c"

View File

@@ -20,7 +20,7 @@ esp_err_t wifi_manager_stop(void);
bool wifi_manager_is_ready(void);
void wifi_manager_get_ip(char *buf, size_t buf_len);
// ---------- direct_thermal_printer ----------
// ---------- thermal_printer ----------
typedef struct {
bool has_paper;
int8_t paper_gpio_level;
@@ -42,15 +42,12 @@ typedef struct {
uint32_t timeout_ms;
bool ignore_precheck;
const volatile bool *cancel_flag;
} platform_direct_print_request_t;
} platform_printer_print_request_t;
esp_err_t platform_direct_printer_init(void);
void platform_direct_printer_deinit(void);
esp_err_t platform_direct_printer_connect(uint32_t timeout_ms);
void platform_direct_printer_disconnect(void);
bool platform_direct_printer_is_connected(void);
esp_err_t platform_direct_printer_get_sensors(platform_printer_sensors_t *out_sensors);
esp_err_t platform_direct_printer_get_debug_config(uint16_t *out_shift_clock_high_us,
esp_err_t platform_printer_init(void);
void platform_printer_deinit(void);
esp_err_t platform_printer_get_sensors(platform_printer_sensors_t *out_sensors);
esp_err_t platform_printer_get_debug_config(uint16_t *out_shift_clock_high_us,
uint16_t *out_shift_clock_low_us,
uint16_t *out_latch_pulse_us,
bool *out_strobe_active_high,
@@ -59,7 +56,7 @@ esp_err_t platform_direct_printer_get_debug_config(uint16_t *out_shift_clock_hig
uint16_t *out_override_strobe_interval_us,
uint16_t *out_override_motor_step_us,
uint8_t *out_override_steps_per_line);
esp_err_t platform_direct_printer_set_debug_config(bool has_config,
esp_err_t platform_printer_set_debug_config(bool has_config,
uint16_t shift_clock_high_us,
uint16_t shift_clock_low_us,
uint16_t latch_pulse_us,
@@ -72,10 +69,10 @@ esp_err_t platform_direct_printer_set_debug_config(bool has_config,
bool reset_defaults,
char *err,
size_t err_len);
esp_err_t platform_direct_printer_print(const platform_direct_print_request_t *request,
esp_err_t platform_printer_print(const platform_printer_print_request_t *request,
char *err,
size_t err_len);
esp_err_t platform_direct_printer_gap_move(uint32_t timeout_ms, char *err, size_t err_len);
esp_err_t platform_printer_gap_move(uint32_t timeout_ms, char *err, size_t err_len);
// ---------- display_st7789 ----------
esp_err_t platform_display_init(void);
@@ -149,25 +146,23 @@ uint32_t runtime_policy_printer_queue_retry_delay_ms(void);
uint32_t runtime_policy_printer_status_poll_interval_ms(void);
uint32_t runtime_policy_printer_stop_timeout_ms(void);
bool runtime_policy_direct_printer_enabled(void);
uint32_t runtime_policy_direct_printer_operation_timeout_ms(void);
uint16_t runtime_policy_direct_printer_strobe_on_us(void);
uint16_t runtime_policy_direct_printer_strobe_interval_us(void);
uint16_t runtime_policy_direct_printer_motor_step_us(void);
bool runtime_policy_direct_printer_motor_reverse(void);
uint8_t runtime_policy_direct_printer_steps_per_line(void);
uint16_t runtime_policy_direct_printer_gap_steps(void);
float runtime_policy_direct_printer_temp_min_c(void);
float runtime_policy_direct_printer_temp_max_c(void);
uint8_t runtime_policy_direct_printer_battery_min_percent(void);
uint8_t runtime_policy_direct_printer_paper_present_level(void);
uint16_t runtime_policy_direct_printer_battery_empty_mv(void);
uint16_t runtime_policy_direct_printer_battery_full_mv(void);
uint16_t runtime_policy_direct_printer_battery_divider_ratio_x1000(void);
uint32_t runtime_policy_direct_printer_ntc_pullup_ohms(void);
uint32_t runtime_policy_direct_printer_ntc_r25_ohms(void);
uint32_t runtime_policy_direct_printer_ntc_beta(void);
uint32_t runtime_policy_printer_connect_timeout_ms(void);
uint32_t runtime_policy_printer_operation_timeout_ms(void);
uint16_t runtime_policy_printer_strobe_on_us(void);
uint16_t runtime_policy_printer_strobe_interval_us(void);
uint16_t runtime_policy_printer_motor_step_us(void);
bool runtime_policy_printer_motor_reverse(void);
uint8_t runtime_policy_printer_steps_per_line(void);
uint16_t runtime_policy_printer_gap_steps(void);
float runtime_policy_printer_temp_min_c(void);
float runtime_policy_printer_temp_max_c(void);
uint8_t runtime_policy_printer_battery_min_percent(void);
uint8_t runtime_policy_printer_paper_present_level(void);
uint16_t runtime_policy_printer_battery_empty_mv(void);
uint16_t runtime_policy_printer_battery_full_mv(void);
uint16_t runtime_policy_printer_battery_divider_ratio_x1000(void);
uint32_t runtime_policy_printer_ntc_pullup_ohms(void);
uint32_t runtime_policy_printer_ntc_r25_ohms(void);
uint32_t runtime_policy_printer_ntc_beta(void);
uint32_t runtime_policy_image_generation_timeout_default_ms(void);
uint32_t runtime_policy_image_generation_timeout_min_ms(void);

View File

@@ -179,7 +179,7 @@ static esp_err_t lcd_recover_panel_for_shared_spi(void)
}
/*
* Direct-printer path temporarily takes over shared MOSI/CLK as GPIO.
* Printer path temporarily takes over shared MOSI/CLK as GPIO.
* Recover LCD SPI routing only when printer touched shared pins.
*/
esp_err_t recover_rc = st7789p3_recover_spi_bus(s_lcd.panel);

View File

@@ -34,80 +34,72 @@
#define CONFIG_TQ_PRINTER_STOP_TIMEOUT_MS 8000
#endif
#ifndef CONFIG_TQ_DIRECT_PRINTER_ENABLE
#define CONFIG_TQ_DIRECT_PRINTER_ENABLE 1
#ifndef CONFIG_TQ_PRINTER_OPERATION_TIMEOUT_MS
#define CONFIG_TQ_PRINTER_OPERATION_TIMEOUT_MS 90000
#endif
#ifndef CONFIG_TQ_DIRECT_PRINTER_OPERATION_TIMEOUT_MS
#define CONFIG_TQ_DIRECT_PRINTER_OPERATION_TIMEOUT_MS 90000
#ifndef CONFIG_TQ_PRINTER_STROBE_ON_US
#define CONFIG_TQ_PRINTER_STROBE_ON_US 1000
#endif
#ifndef CONFIG_TQ_DIRECT_PRINTER_STROBE_ON_US
#define CONFIG_TQ_DIRECT_PRINTER_STROBE_ON_US 1000
#ifndef CONFIG_TQ_PRINTER_STROBE_INTERVAL_US
#define CONFIG_TQ_PRINTER_STROBE_INTERVAL_US 200
#endif
#ifndef CONFIG_TQ_DIRECT_PRINTER_STROBE_INTERVAL_US
#define CONFIG_TQ_DIRECT_PRINTER_STROBE_INTERVAL_US 200
#ifndef CONFIG_TQ_PRINTER_MOTOR_STEP_US
#define CONFIG_TQ_PRINTER_MOTOR_STEP_US 2000
#endif
#ifndef CONFIG_TQ_DIRECT_PRINTER_MOTOR_STEP_US
#define CONFIG_TQ_DIRECT_PRINTER_MOTOR_STEP_US 2000
#ifndef CONFIG_TQ_PRINTER_MOTOR_REVERSE
#define CONFIG_TQ_PRINTER_MOTOR_REVERSE 0
#endif
#ifndef CONFIG_TQ_DIRECT_PRINTER_MOTOR_REVERSE
#define CONFIG_TQ_DIRECT_PRINTER_MOTOR_REVERSE 0
#ifndef CONFIG_TQ_PRINTER_STEPS_PER_LINE
#define CONFIG_TQ_PRINTER_STEPS_PER_LINE 2
#endif
#ifndef CONFIG_TQ_DIRECT_PRINTER_STEPS_PER_LINE
#define CONFIG_TQ_DIRECT_PRINTER_STEPS_PER_LINE 2
#ifndef CONFIG_TQ_PRINTER_GAP_STEPS
#define CONFIG_TQ_PRINTER_GAP_STEPS 96
#endif
#ifndef CONFIG_TQ_DIRECT_PRINTER_GAP_STEPS
#define CONFIG_TQ_DIRECT_PRINTER_GAP_STEPS 96
#ifndef CONFIG_TQ_PRINTER_TEMP_MIN_C
#define CONFIG_TQ_PRINTER_TEMP_MIN_C 15
#endif
#ifndef CONFIG_TQ_DIRECT_PRINTER_TEMP_MIN_C
#define CONFIG_TQ_DIRECT_PRINTER_TEMP_MIN_C 15
#ifndef CONFIG_TQ_PRINTER_TEMP_MAX_C
#define CONFIG_TQ_PRINTER_TEMP_MAX_C 55
#endif
#ifndef CONFIG_TQ_DIRECT_PRINTER_TEMP_MAX_C
#define CONFIG_TQ_DIRECT_PRINTER_TEMP_MAX_C 55
#ifndef CONFIG_TQ_PRINTER_BATTERY_MIN_PERCENT
#define CONFIG_TQ_PRINTER_BATTERY_MIN_PERCENT 5
#endif
#ifndef CONFIG_TQ_DIRECT_PRINTER_BATTERY_MIN_PERCENT
#define CONFIG_TQ_DIRECT_PRINTER_BATTERY_MIN_PERCENT 5
#ifndef CONFIG_TQ_PRINTER_PAPER_PRESENT_LEVEL
#define CONFIG_TQ_PRINTER_PAPER_PRESENT_LEVEL 0
#endif
#ifndef CONFIG_TQ_DIRECT_PRINTER_PAPER_PRESENT_LEVEL
#define CONFIG_TQ_DIRECT_PRINTER_PAPER_PRESENT_LEVEL 0
#ifndef CONFIG_TQ_PRINTER_BATTERY_EMPTY_MV
#define CONFIG_TQ_PRINTER_BATTERY_EMPTY_MV 3300
#endif
#ifndef CONFIG_TQ_DIRECT_PRINTER_BATTERY_EMPTY_MV
#define CONFIG_TQ_DIRECT_PRINTER_BATTERY_EMPTY_MV 3300
#ifndef CONFIG_TQ_PRINTER_BATTERY_FULL_MV
#define CONFIG_TQ_PRINTER_BATTERY_FULL_MV 4200
#endif
#ifndef CONFIG_TQ_DIRECT_PRINTER_BATTERY_FULL_MV
#define CONFIG_TQ_DIRECT_PRINTER_BATTERY_FULL_MV 4200
#ifndef CONFIG_TQ_PRINTER_BATTERY_DIVIDER_RATIO_X1000
#define CONFIG_TQ_PRINTER_BATTERY_DIVIDER_RATIO_X1000 2000
#endif
#ifndef CONFIG_TQ_DIRECT_PRINTER_BATTERY_DIVIDER_RATIO_X1000
#define CONFIG_TQ_DIRECT_PRINTER_BATTERY_DIVIDER_RATIO_X1000 2000
#ifndef CONFIG_TQ_PRINTER_NTC_PULLUP_OHMS
#define CONFIG_TQ_PRINTER_NTC_PULLUP_OHMS 10000
#endif
#ifndef CONFIG_TQ_DIRECT_PRINTER_NTC_PULLUP_OHMS
#define CONFIG_TQ_DIRECT_PRINTER_NTC_PULLUP_OHMS 10000
#ifndef CONFIG_TQ_PRINTER_NTC_R25_OHMS
#define CONFIG_TQ_PRINTER_NTC_R25_OHMS 10000
#endif
#ifndef CONFIG_TQ_DIRECT_PRINTER_NTC_R25_OHMS
#define CONFIG_TQ_DIRECT_PRINTER_NTC_R25_OHMS 10000
#endif
#ifndef CONFIG_TQ_DIRECT_PRINTER_NTC_BETA
#define CONFIG_TQ_DIRECT_PRINTER_NTC_BETA 3950
#endif
#ifndef CONFIG_TQ_PRINTER_CONNECT_TIMEOUT_MS
#define CONFIG_TQ_PRINTER_CONNECT_TIMEOUT_MS 15000
#ifndef CONFIG_TQ_PRINTER_NTC_BETA
#define CONFIG_TQ_PRINTER_NTC_BETA 3950
#endif
#ifndef CONFIG_TQ_Z_IMAGE_TIMEOUT_MS
@@ -189,85 +181,77 @@ uint32_t runtime_policy_printer_stop_timeout_ms(void) {
return clamp_u32(CONFIG_TQ_PRINTER_STOP_TIMEOUT_MS, 1000, 30000);
}
bool runtime_policy_direct_printer_enabled(void) {
return CONFIG_TQ_DIRECT_PRINTER_ENABLE != 0;
uint32_t runtime_policy_printer_operation_timeout_ms(void) {
return clamp_u32(CONFIG_TQ_PRINTER_OPERATION_TIMEOUT_MS, 1000, 300000);
}
uint32_t runtime_policy_direct_printer_operation_timeout_ms(void) {
return clamp_u32(CONFIG_TQ_DIRECT_PRINTER_OPERATION_TIMEOUT_MS, 1000, 300000);
uint16_t runtime_policy_printer_strobe_on_us(void) {
return clamp_u16((uint16_t)CONFIG_TQ_PRINTER_STROBE_ON_US, 100, 10000);
}
uint16_t runtime_policy_direct_printer_strobe_on_us(void) {
return clamp_u16((uint16_t)CONFIG_TQ_DIRECT_PRINTER_STROBE_ON_US, 100, 10000);
uint16_t runtime_policy_printer_strobe_interval_us(void) {
return clamp_u16((uint16_t)CONFIG_TQ_PRINTER_STROBE_INTERVAL_US, 0, 10000);
}
uint16_t runtime_policy_direct_printer_strobe_interval_us(void) {
return clamp_u16((uint16_t)CONFIG_TQ_DIRECT_PRINTER_STROBE_INTERVAL_US, 0, 10000);
uint16_t runtime_policy_printer_motor_step_us(void) {
return clamp_u16((uint16_t)CONFIG_TQ_PRINTER_MOTOR_STEP_US, 100, 20000);
}
uint16_t runtime_policy_direct_printer_motor_step_us(void) {
return clamp_u16((uint16_t)CONFIG_TQ_DIRECT_PRINTER_MOTOR_STEP_US, 100, 20000);
bool runtime_policy_printer_motor_reverse(void) {
return CONFIG_TQ_PRINTER_MOTOR_REVERSE != 0;
}
bool runtime_policy_direct_printer_motor_reverse(void) {
return CONFIG_TQ_DIRECT_PRINTER_MOTOR_REVERSE != 0;
uint8_t runtime_policy_printer_steps_per_line(void) {
return clamp_u8((uint8_t)CONFIG_TQ_PRINTER_STEPS_PER_LINE, 1, 8);
}
uint8_t runtime_policy_direct_printer_steps_per_line(void) {
return clamp_u8((uint8_t)CONFIG_TQ_DIRECT_PRINTER_STEPS_PER_LINE, 1, 8);
uint16_t runtime_policy_printer_gap_steps(void) {
return clamp_u16((uint16_t)CONFIG_TQ_PRINTER_GAP_STEPS, 1, 2000);
}
uint16_t runtime_policy_direct_printer_gap_steps(void) {
return clamp_u16((uint16_t)CONFIG_TQ_DIRECT_PRINTER_GAP_STEPS, 1, 2000);
float runtime_policy_printer_temp_min_c(void) {
return (float)clamp_u32((uint32_t)CONFIG_TQ_PRINTER_TEMP_MIN_C, 0, 120);
}
float runtime_policy_direct_printer_temp_min_c(void) {
return (float)clamp_u32((uint32_t)CONFIG_TQ_DIRECT_PRINTER_TEMP_MIN_C, 0, 120);
float runtime_policy_printer_temp_max_c(void) {
return (float)clamp_u32((uint32_t)CONFIG_TQ_PRINTER_TEMP_MAX_C, 1, 150);
}
float runtime_policy_direct_printer_temp_max_c(void) {
return (float)clamp_u32((uint32_t)CONFIG_TQ_DIRECT_PRINTER_TEMP_MAX_C, 1, 150);
uint8_t runtime_policy_printer_battery_min_percent(void) {
return clamp_u8((uint8_t)CONFIG_TQ_PRINTER_BATTERY_MIN_PERCENT, 0, 100);
}
uint8_t runtime_policy_direct_printer_battery_min_percent(void) {
return clamp_u8((uint8_t)CONFIG_TQ_DIRECT_PRINTER_BATTERY_MIN_PERCENT, 0, 100);
uint8_t runtime_policy_printer_paper_present_level(void) {
return clamp_u8((uint8_t)CONFIG_TQ_PRINTER_PAPER_PRESENT_LEVEL, 0, 1);
}
uint8_t runtime_policy_direct_printer_paper_present_level(void) {
return clamp_u8((uint8_t)CONFIG_TQ_DIRECT_PRINTER_PAPER_PRESENT_LEVEL, 0, 1);
uint16_t runtime_policy_printer_battery_empty_mv(void) {
return clamp_u16((uint16_t)CONFIG_TQ_PRINTER_BATTERY_EMPTY_MV, 2500, 5000);
}
uint16_t runtime_policy_direct_printer_battery_empty_mv(void) {
return clamp_u16((uint16_t)CONFIG_TQ_DIRECT_PRINTER_BATTERY_EMPTY_MV, 2500, 5000);
}
uint16_t runtime_policy_direct_printer_battery_full_mv(void) {
uint16_t empty_mv = runtime_policy_direct_printer_battery_empty_mv();
uint16_t full_mv = clamp_u16((uint16_t)CONFIG_TQ_DIRECT_PRINTER_BATTERY_FULL_MV, 2600, 6000);
uint16_t runtime_policy_printer_battery_full_mv(void) {
uint16_t empty_mv = runtime_policy_printer_battery_empty_mv();
uint16_t full_mv = clamp_u16((uint16_t)CONFIG_TQ_PRINTER_BATTERY_FULL_MV, 2600, 6000);
if (full_mv <= empty_mv) {
full_mv = (uint16_t)(empty_mv + 100);
}
return full_mv;
}
uint16_t runtime_policy_direct_printer_battery_divider_ratio_x1000(void) {
return clamp_u16((uint16_t)CONFIG_TQ_DIRECT_PRINTER_BATTERY_DIVIDER_RATIO_X1000, 1000, 10000);
uint16_t runtime_policy_printer_battery_divider_ratio_x1000(void) {
return clamp_u16((uint16_t)CONFIG_TQ_PRINTER_BATTERY_DIVIDER_RATIO_X1000, 1000, 10000);
}
uint32_t runtime_policy_direct_printer_ntc_pullup_ohms(void) {
return clamp_u32(CONFIG_TQ_DIRECT_PRINTER_NTC_PULLUP_OHMS, 1000, 200000);
uint32_t runtime_policy_printer_ntc_pullup_ohms(void) {
return clamp_u32(CONFIG_TQ_PRINTER_NTC_PULLUP_OHMS, 1000, 200000);
}
uint32_t runtime_policy_direct_printer_ntc_r25_ohms(void) {
return clamp_u32(CONFIG_TQ_DIRECT_PRINTER_NTC_R25_OHMS, 1000, 200000);
uint32_t runtime_policy_printer_ntc_r25_ohms(void) {
return clamp_u32(CONFIG_TQ_PRINTER_NTC_R25_OHMS, 1000, 200000);
}
uint32_t runtime_policy_direct_printer_ntc_beta(void) {
return clamp_u32(CONFIG_TQ_DIRECT_PRINTER_NTC_BETA, 1000, 10000);
}
uint32_t runtime_policy_printer_connect_timeout_ms(void) {
return clamp_u32(CONFIG_TQ_PRINTER_CONNECT_TIMEOUT_MS, 1000, 60000);
uint32_t runtime_policy_printer_ntc_beta(void) {
return clamp_u32(CONFIG_TQ_PRINTER_NTC_BETA, 1000, 10000);
}
uint32_t runtime_policy_image_generation_timeout_default_ms(void) {

View File

@@ -14,10 +14,6 @@
#include "freertos/task.h"
#include "sdkconfig.h"
#ifndef CONFIG_TQ_DIRECT_PRINTER_ENABLE
#define CONFIG_TQ_DIRECT_PRINTER_ENABLE 1
#endif
#ifndef CONFIG_TQ_KEY_PRINT_BOOST_ACTIVE_HIGH
#define CONFIG_TQ_KEY_PRINT_BOOST_ACTIVE_HIGH 1
#endif
@@ -63,7 +59,6 @@ typedef struct {
typedef struct {
bool initialized;
bool connected;
uint8_t motor_phase;
direct_debug_config_t debug;
SemaphoreHandle_t lock;
@@ -71,9 +66,9 @@ typedef struct {
adc_oneshot_unit_handle_t adc2_handle;
adc_pin_t battery_adc;
adc_pin_t ntc_adc;
} direct_printer_state_t;
} printer_state_t;
static direct_printer_state_t s_state;
static printer_state_t s_state;
static const uint8_t k_motor_step_table[4] = {0x05, 0x09, 0x0A, 0x06};
@@ -228,7 +223,7 @@ static void motor_step_once_locked(uint16_t step_delay_us) {
if (step_delay_us > 0) {
esp_rom_delay_us(step_delay_us);
}
if (runtime_policy_direct_printer_motor_reverse()) {
if (runtime_policy_printer_motor_reverse()) {
s_state.motor_phase = (uint8_t)((s_state.motor_phase + 3) & 0x03);
} else {
s_state.motor_phase = (uint8_t)((s_state.motor_phase + 1) & 0x03);
@@ -362,7 +357,7 @@ static bool read_paper_present_locked(int *out_level) {
if (out_level != NULL) {
*out_level = level;
}
return level == (int)runtime_policy_direct_printer_paper_present_level();
return level == (int)runtime_policy_printer_paper_present_level();
}
static uint16_t battery_raw_to_mv(int raw) {
@@ -373,7 +368,7 @@ static uint16_t battery_raw_to_mv(int raw) {
raw = ADC_RAW_MAX;
}
float adc_mv = ((float)raw * 3300.0f) / (float)ADC_RAW_MAX;
float ratio = (float)runtime_policy_direct_printer_battery_divider_ratio_x1000() / 1000.0f;
float ratio = (float)runtime_policy_printer_battery_divider_ratio_x1000() / 1000.0f;
float batt_mv = adc_mv * ratio;
if (batt_mv < 0.0f) {
batt_mv = 0.0f;
@@ -385,8 +380,8 @@ static uint16_t battery_raw_to_mv(int raw) {
}
static uint8_t battery_mv_to_percent(uint16_t batt_mv) {
uint16_t empty_mv = runtime_policy_direct_printer_battery_empty_mv();
uint16_t full_mv = runtime_policy_direct_printer_battery_full_mv();
uint16_t empty_mv = runtime_policy_printer_battery_empty_mv();
uint16_t full_mv = runtime_policy_printer_battery_full_mv();
if (full_mv <= empty_mv) {
return 100;
}
@@ -404,9 +399,9 @@ static float ntc_raw_to_temp_c(int raw) {
return 25.0f;
}
float pullup = (float)runtime_policy_direct_printer_ntc_pullup_ohms();
float r25 = (float)runtime_policy_direct_printer_ntc_r25_ohms();
float beta = (float)runtime_policy_direct_printer_ntc_beta();
float pullup = (float)runtime_policy_printer_ntc_pullup_ohms();
float r25 = (float)runtime_policy_printer_ntc_r25_ohms();
float beta = (float)runtime_policy_printer_ntc_beta();
if (pullup <= 0.0f || r25 <= 0.0f || beta <= 0.0f) {
return 25.0f;
}
@@ -433,7 +428,7 @@ static void sample_sensors_locked(platform_printer_sensors_t *out_sensors) {
int paper_level = -1;
out_sensors->has_paper = read_paper_present_locked(&paper_level);
out_sensors->paper_gpio_level = (int8_t)paper_level;
out_sensors->paper_present_level = runtime_policy_direct_printer_paper_present_level();
out_sensors->paper_present_level = runtime_policy_printer_paper_present_level();
out_sensors->battery_percent = 100;
out_sensors->temperature_c = 25.0f;
out_sensors->updated_ms = esp_timer_get_time() / 1000;
@@ -459,8 +454,8 @@ static esp_err_t precheck_before_print_locked(char *err, size_t err_len) {
return ESP_ERR_INVALID_STATE;
}
float temp_min = runtime_policy_direct_printer_temp_min_c();
float temp_max = runtime_policy_direct_printer_temp_max_c();
float temp_min = runtime_policy_printer_temp_min_c();
float temp_max = runtime_policy_printer_temp_max_c();
if (temp_max <= temp_min) {
temp_max = temp_min + 1.0f;
}
@@ -469,7 +464,7 @@ static esp_err_t precheck_before_print_locked(char *err, size_t err_len) {
return ESP_ERR_INVALID_STATE;
}
uint8_t battery_min = runtime_policy_direct_printer_battery_min_percent();
uint8_t battery_min = runtime_policy_printer_battery_min_percent();
if (sensors.battery_percent < battery_min) {
write_err(err, err_len, "battery too low");
return ESP_ERR_INVALID_STATE;
@@ -485,10 +480,7 @@ static bool has_timed_out(int64_t deadline_ms) {
return (esp_timer_get_time() / 1000) > deadline_ms;
}
esp_err_t platform_direct_printer_init(void) {
#if !CONFIG_TQ_DIRECT_PRINTER_ENABLE
return ESP_ERR_NOT_SUPPORTED;
#else
esp_err_t platform_printer_init(void) {
if (s_state.initialized) {
return ESP_OK;
}
@@ -552,21 +544,21 @@ esp_err_t platform_direct_printer_init(void) {
init_adc_pin_if_possible(CONFIG_TQ_NTC_ADC_PIN, "ntc_adc", &s_state.ntc_adc);
s_state.motor_phase = 0;
s_state.connected = false;
set_gpio_level_if_valid(CONFIG_TQ_KEY_PRINT_PIN, boost_on_level_locked());
vTaskDelay(pdMS_TO_TICKS(10));
safe_drive_off_locked(true);
s_state.initialized = true;
ESP_LOGI(TAG, "printer initialized");
return ESP_OK;
#endif
}
void platform_direct_printer_deinit(void) {
void platform_printer_deinit(void) {
if (!s_state.initialized) {
return;
}
if (s_state.lock != NULL && xSemaphoreTake(s_state.lock, pdMS_TO_TICKS(100)) == pdTRUE) {
safe_drive_off_locked(false);
s_state.connected = false;
xSemaphoreGive(s_state.lock);
}
@@ -584,67 +576,7 @@ void platform_direct_printer_deinit(void) {
memset(&s_state, 0, sizeof(s_state));
}
esp_err_t platform_direct_printer_connect(uint32_t timeout_ms) {
#if !CONFIG_TQ_DIRECT_PRINTER_ENABLE
(void)timeout_ms;
return ESP_ERR_NOT_SUPPORTED;
#else
esp_err_t err = platform_direct_printer_init();
if (err != ESP_OK) {
return err;
}
uint32_t lock_timeout_ms = timeout_ms == 0 ? 500 : timeout_ms;
if (lock_timeout_ms > 5000) {
lock_timeout_ms = 5000;
}
if (xSemaphoreTake(s_state.lock, pdMS_TO_TICKS(lock_timeout_ms)) != pdTRUE) {
return ESP_ERR_TIMEOUT;
}
if (!s_state.connected) {
err = ensure_shared_shift_pins_gpio_locked();
if (err != ESP_OK) {
xSemaphoreGive(s_state.lock);
return err;
}
set_gpio_level_if_valid(CONFIG_TQ_KEY_PRINT_PIN, boost_on_level_locked());
vTaskDelay(pdMS_TO_TICKS(10));
safe_drive_off_locked(true);
s_state.connected = true;
}
xSemaphoreGive(s_state.lock);
return ESP_OK;
#endif
}
void platform_direct_printer_disconnect(void) {
if (!s_state.initialized || s_state.lock == NULL) {
return;
}
if (xSemaphoreTake(s_state.lock, pdMS_TO_TICKS(500)) != pdTRUE) {
return;
}
safe_drive_off_locked(false);
s_state.connected = false;
xSemaphoreGive(s_state.lock);
}
bool platform_direct_printer_is_connected(void) {
if (!s_state.initialized || s_state.lock == NULL) {
return false;
}
if (xSemaphoreTake(s_state.lock, pdMS_TO_TICKS(100)) != pdTRUE) {
return false;
}
bool connected = s_state.connected;
xSemaphoreGive(s_state.lock);
return connected;
}
esp_err_t platform_direct_printer_get_sensors(platform_printer_sensors_t *out_sensors) {
esp_err_t platform_printer_get_sensors(platform_printer_sensors_t *out_sensors) {
if (out_sensors == NULL) {
return ESP_ERR_INVALID_ARG;
}
@@ -659,7 +591,7 @@ esp_err_t platform_direct_printer_get_sensors(platform_printer_sensors_t *out_se
return ESP_OK;
}
esp_err_t platform_direct_printer_get_debug_config(uint16_t *out_shift_clock_high_us,
esp_err_t platform_printer_get_debug_config(uint16_t *out_shift_clock_high_us,
uint16_t *out_shift_clock_low_us,
uint16_t *out_latch_pulse_us,
bool *out_strobe_active_high,
@@ -668,25 +600,13 @@ esp_err_t platform_direct_printer_get_debug_config(uint16_t *out_shift_clock_hig
uint16_t *out_override_strobe_interval_us,
uint16_t *out_override_motor_step_us,
uint8_t *out_override_steps_per_line) {
#if !CONFIG_TQ_DIRECT_PRINTER_ENABLE
(void)out_shift_clock_high_us;
(void)out_shift_clock_low_us;
(void)out_latch_pulse_us;
(void)out_strobe_active_high;
(void)out_boost_active_high;
(void)out_override_strobe_on_us;
(void)out_override_strobe_interval_us;
(void)out_override_motor_step_us;
(void)out_override_steps_per_line;
return ESP_ERR_NOT_SUPPORTED;
#else
if (out_shift_clock_high_us == NULL || out_shift_clock_low_us == NULL || out_latch_pulse_us == NULL ||
out_strobe_active_high == NULL || out_boost_active_high == NULL || out_override_strobe_on_us == NULL ||
out_override_strobe_interval_us == NULL || out_override_motor_step_us == NULL ||
out_override_steps_per_line == NULL) {
return ESP_ERR_INVALID_ARG;
}
esp_err_t init_rc = platform_direct_printer_init();
esp_err_t init_rc = platform_printer_init();
if (init_rc != ESP_OK) {
return init_rc;
}
@@ -704,10 +624,9 @@ esp_err_t platform_direct_printer_get_debug_config(uint16_t *out_shift_clock_hig
*out_override_steps_per_line = s_state.debug.override_steps_per_line;
xSemaphoreGive(s_state.lock);
return ESP_OK;
#endif
}
esp_err_t platform_direct_printer_set_debug_config(bool has_config,
esp_err_t platform_printer_set_debug_config(bool has_config,
uint16_t shift_clock_high_us,
uint16_t shift_clock_low_us,
uint16_t latch_pulse_us,
@@ -720,27 +639,12 @@ esp_err_t platform_direct_printer_set_debug_config(bool has_config,
bool reset_defaults,
char *err,
size_t err_len) {
#if !CONFIG_TQ_DIRECT_PRINTER_ENABLE
(void)has_config;
(void)shift_clock_high_us;
(void)shift_clock_low_us;
(void)latch_pulse_us;
(void)strobe_active_high;
(void)boost_active_high;
(void)override_strobe_on_us;
(void)override_strobe_interval_us;
(void)override_motor_step_us;
(void)override_steps_per_line;
(void)reset_defaults;
write_err(err, err_len, "printer driver disabled");
return ESP_ERR_NOT_SUPPORTED;
#else
if (!has_config && !reset_defaults) {
write_err(err, err_len, "invalid args");
return ESP_ERR_INVALID_ARG;
}
esp_err_t init_rc = platform_direct_printer_init();
esp_err_t init_rc = platform_printer_init();
if (init_rc != ESP_OK) {
write_err(err, err_len, "printer driver not initialized");
return init_rc;
@@ -798,19 +702,14 @@ esp_err_t platform_direct_printer_set_debug_config(bool has_config,
s_state.debug.override_steps_per_line = override_steps_per_line;
}
safe_drive_off_locked(s_state.connected);
safe_drive_off_locked(true);
xSemaphoreGive(s_state.lock);
return ESP_OK;
#endif
}
esp_err_t platform_direct_printer_print(const platform_direct_print_request_t *request,
esp_err_t platform_printer_print(const platform_printer_print_request_t *request,
char *err,
size_t err_len) {
#if !CONFIG_TQ_DIRECT_PRINTER_ENABLE
write_err(err, err_len, "printer driver disabled");
return ESP_ERR_NOT_SUPPORTED;
#else
if (request == NULL || request->raster == NULL || request->width == 0 || request->height == 0) {
write_err(err, err_len, "invalid args");
return ESP_ERR_INVALID_ARG;
@@ -834,7 +733,7 @@ esp_err_t platform_direct_printer_print(const platform_direct_print_request_t *r
uint32_t timeout_ms = request->timeout_ms;
if (timeout_ms == 0) {
timeout_ms = runtime_policy_direct_printer_operation_timeout_ms();
timeout_ms = runtime_policy_printer_operation_timeout_ms();
}
if (xSemaphoreTake(s_state.lock, pdMS_TO_TICKS(1000)) != pdTRUE) {
@@ -842,12 +741,6 @@ esp_err_t platform_direct_printer_print(const platform_direct_print_request_t *r
return ESP_ERR_TIMEOUT;
}
if (!s_state.connected) {
xSemaphoreGive(s_state.lock);
write_err(err, err_len, "printer not connected");
return ESP_ERR_INVALID_STATE;
}
esp_err_t rc = ensure_shared_shift_pins_gpio_locked();
if (rc != ESP_OK) {
safe_drive_off_locked(true);
@@ -858,16 +751,16 @@ esp_err_t platform_direct_printer_print(const platform_direct_print_request_t *r
uint16_t strobe_on_us = (request->strobe_on_time_us > 0)
? request->strobe_on_time_us
: runtime_policy_direct_printer_strobe_on_us();
: runtime_policy_printer_strobe_on_us();
uint16_t strobe_interval_us = (request->strobe_interval_us > 0)
? request->strobe_interval_us
: runtime_policy_direct_printer_strobe_interval_us();
: runtime_policy_printer_strobe_interval_us();
uint16_t motor_step_us = (request->motor_step_delay_us > 0)
? request->motor_step_delay_us
: runtime_policy_direct_printer_motor_step_us();
: runtime_policy_printer_motor_step_us();
uint8_t steps_per_line = (request->motor_steps_per_line > 0)
? request->motor_steps_per_line
: runtime_policy_direct_printer_steps_per_line();
: runtime_policy_printer_steps_per_line();
if (s_state.debug.override_strobe_on_us > 0) {
strobe_on_us = s_state.debug.override_strobe_on_us;
@@ -944,42 +837,31 @@ esp_err_t platform_direct_printer_print(const platform_direct_print_request_t *r
safe_drive_off_locked(true);
xSemaphoreGive(s_state.lock);
return rc;
#endif
}
esp_err_t platform_direct_printer_gap_move(uint32_t timeout_ms, char *err, size_t err_len) {
#if !CONFIG_TQ_DIRECT_PRINTER_ENABLE
write_err(err, err_len, "printer driver disabled");
return ESP_ERR_NOT_SUPPORTED;
#else
esp_err_t platform_printer_gap_move(uint32_t timeout_ms, char *err, size_t err_len) {
if (!s_state.initialized || s_state.lock == NULL) {
write_err(err, err_len, "printer driver not initialized");
return ESP_ERR_INVALID_STATE;
}
if (timeout_ms == 0) {
timeout_ms = runtime_policy_direct_printer_operation_timeout_ms();
timeout_ms = runtime_policy_printer_operation_timeout_ms();
}
if (xSemaphoreTake(s_state.lock, pdMS_TO_TICKS(1000)) != pdTRUE) {
write_err(err, err_len, "printer lock timeout");
return ESP_ERR_TIMEOUT;
}
if (!s_state.connected) {
xSemaphoreGive(s_state.lock);
write_err(err, err_len, "printer not connected");
return ESP_ERR_INVALID_STATE;
}
esp_err_t rc = ESP_OK;
uint16_t steps = runtime_policy_direct_printer_gap_steps();
uint16_t step_delay_us = runtime_policy_direct_printer_motor_step_us();
uint16_t steps = runtime_policy_printer_gap_steps();
uint16_t step_delay_us = runtime_policy_printer_motor_step_us();
if (s_state.debug.override_motor_step_us > 0) {
step_delay_us = s_state.debug.override_motor_step_us;
}
platform_printer_sensors_t sensors = {0};
sample_sensors_locked(&sensors);
uint8_t battery_min = runtime_policy_direct_printer_battery_min_percent();
uint8_t battery_min = runtime_policy_printer_battery_min_percent();
if (sensors.battery_percent < battery_min) {
write_err(err, err_len, "battery too low");
safe_drive_off_locked(true);
@@ -1016,5 +898,4 @@ esp_err_t platform_direct_printer_gap_move(uint32_t timeout_ms, char *err, size_
safe_drive_off_locked(true);
xSemaphoreGive(s_state.lock);
return rc;
#endif
}

View File

@@ -37,11 +37,6 @@ config TQ_LIFECYCLE_RETRY_BACKOFF_MS
range 100 10000
default 800
config TQ_PRINTER_CONNECT_TIMEOUT_MS
int "Printer connect timeout (ms)"
range 1000 60000
default 15000
config TQ_PRINTER_CONTROL_LOCK_TIMEOUT_MS
int "Printer control lane lock timeout (ms)"
range 100 5000
@@ -67,110 +62,89 @@ config TQ_PRINTER_STOP_TIMEOUT_MS
range 1000 30000
default 8000
config TQ_DIRECT_PRINTER_ENABLE
bool "Enable thermal printer driver"
default y
config TQ_DIRECT_PRINTER_OPERATION_TIMEOUT_MS
config TQ_PRINTER_OPERATION_TIMEOUT_MS
int "Printer max operation timeout (ms)"
range 1000 300000
default 90000
depends on TQ_DIRECT_PRINTER_ENABLE
config TQ_DIRECT_PRINTER_STROBE_ON_US
config TQ_PRINTER_STROBE_ON_US
int "Printer strobe on-time (us)"
range 100 10000
default 1000
depends on TQ_DIRECT_PRINTER_ENABLE
config TQ_DIRECT_PRINTER_STROBE_INTERVAL_US
config TQ_PRINTER_STROBE_INTERVAL_US
int "Printer strobe interval (us)"
range 0 10000
default 200
depends on TQ_DIRECT_PRINTER_ENABLE
config TQ_DIRECT_PRINTER_MOTOR_STEP_US
config TQ_PRINTER_MOTOR_STEP_US
int "Printer motor step delay (us)"
range 100 20000
default 2000
depends on TQ_DIRECT_PRINTER_ENABLE
config TQ_DIRECT_PRINTER_MOTOR_REVERSE
config TQ_PRINTER_MOTOR_REVERSE
bool "Printer motor direction reversed"
default n
depends on TQ_DIRECT_PRINTER_ENABLE
config TQ_DIRECT_PRINTER_STEPS_PER_LINE
config TQ_PRINTER_STEPS_PER_LINE
int "Printer motor steps per printed line"
range 1 8
default 2
depends on TQ_DIRECT_PRINTER_ENABLE
config TQ_DIRECT_PRINTER_GAP_STEPS
config TQ_PRINTER_GAP_STEPS
int "Printer gap move steps"
range 1 2000
default 96
depends on TQ_DIRECT_PRINTER_ENABLE
config TQ_DIRECT_PRINTER_TEMP_MIN_C
config TQ_PRINTER_TEMP_MIN_C
int "Printer allowed minimum temperature (C)"
range 0 120
default 15
depends on TQ_DIRECT_PRINTER_ENABLE
config TQ_DIRECT_PRINTER_TEMP_MAX_C
config TQ_PRINTER_TEMP_MAX_C
int "Printer allowed maximum temperature (C)"
range 1 150
default 55
depends on TQ_DIRECT_PRINTER_ENABLE
config TQ_DIRECT_PRINTER_BATTERY_MIN_PERCENT
config TQ_PRINTER_BATTERY_MIN_PERCENT
int "Printer minimum battery percent"
range 0 100
default 5
depends on TQ_DIRECT_PRINTER_ENABLE
config TQ_DIRECT_PRINTER_PAPER_PRESENT_LEVEL
config TQ_PRINTER_PAPER_PRESENT_LEVEL
int "Printer paper-present GPIO level (0/1)"
range 0 1
default 0
depends on TQ_DIRECT_PRINTER_ENABLE
config TQ_DIRECT_PRINTER_BATTERY_EMPTY_MV
config TQ_PRINTER_BATTERY_EMPTY_MV
int "Printer battery empty voltage (mV)"
range 2500 5000
default 3300
depends on TQ_DIRECT_PRINTER_ENABLE
config TQ_DIRECT_PRINTER_BATTERY_FULL_MV
config TQ_PRINTER_BATTERY_FULL_MV
int "Printer battery full voltage (mV)"
range 2600 6000
default 4200
depends on TQ_DIRECT_PRINTER_ENABLE
config TQ_DIRECT_PRINTER_BATTERY_DIVIDER_RATIO_X1000
config TQ_PRINTER_BATTERY_DIVIDER_RATIO_X1000
int "Printer battery divider ratio x1000"
range 1000 10000
default 2000
depends on TQ_DIRECT_PRINTER_ENABLE
config TQ_DIRECT_PRINTER_NTC_PULLUP_OHMS
config TQ_PRINTER_NTC_PULLUP_OHMS
int "Printer NTC pull-up resistor (ohms)"
range 1000 200000
default 10000
depends on TQ_DIRECT_PRINTER_ENABLE
config TQ_DIRECT_PRINTER_NTC_R25_OHMS
config TQ_PRINTER_NTC_R25_OHMS
int "Printer NTC R25 resistance (ohms)"
range 1000 200000
default 10000
depends on TQ_DIRECT_PRINTER_ENABLE
config TQ_DIRECT_PRINTER_NTC_BETA
config TQ_PRINTER_NTC_BETA
int "Printer NTC beta constant"
range 1000 10000
default 3950
depends on TQ_DIRECT_PRINTER_ENABLE
config TQ_Z_IMAGE_API_KEY
string "Z-Image API Key for DashScope HTTP (optional, fallback to Voice API key)"
@@ -218,10 +192,6 @@ config TQ_Z_IMAGE_HTTP_READ_CHUNK_BYTES
range 4096 32768
default 16384
config TQ_Z_IMAGE_COEX_PREFER_WIFI_DURING_DOWNLOAD
bool "Prefer Wi-Fi RF during image download"
default y
config TQ_VOICE_API_KEY
string "Voice API Key for DashScope WebSocket (optional)"
default "sk-7a50eca6856d4afb968ac3bf512f6d1b"

View File

@@ -21,7 +21,6 @@ CONFIG_TQ_WIFI_PROV_SOFTAP_MAX_CONN=4
CONFIG_TQ_Z_IMAGE_DEFAULT_SIZE="512*768"
CONFIG_TQ_Z_IMAGE_HTTP_BUFFER_BYTES=16384
CONFIG_TQ_Z_IMAGE_HTTP_READ_CHUNK_BYTES=16384
CONFIG_TQ_Z_IMAGE_COEX_PREFER_WIFI_DURING_DOWNLOAD=y
# CONFIG_PARTITION_TABLE_SINGLE_APP_LARGE is not set
CONFIG_PARTITION_TABLE_CUSTOM=y
CONFIG_PARTITION_TABLE_CUSTOM_FILENAME="partitions.csv"