M module-apps/apps-common/ApplicationCommon.cpp => module-apps/apps-common/ApplicationCommon.cpp +1 -1
@@ 2,7 2,7 @@
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
#include "ApplicationCommon.hpp"
-#include "GuiTimer.hpp" // for GuiTimer
+#include "GuiTimer.hpp" // for GuiTimer
#include "Timers/TimerFactory.hpp" // for Timer
#include "status-bar/Time.hpp"
#include "messages/AppSwitchWindowPopupMessage.hpp"
M => +14 -0
@@ 7,6 7,7 @@
#include "service-db/Settings.hpp"
#include "service-db/agents/settings/SystemSettings.hpp"
#include "popups/data/PopupData.hpp"
#include "popups/data/BedtimeReminderPopupRequestParams.hpp"
namespace app
{
@@ 132,6 133,19 @@ namespace app
std::make_unique<gui::AlarmPopupRequestParams>(popupParams));
return true;
});
popupBlueprint.registerBlueprint(
ID::BedtimeNotification, [&](gui::popup::ID id, std::unique_ptr<gui::PopupRequestParams> ¶ms) {
auto popupParams = dynamic_cast<gui::BedtimeReminderPopupRequestParams *>(params.get());
if (popupParams == nullptr) {
return false;
}
switchWindowPopup(gui::popup::resolveWindowName(id),
params->getDisposition(),
std::make_unique<gui::BedtimeReminderPopupRequestParams>(popupParams->eventRecord));
return true;
});
}
std::optional<gui::popup::Blueprint> ApplicationCommon::popupBlueprintFallback(gui::popup::ID id)
M module-apps/apps-common/CMakeLists.txt => module-apps/apps-common/CMakeLists.txt +1 -0
@@ 75,6 75,7 @@ target_sources(apps-common
widgets/TimeSetFmtSpinner.hpp
actions/AlarmRingingData.hpp
actions/AlarmTriggeredAction.hpp
+ popups/data/BedtimeReminderPopupRequestParams.hpp
models/SongContext.hpp
models/SongsRepository.hpp
R => +6 -2
@@ 1,16 1,20 @@
// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
// Copyright (c) 2017-2022, Mudita Sp. z.o.o. All rights reserved.
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
#pragma once
#include <apps-common/popups/data/PopupRequestParams.hpp>
#include <Tables/Record.hpp>
namespace gui
{
class BedtimeReminderPopupRequestParams : public PopupRequestParams
{
public:
BedtimeReminderPopupRequestParams() : PopupRequestParams{gui::popup::ID::BedtimeNotification}
BedtimeReminderPopupRequestParams(Record record)
: PopupRequestParams{gui::popup::ID::BedtimeNotification}, eventRecord{record}
{}
Record eventRecord;
};
} // namespace gui
M module-services/service-time/AlarmOperations.cpp => module-services/service-time/AlarmOperations.cpp +30 -14
@@ 1,4 1,4 @@
-// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// Copyright (c) 2017-2022, Mudita Sp. z.o.o. All rights reserved.
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
#include "AlarmOperations.hpp"
@@ 128,18 128,13 @@ namespace alarms
void AlarmOperationsCommon::turnOffRingingAlarm(const std::uint32_t id, OnTurnOffRingingAlarm callback)
{
- auto found = findSingleEventById(ongoingSingleEvents, id);
- if (found == ongoingSingleEvents.end()) {
- LOG_ERROR("Trying to turn off nonexisting event");
+ bool ongoingEventsResult = turnOffAlarmIfFoundInOngoingEvents(id);
+ bool bedtimeEventsResult = turnOffAlarmIfFoundInBedtime(id);
+ if (not ongoingEventsResult and not bedtimeEventsResult) {
+ LOG_ERROR("Trying to turn off nonexisting event ID %d", static_cast<int>(id));
callback(false);
- return;
}
- switchAlarmExecution(*(*found), false);
- ongoingSingleEvents.erase(found);
- processOngoingEvents();
-
- handleActiveAlarmsCountChange();
callback(true);
}
@@ 338,6 333,26 @@ namespace alarms
}
}
+ bool AlarmOperationsCommon::turnOffAlarmIfFoundInOngoingEvents(std::uint32_t id)
+ {
+ auto found = findSingleEventById(ongoingSingleEvents, id);
+ if (found == ongoingSingleEvents.end()) {
+ return false;
+ }
+
+ switchAlarmExecution(*(*found), false);
+ ongoingSingleEvents.erase(found);
+ processOngoingEvents();
+ handleActiveAlarmsCountChange();
+
+ return true;
+ }
+
+ bool AlarmOperationsCommon::turnOffAlarmIfFoundInBedtime(const std::uint32_t id)
+ {
+ return false;
+ }
+
void AlarmOperationsCommon::onAlarmTurnedOff(const std::shared_ptr<AlarmEventRecord> &event,
alarms::AlarmType alarmType)
{}
@@ 433,15 448,16 @@ namespace alarms
callback(std::move(snoozedEvents));
}
- auto findSingleEventById(std::vector<std::unique_ptr<SingleEventRecord>> &events, const std::uint32_t id)
- -> std::vector<std::unique_ptr<SingleEventRecord>>::iterator
+ auto findSingleEventById(EventsContainer<SingleEventRecord> &events, const std::uint32_t id)
+ -> EventsContainer<SingleEventRecord>::iterator
{
return std::find_if(events.begin(), events.end(), [id](const std::unique_ptr<SingleEventRecord> &event) {
return id == event->parent->ID;
});
}
- auto findSnoozedEventById(std::vector<std::unique_ptr<SnoozedAlarmEventRecord>> &events, const std::uint32_t id)
- -> std::vector<std::unique_ptr<SnoozedAlarmEventRecord>>::iterator
+
+ auto findSnoozedEventById(EventsContainer<SnoozedAlarmEventRecord> &events, const std::uint32_t id)
+ -> EventsContainer<SnoozedAlarmEventRecord>::iterator
{
return std::find_if(events.begin(), events.end(), [id](const std::unique_ptr<SnoozedAlarmEventRecord> &event) {
return id == event->parent->ID;
M module-services/service-time/AlarmOperations.hpp => module-services/service-time/AlarmOperations.hpp +12 -8
@@ 15,6 15,8 @@
namespace alarms
{
+ template <typename T> using EventsContainer = std::vector<std::unique_ptr<T>>;
+
class IAlarmOperations
{
public:
@@ 114,14 116,17 @@ namespace alarms
AlarmHandlerFactory alarmHandlerFactory;
// Events we are waiting for (on one timepoint)
- std::vector<std::unique_ptr<SingleEventRecord>> nextSingleEvents;
- std::vector<std::unique_ptr<SingleEventRecord>> ongoingSingleEvents;
- std::vector<std::unique_ptr<SnoozedAlarmEventRecord>> snoozedSingleEvents;
+ EventsContainer<SingleEventRecord> nextSingleEvents;
+ EventsContainer<SingleEventRecord> ongoingSingleEvents;
+ EventsContainer<SnoozedAlarmEventRecord> snoozedSingleEvents;
alarms::AlarmType getAlarmEventType(const SingleEventRecord &event);
virtual void handleAlarmEvent(const std::shared_ptr<AlarmEventRecord> &event,
alarms::AlarmType alarmType,
bool newStateOn);
+ virtual bool turnOffAlarmIfFoundInBedtime(std::uint32_t id);
+ bool turnOffAlarmIfFoundInOngoingEvents(std::uint32_t id);
+ void switchAlarmExecution(const SingleEventRecord &singleAlarmEvent, bool newStateOn);
private:
GetCurrentTime getCurrentTimeCallback;
@@ 139,7 144,6 @@ namespace alarms
std::vector<AlarmEventRecord> records,
OnGetAlarmsProcessed handledCallback);
void checkAndUpdateCache(AlarmEventRecord record);
- void switchAlarmExecution(const SingleEventRecord &singleAlarmEvent, bool newStateOn);
void processEvents(TimePoint now);
void processOngoingEvents();
void processNextEventsQueue(const TimePoint now);
@@ 160,8 164,8 @@ namespace alarms
IAlarmOperations::GetCurrentTime getCurrentTimeCallback) const override;
};
- auto findSingleEventById(std::vector<std::unique_ptr<SingleEventRecord>> &events, const std::uint32_t id)
- -> std::vector<std::unique_ptr<SingleEventRecord>>::iterator;
- auto findSnoozedEventById(std::vector<std::unique_ptr<SnoozedAlarmEventRecord>> &events, const std::uint32_t id)
- -> std::vector<std::unique_ptr<SnoozedAlarmEventRecord>>::iterator;
+ auto findSingleEventById(EventsContainer<SingleEventRecord> &events, const std::uint32_t id)
+ -> EventsContainer<SingleEventRecord>::iterator;
+ auto findSnoozedEventById(EventsContainer<SnoozedAlarmEventRecord> &events, const std::uint32_t id)
+ -> EventsContainer<SnoozedAlarmEventRecord>::iterator;
} // namespace alarms
M module-services/service-time/tests/CMakeLists.txt => module-services/service-time/tests/CMakeLists.txt +19 -10
@@ 19,16 19,25 @@ add_catch2_executable(
module-db
)
-add_gtest_executable(
- NAME
- service-time-alarm-operations
- SRCS
- tests-AlarmOperations.cpp
- LIBS
+add_library(service-time-alarm-operations-source OBJECT
+ tests-AlarmOperations.cpp)
+
+target_link_libraries(service-time-alarm-operations-source
+ PUBLIC
module-sys
service-time
- INCLUDE
- $<TARGET_PROPERTY:service-time,INCLUDE_DIRECTORIES>
- DEFS
- COMMON_ALARM_OPERATIONS_TEST
+ gtest_main
+ gmock
+ log-api)
+
+target_include_directories(service-time-alarm-operations-source
+ PUBLIC
+ $<TARGET_PROPERTY:service-time,INCLUDE_DIRECTORIES>)
+
+add_executable(googletest-service-time-alarm-operations)
+target_link_libraries(googletest-service-time-alarm-operations
+ PUBLIC
+ service-time-alarm-operations-source
)
+
+add_gtest_manually_prepared_target(NAME googletest-service-time-alarm-operations)
M module-services/service-time/tests/tests-AlarmOperations.cpp => module-services/service-time/tests/tests-AlarmOperations.cpp +10 -111
@@ 1,123 1,22 @@
-// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// Copyright (c) 2017-2022, Mudita Sp. z.o.o. All rights reserved.
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
-#include <AlarmOperations.hpp>
-#include <AlarmRepository.hpp>
-#include <service-time/AlarmHandler.hpp>
-
-#include <module-db/Interface/AlarmEventRecord.hpp>
-
-#include <gtest/gtest.h>
-#include <gmock/gmock.h>
-
-class MockAlarmHandler : public alarms::AlarmHandler
-{
- public:
- MOCK_METHOD(bool, handle, (const AlarmEventRecord &record), ());
- MOCK_METHOD(bool, handleOff, (const AlarmEventRecord &record), ());
-};
-
-class MockAlarmEventsRepository : public alarms::AbstractAlarmEventsRepository
-{
- public:
- std::vector<AlarmEventRecord> nextRecords;
-
- MOCK_METHOD(void,
- getAlarmEvent,
- (const std::uint32_t alarmId, const alarms::OnGetAlarmEventCallback &callback),
- ());
- MOCK_METHOD(void,
- getAlarmEvents,
- (std::uint32_t offset, std::uint32_t limit, const alarms::OnGetAlarmEventsCallback &callback),
- ());
- MOCK_METHOD(void, toggleAll, (const bool toggle, const alarms::OnToggleAll &callback), ());
-
- auto addAlarmEvent(const AlarmEventRecord &alarmEvent, const alarms::OnAddAlarmEventCallback &callback) -> void
- {
- addSingleEvent(alarmEvent);
- callback({true});
- }
-
- auto updateAlarmEvent(const AlarmEventRecord &alarmEvent, const alarms::OnAddAlarmEventCallback &callback) -> void
- {
- nextRecords.erase(std::remove_if(nextRecords.begin(),
- nextRecords.end(),
- [&alarmEvent](const AlarmEventRecord &ae) { return ae.ID == alarmEvent.ID; }),
- nextRecords.end());
- addSingleEvent(alarmEvent);
- callback({true});
- }
- auto removeAlarmEvent(const std::uint32_t alarmId, const alarms::OnRemoveAlarmEventCallback &callback) -> void
- {
- nextRecords.erase(std::remove_if(nextRecords.begin(),
- nextRecords.end(),
- [&alarmId](const AlarmEventRecord &ae) { return ae.ID == alarmId; }),
- nextRecords.end());
- callback({true});
- }
-
- void getAlarmEventsInRange(std::uint32_t offset,
- std::uint32_t limit,
- const alarms::OnGetAlarmEventsInRangeCallback &callback)
- {
- callback({nextRecords, nextRecords.size()});
- }
-
- void getAlarmEnabledEvents(const alarms::OnGetAlarmEventsCallback &callback)
- {
- std::vector<AlarmEventRecord> result;
- for (const auto &rec : nextRecords) {
- if (rec.enabled) {
- result.push_back(rec);
- }
- }
- callback({result});
- }
-
- void addSingleEvent(const AlarmEventRecord record)
- {
- nextRecords.push_back(record);
- }
-};
-
-/// Time point from string with current test machine time shift
-TimePoint TimePointFromStringWithShift(std::string timeString)
-{
- const auto timeToCalc = TimePointFromString("2000-01-01 12:00:00");
- const auto fromTimeT = std::chrono::system_clock::to_time_t(timeToCalc);
- const auto fromLocal = std::localtime(&fromTimeT);
- fromLocal->tm_hour = 12;
- fromLocal->tm_min = 0;
- auto time = TimePointFloorMinutes(std::chrono::system_clock::from_time_t(std::mktime(fromLocal)));
- auto currentTimeShift = timeToCalc - time;
-
- return TimePointFromString(timeString.c_str()) - currentTimeShift;
-}
-
-alarms::IAlarmOperations::GetCurrentTime timeInjector = []() {
- return TimePointFromStringWithShift("2022-11-11 05:00:00");
-};
-alarms::IAlarmOperations::OnUpdateAlarmProcessed universalBoolCallback = [](bool success) { EXPECT_EQ(success, true); };
-
-class AlarmOperationsFixture : public ::testing::Test
+#include "tests-AlarmOperations.hpp"
+namespace
{
- protected:
- std::unique_ptr<alarms::IAlarmOperations> getMockedAlarmOperations(
- std::unique_ptr<MockAlarmEventsRepository> &alarmRepo);
-};
+ alarms::IAlarmOperations::OnUpdateAlarmProcessed universalBoolCallback = [](bool success) {
+ EXPECT_EQ(success, true);
+ };
+ alarms::IAlarmOperations::GetCurrentTime timeInjector = []() {
+ return TimePointFromStringWithShift("2022-11-11 05:00:00");
+ };
+} // namespace
-#if defined COMMON_ALARM_OPERATIONS_TEST
std::unique_ptr<alarms::IAlarmOperations> AlarmOperationsFixture::getMockedAlarmOperations(
std::unique_ptr<MockAlarmEventsRepository> &alarmRepo)
{
return std::make_unique<alarms::AlarmOperationsCommon>(std::move(alarmRepo), timeInjector);
}
-#endif
-
-constexpr auto defRRule = "";
-constexpr auto defMusic = "";
-constexpr auto defEnabled = true;
-constexpr auto defSnooze = 15;
TEST_F(AlarmOperationsFixture, getEnabledEvents)
{
A module-services/service-time/tests/tests-AlarmOperations.hpp => module-services/service-time/tests/tests-AlarmOperations.hpp +110 -0
@@ 0,0 1,110 @@
+// Copyright (c) 2017-2022, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+#pragma once
+
+#include <gmock/gmock.h>
+#include <gtest/gtest.h>
+#include <service-time/AlarmHandler.hpp>
+#include <module-db/Interface/AlarmEventRecord.hpp>
+#include <AlarmOperations.hpp>
+#include <AlarmRepository.hpp>
+
+class MockAlarmHandler : public alarms::AlarmHandler
+{
+ public:
+ MOCK_METHOD(bool, handle, (const AlarmEventRecord &record), ());
+ MOCK_METHOD(bool, handleOff, (const AlarmEventRecord &record), ());
+};
+
+class MockAlarmEventsRepository : public alarms::AbstractAlarmEventsRepository
+{
+ public:
+ std::vector<AlarmEventRecord> nextRecords;
+
+ MOCK_METHOD(void,
+ getAlarmEvent,
+ (const std::uint32_t alarmId, const alarms::OnGetAlarmEventCallback &callback),
+ ());
+ MOCK_METHOD(void,
+ getAlarmEvents,
+ (std::uint32_t offset, std::uint32_t limit, const alarms::OnGetAlarmEventsCallback &callback),
+ ());
+ MOCK_METHOD(void, toggleAll, (const bool toggle, const alarms::OnToggleAll &callback), ());
+
+ auto addAlarmEvent(const AlarmEventRecord &alarmEvent, const alarms::OnAddAlarmEventCallback &callback) -> void
+ {
+ addSingleEvent(alarmEvent);
+ callback({true});
+ }
+
+ auto updateAlarmEvent(const AlarmEventRecord &alarmEvent, const alarms::OnAddAlarmEventCallback &callback) -> void
+ {
+ nextRecords.erase(std::remove_if(nextRecords.begin(),
+ nextRecords.end(),
+ [&alarmEvent](const AlarmEventRecord &ae) { return ae.ID == alarmEvent.ID; }),
+ nextRecords.end());
+ addSingleEvent(alarmEvent);
+ callback({true});
+ }
+ auto removeAlarmEvent(const std::uint32_t alarmId, const alarms::OnRemoveAlarmEventCallback &callback) -> void
+ {
+ nextRecords.erase(std::remove_if(nextRecords.begin(),
+ nextRecords.end(),
+ [&alarmId](const AlarmEventRecord &ae) { return ae.ID == alarmId; }),
+ nextRecords.end());
+ callback({true});
+ }
+
+ void getAlarmEventsInRange(std::uint32_t offset,
+ std::uint32_t limit,
+ const alarms::OnGetAlarmEventsInRangeCallback &callback)
+ {
+ callback({nextRecords, nextRecords.size()});
+ }
+
+ void getAlarmEnabledEvents(const alarms::OnGetAlarmEventsCallback &callback)
+ {
+ std::vector<AlarmEventRecord> result;
+ for (const auto &rec : nextRecords) {
+ if (rec.enabled) {
+ result.push_back(rec);
+ }
+ }
+ callback({result});
+ }
+
+ void addSingleEvent(const AlarmEventRecord record)
+ {
+ nextRecords.push_back(record);
+ }
+};
+
+namespace
+{
+ /// Time point from string with current test machine time shift
+ TimePoint TimePointFromStringWithShift(std::string timeString)
+ {
+ const auto timeToCalc = TimePointFromString("2000-01-01 12:00:00");
+ const auto fromTimeT = std::chrono::system_clock::to_time_t(timeToCalc);
+ const auto fromLocal = std::localtime(&fromTimeT);
+ fromLocal->tm_hour = 12;
+ fromLocal->tm_min = 0;
+ auto time = TimePointFloorMinutes(std::chrono::system_clock::from_time_t(std::mktime(fromLocal)));
+ auto currentTimeShift = timeToCalc - time;
+
+ return TimePointFromString(timeString.c_str()) - currentTimeShift;
+ }
+
+} // namespace
+
+class AlarmOperationsFixture : public ::testing::Test
+{
+ protected:
+ virtual std::unique_ptr<alarms::IAlarmOperations> getMockedAlarmOperations(
+ std::unique_ptr<MockAlarmEventsRepository> &alarmRepo);
+};
+
+constexpr auto defRRule = "";
+constexpr auto defMusic = "";
+constexpr auto defEnabled = true;
+constexpr auto defSnooze = 15;
M products/BellHybrid/alarms/BellAlarmHandler.cpp => products/BellHybrid/alarms/BellAlarmHandler.cpp +1 -1
@@ 17,7 17,7 @@ namespace alarms
auto result{true};
if (record.enabled) {
for (const auto &action : actions) {
- result &= action->execute();
+ result &= action->execute(record.ID);
}
}
return result;
M products/BellHybrid/alarms/CMakeLists.txt => products/BellHybrid/alarms/CMakeLists.txt +0 -1
@@ 20,7 20,6 @@ target_sources(alarms
include/AlarmSoundPaths.hpp
include/popups/AlarmActivatedPopupRequestParams.hpp
include/popups/AlarmDeactivatedPopupRequestParams.hpp
- include/popups/BedtimeReminderPopupRequestParams.hpp
)
target_include_directories(alarms
M products/BellHybrid/alarms/include/AbstractAlarmAction.hpp => products/BellHybrid/alarms/include/AbstractAlarmAction.hpp +7 -4
@@ 1,15 1,18 @@
-// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// Copyright (c) 2017-2022, Mudita Sp. z.o.o. All rights reserved.
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
#pragma once
+#include <Tables/Record.hpp>
+#include <cstdint>
+
namespace alarms
{
class AbstractAlarmAction
{
public:
- virtual ~AbstractAlarmAction() = default;
- virtual bool execute() = 0;
- virtual bool turnOff() = 0;
+ virtual ~AbstractAlarmAction() = default;
+ virtual bool execute(Record record) = 0;
+ virtual bool turnOff() = 0;
};
} // namespace alarms
M products/BellHybrid/alarms/src/actions/FrontlightAction.cpp => products/BellHybrid/alarms/src/actions/FrontlightAction.cpp +8 -8
@@ 18,7 18,7 @@ namespace alarms
{
public:
explicit ManualFrontlightAction(sys::Service &service);
- bool execute() override;
+ bool execute(Record record) override;
bool turnOff() override;
private:
@@ 31,7 31,7 @@ namespace alarms
{
public:
explicit LinearProgressFrontlightAction(sys::Service &service);
- bool execute() override;
+ bool execute(Record record) override;
bool turnOff() override;
private:
@@ 60,7 60,7 @@ namespace alarms
service::ServiceProxy{service.weak_from_this()}}
{}
- bool FrontlightAction::execute()
+ bool FrontlightAction::execute([[maybe_unused]] Record record)
{
std::string settingString;
@@ 84,7 84,7 @@ namespace alarms
case SettingsDependency::None:
break;
}
- return pimpl->execute();
+ return pimpl->execute(record);
}
bool FrontlightAction::turnOff()
@@ 109,7 109,7 @@ namespace alarms
ManualFrontlightAction::ManualFrontlightAction(sys::Service &service) : service{service}
{}
- bool ManualFrontlightAction::execute()
+ bool ManualFrontlightAction::execute([[maybe_unused]] Record record)
{
auto params = prepareParameters();
service.bus.sendUnicast(std::make_shared<sevm::ScreenLightControlMessage>(
@@ 136,7 136,7 @@ namespace alarms
settings.init(service::ServiceProxy{service.weak_from_this()});
}
- bool LinearProgressFrontlightAction::execute()
+ bool LinearProgressFrontlightAction::execute([[maybe_unused]] Record record)
{
const auto params = prepareParameters();
service.bus.sendUnicast(std::make_shared<sevm::ScreenLightSetAutoProgressiveModeParams>(params),
@@ 155,9 155,9 @@ namespace alarms
return screen_light_control::LinearProgressModeParameters{
.startBrightnessValue = 0.0f,
.functions = {screen_light_control::functions::LinearProgressFunction{.target = 10.0f,
- .duration = firstTargetDuration},
+ .duration = firstTargetDuration},
screen_light_control::functions::LinearProgressFunction{.target = 100.0f,
- .duration = secondTargetDuration}},
+ .duration = secondTargetDuration}},
.brightnessHysteresis = 0.0f};
}
M products/BellHybrid/alarms/src/actions/FrontlightAction.hpp => products/BellHybrid/alarms/src/actions/FrontlightAction.hpp +1 -1
@@ 29,7 29,7 @@ namespace alarms
FrontlightAction(sys::Service &service,
Mode mode,
SettingsDependency settingsDependency = SettingsDependency::None);
- bool execute() override;
+ bool execute(Record record) override;
bool turnOff() override;
private:
M products/BellHybrid/alarms/src/actions/NotifyGUIAction.cpp => products/BellHybrid/alarms/src/actions/NotifyGUIAction.cpp +2 -2
@@ 1,4 1,4 @@
-// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// Copyright (c) 2017-2022, Mudita Sp. z.o.o. All rights reserved.
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
#include "NotifyGUIAction.hpp"
@@ 10,7 10,7 @@ namespace alarms
{
NotifyGUIAction::NotifyGUIAction(sys::Service &service) : service{service}
{}
- bool NotifyGUIAction::execute()
+ bool NotifyGUIAction::execute([[maybe_unused]] Record record)
{
return service.bus.sendUnicast(std::make_shared<app::actions::AlarmTriggeredAction>(), service::name::appmgr);
}
M products/BellHybrid/alarms/src/actions/NotifyGUIAction.hpp => products/BellHybrid/alarms/src/actions/NotifyGUIAction.hpp +2 -2
@@ 1,4 1,4 @@
-// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// Copyright (c) 2017-2022, Mudita Sp. z.o.o. All rights reserved.
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
#pragma once
@@ 13,7 13,7 @@ namespace alarms
{
public:
explicit NotifyGUIAction(sys::Service &service);
- bool execute() override;
+ bool execute(Record record) override;
bool turnOff() override;
private:
M products/BellHybrid/alarms/src/actions/NotifyGUIBedtimeReminderAction.cpp => products/BellHybrid/alarms/src/actions/NotifyGUIBedtimeReminderAction.cpp +5 -3
@@ 1,4 1,4 @@
-// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// Copyright (c) 2017-2022, Mudita Sp. z.o.o. All rights reserved.
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
#include "NotifyGUIBedtimeReminderAction.hpp"
@@ 10,10 10,12 @@ namespace alarms
{
NotifyGUIBedtimeReminderAction::NotifyGUIBedtimeReminderAction(sys::Service &service) : service{service}
{}
- bool NotifyGUIBedtimeReminderAction::execute()
+
+ bool NotifyGUIBedtimeReminderAction::execute(Record record)
{
- return service.bus.sendUnicast(std::make_shared<BedtimeNotification>(), service::name::appmgr);
+ return service.bus.sendUnicast(std::make_shared<BedtimeNotification>(record), service::name::appmgr);
}
+
bool NotifyGUIBedtimeReminderAction::turnOff()
{
return true;
M products/BellHybrid/alarms/src/actions/NotifyGUIBedtimeReminderAction.hpp => products/BellHybrid/alarms/src/actions/NotifyGUIBedtimeReminderAction.hpp +2 -2
@@ 1,4 1,4 @@
-// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// Copyright (c) 2017-2022, Mudita Sp. z.o.o. All rights reserved.
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
#pragma once
@@ 13,7 13,7 @@ namespace alarms
{
public:
explicit NotifyGUIBedtimeReminderAction(sys::Service &service);
- bool execute() override;
+ bool execute(Record record) override;
bool turnOff() override;
private:
M products/BellHybrid/alarms/src/actions/PlayAudioActions.cpp => products/BellHybrid/alarms/src/actions/PlayAudioActions.cpp +2 -2
@@ 1,4 1,4 @@
-// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// Copyright (c) 2017-2022, Mudita Sp. z.o.o. All rights reserved.
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
#include "AlarmSoundPaths.hpp"
@@ 35,7 35,7 @@ namespace alarms
const auto msg = std::make_shared<service::AudioStopRequest>(stopPlaybackVec);
return service.bus.sendUnicast(msg, service::audioServiceName);
}
- bool PlayAudioAction::execute()
+ bool PlayAudioAction::execute([[maybe_unused]] Record record)
{
const auto tone = settings.getValue(toneSetting, settings::SettingsScope::Global);
std::optional<std::chrono::minutes> duration{};
M products/BellHybrid/alarms/src/actions/PlayAudioActions.hpp => products/BellHybrid/alarms/src/actions/PlayAudioActions.hpp +2 -2
@@ 1,4 1,4 @@
-// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// Copyright (c) 2017-2022, Mudita Sp. z.o.o. All rights reserved.
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
#pragma once
@@ 19,7 19,7 @@ namespace alarms
{
public:
bool turnOff() override;
- bool execute() override;
+ bool execute(Record record) override;
explicit PlayAudioAction(sys::Service &service,
const std::filesystem::path &tonesDirPath,
std::string_view toneSetting,
M products/BellHybrid/apps/application-bell-bedtime/presenter/BellBedtimeWindowPresenter.hpp => products/BellHybrid/apps/application-bell-bedtime/presenter/BellBedtimeWindowPresenter.hpp +2 -2
@@ 30,8 30,8 @@ namespace app::bell_bedtime
class View
{
public:
- virtual ~View() noexcept = default;
- virtual void exit() = 0;
+ virtual ~View() noexcept = default;
+ virtual void exit() = 0;
};
class AbstractBedtimePresenter : public BasePresenter<View>
M products/BellHybrid/apps/common/CMakeLists.txt => products/BellHybrid/apps/common/CMakeLists.txt +1 -0
@@ 128,6 128,7 @@ target_link_libraries(application-bell-common
module-gui
bell::db
Microsoft.GSL::GSL
+ bell::alarms
)
if (${ENABLE_TESTS})
M products/BellHybrid/apps/common/include/common/data/BatteryUtils.hpp => products/BellHybrid/apps/common/include/common/data/BatteryUtils.hpp +1 -0
@@ 7,6 7,7 @@
#include <algorithm>
#include <optional>
#include <string>
+#include <array>
#include <Units.hpp>
M products/BellHybrid/apps/common/include/common/models/BedtimeModel.hpp => products/BellHybrid/apps/common/include/common/models/BedtimeModel.hpp +1 -1
@@ 1,4 1,4 @@
-// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// Copyright (c) 2017-2022, Mudita Sp. z.o.o. All rights reserved.
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
#pragma once
M => +4 -1
@@ 1,4 1,4 @@
// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
// Copyright (c) 2017-2022, Mudita Sp. z.o.o. All rights reserved.
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
#pragma once
@@ 23,11 23,14 @@ namespace gui
app::ApplicationCommon *app;
Icon *icon = nullptr;
Record currentEventRecord;
bool onInput(const InputEvent &inputEvent) override;
void returnToPreviousWindow();
void buildInterface() override;
public:
bool handleSwitchData(gui::SwitchData *data) override;
explicit BedtimeNotificationWindow(app::ApplicationCommon *app);
void onBeforeShow(ShowMode mode, SwitchData *data) override;
};
M => +23 -1
@@ 1,15 1,17 @@
// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
// Copyright (c) 2017-2022, Mudita Sp. z.o.o. All rights reserved.
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
#include <audio/AudioMessage.hpp>
#include <apps-common/popups/Popups.hpp>
#include <apps-common/popups/data/PopupRequestParams.hpp>
#include <popups/data/BedtimeReminderPopupRequestParams.hpp>
#include <common/popups/BedtimeNotificationWindow.hpp>
#include <gui/input/InputEvent.hpp>
#include <gui/widgets/Icon.hpp>
#include <i18n/i18n.hpp>
#include <purefs/filesystem_paths.hpp>
#include <service-appmgr/Controller.hpp>
#include <service-time/AlarmServiceAPI.hpp>
namespace gui
{
@@ 42,6 44,25 @@ namespace gui
icon->image->setMargins(Margins(0, icon::image_top_margin, 0, icon::image_bottom_margin));
icon->text->setFont(style::window::font::verybiglight);
}
bool BedtimeNotificationWindow::handleSwitchData(SwitchData *data)
{
if (data == nullptr) {
LOG_ERROR("Received null pointer");
return false;
}
auto *eventData = dynamic_cast<gui::BedtimeReminderPopupRequestParams *>(data);
if (eventData == nullptr) {
LOG_ERROR("eventData is null pointer");
return false;
}
currentEventRecord = eventData->eventRecord;
return true;
}
void BedtimeNotificationWindow::onBeforeShow(ShowMode mode, [[maybe_unused]] SwitchData *data)
{
WindowWithTimer::onBeforeShow(mode, data);
@@ 55,6 76,7 @@ namespace gui
void BedtimeNotificationWindow::returnToPreviousWindow()
{
alarms::AlarmServiceAPI::requestTurnOffRingingAlarm(app, currentEventRecord.ID);
detachTimerIfExists();
app::manager::Controller::sendAction(
application,
M products/BellHybrid/services/appmgr/include/appmgr/messages/AlarmMessage.hpp => products/BellHybrid/services/appmgr/include/appmgr/messages/AlarmMessage.hpp +8 -4
@@ 1,4 1,4 @@
-// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// Copyright (c) 2017-2022, Mudita Sp. z.o.o. All rights reserved.
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
#pragma once
@@ 6,7 6,7 @@
#include <Service/Message.hpp>
#include <popups/AlarmActivatedPopupRequestParams.hpp>
#include <popups/AlarmDeactivatedPopupRequestParams.hpp>
-#include <popups/BedtimeReminderPopupRequestParams.hpp>
+#include <popups/data/BedtimeReminderPopupRequestParams.hpp>
#include <service-appmgr/Actions.hpp>
#include <service-appmgr/messages/ActionRequest.hpp>
@@ 39,12 39,16 @@ class AlarmDeactivated : public sys::DataMessage, public app::manager::actions::
class BedtimeNotification : public sys::DataMessage, public app::manager::actions::ConvertibleToAction
{
public:
- BedtimeNotification() : sys::DataMessage{MessageType::MessageTypeUninitialized}
+ BedtimeNotification(Record record) : sys::DataMessage{MessageType::MessageTypeUninitialized}, eventRecord{record}
{}
[[nodiscard]] auto toAction() const -> std::unique_ptr<app::manager::ActionRequest> override
{
return std::make_unique<app::manager::ActionRequest>(
- sender, app::manager::actions::ShowPopup, std::make_unique<gui::BedtimeReminderPopupRequestParams>());
+ sender,
+ app::manager::actions::ShowPopup,
+ std::make_unique<gui::BedtimeReminderPopupRequestParams>(eventRecord));
}
+
+ Record eventRecord;
};
M products/BellHybrid/services/time/AlarmOperations.cpp => products/BellHybrid/services/time/AlarmOperations.cpp +52 -2
@@ 152,6 152,18 @@ namespace alarms
bedtime(std::move(bedtimeSettingsProvider))
{}
+ bool AlarmOperations::turnOffAlarmIfFoundInBedtime(const std::uint32_t id)
+ {
+ if (not bedtime.isEventInContainer(id)) {
+ return false;
+ }
+
+ switchAlarmExecution(*(*bedtime.findEvent(id)), false);
+ bedtime.removeAllEvents();
+
+ return true;
+ }
+
void AlarmOperations::minuteUpdated(TimePoint now)
{
/**
@@ 201,8 213,10 @@ namespace alarms
void AlarmOperations::processBedtime(TimePoint now)
{
if (bedtime.decide(now)) {
- auto bedtimeEvent = std::make_shared<AlarmEventRecord>();
- bedtimeEvent.get()->enabled = true;
+
+ auto bedtimeEvent = bedtime.createEvent();
+ bedtime.pushEvent(bedtimeEvent);
+
handleAlarmEvent(bedtimeEvent, alarms::AlarmType::BedtimeReminder, true);
}
}
@@ 282,7 296,9 @@ namespace alarms
handleAlarmEvent(event, alarms::AlarmType::PreWakeUpChime, false);
handleAlarmEvent(event, alarms::AlarmType::PreWakeUpFrontlight, false);
+ handleAlarmEvent(event, alarms::AlarmType::BedtimeReminder, false);
}
+
bool AlarmOperations::isBedtimeAllowed() const
{
return ongoingSingleEvents.empty() && snoozedSingleEvents.empty() && not preWakeUp.isActive();
@@ 336,6 352,40 @@ namespace alarms
return activated && isTimeForBed(now, time);
}
+ auto Bedtime::createEvent() -> std::shared_ptr<AlarmEventRecord>
+ {
+ auto bedtimeEvent = std::make_shared<AlarmEventRecord>();
+ bedtimeEvent->enabled = true;
+ bedtimeEvent->ID = nextFreeId;
+ nextFreeId++;
+
+ return bedtimeEvent;
+ }
+
+ void Bedtime::pushEvent(const std::shared_ptr<AlarmEventRecord> &bedtimeEvent)
+ {
+ auto bedtimeSingleEvent = std::make_unique<SingleEventRecord>();
+ bedtimeSingleEvent->parent = bedtimeEvent;
+
+ bedtimeSingleEvents.push_back(std::move(bedtimeSingleEvent));
+ }
+
+ bool Bedtime::isEventInContainer(std::uint32_t id)
+ {
+ return findEvent(id) == bedtimeSingleEvents.end() ? false : true;
+ }
+
+ EventsContainer<SingleEventRecord>::iterator Bedtime::findEvent(uint32_t id)
+ {
+ return findSingleEventById(bedtimeSingleEvents, id);
+ }
+
+ void Bedtime::removeAllEvents()
+ {
+ bedtimeSingleEvents.clear();
+ nextFreeId = resonableIdOffset;
+ }
+
auto Bedtime::isTimeForBed(const TimePoint &now, const time_t &bedtime) -> bool
{
auto time_tNow = TimePointToTimeT(now);
M products/BellHybrid/services/time/include/time/AlarmOperations.hpp => products/BellHybrid/services/time/include/time/AlarmOperations.hpp +10 -0
@@ 80,10 80,18 @@ namespace alarms
public:
explicit Bedtime(std::unique_ptr<AbstractBedtimeSettingsProvider> &&settingsProvider);
auto decide(TimePoint now) -> bool;
+ auto createEvent() -> std::shared_ptr<AlarmEventRecord>;
+ void pushEvent(const std::shared_ptr<AlarmEventRecord> &bedtimeEvent);
+ bool isEventInContainer(std::uint32_t id);
+ EventsContainer<SingleEventRecord>::iterator findEvent(std::uint32_t id);
+ void removeAllEvents();
private:
auto isTimeForBed(const TimePoint &now, const time_t &bedtime) -> bool;
+ static constexpr auto resonableIdOffset = 1000;
+ uint32_t nextFreeId{resonableIdOffset};
+ EventsContainer<SingleEventRecord> bedtimeSingleEvents;
const std::unique_ptr<AbstractBedtimeSettingsProvider> settingsProvider;
};
@@ 96,6 104,8 @@ namespace alarms
std::unique_ptr<SnoozeChimeSettingsProvider> &&snoozeChimeSettingsProvider,
std::unique_ptr<AbstractBedtimeSettingsProvider> &&BedtimeModel);
+ bool turnOffAlarmIfFoundInBedtime(const std::uint32_t id) override;
+
private:
void minuteUpdated(TimePoint now) override;
void stopAllSnoozedAlarms() override;
M products/BellHybrid/services/time/tests/CMakeLists.txt => products/BellHybrid/services/time/tests/CMakeLists.txt +1 -0
@@ 4,6 4,7 @@ add_gtest_executable(
SRCS
test-BellAlarmOperations.cpp
LIBS
+ service-time-alarm-operations-source
module-sys
bell::time
INCLUDE
M products/BellHybrid/services/time/tests/test-BellAlarmOperations.cpp => products/BellHybrid/services/time/tests/test-BellAlarmOperations.cpp +23 -18
@@ 1,4 1,4 @@
-// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// Copyright (c) 2017-2022, Mudita Sp. z.o.o. All rights reserved.
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
#include <AlarmOperations.hpp>
@@ 8,15 8,16 @@
#include <products/BellHybrid/services/time/include/time/AlarmOperations.hpp>
#include <gtest/gtest.h>
-
-// Included a .cpp file with AlarmOperations tests for the common part (the base class' implementation).
-// It needs to be built into this test in order to test the possible regression introduced by
-// the Bell-specific AlarmOperations class.
-// Generally, this should not be solved this way in other cases.
-#include <service-time/tests/tests-AlarmOperations.cpp>
-
+#include "tests/tests-AlarmOperations.hpp"
namespace
{
+ alarms::IAlarmOperations::OnUpdateAlarmProcessed universalBoolCallback = [](bool success) {
+ EXPECT_EQ(success, true);
+ };
+ alarms::IAlarmOperations::GetCurrentTime timeInjector = []() {
+ return TimePointFromStringWithShift("2022-11-11 05:00:00");
+ };
+
class MockedPreWakeUpSettingsProvider : public alarms::PreWakeUpSettingsProvider
{
public:
@@ 95,17 96,21 @@ namespace
std::move(snoozeChimeSettingsProvider),
std::move(bedtimeSettingsProvider));
}
-} // namespace
-// This function replaces the `getMockedAlarmOperations` function from `service-time/tests/tests-AlarmOperations.cpp`
-std::unique_ptr<alarms::IAlarmOperations> AlarmOperationsFixture::getMockedAlarmOperations(
- std::unique_ptr<MockAlarmEventsRepository> &alarmRepo)
-{
- return ::getMockedAlarmOperations(alarmRepo,
- std::make_unique<MockedPreWakeUpSettingsProvider>(),
- std::make_unique<MockedSnoozeChimeSettingsProvider>(),
- std::make_unique<MockedBedtimeModel>());
-}
+ class BellSpecificAlarmOperationsFixture : public AlarmOperationsFixture
+ {
+ protected:
+ std::unique_ptr<alarms::IAlarmOperations> getMockedAlarmOperations(
+ std::unique_ptr<MockAlarmEventsRepository> &alarmRepo) override
+ {
+ return ::getMockedAlarmOperations(alarmRepo,
+ std::make_unique<MockedPreWakeUpSettingsProvider>(),
+ std::make_unique<MockedSnoozeChimeSettingsProvider>(),
+ std::make_unique<MockedBedtimeModel>());
+ }
+ };
+
+} // namespace
TEST(PreWakeUp, TooEarlyForPreWakeUp)
{
M test/CMakeLists.txt => test/CMakeLists.txt +49 -1
@@ 94,7 94,7 @@ function(add_gtest_executable)
set(_TESTNAME "googletest-${_TEST_ARGS_NAME}")
if(NOT _TEST_ARGS_SRCS)
- message(FATAL_ERROR "You must provide test sources for ${_TESTNAME}")
+ message(FATAL_ERROR "You must provide test sources for ${_TESTNAME}")
endif(NOT _TEST_ARGS_SRCS)
get_directory_property(_TEST_ENTITY TEST_ENTITY)
@@ 244,4 244,52 @@ function(add_test_entity)
add_dependencies(check-${_ARGS_NAME} unittests-${_ARGS_NAME})
endfunction()
+function(add_gtest_manually_prepared_target)
+ cmake_parse_arguments(
+ _TEST_ARGS
+ ""
+ "NAME"
+ ""
+ ${ARGN}
+ )
+
+ if(NOT _TEST_ARGS_NAME)
+ message(FATAL_ERROR "You must provide a test name")
+ endif(NOT _TEST_ARGS_NAME)
+
+ target_compile_options(${_TEST_ARGS_NAME} PUBLIC "-fsanitize=address")
+ target_link_options(${_TEST_ARGS_NAME} PUBLIC "-fsanitize=address")
+
+ # disable logs in unit tests
+ if (NOT ${ENABLE_TEST_LOGS})
+ target_sources(${_TEST_ARGS_NAME} PRIVATE ${ROOT_TEST_DIR}/mock-logs.cpp)
+ target_sources(${_TEST_ARGS_NAME} PRIVATE ${ROOT_TEST_DIR}/mock-freertos-tls.cpp)
+ endif (NOT ${ENABLE_TEST_LOGS})
+
+ set(_TEST_LABELS "")
+ if(_TEST_ARGS_USE_FS)
+ enable_test_filesystem()
+ endif()
+
+ target_compile_options(${_TEST_ARGS_NAME} PUBLIC "-pthread")
+ target_link_options(${_TEST_ARGS_NAME} PUBLIC "-pthread")
+
+ add_dependencies(unittests ${_TEST_ARGS_NAME})
+ add_dependencies(check ${_TEST_ARGS_NAME})
+
+ get_directory_property(_TEST_ENTITY TEST_ENTITY)
+ if(_TEST_ENTITY)
+ add_dependencies(unittests-${_TEST_ENTITY} ${_TEST_ARGS_NAME})
+ list(APPEND _TEST_LABELS ${_TEST_ENTITY})
+ endif()
+
+ gtest_add_tests(
+ TARGET ${_TEST_ARGS_NAME}
+ WORKING_DIRECTORY ${CMAKE_BINARY_DIR}
+ TEST_LIST _TEST_LIST
+ )
+
+ set_tests_properties(${_TEST_LIST} PROPERTIES LABELS ${_TEST_LABELS})
+endfunction()
+
set(_CATCH_DISCOVER_TESTS_SCRIPT ${_CATCH_DISCOVER_TESTS_SCRIPT} PARENT_SCOPE)