diff --git a/CMakeLists.txt b/CMakeLists.txt index 88ae94e..1ecb221 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1,5 +1,5 @@ cmake_minimum_required(VERSION 3.20) -project(PomodoroTimer VERSION 2.0.0 LANGUAGES CXX) +project(PomodoroTimer VERSION 0.1.1 LANGUAGES CXX) # Set C++ standard set(CMAKE_CXX_STANDARD 17) diff --git a/LICENSE b/LICENSE index bce361a..26aa4fc 100644 --- a/LICENSE +++ b/LICENSE @@ -1,6 +1,6 @@ MIT License -Copyright (c) [year] [fullname] +Copyright (c) 2025 Dmytro Hovenko Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/StatisticsDialog.cpp b/StatisticsDialog.cpp index 9ed37f5..5ae020f 100644 --- a/StatisticsDialog.cpp +++ b/StatisticsDialog.cpp @@ -15,6 +15,8 @@ #include #include +#include "TimerState.h" + // StatisticsChart implementation StatisticsChart::StatisticsChart(QWidget *parent) : QWidget(parent), m_maxValue(0) @@ -49,6 +51,7 @@ void StatisticsChart::paintEvent(QPaintEvent *event) return; } + constexpr int LABEL_SKIP_INTERVAL = 3; const int margin = 40; const int chartWidth = width() - 2 * margin; const int chartHeight = height() - 2 * margin; @@ -77,7 +80,7 @@ void StatisticsChart::paintEvent(QPaintEvent *event) painter.drawRect(barRect); // Draw date labels (every 3rd day to avoid crowding) - if ((x - margin) % (barWidth * 3) == 0) { + if ((x - margin) % (barWidth * LABEL_SKIP_INTERVAL) == 0) { painter.setPen(Qt::black); QString dateStr = it.key().toString("dd/MM"); painter.drawText(x, height() - 10, dateStr); @@ -320,10 +323,16 @@ void StatisticsDialog::loadDailyStatistics() QDate today = QDate::currentDate(); for (int i = 0; i < 30; ++i) { QDate date = today.addDays(-i); - QString key = QString("dailyStats/workTime_%1").arg(date.toString("yyyy-MM-dd")); - int workTime = settings.value(key, 0).toInt(); - if (workTime > 0) { - m_dailyWorkTime[date] = workTime / 60; // Convert to minutes + QSettings settings; + QVariantMap dailyStats = settings.value("dailyStats").toMap(); + + for (auto it = dailyStats.begin(); it != dailyStats.end(); ++it) { + QDate date = QDate::fromString(it.key(), "yyyy-MM-dd"); + if (date.isValid()) { + QVariantMap dayData = it.value().toMap(); + m_dailyWorkTime[date] = dayData["workTime"].toInt(); + m_dailySessions[date] = dayData["sessions"].toInt(); + } } QString sessionKey = QString("dailyStats/sessions_%1").arg(date.toString("yyyy-MM-dd")); @@ -338,45 +347,37 @@ void StatisticsDialog::updateOverview() { m_totalSessionsLabel->setText(QString::number(m_totalSessions)); + // Правильное форматирование времени + m_totalTimeLabel->setText(TimerStateHelper::formatDuration(m_totalWorkTime + m_totalBreakTime)); + m_workTimeLabel->setText(TimerStateHelper::formatDuration(m_totalWorkTime)); + m_breakTimeLabel->setText(TimerStateHelper::formatDuration(m_totalBreakTime)); // исправлено + + int avgSession = m_totalSessions > 0 ? (m_totalWorkTime / m_totalSessions) : 0; + m_avgSessionLabel->setText(TimerStateHelper::formatDuration(avgSession)); + int totalMinutes = (m_totalWorkTime + m_totalBreakTime) / 60; - m_totalTimeLabel->setText(QString("%1h %2m") - .arg(totalMinutes / 60) - .arg(totalMinutes % 60)); - int workMinutes = m_totalWorkTime / 60; - m_workTimeLabel->setText(QString("%1h %2m") - .arg(workMinutes / 60) - .arg(workMinutes % 60)); - - int breakMinutes = m_totalBreakTime / 60; - m_breakTimeLabel->setText(QString("%1h %2m") - .arg(breakMinutes / 60) - .arg(breakMinutes % 60)); - - int avgSession = m_totalSessions > 0 ? workMinutes / m_totalSessions : 0; - m_avgSessionLabel->setText(QString("%1 minutes").arg(avgSession)); - int efficiency = totalMinutes > 0 ? (workMinutes * 100 / totalMinutes) : 0; m_efficiencyLabel->setText(QString("%1%").arg(efficiency)); // Period statistics QDate today = QDate::currentDate(); int todayMinutes = m_dailyWorkTime.value(today, 0); - m_todayLabel->setText(QString("%1 minutes").arg(todayMinutes)); + m_todayLabel->setText(TimerStateHelper::formatDuration(todayMinutes * 60)); // Calculate week total int weekTotal = 0; for (int i = 0; i < 7; ++i) { weekTotal += m_dailyWorkTime.value(today.addDays(-i), 0); } - m_weekLabel->setText(QString("%1 minutes").arg(weekTotal)); + m_weekLabel->setText(TimerStateHelper::formatDuration(weekTotal * 60)); // Calculate month total int monthTotal = 0; for (int i = 0; i < 30; ++i) { monthTotal += m_dailyWorkTime.value(today.addDays(-i), 0); } - m_monthLabel->setText(QString("%1 minutes").arg(monthTotal)); + m_monthLabel->setText(TimerStateHelper::formatDuration(monthTotal * 60)); } void StatisticsDialog::updateChart() diff --git a/TimerState.h b/TimerState.h index a49ed54..00c7b51 100644 --- a/TimerState.h +++ b/TimerState.h @@ -45,10 +45,6 @@ public: return text; } - static QString getStateTextString(TimerState state) { - return getStateText(state); - } - static int getDurationForState(TimerState state, int workDuration, int shortBreak, int longBreak) noexcept { switch (state) { case TimerState::Work: @@ -60,6 +56,17 @@ public: } return 0; } + + static QString formatDuration(int seconds) noexcept + { + const int hours = seconds / 3600; + const int minutes = (seconds % 3600) / 60; + if (hours > 0) + { + return QString("%1h %2m").arg(hours).arg(minutes); + } + return QString("%1m").arg(minutes); + } }; #endif // TIMERSTATE_H diff --git a/main.cpp b/main.cpp index ae1aa4a..531c177 100644 --- a/main.cpp +++ b/main.cpp @@ -11,7 +11,7 @@ namespace { // Application constants - use QStringLiteral for compile-time optimization const QString APP_NAME = QStringLiteral("Pomodoro Timer"); - const QString APP_VERSION = QStringLiteral("0.1.0"); + const QString APP_VERSION = QStringLiteral("0.1.1"); const QString ORGANIZATION = QStringLiteral("PomodoroApp"); // Icon generation constants diff --git a/pomodoro-timer.desktop.in b/pomodoro-timer.desktop.in index df15857..129a86f 100644 --- a/pomodoro-timer.desktop.in +++ b/pomodoro-timer.desktop.in @@ -1,5 +1,5 @@ [Desktop Entry] -Version=1.0 +Version=0.1.1 Name=Pomodoro Timer GenericName=Time Management Comment=A simple Pomodoro timer to help you focus.