@@ -2,6 +2,7 @@ package main
22
33import (
44 "encoding/json"
5+ "flag"
56 "fmt"
67 "log"
78 "os"
@@ -526,12 +527,27 @@ func (m model) mainViewRender() string {
526527
527528 // Quick stats
528529 stats := m .tracker .getTodaysStats ()
529- quickStats := fmt .Sprintf ("\n %s\n %s\n %s\n %s\n " ,
530+ quickStats := fmt .Sprintf ("\n %s\n %s\n %s\n %s" ,
530531 subtitleStyle .Render ("Today's Summary:" ),
531532 workStyle .Render (fmt .Sprintf (" Work: %s" , formatDuration (stats .WorkTime ))),
532533 breakStyle .Render (fmt .Sprintf (" Break: %s" , formatDuration (stats .BreakTime ))),
533534 subtitleStyle .Render (fmt .Sprintf (" Total: %s" , formatDuration (stats .TotalTime ))))
534535
536+ // Project breakdown for main view
537+ projects := m .tracker .getTodaysProjects ()
538+ // Debug: Always show the projects section to see what's in it
539+ quickStats += "\n \n " + subtitleStyle .Render ("Projects:" )
540+ if len (projects ) == 0 {
541+ quickStats += "\n " + infoStyle .Render (" No projects found" )
542+ } else {
543+ for project , duration := range projects {
544+ if project == "" {
545+ project = "General"
546+ }
547+ quickStats += "\n " + workStyle .Render (fmt .Sprintf (" %s: %s" , project , formatDuration (duration )))
548+ }
549+ }
550+
535551 // Message
536552 var message string
537553 if m .message != "" {
@@ -862,6 +878,19 @@ func (tt *TimeTracker) getTodaysStats() struct {
862878 }
863879}
864880
881+ func (tt * TimeTracker ) getTodaysProjects () map [string ]time.Duration {
882+ activities := tt .getTodaysActivities ()
883+ projects := make (map [string ]time.Duration )
884+
885+ for _ , activity := range activities {
886+ if activity .Type == Work {
887+ projects [activity .Project ] += activity .Duration
888+ }
889+ }
890+
891+ return projects
892+ }
893+
865894func (tt * TimeTracker ) generateTodaysSummary () string {
866895 stats := tt .getTodaysStats ()
867896 activities := tt .getTodaysActivities ()
@@ -938,7 +967,160 @@ func formatDuration(d time.Duration) string {
938967 return fmt .Sprintf ("%dh%02d" , hours , minutes )
939968}
940969
970+ func printCLIHelp () {
971+ fmt .Println ("tt - Time Tracker" )
972+ fmt .Println ()
973+ fmt .Println ("USAGE:" )
974+ fmt .Println (" tt Start TUI interface" )
975+ fmt .Println (" tt [command] Run command and exit" )
976+ fmt .Println ()
977+ fmt .Println ("COMMANDS:" )
978+ fmt .Println (" -s Start your day" )
979+ fmt .Println (" -a \" task name\" Add completed task" )
980+ fmt .Println (" -c \" comment\" Add comment (use with -a)" )
981+ fmt .Println (" -r Show today's report" )
982+ fmt .Println (" -x Extend last task to now" )
983+ fmt .Println (" -h Show this help" )
984+ fmt .Println ()
985+ fmt .Println ("EXAMPLES:" )
986+ fmt .Println (" tt -s # Start your day" )
987+ fmt .Println (" tt -a \" Meeting: Standup\" " )
988+ fmt .Println (" tt -a \" Lunch **\" # Break task" )
989+ fmt .Println (" tt -a \" Dev work\" -c \" Fixed login bug\" " )
990+ fmt .Println (" tt -r # View today's report" )
991+ fmt .Println (" tt -x # Extend last task" )
992+ fmt .Println ()
993+ fmt .Println ("TASK TYPES:" )
994+ fmt .Println (" Regular task: \" Meeting: Standup\" " )
995+ fmt .Println (" Break task: \" Lunch **\" " )
996+ fmt .Println (" Ignored task: \" Commuting ***\" " )
997+ }
998+
999+ func printTodaysReport (tracker * TimeTracker ) {
1000+ activities := tracker .getTodaysActivities ()
1001+ stats := tracker .getTodaysStats ()
1002+
1003+ fmt .Println ("📊 Today's Report" )
1004+ fmt .Println ("================" )
1005+ fmt .Println ()
1006+
1007+ // Summary
1008+ fmt .Printf ("Work: %s\n " , formatDuration (stats .WorkTime ))
1009+ fmt .Printf ("Break: %s\n " , formatDuration (stats .BreakTime ))
1010+ fmt .Printf ("Total: %s\n " , formatDuration (stats .TotalTime ))
1011+ fmt .Println ()
1012+
1013+ // Projects
1014+ projects := tracker .getTodaysProjects ()
1015+ if len (projects ) > 0 {
1016+ fmt .Println ("Projects:" )
1017+ for project , duration := range projects {
1018+ if project == "" {
1019+ project = "General"
1020+ }
1021+ fmt .Printf (" %s: %s\n " , project , formatDuration (duration ))
1022+ }
1023+ fmt .Println ()
1024+ }
1025+
1026+ // Activities
1027+ if len (activities ) > 0 {
1028+ fmt .Println ("Activities:" )
1029+ for _ , activity := range activities {
1030+ timeStr := activity .Start .Format ("15:04" ) + "-" + activity .End .Format ("15:04" )
1031+ typeStr := ""
1032+ switch activity .Type {
1033+ case Break :
1034+ typeStr = " [BREAK]"
1035+ case Ignored :
1036+ typeStr = " [IGNORED]"
1037+ }
1038+
1039+ fmt .Printf (" %s %s %s%s\n " ,
1040+ timeStr ,
1041+ formatDuration (activity .Duration ),
1042+ activity .Name ,
1043+ typeStr )
1044+ }
1045+ } else {
1046+ fmt .Println ("No activities logged today." )
1047+ }
1048+ }
1049+
9411050func main () {
1051+ // Parse command line flags
1052+ var (
1053+ addTask = flag .String ("a" , "" , "Add a completed task" )
1054+ startDay = flag .Bool ("s" , false , "Start your day" )
1055+ showReport = flag .Bool ("r" , false , "Show today's report" )
1056+ extend = flag .Bool ("x" , false , "Extend last task to current time" )
1057+ showHelp = flag .Bool ("h" , false , "Show help" )
1058+ comment = flag .String ("c" , "" , "Add comment to task (use with -a)" )
1059+ )
1060+ flag .Parse ()
1061+
1062+ // Handle CLI commands
1063+ if * showHelp {
1064+ printCLIHelp ()
1065+ return
1066+ }
1067+
1068+ // Initialize tracker for CLI operations
1069+ tracker := & TimeTracker {}
1070+ tracker .loadConfig ()
1071+ tracker .loadEntries ()
1072+
1073+ if * startDay {
1074+ err := tracker .addStart ()
1075+ if err != nil {
1076+ fmt .Printf ("Error starting day: %v\n " , err )
1077+ os .Exit (1 )
1078+ }
1079+ fmt .Println ("✅ Day started!" )
1080+ return
1081+ }
1082+
1083+ if * addTask != "" {
1084+ entry := Entry {
1085+ Timestamp : time .Now (),
1086+ Name : * addTask ,
1087+ Comment : * comment ,
1088+ }
1089+
1090+ err := tracker .addEntry (entry )
1091+ if err != nil {
1092+ fmt .Printf ("Error adding task: %v\n " , err )
1093+ os .Exit (1 )
1094+ }
1095+
1096+ // Calculate and show duration
1097+ var durationMsg string
1098+ if len (tracker .entries ) > 1 {
1099+ lastEntry := tracker .entries [len (tracker .entries )- 2 ]
1100+ duration := entry .Timestamp .Sub (lastEntry .Timestamp )
1101+ durationMsg = fmt .Sprintf (" (%s)" , formatDuration (duration ))
1102+ }
1103+
1104+ fmt .Printf ("✅ Task completed: %s%s\n " , * addTask , durationMsg )
1105+ return
1106+ }
1107+
1108+ if * extend {
1109+ err := tracker .extend ()
1110+ if err != nil {
1111+ fmt .Printf ("Error extending task: %v\n " , err )
1112+ os .Exit (1 )
1113+ }
1114+ fmt .Println ("✅ Task extended to current time!" )
1115+ return
1116+ }
1117+
1118+ if * showReport {
1119+ printTodaysReport (tracker )
1120+ return
1121+ }
1122+
1123+ // If no CLI flags, start TUI
9421124 p := tea .NewProgram (initialModel (), tea .WithAltScreen ())
9431125 if _ , err := p .Run (); err != nil {
9441126 log .Fatal (err )
0 commit comments