11using System ;
22using System . Collections . Generic ;
3+ using System . Globalization ;
34using System . Windows ;
45using System . Windows . Input ; // Required for MouseButtonEventArgs, MouseButtonState
6+ using System . Windows . Controls ;
57using System . Threading . Tasks ; // For async operations
68
79namespace TimeTask
810{
911 // Removed duplicate namespace declaration
1012 public partial class AddTaskWindow : Window
1113 {
14+ public sealed class DraftSmartSuggestion
15+ {
16+ public string NormalizedDescription { get ; set ; }
17+ public double TaskLikelihoodScore { get ; set ; }
18+ public bool IsPotentialTask { get ; set ; }
19+ public string Importance { get ; set ; }
20+ public string Urgency { get ; set ; }
21+ public int SuggestedQuadrantIndex { get ; set ; } = - 1 ;
22+ public DateTime ? SuggestedReminderTime { get ; set ; }
23+ }
24+
1225 private LlmService _llmService ;
1326 private DatabaseService _databaseService ;
1427 private bool _isClarificationRound = false ; // State for clarification
1528 private string _originalTaskDescription = string . Empty ; // To store original task if clarification is needed
1629 private bool _isLlmConfigErrorNotified = false ; // Flag to track if user has been notified of LLM config error
1730 private readonly IntentRecognizer _intentRecognizer = new IntentRecognizer ( ) ;
31+ private bool _reminderEditedByUser ;
32+ private bool _quadrantEditedByUser ;
33+ private bool _isUpdatingReminderControls ;
34+ private bool _isUpdatingQuadrantSelection ;
35+ private bool _autoReminderApplied ;
1836
1937 public string TaskDescription { get ; private set ; }
2038 public int SelectedListIndex { get ; private set ; } // 0-indexed
@@ -75,6 +93,8 @@ private void InitializeCombobox(int? defaultQuadrantIndex)
7593 ReminderDatePicker . SelectedDate = DateTime . Today ;
7694 ReminderHourComboBox . SelectedIndex = 0 ; // Default to "00"
7795 ReminderMinuteComboBox . SelectedIndex = 0 ; // Default to "00"
96+
97+ RefreshSmartAssistant ( ) ;
7898 }
7999
80100 /// <summary>
@@ -112,9 +132,12 @@ public void SetPreFilledTask(string description, string quadrant)
112132
113133 if ( quadrantMap . TryGetValue ( quadrant , out int index ) )
114134 {
135+ _quadrantEditedByUser = false ;
115136 ListSelectorComboBox . SelectedIndex = index ;
116137 }
117138 }
139+
140+ RefreshSmartAssistant ( ) ;
118141 }
119142
120143 // Removed older synchronous AddTaskButton_Click method. The async version below is used.
@@ -408,6 +431,40 @@ private static bool ContainsDummy(string value)
408431 value . IndexOf ( "dummy response" , StringComparison . OrdinalIgnoreCase ) >= 0 ;
409432 }
410433
434+ public static DraftSmartSuggestion AnalyzeDraftInput ( string rawText , DateTime now )
435+ {
436+ var recognizer = new IntentRecognizer ( ) ;
437+ var parser = new VoiceReminderTimeParser ( ) ;
438+ string normalized = string . IsNullOrWhiteSpace ( rawText ) ? string . Empty : rawText . Trim ( ) ;
439+ string extracted = recognizer . ExtractTaskDescription ( normalized ) ;
440+ if ( ! string . IsNullOrWhiteSpace ( extracted ) )
441+ {
442+ normalized = extracted . Trim ( ) ;
443+ }
444+
445+ var suggestion = new DraftSmartSuggestion
446+ {
447+ NormalizedDescription = normalized ,
448+ TaskLikelihoodScore = recognizer . ScoreTaskLikelihood ( rawText ) ,
449+ IsPotentialTask = recognizer . IsPotentialTask ( rawText )
450+ } ;
451+
452+ if ( ! string . IsNullOrWhiteSpace ( normalized ) )
453+ {
454+ var ( importance , urgency ) = recognizer . EstimatePriority ( normalized ) ;
455+ suggestion . Importance = importance ;
456+ suggestion . Urgency = urgency ;
457+ suggestion . SuggestedQuadrantIndex = GetIndexFromPriority ( importance , urgency ) ;
458+ }
459+
460+ if ( parser . TryParse ( rawText , now , out DateTime reminderTime ) )
461+ {
462+ suggestion . SuggestedReminderTime = reminderTime ;
463+ }
464+
465+ return suggestion ;
466+ }
467+
411468 private string NormalizeTaskText ( string raw )
412469 {
413470 if ( string . IsNullOrWhiteSpace ( raw ) )
@@ -422,5 +479,152 @@ private string NormalizeTaskText(string raw)
422479
423480 return trimmed ;
424481 }
482+
483+ private void TaskDescriptionTextBox_TextChanged ( object sender , TextChangedEventArgs e )
484+ {
485+ RefreshSmartAssistant ( ) ;
486+ }
487+
488+ private void ReminderInput_Changed ( object sender , RoutedEventArgs e )
489+ {
490+ if ( ! _isUpdatingReminderControls )
491+ {
492+ _reminderEditedByUser = true ;
493+ }
494+
495+ UpdatePreviewSummary ( ) ;
496+ }
497+
498+ private void ListSelectorComboBox_SelectionChanged ( object sender , SelectionChangedEventArgs e )
499+ {
500+ if ( ! _isUpdatingQuadrantSelection )
501+ {
502+ _quadrantEditedByUser = true ;
503+ }
504+
505+ UpdatePreviewSummary ( ) ;
506+ }
507+
508+ private void RefreshSmartAssistant ( )
509+ {
510+ var suggestion = AnalyzeDraftInput ( TaskDescriptionTextBox . Text , DateTime . Now ) ;
511+ if ( string . IsNullOrWhiteSpace ( suggestion . NormalizedDescription ) )
512+ {
513+ SmartAssistantBorder . Visibility = Visibility . Collapsed ;
514+ if ( _autoReminderApplied && ! _reminderEditedByUser )
515+ {
516+ ApplyReminderTime ( null ) ;
517+ _autoReminderApplied = false ;
518+ }
519+
520+ return ;
521+ }
522+
523+ SmartAssistantBorder . Visibility = Visibility . Visible ;
524+ SmartTaskSignalText . Text = suggestion . IsPotentialTask
525+ ? I18n . Tf ( "AddTask_SmartTaskSignalStrongFormat" , Math . Round ( suggestion . TaskLikelihoodScore * 100 ) )
526+ : I18n . Tf ( "AddTask_SmartTaskSignalWeakFormat" , Math . Round ( suggestion . TaskLikelihoodScore * 100 ) ) ;
527+
528+ string quadrantLabel = suggestion . SuggestedQuadrantIndex >= 0 && suggestion . SuggestedQuadrantIndex < ListSelectorComboBox . Items . Count
529+ ? ListSelectorComboBox . Items [ suggestion . SuggestedQuadrantIndex ] as string
530+ : I18n . T ( "AddTask_SmartQuadrantUnavailable" ) ;
531+ SmartQuadrantSuggestionText . Text = I18n . Tf ( "AddTask_SmartQuadrantFormat" , quadrantLabel ) ;
532+
533+ if ( suggestion . SuggestedReminderTime . HasValue )
534+ {
535+ SmartReminderSuggestionText . Text = I18n . Tf (
536+ "AddTask_SmartReminderDetectedFormat" ,
537+ suggestion . SuggestedReminderTime . Value . ToString ( "yyyy-MM-dd HH:mm" , I18n . CurrentCulture ) ) ;
538+
539+ if ( ! _reminderEditedByUser )
540+ {
541+ ApplyReminderTime ( suggestion . SuggestedReminderTime ) ;
542+ _autoReminderApplied = true ;
543+ }
544+ }
545+ else
546+ {
547+ SmartReminderSuggestionText . Text = I18n . T ( "AddTask_SmartReminderNone" ) ;
548+ if ( _autoReminderApplied && ! _reminderEditedByUser )
549+ {
550+ ApplyReminderTime ( null ) ;
551+ _autoReminderApplied = false ;
552+ }
553+ }
554+
555+ if ( suggestion . SuggestedQuadrantIndex >= 0 && ! _quadrantEditedByUser )
556+ {
557+ _isUpdatingQuadrantSelection = true ;
558+ try
559+ {
560+ ListSelectorComboBox . SelectedIndex = suggestion . SuggestedQuadrantIndex ;
561+ }
562+ finally
563+ {
564+ _isUpdatingQuadrantSelection = false ;
565+ }
566+ }
567+
568+ UpdatePreviewSummary ( ) ;
569+ }
570+
571+ private void ApplyReminderTime ( DateTime ? reminderTime )
572+ {
573+ _isUpdatingReminderControls = true ;
574+ try
575+ {
576+ if ( reminderTime . HasValue )
577+ {
578+ EnableReminderCheckBox . IsChecked = true ;
579+ ReminderDatePicker . SelectedDate = reminderTime . Value . Date ;
580+ ReminderHourComboBox . SelectedItem = reminderTime . Value . Hour . ToString ( "D2" , CultureInfo . InvariantCulture ) ;
581+ ReminderMinuteComboBox . SelectedItem = reminderTime . Value . Minute . ToString ( "D2" , CultureInfo . InvariantCulture ) ;
582+ }
583+ else
584+ {
585+ EnableReminderCheckBox . IsChecked = false ;
586+ ReminderDatePicker . SelectedDate = DateTime . Today ;
587+ ReminderHourComboBox . SelectedIndex = 0 ;
588+ ReminderMinuteComboBox . SelectedIndex = 0 ;
589+ }
590+ }
591+ finally
592+ {
593+ _isUpdatingReminderControls = false ;
594+ }
595+ }
596+
597+ private void UpdatePreviewSummary ( )
598+ {
599+ string quadrantText = ListSelectorComboBox . SelectedItem as string ?? I18n . T ( "AddTask_SmartQuadrantUnavailable" ) ;
600+ DateTime ? selectedReminder = GetReminderTimeFromControls ( ) ;
601+
602+ SmartPreviewText . Text = selectedReminder . HasValue
603+ ? I18n . Tf ( "AddTask_SmartPreviewFormat" , quadrantText , selectedReminder . Value . ToString ( "yyyy-MM-dd HH:mm" , I18n . CurrentCulture ) )
604+ : I18n . Tf ( "AddTask_SmartPreviewNoReminderFormat" , quadrantText ) ;
605+ }
606+
607+ private DateTime ? GetReminderTimeFromControls ( )
608+ {
609+ if ( EnableReminderCheckBox . IsChecked != true || ! ReminderDatePicker . SelectedDate . HasValue )
610+ {
611+ return null ;
612+ }
613+
614+ int hour = 0 ;
615+ int minute = 0 ;
616+ if ( ReminderHourComboBox . SelectedItem != null )
617+ {
618+ int . TryParse ( ReminderHourComboBox . SelectedItem . ToString ( ) , out hour ) ;
619+ }
620+
621+ if ( ReminderMinuteComboBox . SelectedItem != null )
622+ {
623+ int . TryParse ( ReminderMinuteComboBox . SelectedItem . ToString ( ) , out minute ) ;
624+ }
625+
626+ DateTime date = ReminderDatePicker . SelectedDate . Value ;
627+ return new DateTime ( date . Year , date . Month , date . Day , hour , minute , 0 ) ;
628+ }
425629 }
426630} // Closing brace for namespace TimeTask
0 commit comments