| import gleam/list |
| import gleam/float |
| import gleam/int |
|
|
| import gleam/option.{type Option, None, Some} |
|
|
| // |
|
|
| pub type HeadPosture { |
| Upright |
| TiltedLeft |
| TiltedRight |
| SlumpedForward |
| LookingAway |
| RecedingFromCamera |
| } |
|
|
| pub type BiometricData { |
| BiometricData( |
| timestamp: Int, |
| eye_gaze_x: Float, |
| eye_gaze_y: Float, |
| head_posture: HeadPosture, |
| blink_rate: Float, |
| pupil_size: Float, |
| attention_score: Float, |
| is_user_present: Bool, |
| ) |
| } |
|
|
| pub type AlertLevel { |
| Green |
| Yellow |
| Orange |
| Red |
| Critical |
| } |
|
|
| pub type FocusMetrics { |
| FocusMetrics( |
| current_focus_score: Float, |
| average_focus: Float, |
| focus_trend: String, |
| recommendations: List(String), |
| alert_level: AlertLevel, |
| session_fatigue: Float, |
| ) |
| } |
|
|
| pub type BiometricSession { |
| BiometricSession( |
| session_id: String, |
| data_points: List(BiometricData), |
| start_time: Int, |
| end_time: Int, |
| total_duration: Int, |
| peak_focus: Float, |
| average_blink_rate: Float, |
| ) |
| } |
|
|
| // |
|
|
| pub fn request_biometric_permission() -> String { |
| "IDENTITY SYNC: Camera access required for Neural Focus Tracking. |
| Encryption: AES-256. Purpose: Real-time Ocular Fatigue Analysis." |
| } |
|
|
| // |
|
|
| pub fn calculate_focus_score(data: BiometricData) -> Float { |
| let eye_score = { |
| case data.eye_gaze_x, data.eye_gaze_y { |
| x, y if x >. 200.0 && x <. 800.0 && y >. 200.0 && y <. 800.0 -> 100.0 |
| _, _ -> 40.0 |
| } |
| } |
|
|
| let posture_score = { |
| case data.head_posture { |
| Upright -> 100.0 |
| TiltedLeft | TiltedRight -> 75.0 |
| SlumpedForward -> 30.0 |
| LookingAway -> 10.0 |
| RecedingFromCamera -> 5.0 |
| } |
| } |
|
|
| let blink_score = { |
| case data.blink_rate { |
| b if b >. 12.0 && b <. 20.0 -> 100.0 |
| b if b >=. 20.0 && b <. 30.0 -> 70.0 |
| _ -> 40.0 |
| } |
| } |
|
|
| // FIXED: Using braces for math grouping per Gleam syntax |
| {eye_score +. posture_score +. blink_score} /. 3.0 |
| } |
|
|
| pub fn monitor_focus_stream( |
| current: BiometricData, |
| previous: Option(BiometricData), |
| ) -> FocusMetrics { |
| let current_score = calculate_focus_score(current) |
|
|
| // FIXED: Using braces {} for math expression grouping |
| let average_score = { |
| case previous { |
| Some(p) -> {current_score +. calculate_focus_score(p)} /. 2.0 |
| None -> current_score |
| } |
| } |
|
|
| let trend = { |
| case previous { |
| Some(p) -> { |
| let prev_score = calculate_focus_score(p) |
| case current_score >. prev_score { |
| True -> "🚀 ASCENDING" |
| False -> "📉 DECAYING" |
| } |
| } |
| None -> "→ SYNCHRONIZING" |
| } |
| } |
|
|
| let alert = { |
| case current_score { |
| s if s >. 85.0 -> Green |
| s if s >. 70.0 -> Yellow |
| s if s >. 50.0 -> Orange |
| s if s >. 30.0 -> Red |
| _ -> Critical |
| } |
| } |
|
|
| let recommendations = generate_dynamic_recommendations(alert, current.blink_rate) |
|
|
| FocusMetrics( |
| current_focus_score: current_score, |
| average_focus: average_score, |
| focus_trend: trend, |
| recommendations: recommendations, |
| alert_level: alert, |
| session_fatigue: calculate_fatigue_index(current), |
| ) |
| } |
|
|
| // |
|
|
| fn generate_dynamic_recommendations(alert: AlertLevel, blink: Float) -> List(String) { |
| let base = case alert { |
| Green -> ["Neural link stable. Maintain current flow state."] |
| Yellow -> ["Minor posture drift detected. Re-align spine."] |
| Orange -> ["Synaptic fatigue detected. Perform 20-20-20 rule."] |
| Red -> ["CRITICAL: Focus collapse imminent. Stand up."] |
| Critical -> ["PROTOCOL INITIATED: System lockout recommended for rest."] |
| } |
|
|
| case blink >. 35.0 { |
| True -> list.append(base, ["Ocular dryness detected. Increase blink frequency."]) |
| False -> base |
| } |
| } |
|
|
| // |
|
|
| fn calculate_fatigue_index(data: BiometricData) -> Float { |
| let p_size = data.pupil_size |
| let blink = data.blink_rate |
| // Heuristic formula for neural fatigue |
| {p_size *. 1.5 +. blink *. 0.8} /. 2.0 |
| } |
|
|
| pub fn detect_posture_threats(data: BiometricData) -> Option(String) { |
| case data.head_posture { |
| SlumpedForward -> Some("BIO-ALERT: Slumping detected. Spinal health at risk.") |
| LookingAway -> Some("BIO-ALERT: Sustained gaze deviation.") |
| _ -> None |
| } |
| } |
|
|
| // |
|
|
| pub fn get_neural_audio_instruction(metrics: FocusMetrics) -> String { |
| case metrics.alert_level { |
| Green -> "SET_BPM_140_NEURAL_FLOW" |
| Yellow -> "SET_BPM_120_LOFI_STEADY" |
| Orange -> "SET_BPM_90_AMBIENT_RECOVERY" |
| Red -> "SET_BPM_60_THETA_WAVES" |
| Critical -> "AUDIO_MUTE_MANDATORY_BREAK" |
| } |
| } |
|
|
| // |
|
|
| pub fn generate_biometric_report(session: BiometricSession) -> String { |
| let n = list.length(session.data_points) |
| let total_focus = list.fold(session.data_points, 0.0, fn(acc, dp) { |
| acc +. calculate_focus_score(dp) |
| }) |
| |
| let avg = case n { |
| 0 -> 0.0 |
| _ -> total_focus /. int.to_float(n) |
| } |
|
|
| "<div class='neural-report-box'> |
| <h2 class='glitch-text'>Neural Performance Analytics</h2> |
| <div class='stat-row'> |
| <div class='stat'><h4>Mastery</h4><p>" <> float.to_string(avg) <> "%</p></div> |
| <div class='stat'><h4>Stability</h4><p>" <> float.to_string(session.peak_focus) <> "%</p></div> |
| <div class='stat'><h4>Duration</h4><p>" <> int.to_string(session.total_duration) <> "m</p></div> |
| </div> |
| <div class='report-footer'>System: FlashSync Zenith v4.0</div> |
| </div>" |
| } |
|
|
| pub fn export_to_json(session: BiometricSession) -> String { |
| // Manual JSON construction for high performance |
| "{ \"session_id\": \"" <> session.session_id <> "\", \"avg_focus\": " <> |
| float.to_string(session.peak_focus) <> " }" |
| } |
|
|
| // |
|
|
| pub fn render_focus_orb(score: Float) -> String { |
| let size = {score *. 2.0} |
| let color = case score { |
| s if s >. 80.0 -> "#00f2ff" |
| s if s >. 50.0 -> "#bc13fe" |
| _ -> "#ff006e" |
| } |
| |
| "<div class='focus-orb' style='width:" <> float.to_string(size) <> "px; background:" <> color <> "; box-shadow: 0 0 50px " <> color <> ";'></div>" |
| } |
|
|
| // |
|
|
| pub fn create_new_session(user_id: String) -> BiometricSession { |
| BiometricSession( |
| session_id: "SYNC-" <> user_id <> "-" <> int.to_string(101), |
| data_points: [], |
| start_time: 0, |
| end_time: 0, |
| total_duration: 0, |
| peak_focus: 0.0, |
| average_blink_rate: 0.0, |
| ) |
| } |
|
|
| pub fn check_microbreak_eligibility(active_minutes: Int) -> Bool { |
| active_minutes % 25 == 0 && active_minutes > 0 |
| } |
|
|
| pub fn finalize_session_data(session: BiometricSession) -> String { |
| "ARCHIVING_NEURAL_LOG_" <> session.session_id <> "... SUCCESS." |
| } |
|
|
|
|
|
|