mirror of
https://github.com/johndoe6345789/metabuilder.git
synced 2026-04-24 22:04:56 +00:00
feat(styles): create global styles entry point and organize global styles feat(styles): implement base HTML element styles and utility classes for flexbox feat(styles): establish layout, position, spacing, and text utility classes feat(styles): introduce mixins for animations, cards, dialogs, flexbox, grid, and responsive design test(quick_guide): add component and metadata validation tests for quick_guide package test(ui_level6): implement metadata validation tests for ui_level6 package
341 lines
12 KiB
QML
341 lines
12 KiB
QML
import QtQuick
|
|
import QtQuick.Controls
|
|
import QtQuick.Layouts
|
|
import "../contexts"
|
|
import "../fakemui"
|
|
|
|
/**
|
|
* UserInfo.qml - User profile and connection status
|
|
* Uses Python AppController (app) - shows session info
|
|
*/
|
|
Item {
|
|
id: root
|
|
|
|
// State
|
|
property var sessionInfo: null
|
|
property string debugLogs: ""
|
|
property string connectionStatus: "unknown"
|
|
|
|
Component.onCompleted: {
|
|
app.sessionInfoChanged.connect(onSessionInfo)
|
|
app.debugLog.connect(onDebugLog)
|
|
// Request session info if in nerd mode
|
|
if (NerdModeContext.nerdMode) {
|
|
app.setNerdMode(true) // This emits sessionInfoChanged
|
|
}
|
|
// Check connection by loading tasks
|
|
connectionStatus = "checking"
|
|
app.tasksLoaded.connect(onConnected)
|
|
app.errorOccurred.connect(onConnectionError)
|
|
}
|
|
|
|
Component.onDestruction: {
|
|
app.sessionInfoChanged.disconnect(onSessionInfo)
|
|
app.debugLog.disconnect(onDebugLog)
|
|
app.tasksLoaded.disconnect(onConnected)
|
|
app.errorOccurred.disconnect(onConnectionError)
|
|
}
|
|
|
|
function onSessionInfo(jsonStr) {
|
|
try {
|
|
sessionInfo = JSON.parse(jsonStr)
|
|
} catch (e) {
|
|
sessionInfo = null
|
|
}
|
|
}
|
|
|
|
function onDebugLog(entry) {
|
|
debugLogs = app.getDebugLogs()
|
|
}
|
|
|
|
function onConnected() {
|
|
connectionStatus = "connected"
|
|
}
|
|
|
|
function onConnectionError(msg) {
|
|
if (msg.includes("session") || msg.includes("auth")) {
|
|
connectionStatus = "disconnected"
|
|
}
|
|
}
|
|
|
|
function openCodex() {
|
|
app.openCodexBrowser()
|
|
}
|
|
|
|
ScrollView {
|
|
anchors.fill: parent
|
|
anchors.margins: 16
|
|
clip: true
|
|
|
|
ColumnLayout {
|
|
width: parent.width
|
|
spacing: 16
|
|
|
|
// Connection status card
|
|
CCard {
|
|
Layout.fillWidth: true
|
|
Layout.maximumWidth: 600
|
|
Layout.alignment: Qt.AlignHCenter
|
|
Layout.preferredHeight: contentCol1.implicitHeight + 48
|
|
|
|
ColumnLayout {
|
|
id: contentCol1
|
|
Layout.fillWidth: true
|
|
Layout.fillHeight: true
|
|
Layout.margins: 24
|
|
spacing: 16
|
|
|
|
Text {
|
|
text: LanguageContext.t("connectionStatus")
|
|
font.pixelSize: 18
|
|
font.bold: true
|
|
color: Theme.text
|
|
}
|
|
|
|
RowLayout {
|
|
spacing: 12
|
|
|
|
// Status indicator
|
|
Rectangle {
|
|
width: 12
|
|
height: 12
|
|
radius: 6
|
|
color: connectionStatus === "connected" ? Theme.success :
|
|
connectionStatus === "disconnected" ? Theme.error : Theme.warning
|
|
}
|
|
|
|
Text {
|
|
text: connectionStatus === "connected" ? LanguageContext.t("connected") :
|
|
connectionStatus === "disconnected" ? LanguageContext.t("disconnected") :
|
|
connectionStatus === "checking" ? "Checking..." :
|
|
LanguageContext.t("unknown")
|
|
font.pixelSize: 16
|
|
color: Theme.text
|
|
}
|
|
}
|
|
|
|
Text {
|
|
text: connectionStatus === "connected" ?
|
|
LanguageContext.t("connectedDesc") :
|
|
connectionStatus === "disconnected" ?
|
|
"Set up your .env file with CODEX_SESSION_TOKEN" :
|
|
"Checking connection..."
|
|
font.pixelSize: 14
|
|
color: Theme.textSecondary
|
|
wrapMode: Text.WordWrap
|
|
Layout.fillWidth: true
|
|
}
|
|
|
|
// Actions
|
|
RowLayout {
|
|
spacing: 12
|
|
|
|
CButton {
|
|
text: "Open Codex in Browser"
|
|
variant: "outlined"
|
|
onClicked: openCodex()
|
|
}
|
|
|
|
CButton {
|
|
text: LanguageContext.t("refresh")
|
|
variant: "text"
|
|
onClicked: {
|
|
connectionStatus = "checking"
|
|
app.loadTasks()
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
// Session Info card (nerd mode only)
|
|
CCard {
|
|
Layout.fillWidth: true
|
|
Layout.maximumWidth: 600
|
|
Layout.alignment: Qt.AlignHCenter
|
|
Layout.preferredHeight: contentCol2.implicitHeight + 48
|
|
visible: NerdModeContext.nerdMode
|
|
|
|
ColumnLayout {
|
|
id: contentCol2
|
|
Layout.fillWidth: true
|
|
Layout.fillHeight: true
|
|
Layout.margins: 24
|
|
spacing: 16
|
|
|
|
Text {
|
|
text: "Session Info"
|
|
font.pixelSize: 18
|
|
font.bold: true
|
|
color: Theme.text
|
|
}
|
|
|
|
GridLayout {
|
|
Layout.fillWidth: true
|
|
columns: 2
|
|
columnSpacing: 16
|
|
rowSpacing: 12
|
|
|
|
Text {
|
|
text: "Has Session"
|
|
font.pixelSize: 14
|
|
font.bold: true
|
|
color: Theme.textSecondary
|
|
}
|
|
|
|
Text {
|
|
text: sessionInfo?.has_session ? "Yes" : "No"
|
|
font.pixelSize: 14
|
|
color: sessionInfo?.has_session ? Theme.success : Theme.error
|
|
}
|
|
|
|
Text {
|
|
text: "Base URL"
|
|
font.pixelSize: 14
|
|
font.bold: true
|
|
color: Theme.textSecondary
|
|
}
|
|
|
|
Text {
|
|
text: sessionInfo?.base_url || "—"
|
|
font.pixelSize: 14
|
|
color: Theme.text
|
|
font.family: "monospace"
|
|
}
|
|
|
|
Text {
|
|
text: "Cookie Preview"
|
|
font.pixelSize: 14
|
|
font.bold: true
|
|
color: Theme.textSecondary
|
|
}
|
|
|
|
Text {
|
|
text: sessionInfo?.cookie_preview || "—"
|
|
font.pixelSize: 14
|
|
color: Theme.text
|
|
font.family: "monospace"
|
|
elide: Text.ElideMiddle
|
|
Layout.maximumWidth: 200
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
// Debug Logs card (nerd mode only)
|
|
CCard {
|
|
Layout.fillWidth: true
|
|
Layout.maximumWidth: 600
|
|
Layout.alignment: Qt.AlignHCenter
|
|
Layout.preferredHeight: contentCol3.implicitHeight + 48
|
|
visible: NerdModeContext.nerdMode
|
|
|
|
ColumnLayout {
|
|
id: contentCol3
|
|
Layout.fillWidth: true
|
|
Layout.fillHeight: true
|
|
Layout.margins: 24
|
|
spacing: 16
|
|
|
|
RowLayout {
|
|
Layout.fillWidth: true
|
|
|
|
Text {
|
|
text: "Debug Logs"
|
|
font.pixelSize: 18
|
|
font.bold: true
|
|
color: Theme.text
|
|
}
|
|
|
|
Item { Layout.fillWidth: true }
|
|
|
|
CButton {
|
|
text: "Clear"
|
|
variant: "text"
|
|
size: "small"
|
|
onClicked: {
|
|
app.clearDebugLogs()
|
|
debugLogs = ""
|
|
}
|
|
}
|
|
}
|
|
|
|
ScrollView {
|
|
Layout.fillWidth: true
|
|
Layout.preferredHeight: 200
|
|
clip: true
|
|
|
|
TextArea {
|
|
text: debugLogs || "(no logs yet)"
|
|
font.family: "monospace"
|
|
font.pixelSize: 11
|
|
color: Theme.text
|
|
readOnly: true
|
|
wrapMode: Text.NoWrap
|
|
|
|
background: Rectangle {
|
|
color: Theme.surface
|
|
radius: 4
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
// Setup instructions
|
|
CCard {
|
|
Layout.fillWidth: true
|
|
Layout.maximumWidth: 600
|
|
Layout.alignment: Qt.AlignHCenter
|
|
Layout.preferredHeight: contentCol4.implicitHeight + 48
|
|
visible: connectionStatus === "disconnected"
|
|
|
|
ColumnLayout {
|
|
id: contentCol4
|
|
Layout.fillWidth: true
|
|
Layout.fillHeight: true
|
|
Layout.margins: 24
|
|
spacing: 16
|
|
|
|
Text {
|
|
text: "Setup Instructions"
|
|
font.pixelSize: 18
|
|
font.bold: true
|
|
color: Theme.text
|
|
}
|
|
|
|
Text {
|
|
text: "1. Open ChatGPT/Codex in your browser"
|
|
font.pixelSize: 14
|
|
color: Theme.textSecondary
|
|
}
|
|
|
|
Text {
|
|
text: "2. Open DevTools → Application → Cookies"
|
|
font.pixelSize: 14
|
|
color: Theme.textSecondary
|
|
}
|
|
|
|
Text {
|
|
text: "3. Copy the __Secure-next-auth.session-token value"
|
|
font.pixelSize: 14
|
|
color: Theme.textSecondary
|
|
}
|
|
|
|
Text {
|
|
text: "4. Create a .env file with CODEX_SESSION_TOKEN=<token>"
|
|
font.pixelSize: 14
|
|
color: Theme.textSecondary
|
|
}
|
|
|
|
Text {
|
|
text: "5. Restart the app"
|
|
font.pixelSize: 14
|
|
color: Theme.textSecondary
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|