mirror of
https://github.com/PhotonVision/photonvision
synced 2026-06-22 01:11:40 +00:00
Adds support for user-created custom themes. Custom theme interface is tucked into the global settings in a non-invasive manner to avoid major design changes. Builds on the theme structure established by the dark theme update. <img width="1486" height="953" alt="image" src="https://github.com/user-attachments/assets/716bcfc7-af74-41dc-b14a-cfc2f2d2caa9" /> <img width="1486" height="956" alt="image" src="https://github.com/user-attachments/assets/a00f9620-0b1d-4f67-b010-e94dda5dc212" /> Here's a few examples of what teams could do, using a few color schemes from local teams. Imagine the possibilities! <img width="1485" height="951" alt="image" src="https://github.com/user-attachments/assets/c3da37b8-f6be-4152-81e0-533297f517fc" /> <img width="1483" height="951" alt="image" src="https://github.com/user-attachments/assets/0d453f7a-cf6f-4c27-97db-603b54c1f73e" /> <img width="1485" height="952" alt="image" src="https://github.com/user-attachments/assets/bf8c7770-e60d-4875-9580-ed7e54e089f4" /> <img width="1484" height="952" alt="image" src="https://github.com/user-attachments/assets/326d89e6-dd6e-4e05-a9fa-c9fc6f880847" /> <img width="1482" height="951" alt="image" src="https://github.com/user-attachments/assets/eb5a2a5d-c103-482c-a62a-5ccd5ba21cc5" /> <img width="1482" height="950" alt="image" src="https://github.com/user-attachments/assets/4831ca56-f322-4345-97af-8963ae8539b1" /> Looking for high contrast? Just moments away: <img width="1484" height="949" alt="image" src="https://github.com/user-attachments/assets/7ffc65c6-7000-4566-b4f0-c8247f75fb3d" />
121 lines
3.4 KiB
Vue
121 lines
3.4 KiB
Vue
<script setup lang="ts">
|
|
import { useStateStore } from "@/stores/StateStore";
|
|
import { useSettingsStore } from "@/stores/settings/GeneralSettingsStore";
|
|
import { useCameraSettingsStore } from "@/stores/settings/CameraSettingsStore";
|
|
import { AutoReconnectingWebsocket } from "@/lib/AutoReconnectingWebsocket";
|
|
import { inject, onBeforeMount } from "vue";
|
|
import PhotonSidebar from "@/components/app/photon-sidebar.vue";
|
|
import PhotonLogView from "@/components/app/photon-log-view.vue";
|
|
import PhotonErrorSnackbar from "@/components/app/photon-error-snackbar.vue";
|
|
import { useTheme } from "vuetify";
|
|
import { restoreThemeConfig } from "@/lib/ThemeManager";
|
|
|
|
const is_demo = import.meta.env.MODE === "demo";
|
|
if (!is_demo) {
|
|
const websocket = new AutoReconnectingWebsocket(
|
|
`ws://${inject("backendHost")}/websocket_data`,
|
|
() => {
|
|
useStateStore().$patch({ backendConnected: true });
|
|
},
|
|
(data) => {
|
|
if (data.log !== undefined) {
|
|
useStateStore().addLogFromWebsocket(data.log);
|
|
}
|
|
if (data.settings !== undefined) {
|
|
useSettingsStore().updateGeneralSettingsFromWebsocket(data.settings);
|
|
}
|
|
if (data.cameraSettings !== undefined) {
|
|
useCameraSettingsStore().updateCameraSettingsFromWebsocket(data.cameraSettings);
|
|
}
|
|
if (data.ntConnectionInfo !== undefined) {
|
|
useStateStore().updateNTConnectionStatusFromWebsocket(data.ntConnectionInfo);
|
|
}
|
|
if (data.metrics !== undefined) {
|
|
useSettingsStore().updateMetricsFromWebsocket(data.metrics);
|
|
}
|
|
if (data.updatePipelineResult !== undefined) {
|
|
useStateStore().updateBackendResultsFromWebsocket(data.updatePipelineResult);
|
|
}
|
|
if (data.mutatePipelineSettings !== undefined && data.cameraUniqueName !== undefined) {
|
|
useCameraSettingsStore().changePipelineSettingsInStore(data.mutatePipelineSettings, data.cameraUniqueName);
|
|
}
|
|
if (data.calibrationData !== undefined) {
|
|
useStateStore().updateCalibrationStateValuesFromWebsocket(data.calibrationData);
|
|
}
|
|
if (data.visionSourceManager !== undefined) {
|
|
useStateStore().updateDiscoveredCameras(data.visionSourceManager);
|
|
}
|
|
},
|
|
() => {
|
|
useStateStore().$patch({ backendConnected: false });
|
|
}
|
|
);
|
|
useStateStore().$patch({ websocket: websocket });
|
|
}
|
|
|
|
const theme = useTheme();
|
|
onBeforeMount(() => {
|
|
restoreThemeConfig(theme);
|
|
});
|
|
</script>
|
|
|
|
<template>
|
|
<v-app>
|
|
<photon-sidebar />
|
|
<v-main>
|
|
<v-container class="main-container" fluid fill-height>
|
|
<v-layout>
|
|
<v-container class="align-start pa-0 ma-0" fluid>
|
|
<router-view />
|
|
</v-container>
|
|
</v-layout>
|
|
</v-container>
|
|
</v-main>
|
|
|
|
<photon-log-view />
|
|
<photon-error-snackbar />
|
|
</v-app>
|
|
</template>
|
|
|
|
<style lang="scss">
|
|
@use "@/assets/styles/settings";
|
|
@use "@/assets/styles/variables";
|
|
@use "sass:map";
|
|
|
|
@media #{map.get(settings.$display-breakpoints, 'md-and-down')} {
|
|
html {
|
|
font-size: 14px !important;
|
|
}
|
|
}
|
|
|
|
/* Custom scrollbar styles */
|
|
::-webkit-scrollbar {
|
|
width: 12px;
|
|
}
|
|
|
|
::-webkit-scrollbar-track {
|
|
background: rgb(var(--v-theme-background));
|
|
}
|
|
|
|
::-webkit-scrollbar-thumb {
|
|
background-color: rgb(var(--v-theme-accent));
|
|
border-radius: 10px;
|
|
}
|
|
|
|
::-webkit-scrollbar-thumb:hover {
|
|
background-color: rgb(var(--v-theme-primary));
|
|
}
|
|
|
|
.main-container {
|
|
padding: 0 !important;
|
|
}
|
|
|
|
.v-overlay__scrim {
|
|
background-color: #111111;
|
|
}
|
|
|
|
div.v-layout {
|
|
overflow: unset !important;
|
|
}
|
|
</style>
|