217 lines
6.9 KiB
Text
217 lines
6.9 KiB
Text
import { DarkLineEdit } from "../components/dark_line_edit.slint";
|
|
import { Theme } from "../theme.slint";
|
|
import { DarkButton } from "../components/dark_button.slint";
|
|
import { DarkComboBox } from "../components/dark_combo_box.slint";
|
|
import { FlasherBridge } from "../globals.slint";
|
|
|
|
export component TabFlasher inherits Rectangle {
|
|
background: Theme.bg-primary;
|
|
|
|
VerticalLayout {
|
|
padding: 20px;
|
|
spacing: 16px;
|
|
alignment: start;
|
|
|
|
Text {
|
|
text: "Firmware Flasher";
|
|
color: Theme.fg-primary;
|
|
font-size: 20px;
|
|
font-weight: 700;
|
|
}
|
|
|
|
Text {
|
|
text: "Flash firmware via ESP32 programming port (CH340/CP2102).";
|
|
color: Theme.fg-secondary;
|
|
font-size: 12px;
|
|
wrap: word-wrap;
|
|
}
|
|
|
|
// Port selection
|
|
Rectangle {
|
|
background: Theme.bg-secondary;
|
|
border-radius: 8px;
|
|
|
|
VerticalLayout {
|
|
padding: 16px;
|
|
spacing: 10px;
|
|
|
|
Text {
|
|
text: "Programming Port (CH340/CP210x only)";
|
|
color: Theme.accent-cyan;
|
|
font-size: 14px;
|
|
font-weight: 600;
|
|
}
|
|
|
|
HorizontalLayout {
|
|
spacing: 8px;
|
|
|
|
if FlasherBridge.prog-ports.length > 0 : DarkComboBox {
|
|
horizontal-stretch: 1;
|
|
model: FlasherBridge.prog-ports;
|
|
selected(value) => {
|
|
FlasherBridge.selected-prog-port = value;
|
|
}
|
|
}
|
|
|
|
if FlasherBridge.prog-ports.length == 0 : DarkLineEdit {
|
|
horizontal-stretch: 1;
|
|
text <=> FlasherBridge.selected-prog-port;
|
|
placeholder-text: "/dev/ttyUSB0";
|
|
}
|
|
|
|
DarkButton {
|
|
text: "Refresh";
|
|
clicked => { FlasherBridge.refresh-prog-ports(); }
|
|
}
|
|
}
|
|
|
|
if FlasherBridge.prog-ports.length == 0 : Text {
|
|
text: "No CH340/CP210x port detected. Enter path manually or plug in the programming cable.";
|
|
color: Theme.accent-yellow;
|
|
font-size: 11px;
|
|
wrap: word-wrap;
|
|
}
|
|
}
|
|
}
|
|
|
|
// Flash target partition
|
|
Rectangle {
|
|
background: Theme.bg-secondary;
|
|
border-radius: 8px;
|
|
|
|
VerticalLayout {
|
|
padding: 16px;
|
|
spacing: 10px;
|
|
|
|
Text {
|
|
text: "Target Partition";
|
|
color: Theme.accent-cyan;
|
|
font-size: 14px;
|
|
font-weight: 600;
|
|
}
|
|
|
|
DarkComboBox {
|
|
model: ["full (0x0)", "factory (0x20000)", "ota_0 (0x220000)"];
|
|
current-index <=> FlasherBridge.flash-offset-index;
|
|
}
|
|
}
|
|
}
|
|
|
|
// Firmware file
|
|
Rectangle {
|
|
background: Theme.bg-secondary;
|
|
border-radius: 8px;
|
|
|
|
VerticalLayout {
|
|
padding: 16px;
|
|
spacing: 10px;
|
|
|
|
Text {
|
|
text: "Firmware File";
|
|
color: Theme.accent-cyan;
|
|
font-size: 14px;
|
|
font-weight: 600;
|
|
}
|
|
|
|
HorizontalLayout {
|
|
spacing: 8px;
|
|
|
|
Text {
|
|
horizontal-stretch: 1;
|
|
text: FlasherBridge.firmware-path != "" ? FlasherBridge.firmware-path : "No file selected";
|
|
color: FlasherBridge.firmware-path != "" ? Theme.fg-primary : Theme.fg-secondary;
|
|
font-size: 12px;
|
|
vertical-alignment: center;
|
|
overflow: elide;
|
|
}
|
|
|
|
DarkButton {
|
|
text: "Browse...";
|
|
clicked => { FlasherBridge.browse-firmware(); }
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
// Flash button + progress
|
|
Rectangle {
|
|
background: Theme.bg-secondary;
|
|
border-radius: 8px;
|
|
|
|
VerticalLayout {
|
|
padding: 16px;
|
|
spacing: 10px;
|
|
|
|
HorizontalLayout {
|
|
spacing: 12px;
|
|
|
|
DarkButton {
|
|
text: FlasherBridge.flashing ? "Flashing..." : "Flash Firmware";
|
|
enabled: !FlasherBridge.flashing
|
|
&& FlasherBridge.firmware-path != ""
|
|
&& FlasherBridge.selected-prog-port != "";
|
|
clicked => { FlasherBridge.flash(); }
|
|
}
|
|
|
|
Text {
|
|
text: FlasherBridge.flash-status;
|
|
color: Theme.fg-primary;
|
|
font-size: 12px;
|
|
vertical-alignment: center;
|
|
horizontal-stretch: 1;
|
|
}
|
|
}
|
|
|
|
if FlasherBridge.flashing || FlasherBridge.flash-progress > 0 : Rectangle {
|
|
height: 20px;
|
|
background: Theme.bg-primary;
|
|
border-radius: 4px;
|
|
|
|
Rectangle {
|
|
x: 0;
|
|
width: parent.width * clamp(FlasherBridge.flash-progress, 0, 1);
|
|
height: 100%;
|
|
background: FlasherBridge.flash-progress >= 1.0 ? Theme.accent-green : Theme.accent-purple;
|
|
border-radius: 4px;
|
|
}
|
|
|
|
Text {
|
|
text: round(FlasherBridge.flash-progress * 100) + "%";
|
|
color: Theme.fg-primary;
|
|
font-size: 11px;
|
|
horizontal-alignment: center;
|
|
vertical-alignment: center;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
// Warning
|
|
Rectangle {
|
|
background: #ff555520;
|
|
border-radius: 8px;
|
|
border-width: 1px;
|
|
border-color: Theme.accent-red;
|
|
|
|
VerticalLayout {
|
|
padding: 12px;
|
|
spacing: 4px;
|
|
|
|
Text {
|
|
text: "Warning";
|
|
color: Theme.accent-red;
|
|
font-size: 13px;
|
|
font-weight: 600;
|
|
}
|
|
Text {
|
|
text: "Do not disconnect the keyboard during flashing. The device will reboot automatically when done.";
|
|
color: Theme.fg-secondary;
|
|
font-size: 11px;
|
|
wrap: word-wrap;
|
|
}
|
|
}
|
|
}
|
|
|
|
Rectangle { vertical-stretch: 1; }
|
|
}
|
|
}
|