vOOice/VoiceInk/Views/MetricsView.swift
2025-07-02 09:15:29 +05:45

77 lines
2.8 KiB
Swift

import SwiftUI
import SwiftData
import Charts
import KeyboardShortcuts
struct MetricsView: View {
@Environment(\.modelContext) private var modelContext
@Query(sort: \Transcription.timestamp) private var transcriptions: [Transcription]
@EnvironmentObject private var whisperState: WhisperState
@EnvironmentObject private var hotkeyManager: HotkeyManager
@StateObject private var licenseViewModel = LicenseViewModel()
@State private var hasLoadedData = false
let skipSetupCheck: Bool
init(skipSetupCheck: Bool = false) {
self.skipSetupCheck = skipSetupCheck
}
var body: some View {
VStack {
// Trial Message
if case .trial(let daysRemaining) = licenseViewModel.licenseState {
TrialMessageView(
message: "You have \(daysRemaining) days left in your trial",
type: daysRemaining <= 2 ? .warning : .info,
onAddLicenseKey: {
// Post notification to navigate to VoiceInk Pro tab
NotificationCenter.default.post(
name: .navigateToDestination,
object: nil,
userInfo: ["destination": "VoiceInk Pro"]
)
}
)
.padding()
} else if case .trialExpired = licenseViewModel.licenseState {
TrialMessageView(
message: "Your trial has expired. Upgrade to continue using VoiceInk",
type: .expired,
onAddLicenseKey: {
// Also allow navigation from expired state
NotificationCenter.default.post(
name: .navigateToDestination,
object: nil,
userInfo: ["destination": "VoiceInk Pro"]
)
}
)
.padding()
}
Group {
if skipSetupCheck {
MetricsContent(transcriptions: Array(transcriptions))
} else if isSetupComplete {
MetricsContent(transcriptions: Array(transcriptions))
} else {
MetricsSetupView()
}
}
}
.background(Color(.controlBackgroundColor))
.task {
// Ensure the model context is ready
hasLoadedData = true
}
}
private var isSetupComplete: Bool {
hasLoadedData &&
whisperState.currentTranscriptionModel != nil &&
hotkeyManager.selectedHotkey1 != .none &&
AXIsProcessTrusted() &&
CGPreflightScreenCaptureAccess()
}
}