<template>
<section class="page">
<GnPageHeader title="Modes" kicker="System" />
<AppLoadingState v-if="modesStore.isLoading" text="Loading modes" />
<AppErrorState
v-else-if="modesStore.error"
title="Modes loading failed"
:error="modesStore.error"
:retry="modesStore.loadModes"
/>
<AppEmptyState
v-else-if="modesStore.modes.length === 0"
title="No modes"
message="No system modes configured."
/>
<div v-else class="modes-grid">
<div
v-for="mode in modesStore.modes"
:key="mode.tag"
class="mode-card-item"
>
<GnActionCard :title="mode.label || mode.tag">
<template #default>
<p v-if="mode.description">{{ mode.description }}</p>
<div class="mode-meta">
<GnBadge
:variant="modesStore.isActive(mode.tag) ? 'success' : 'secondary'"
>
{{ modesStore.isActive(mode.tag) ? 'On' : 'Off' }}
</GnBadge>
</div>
</template>
<template #actions>
<GnButton
:variant="modesStore.isActive(mode.tag) ? 'danger' : 'primary'"
:icon="modesStore.isActive(mode.tag) ? 'ph-moon' : 'ph-sun'"
:loading="modesStore.isLoadingToggle && activeTag === mode.tag"
@click="toggle(mode.tag)"
>
{{ modesStore.isActive(mode.tag) ? 'Disable' : 'Enable' }}
</GnButton>
</template>
</GnActionCard>
</div>
</div>
</section>
</template>
<script setup>
import { ref, onMounted } from "vue";
import { useModesStore } from "../../../stores/modes";
import {
GnPageHeader,
GnBadge,
GnButton,
GnActionCard,
useToast,
} from "gnexus-ui-kit/vue";
import AppEmptyState from "../../../components/feedback/AppEmptyState.vue";
import AppErrorState from "../../../components/feedback/AppErrorState.vue";
import AppLoadingState from "../../../components/feedback/AppLoadingState.vue";
const modesStore = useModesStore();
const toast = useToast();
const activeTag = ref(null);
onMounted(() => {
modesStore.loadModes();
});
async function toggle(tag) {
activeTag.value = tag;
const result = await modesStore.toggleMode(tag);
activeTag.value = null;
if (result?.ok) {
toast.success({
title: modesStore.isActive(tag) ? `"${tag}" enabled` : `"${tag}" disabled`,
});
} else {
toast.error({
title: `Failed to toggle "${tag}"`,
text: result?.error?.message || "Unknown error",
});
}
}
</script>
<style scoped>
.modes-grid {
display: grid;
grid-template-columns: repeat(auto-fill, minmax(280px, 1fr));
gap: 16px;
}
.mode-meta {
display: flex;
flex-wrap: wrap;
gap: 8px;
align-items: center;
}
</style>