Reformatted all the files according to clang-format style

main
Avamander 2021-04-18 20:28:14 +07:00
parent e56ebb8bd6
commit 40d45d923b
179 changed files with 10119 additions and 10688 deletions

@ -1,6 +1,6 @@
---
Language: Cpp
AccessModifierOffset: -2
AccessModifierOffset: 2
AlignAfterOpenBracket: Align
AlignConsecutiveMacros: true
AlignConsecutiveAssignments: false
@ -21,8 +21,8 @@ AlwaysBreakAfterDefinitionReturnType: None
AlwaysBreakAfterReturnType: None
AlwaysBreakBeforeMultilineStrings: false
AlwaysBreakTemplateDeclarations: MultiLine
BinPackArguments: true
BinPackParameters: true
BinPackArguments: false
BinPackParameters: false
BraceWrapping:
AfterCaseLabel: false
AfterClass: false
@ -52,14 +52,14 @@ BreakStringLiterals: true
ColumnLimit: 140
CommentPragmas: '^ IWYU pragma:'
CompactNamespaces: false
ConstructorInitializerAllOnOneLineOrOnePerLine: false
ConstructorInitializerAllOnOneLineOrOnePerLine: true
ConstructorInitializerIndentWidth: 2
ContinuationIndentWidth: 2
Cpp11BracedListStyle: true
DeriveLineEnding: false
DerivePointerAlignment: false
DisableFormat: false
ExperimentalAutoDetectBinPacking: false
ExperimentalAutoDetectBinPacking: true
FixNamespaceComments: false
ForEachMacros:
- foreach
@ -90,10 +90,6 @@ MacroBlockBegin: ''
MacroBlockEnd: ''
MaxEmptyLinesToKeep: 1
NamespaceIndentation: All
ObjCBinPackProtocolList: Auto
ObjCBlockIndentWidth: 2
ObjCSpaceAfterProperty: false
ObjCSpaceBeforeProtocolList: true
PenaltyBreakAssignment: 2
PenaltyBreakBeforeFirstCallParameter: 19
PenaltyBreakComment: 300

@ -75,7 +75,7 @@ As of now, here is the list of achievements of this project:
- [Flash, upgrade (OTA), time synchronization,...](doc/gettingStarted/gettingStarted.md)
### Develop
- [Generate the fonts and symbols](src/displayapp/fonts/Readme.md)
- [Generate the fonts and symbols](src/displayapp/fonts/README.md)
- [Creating a stopwatch in Pinetime(article)](https://pankajraghav.com/2021/04/03/PINETIME-STOPCLOCK.html)
### Build, flash and debug

@ -26,7 +26,6 @@
* 1 tab == 4 spaces!
*/
#ifndef FREERTOS_CONFIG_H
#define FREERTOS_CONFIG_H
@ -103,7 +102,6 @@
/* Tickless idle/low power functionality. */
/* Define to trap errors during development. */
#if defined(DEBUG_NRF) || defined(DEBUG_NRF_USER)
#define configASSERT(x) ASSERT(x)
@ -140,7 +138,6 @@ INTERRUPT SAFE FREERTOS API FUNCTIONS FROM ANY INTERRUPT THAT HAS A HIGHER
PRIORITY THAN THIS! (higher priorities are lower numeric values. */
#define configLIBRARY_MAX_SYSCALL_INTERRUPT_PRIORITY _PRIO_APP_HIGH
/* Interrupt priorities used by the kernel port layer itself. These are generic
to all Cortex-M ports, and do not rely on any particular library functions. */
#define configKERNEL_INTERRUPT_PRIORITY configLIBRARY_LOWEST_INTERRUPT_PRIORITY
@ -154,7 +151,6 @@ standard names - or at least those used in the unmodified vector table. */
#define vPortSVCHandler SVC_Handler
#define xPortPendSVHandler PendSV_Handler
/*-----------------------------------------------------------
* Settings that are generated automatically
* basing on the settings above
@ -198,9 +194,9 @@ standard names - or at least those used in the unmodified vector table. */
* one or more RTC ticks are lost. The tick interrupt inside RTOS will detect this and make a correction needed. This is needed
* for the RTOS internal timers to be more accurate.
* 1. The auto correction for RTOS tick is disabled even though few RTC tick interrupts were lost. This feature is desirable when debugging
* the RTOS application and stepping though the code. After stepping when the application is continued in debug mode, the auto-corrections of
* RTOS tick might cause asserts. Setting configUSE_DISABLE_TICK_AUTO_CORRECTION_DEBUG to 1 will make RTC and RTOS go out of sync but could be
* convenient for debugging.
* the RTOS application and stepping though the code. After stepping when the application is continued in debug mode, the
* auto-corrections of RTOS tick might cause asserts. Setting configUSE_DISABLE_TICK_AUTO_CORRECTION_DEBUG to 1 will make RTC and RTOS go
* out of sync but could be convenient for debugging.
*/
#define configUSE_DISABLE_TICK_AUTO_CORRECTION_DEBUG 0

@ -23,14 +23,14 @@ void Battery::Update() {
isCharging = !nrf_gpio_pin_read(chargingPin);
isPowerPresent = !nrf_gpio_pin_read(powerPresentPin);
if ( isReading ) return;
if (isReading)
return;
// Non blocking read
samples = 0;
isReading = true;
SaadcInit();
nrfx_saadc_sample();
}
void Battery::adcCallbackStatic(nrfx_saadc_evt_t const* event) {
@ -41,8 +41,7 @@ void Battery::SaadcInit() {
nrfx_saadc_config_t adcConfig = NRFX_SAADC_DEFAULT_CONFIG;
APP_ERROR_CHECK(nrfx_saadc_init(&adcConfig, adcCallbackStatic));
nrf_saadc_channel_config_t adcChannelConfig = {
.resistor_p = NRF_SAADC_RESISTOR_DISABLED,
nrf_saadc_channel_config_t adcChannelConfig = {.resistor_p = NRF_SAADC_RESISTOR_DISABLED,
.resistor_n = NRF_SAADC_RESISTOR_DISABLED,
.gain = NRF_SAADC_GAIN1_5,
.reference = NRF_SAADC_REFERENCE_INTERNAL,
@ -50,11 +49,9 @@ void Battery::SaadcInit() {
.mode = NRF_SAADC_MODE_SINGLE_ENDED,
.burst = NRF_SAADC_BURST_ENABLED,
.pin_p = batteryVoltageAdcInput,
.pin_n = NRF_SAADC_INPUT_DISABLED
};
.pin_n = NRF_SAADC_INPUT_DISABLED};
APP_ERROR_CHECK(nrfx_saadc_channel_init(0, &adcChannelConfig));
APP_ERROR_CHECK(nrfx_saadc_buffer_convert(&saadc_value, 1));
}
void Battery::SaadcEventHandler(nrfx_saadc_evt_t const* p_event) {
@ -85,4 +82,3 @@ void Battery::SaadcEventHandler(nrfx_saadc_evt_t const * p_event) {
}
}
}

@ -11,10 +11,10 @@ namespace Pinetime {
out the sensor values. The total capacity of the CircBuffer
is given as the template parameter N.
*/
template <int N>
class CircBuffer {
template <int N> class CircBuffer {
public:
CircBuffer() : arr{}, sz{}, cap{N}, head{} {}
CircBuffer() : arr {}, sz {}, cap {N}, head {} {
}
/**
insert member function overwrites the next data to the current
HEAD and moves the HEAD to the newly inserted value.
@ -41,18 +41,25 @@ namespace Pinetime {
class Battery {
public:
Battery();
void Init();
void Update();
int PercentRemaining() const { return percentRemainingBuffer.GetAverage(); }
int PercentRemaining() const {
return percentRemainingBuffer.GetAverage();
}
float Voltage() const { return voltage; }
float Voltage() const {
return voltage;
}
bool IsCharging() const { return isCharging; }
bool IsPowerPresent() const { return isPowerPresent; }
bool IsCharging() const {
return isCharging;
}
bool IsPowerPresent() const {
return isPowerPresent;
}
private:
static Battery* instance;

@ -12,50 +12,42 @@ constexpr ble_uuid16_t AlertNotificationClient::unreadAlertStatusUuid;
constexpr ble_uuid16_t AlertNotificationClient::controlPointUuid;
namespace {
int
OnDiscoveryEventCallback(uint16_t conn_handle, const struct ble_gatt_error *error, const struct ble_gatt_svc *service,
void *arg) {
int OnDiscoveryEventCallback(uint16_t conn_handle, const struct ble_gatt_error* error, const struct ble_gatt_svc* service, void* arg) {
auto client = static_cast<AlertNotificationClient*>(arg);
return client->OnDiscoveryEvent(conn_handle, error, service);
}
int OnAlertNotificationCharacteristicDiscoveredCallback(uint16_t conn_handle, const struct ble_gatt_error *error,
const struct ble_gatt_chr *chr, void *arg) {
int OnAlertNotificationCharacteristicDiscoveredCallback(uint16_t conn_handle,
const struct ble_gatt_error* error,
const struct ble_gatt_chr* chr,
void* arg) {
auto client = static_cast<AlertNotificationClient*>(arg);
return client->OnCharacteristicsDiscoveryEvent(conn_handle, error, chr);
}
int OnAlertNotificationDescriptorDiscoveryEventCallback(uint16_t conn_handle,
const struct ble_gatt_error *error,
uint16_t chr_val_handle,
const struct ble_gatt_dsc *dsc,
void *arg) {
int OnAlertNotificationDescriptorDiscoveryEventCallback(
uint16_t conn_handle, const struct ble_gatt_error* error, uint16_t chr_val_handle, const struct ble_gatt_dsc* dsc, void* arg) {
auto client = static_cast<AlertNotificationClient*>(arg);
return client->OnDescriptorDiscoveryEventCallback(conn_handle, error, chr_val_handle, dsc);
}
int NewAlertSubcribeCallback(uint16_t conn_handle,
const struct ble_gatt_error *error,
struct ble_gatt_attr *attr,
void *arg) {
int NewAlertSubcribeCallback(uint16_t conn_handle, const struct ble_gatt_error* error, struct ble_gatt_attr* attr, void* arg) {
auto client = static_cast<AlertNotificationClient*>(arg);
return client->OnNewAlertSubcribe(conn_handle, error, attr);
}
}
AlertNotificationClient::AlertNotificationClient(Pinetime::System::SystemTask& systemTask,
Pinetime::Controllers::NotificationManager &notificationManager) :
systemTask{systemTask}, notificationManager{notificationManager} {
Pinetime::Controllers::NotificationManager& notificationManager)
: systemTask {systemTask}, notificationManager {notificationManager} {
}
bool AlertNotificationClient::OnDiscoveryEvent(uint16_t connectionHandle, const ble_gatt_error *error,
const ble_gatt_svc *service) {
bool AlertNotificationClient::OnDiscoveryEvent(uint16_t connectionHandle, const ble_gatt_error* error, const ble_gatt_svc* service) {
if (service == nullptr && error->status == BLE_HS_EDONE) {
if (isDiscovered) {
NRF_LOG_INFO("ANS Discovery found, starting characteristics discovery");
ble_gattc_disc_all_chrs(connectionHandle, ansStartHandle, ansEndHandle,
OnAlertNotificationCharacteristicDiscoveredCallback, this);
ble_gattc_disc_all_chrs(connectionHandle, ansStartHandle, ansEndHandle, OnAlertNotificationCharacteristicDiscoveredCallback, this);
} else {
NRF_LOG_INFO("ANS not found");
onServiceDiscovered(connectionHandle);
@ -72,7 +64,8 @@ bool AlertNotificationClient::OnDiscoveryEvent(uint16_t connectionHandle, const
return false;
}
int AlertNotificationClient::OnCharacteristicsDiscoveryEvent(uint16_t connectionHandle, const ble_gatt_error *error,
int AlertNotificationClient::OnCharacteristicsDiscoveryEvent(uint16_t connectionHandle,
const ble_gatt_error* error,
const ble_gatt_chr* characteristic) {
if (error->status != 0 && error->status != BLE_HS_EDONE) {
NRF_LOG_INFO("ANS Characteristic discovery ERROR");
@ -83,41 +76,34 @@ int AlertNotificationClient::OnCharacteristicsDiscoveryEvent(uint16_t connection
if (characteristic == nullptr && error->status == BLE_HS_EDONE) {
NRF_LOG_INFO("ANS Characteristic discovery complete");
if (isCharacteristicDiscovered) {
ble_gattc_disc_all_dscs(connectionHandle,
newAlertHandle, ansEndHandle,
OnAlertNotificationDescriptorDiscoveryEventCallback, this);
ble_gattc_disc_all_dscs(connectionHandle, newAlertHandle, ansEndHandle, OnAlertNotificationDescriptorDiscoveryEventCallback, this);
} else
onServiceDiscovered(connectionHandle);
} else {
if (characteristic != nullptr &&
ble_uuid_cmp(((ble_uuid_t *) &supportedNewAlertCategoryUuid), &characteristic->uuid.u) == 0) {
if (characteristic != nullptr && ble_uuid_cmp(((ble_uuid_t*) &supportedNewAlertCategoryUuid), &characteristic->uuid.u) == 0) {
NRF_LOG_INFO("ANS Characteristic discovered : supportedNewAlertCategoryUuid");
supportedNewAlertCategoryHandle = characteristic->val_handle;
} else if (characteristic != nullptr &&
ble_uuid_cmp(((ble_uuid_t *) &supportedUnreadAlertCategoryUuid), &characteristic->uuid.u) == 0) {
} else if (characteristic != nullptr && ble_uuid_cmp(((ble_uuid_t*) &supportedUnreadAlertCategoryUuid), &characteristic->uuid.u) == 0) {
NRF_LOG_INFO("ANS Characteristic discovered : supportedUnreadAlertCategoryUuid");
supportedUnreadAlertCategoryHandle = characteristic->val_handle;
} else if (characteristic != nullptr &&
ble_uuid_cmp(((ble_uuid_t *) &newAlertUuid), &characteristic->uuid.u) == 0) {
} else if (characteristic != nullptr && ble_uuid_cmp(((ble_uuid_t*) &newAlertUuid), &characteristic->uuid.u) == 0) {
NRF_LOG_INFO("ANS Characteristic discovered : newAlertUuid");
newAlertHandle = characteristic->val_handle;
newAlertDefHandle = characteristic->def_handle;
isCharacteristicDiscovered = true;
} else if (characteristic != nullptr &&
ble_uuid_cmp(((ble_uuid_t *) &unreadAlertStatusUuid), &characteristic->uuid.u) == 0) {
} else if (characteristic != nullptr && ble_uuid_cmp(((ble_uuid_t*) &unreadAlertStatusUuid), &characteristic->uuid.u) == 0) {
NRF_LOG_INFO("ANS Characteristic discovered : unreadAlertStatusUuid");
unreadAlertStatusHandle = characteristic->val_handle;
} else if (characteristic != nullptr &&
ble_uuid_cmp(((ble_uuid_t *) &controlPointUuid), &characteristic->uuid.u) == 0) {
} else if (characteristic != nullptr && ble_uuid_cmp(((ble_uuid_t*) &controlPointUuid), &characteristic->uuid.u) == 0) {
NRF_LOG_INFO("ANS Characteristic discovered : controlPointUuid");
controlPointHandle = characteristic->val_handle;
} else NRF_LOG_INFO("ANS Characteristic discovered : 0x%x", characteristic->val_handle);
} else
NRF_LOG_INFO("ANS Characteristic discovered : 0x%x", characteristic->val_handle);
}
return 0;
}
int AlertNotificationClient::OnNewAlertSubcribe(uint16_t connectionHandle, const ble_gatt_error *error,
ble_gatt_attr *attribute) {
int AlertNotificationClient::OnNewAlertSubcribe(uint16_t connectionHandle, const ble_gatt_error* error, ble_gatt_attr* attribute) {
if (error->status == 0) {
NRF_LOG_INFO("ANS New alert subscribe OK");
} else {
@ -128,12 +114,12 @@ int AlertNotificationClient::OnNewAlertSubcribe(uint16_t connectionHandle, const
return 0;
}
int AlertNotificationClient::OnDescriptorDiscoveryEventCallback(uint16_t connectionHandle, const ble_gatt_error *error,
int AlertNotificationClient::OnDescriptorDiscoveryEventCallback(uint16_t connectionHandle,
const ble_gatt_error* error,
uint16_t characteristicValueHandle,
const ble_gatt_dsc* descriptor) {
if (error->status == 0) {
if (characteristicValueHandle == newAlertHandle &&
ble_uuid_cmp(((ble_uuid_t *) &newAlertUuid), &descriptor->uuid.u)) {
if (characteristicValueHandle == newAlertHandle && ble_uuid_cmp(((ble_uuid_t*) &newAlertUuid), &descriptor->uuid.u)) {
if (newAlertDescriptorHandle == 0) {
NRF_LOG_INFO("ANS Descriptor discovered : %d", descriptor->handle);
newAlertDescriptorHandle = descriptor->handle;
@ -160,7 +146,8 @@ void AlertNotificationClient::OnNotification(ble_gap_event *event) {
// Ignore notifications with empty message
const auto packetLen = OS_MBUF_PKTLEN(event->notify_rx.om);
if(packetLen <= headerSize) return;
if (packetLen <= headerSize)
return;
size_t bufferSize = std::min(packetLen + stringTerminatorSize, maxBufferSize);
auto messageSize = std::min(maxMessageSize, (bufferSize - headerSize));

@ -24,11 +24,12 @@ namespace Pinetime {
Pinetime::Controllers::NotificationManager& notificationManager);
bool OnDiscoveryEvent(uint16_t connectionHandle, const ble_gatt_error* error, const ble_gatt_svc* service);
int OnCharacteristicsDiscoveryEvent(uint16_t connectionHandle, const ble_gatt_error *error,
const ble_gatt_chr *characteristic);
int OnCharacteristicsDiscoveryEvent(uint16_t connectionHandle, const ble_gatt_error* error, const ble_gatt_chr* characteristic);
int OnNewAlertSubcribe(uint16_t connectionHandle, const ble_gatt_error* error, ble_gatt_attr* attribute);
int OnDescriptorDiscoveryEventCallback(uint16_t connectionHandle, const ble_gatt_error *error,
uint16_t characteristicValueHandle, const ble_gatt_dsc *descriptor);
int OnDescriptorDiscoveryEventCallback(uint16_t connectionHandle,
const ble_gatt_error* error,
uint16_t characteristicValueHandle,
const ble_gatt_dsc* descriptor);
void OnNotification(ble_gap_event* event);
void Reset();
void Discover(uint16_t connectionHandle, std::function<void(uint16_t)> lambda) override;
@ -41,30 +42,13 @@ namespace Pinetime {
static constexpr uint16_t unreadAlertStatusId = 0x2a45;
static constexpr uint16_t controlPointId = 0x2a44;
static constexpr ble_uuid16_t ansServiceUuid{
.u {.type = BLE_UUID_TYPE_16},
.value = ansServiceId
};
static constexpr ble_uuid16_t supportedNewAlertCategoryUuid{
.u {.type = BLE_UUID_TYPE_16},
.value = supportedNewAlertCategoryId
};
static constexpr ble_uuid16_t supportedUnreadAlertCategoryUuid{
.u {.type = BLE_UUID_TYPE_16},
.value = supportedUnreadAlertCategoryId
};
static constexpr ble_uuid16_t newAlertUuid{
.u {.type = BLE_UUID_TYPE_16},
.value = newAlertId
};
static constexpr ble_uuid16_t unreadAlertStatusUuid{
.u {.type = BLE_UUID_TYPE_16},
.value = unreadAlertStatusId
};
static constexpr ble_uuid16_t controlPointUuid{
.u {.type = BLE_UUID_TYPE_16},
.value = controlPointId
};
static constexpr ble_uuid16_t ansServiceUuid {.u {.type = BLE_UUID_TYPE_16}, .value = ansServiceId};
static constexpr ble_uuid16_t supportedNewAlertCategoryUuid {.u {.type = BLE_UUID_TYPE_16}, .value = supportedNewAlertCategoryId};
static constexpr ble_uuid16_t supportedUnreadAlertCategoryUuid {.u {.type = BLE_UUID_TYPE_16},
.value = supportedUnreadAlertCategoryId};
static constexpr ble_uuid16_t newAlertUuid {.u {.type = BLE_UUID_TYPE_16}, .value = newAlertId};
static constexpr ble_uuid16_t unreadAlertStatusUuid {.u {.type = BLE_UUID_TYPE_16}, .value = unreadAlertStatusId};
static constexpr ble_uuid16_t controlPointUuid {.u {.type = BLE_UUID_TYPE_16}, .value = controlPointId};
uint16_t ansStartHandle = 0;
uint16_t ansEndHandle = 0;

@ -11,7 +11,6 @@ constexpr ble_uuid16_t AlertNotificationService::ansUuid;
constexpr ble_uuid16_t AlertNotificationService::ansCharUuid;
constexpr ble_uuid128_t AlertNotificationService::notificationEventUuid;
int AlertNotificationCallback(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt, void* arg) {
auto anService = static_cast<AlertNotificationService*>(arg);
return anService->OnAlert(conn_handle, attr_handle, ctxt);
@ -27,39 +26,28 @@ void AlertNotificationService::Init() {
}
AlertNotificationService::AlertNotificationService(System::SystemTask& systemTask, NotificationManager& notificationManager)
: characteristicDefinition{
{
.uuid = (ble_uuid_t *) &ansCharUuid,
: characteristicDefinition {{.uuid = (ble_uuid_t*) &ansCharUuid,
.access_cb = AlertNotificationCallback,
.arg = this,
.flags = BLE_GATT_CHR_F_WRITE
},
{
.uuid = (ble_uuid_t *) &notificationEventUuid,
.flags = BLE_GATT_CHR_F_WRITE},
{.uuid = (ble_uuid_t*) &notificationEventUuid,
.access_cb = AlertNotificationCallback,
.arg = this,
.flags = BLE_GATT_CHR_F_NOTIFY,
.val_handle = &eventHandle
},
{
0
}
},
.val_handle = &eventHandle},
{0}},
serviceDefinition {
{
/* Device Information Service */
{/* Device Information Service */
.type = BLE_GATT_SVC_TYPE_PRIMARY,
.uuid = (ble_uuid_t*) &ansUuid,
.characteristics = characteristicDefinition
.characteristics = characteristicDefinition},
{0},
},
{
0
},
}, systemTask{systemTask}, notificationManager{notificationManager} {
systemTask {systemTask},
notificationManager {notificationManager} {
}
int AlertNotificationService::OnAlert(uint16_t conn_handle, uint16_t attr_handle,
struct ble_gatt_access_ctxt *ctxt) {
int AlertNotificationService::OnAlert(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt) {
if (ctxt->op == BLE_GATT_ACCESS_OP_WRITE_CHR) {
constexpr size_t stringTerminatorSize = 1; // end of string '\0'
constexpr size_t headerSize = 3;
@ -68,7 +56,8 @@ int AlertNotificationService::OnAlert(uint16_t conn_handle, uint16_t attr_handle
// Ignore notifications with empty message
const auto packetLen = OS_MBUF_PKTLEN(ctxt->om);
if(packetLen <= headerSize) return 0;
if (packetLen <= headerSize)
return 0;
size_t bufferSize = std::min(packetLen + stringTerminatorSize, maxBufferSize);
auto messageSize = std::min(maxMessageSize, (bufferSize - headerSize));

@ -8,7 +8,8 @@
#undef min
// 00020001-78fc-48fe-8e23-433b3a1942d0
#define NOTIFICATION_EVENT_SERVICE_UUID_BASE {0xd0, 0x42, 0x19, 0x3a, 0x3b, 0x43, 0x23, 0x8e, 0xfe, 0x48, 0xfc, 0x78, 0x01, 0x00, 0x02, 0x00}
#define NOTIFICATION_EVENT_SERVICE_UUID_BASE \
{ 0xd0, 0x42, 0x19, 0x3a, 0x3b, 0x43, 0x23, 0x8e, 0xfe, 0x48, 0xfc, 0x78, 0x01, 0x00, 0x02, 0x00 }
namespace Pinetime {
@ -20,22 +21,16 @@ namespace Pinetime {
class AlertNotificationService {
public:
AlertNotificationService(Pinetime::System::SystemTask &systemTask,
Pinetime::Controllers::NotificationManager &notificationManager);
AlertNotificationService(Pinetime::System::SystemTask& systemTask, Pinetime::Controllers::NotificationManager& notificationManager);
void Init();
int OnAlert(uint16_t conn_handle, uint16_t attr_handle,
struct ble_gatt_access_ctxt *ctxt);
int OnAlert(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt);
void AcceptIncomingCall();
void RejectIncomingCall();
void MuteIncomingCall();
enum class IncomingCallResponses : uint8_t {
Reject = 0x00,
Answer = 0x01,
Mute = 0x02
};
enum class IncomingCallResponses : uint8_t { Reject = 0x00, Answer = 0x01, Mute = 0x02 };
private:
enum class Categories : uint8_t {
@ -55,20 +50,11 @@ namespace Pinetime {
static constexpr uint16_t ansId {0x1811};
static constexpr uint16_t ansCharId {0x2a46};
static constexpr ble_uuid16_t ansUuid {
.u { .type = BLE_UUID_TYPE_16 },
.value = ansId
};
static constexpr ble_uuid16_t ansUuid {.u {.type = BLE_UUID_TYPE_16}, .value = ansId};
static constexpr ble_uuid16_t ansCharUuid {
.u { .type = BLE_UUID_TYPE_16 },
.value = ansCharId
};
static constexpr ble_uuid16_t ansCharUuid {.u {.type = BLE_UUID_TYPE_16}, .value = ansCharId};
static constexpr ble_uuid128_t notificationEventUuid {
.u { .type = BLE_UUID_TYPE_128 },
.value = NOTIFICATION_EVENT_SERVICE_UUID_BASE
};
static constexpr ble_uuid128_t notificationEventUuid {.u {.type = BLE_UUID_TYPE_128}, .value = NOTIFICATION_EVENT_SERVICE_UUID_BASE};
struct ble_gatt_chr_def characteristicDefinition[3];
struct ble_gatt_svc_def serviceDefinition[2];

@ -7,39 +7,26 @@ using namespace Pinetime::Controllers;
constexpr ble_uuid16_t BatteryInformationService::batteryInformationServiceUuid;
constexpr ble_uuid16_t BatteryInformationService::batteryLevelUuid;
int BatteryInformationServiceCallback(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt, void* arg) {
auto* batteryInformationService = static_cast<BatteryInformationService*>(arg);
return batteryInformationService->OnBatteryServiceRequested(conn_handle, attr_handle, ctxt);
}
BatteryInformationService::BatteryInformationService(Controllers::Battery& batteryController) :
batteryController{batteryController},
characteristicDefinition{
{
.uuid = (ble_uuid_t *) &batteryLevelUuid,
BatteryInformationService::BatteryInformationService(Controllers::Battery& batteryController)
: batteryController {batteryController},
characteristicDefinition {{.uuid = (ble_uuid_t*) &batteryLevelUuid,
.access_cb = BatteryInformationServiceCallback,
.arg = this,
.flags = BLE_GATT_CHR_F_READ,
.val_handle = &batteryLevelHandle
},
{
0
}
},
.val_handle = &batteryLevelHandle},
{0}},
serviceDefinition {
{
/* Device Information Service */
{/* Device Information Service */
.type = BLE_GATT_SVC_TYPE_PRIMARY,
.uuid = (ble_uuid_t*) &batteryInformationServiceUuid,
.characteristics = characteristicDefinition
},
{
0
},
.characteristics = characteristicDefinition},
{0},
} {
}
void BatteryInformationService::Init() {
@ -51,7 +38,8 @@ void BatteryInformationService::Init() {
ASSERT(res == 0);
}
int BatteryInformationService::OnBatteryServiceRequested(uint16_t connectionHandle, uint16_t attributeHandle,
int BatteryInformationService::OnBatteryServiceRequested(uint16_t connectionHandle,
uint16_t attributeHandle,
ble_gatt_access_ctxt* context) {
if (attributeHandle == batteryLevelHandle) {
NRF_LOG_INFO("BATTERY : handle = %d", batteryLevelHandle);

@ -16,29 +16,21 @@ namespace Pinetime {
BatteryInformationService(Controllers::Battery& batteryController);
void Init();
int
OnBatteryServiceRequested(uint16_t connectionHandle, uint16_t attributeHandle, ble_gatt_access_ctxt *context);
int OnBatteryServiceRequested(uint16_t connectionHandle, uint16_t attributeHandle, ble_gatt_access_ctxt* context);
private:
Controllers::Battery& batteryController;
static constexpr uint16_t batteryInformationServiceId {0x180F};
static constexpr uint16_t batteryLevelId {0x2A19};
static constexpr ble_uuid16_t batteryInformationServiceUuid {
.u {.type = BLE_UUID_TYPE_16},
.value = batteryInformationServiceId
};
static constexpr ble_uuid16_t batteryInformationServiceUuid {.u {.type = BLE_UUID_TYPE_16}, .value = batteryInformationServiceId};
static constexpr ble_uuid16_t batteryLevelUuid {
.u {.type = BLE_UUID_TYPE_16},
.value = batteryLevelId
};
static constexpr ble_uuid16_t batteryLevelUuid {.u {.type = BLE_UUID_TYPE_16}, .value = batteryLevelId};
struct ble_gatt_chr_def characteristicDefinition[3];
struct ble_gatt_svc_def serviceDefinition[2];
uint16_t batteryLevelHandle;
};
}
}

@ -25,5 +25,3 @@ void Ble::FirmwareUpdateTotalBytes(uint32_t totalBytes) {
void Ble::FirmwareUpdateCurrentBytes(uint32_t currentBytes) {
firmwareUpdateCurrentBytes = currentBytes;
}

@ -12,7 +12,9 @@ namespace Pinetime {
enum class AddressTypes { Public, Random };
Ble() = default;
bool IsConnected() const {return isConnected;}
bool IsConnected() const {
return isConnected;
}
void Connect();
void Disconnect();
@ -20,16 +22,33 @@ namespace Pinetime {
void StopFirmwareUpdate();
void FirmwareUpdateTotalBytes(uint32_t totalBytes);
void FirmwareUpdateCurrentBytes(uint32_t currentBytes);
void State(FirmwareUpdateStates state) { firmwareUpdateState = state; }
void State(FirmwareUpdateStates state) {
firmwareUpdateState = state;
}
bool IsFirmwareUpdating() const { return isFirmwareUpdating; }
uint32_t FirmwareUpdateTotalBytes() const { return firmwareUpdateTotalBytes; }
uint32_t FirmwareUpdateCurrentBytes() const { return firmwareUpdateCurrentBytes; }
FirmwareUpdateStates State() const { return firmwareUpdateState; }
bool IsFirmwareUpdating() const {
return isFirmwareUpdating;
}
uint32_t FirmwareUpdateTotalBytes() const {
return firmwareUpdateTotalBytes;
}
uint32_t FirmwareUpdateCurrentBytes() const {
return firmwareUpdateCurrentBytes;
}
FirmwareUpdateStates State() const {
return firmwareUpdateState;
}
void Address(BleAddress&& addr) {
address = addr;
}
const BleAddress& Address() const {
return address;
}
void AddressType(AddressTypes t) {
addressType = t;
}
void Address(BleAddress&& addr) { address = addr; }
const BleAddress& Address() const { return address; }
void AddressType(AddressTypes t) { addressType = t;}
private:
bool isConnected = false;
bool isFirmwareUpdating = false;
@ -38,7 +57,6 @@ namespace Pinetime {
FirmwareUpdateStates firmwareUpdateState = FirmwareUpdateStates::Idle;
BleAddress address;
AddressTypes addressType;
};
}
}

@ -14,8 +14,10 @@ namespace {
return client->OnDiscoveryEvent(conn_handle, error, service);
}
int OnCurrentTimeCharacteristicDiscoveredCallback(uint16_t conn_handle, const struct ble_gatt_error *error,
const struct ble_gatt_chr *chr, void *arg) {
int OnCurrentTimeCharacteristicDiscoveredCallback(uint16_t conn_handle,
const struct ble_gatt_error* error,
const struct ble_gatt_chr* chr,
void* arg) {
auto client = static_cast<CurrentTimeClient*>(arg);
return client->OnCharacteristicDiscoveryEvent(conn_handle, error, chr);
}
@ -27,21 +29,17 @@ namespace {
}
CurrentTimeClient::CurrentTimeClient(DateTime& dateTimeController) : dateTimeController {dateTimeController} {
}
void CurrentTimeClient::Init() {
}
bool CurrentTimeClient::OnDiscoveryEvent(uint16_t connectionHandle, const ble_gatt_error *error,
const ble_gatt_svc *service) {
bool CurrentTimeClient::OnDiscoveryEvent(uint16_t connectionHandle, const ble_gatt_error* error, const ble_gatt_svc* service) {
if (service == nullptr && error->status == BLE_HS_EDONE) {
if (isDiscovered) {
NRF_LOG_INFO("CTS found, starting characteristics discovery");
ble_gattc_disc_all_chrs(connectionHandle, ctsStartHandle, ctsEndHandle,
OnCurrentTimeCharacteristicDiscoveredCallback, this);
ble_gattc_disc_all_chrs(connectionHandle, ctsStartHandle, ctsEndHandle, OnCurrentTimeCharacteristicDiscoveredCallback, this);
} else {
NRF_LOG_INFO("CTS not found");
onServiceDiscovered(connectionHandle);
@ -59,7 +57,8 @@ bool CurrentTimeClient::OnDiscoveryEvent(uint16_t connectionHandle, const ble_ga
return false;
}
int CurrentTimeClient::OnCharacteristicDiscoveryEvent(uint16_t conn_handle, const ble_gatt_error *error,
int CurrentTimeClient::OnCharacteristicDiscoveryEvent(uint16_t conn_handle,
const ble_gatt_error* error,
const ble_gatt_chr* characteristic) {
if (characteristic == nullptr && error->status == BLE_HS_EDONE) {
if (isCharacteristicDiscovered) {
@ -73,8 +72,7 @@ int CurrentTimeClient::OnCharacteristicDiscoveryEvent(uint16_t conn_handle, cons
return 0;
}
if (characteristic != nullptr &&
ble_uuid_cmp(((ble_uuid_t *) &currentTimeCharacteristicUuid), &characteristic->uuid.u) == 0) {
if (characteristic != nullptr && ble_uuid_cmp(((ble_uuid_t*) &currentTimeCharacteristicUuid), &characteristic->uuid.u) == 0) {
NRF_LOG_INFO("CTS Characteristic discovered : 0x%x", characteristic->val_handle);
isCharacteristicDiscovered = true;
currentTimeHandle = characteristic->val_handle;
@ -82,17 +80,15 @@ int CurrentTimeClient::OnCharacteristicDiscoveryEvent(uint16_t conn_handle, cons
return 0;
}
int CurrentTimeClient::OnCurrentTimeReadResult(uint16_t conn_handle, const ble_gatt_error *error,
const ble_gatt_attr *attribute) {
int CurrentTimeClient::OnCurrentTimeReadResult(uint16_t conn_handle, const ble_gatt_error* error, const ble_gatt_attr* attribute) {
if (error->status == 0) {
// TODO check that attribute->handle equals the handle discovered in OnCharacteristicDiscoveryEvent
CtsData result;
os_mbuf_copydata(attribute->om, 0, sizeof(CtsData), &result);
NRF_LOG_INFO("Received data: %d-%d-%d %d:%d:%d", result.year,
result.month, result.dayofmonth,
result.hour, result.minute, result.second);
dateTimeController.SetTime(result.year, result.month, result.dayofmonth,
0, result.hour, result.minute, result.second, nrf_rtc_counter_get(portNRF_RTC_REG));
NRF_LOG_INFO(
"Received data: %d-%d-%d %d:%d:%d", result.year, result.month, result.dayofmonth, result.hour, result.minute, result.second);
dateTimeController.SetTime(
result.year, result.month, result.dayofmonth, 0, result.hour, result.minute, result.second, nrf_rtc_counter_get(portNRF_RTC_REG));
} else {
NRF_LOG_INFO("Error retrieving current time: %d", error->status);
}

@ -17,11 +17,14 @@ namespace Pinetime {
void Init();
void Reset();
bool OnDiscoveryEvent(uint16_t connectionHandle, const ble_gatt_error* error, const ble_gatt_svc* service);
int OnCharacteristicDiscoveryEvent(uint16_t conn_handle, const ble_gatt_error *error,
const ble_gatt_chr *characteristic);
int OnCharacteristicDiscoveryEvent(uint16_t conn_handle, const ble_gatt_error* error, const ble_gatt_chr* characteristic);
int OnCurrentTimeReadResult(uint16_t conn_handle, const ble_gatt_error* error, const ble_gatt_attr* attribute);
static constexpr const ble_uuid16_t* Uuid() { return &CurrentTimeClient::ctsServiceUuid; }
static constexpr const ble_uuid16_t* CurrentTimeCharacteristicUuid() { return &CurrentTimeClient::currentTimeCharacteristicUuid; }
static constexpr const ble_uuid16_t* Uuid() {
return &CurrentTimeClient::ctsServiceUuid;
}
static constexpr const ble_uuid16_t* CurrentTimeCharacteristicUuid() {
return &CurrentTimeClient::currentTimeCharacteristicUuid;
}
void Discover(uint16_t connectionHandle, std::function<void(uint16_t)> lambda) override;
private:
@ -39,14 +42,8 @@ namespace Pinetime {
static constexpr uint16_t ctsServiceId {0x1805};
static constexpr uint16_t currentTimeCharacteristicId {0x2a2b};
static constexpr ble_uuid16_t ctsServiceUuid {
.u { .type = BLE_UUID_TYPE_16 },
.value = ctsServiceId
};
static constexpr ble_uuid16_t currentTimeCharacteristicUuid {
.u { .type = BLE_UUID_TYPE_16 },
.value = currentTimeCharacteristicId
};
static constexpr ble_uuid16_t ctsServiceUuid {.u {.type = BLE_UUID_TYPE_16}, .value = ctsServiceId};
static constexpr ble_uuid16_t currentTimeCharacteristicUuid {.u {.type = BLE_UUID_TYPE_16}, .value = currentTimeCharacteristicId};
DateTime& dateTimeController;
bool isDiscovered = false;

@ -7,7 +7,6 @@ using namespace Pinetime::Controllers;
constexpr ble_uuid16_t CurrentTimeService::ctsUuid;
constexpr ble_uuid16_t CurrentTimeService::ctChrUuid;
int CTSCallback(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt, void* arg) {
auto cts = static_cast<CurrentTimeService*>(arg);
return cts->OnTimeAccessed(conn_handle, attr_handle, ctxt);
@ -22,9 +21,7 @@ void CurrentTimeService::Init() {
ASSERT(res == 0);
}
int CurrentTimeService::OnTimeAccessed(uint16_t conn_handle, uint16_t attr_handle,
struct ble_gatt_access_ctxt *ctxt) {
int CurrentTimeService::OnTimeAccessed(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt) {
NRF_LOG_INFO("Setting time...");
@ -32,12 +29,11 @@ int CurrentTimeService::OnTimeAccessed(uint16_t conn_handle, uint16_t attr_handl
CtsData result;
os_mbuf_copydata(ctxt->om, 0, sizeof(CtsData), &result);
NRF_LOG_INFO("Received data: %d-%d-%d %d:%d:%d", result.year,
result.month, result.dayofmonth,
result.hour, result.minute, result.second);
NRF_LOG_INFO(
"Received data: %d-%d-%d %d:%d:%d", result.year, result.month, result.dayofmonth, result.hour, result.minute, result.second);
m_dateTimeController.SetTime(result.year, result.month, result.dayofmonth,
0, result.hour, result.minute, result.second, nrf_rtc_counter_get(portNRF_RTC_REG));
m_dateTimeController.SetTime(
result.year, result.month, result.dayofmonth, 0, result.hour, result.minute, result.second, nrf_rtc_counter_get(portNRF_RTC_REG));
} else if (ctxt->op == BLE_GATT_ACCESS_OP_READ_CHR) {
CtsData currentDateTime;
@ -49,39 +45,26 @@ int CurrentTimeService::OnTimeAccessed(uint16_t conn_handle, uint16_t attr_handl
currentDateTime.second = m_dateTimeController.Seconds();
currentDateTime.millis = 0;
int res = os_mbuf_append(ctxt->om, &currentDateTime, sizeof(CtsData));
return (res == 0) ? 0 : BLE_ATT_ERR_INSUFFICIENT_RES;
}
return 0;
}
CurrentTimeService::CurrentTimeService(DateTime &dateTimeController) :
characteristicDefinition{
{
.uuid = (ble_uuid_t *) &ctChrUuid,
CurrentTimeService::CurrentTimeService(DateTime& dateTimeController)
: characteristicDefinition {{.uuid = (ble_uuid_t*) &ctChrUuid,
.access_cb = CTSCallback,
.arg = this,
.flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ
},
{
0
}
},
.flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ},
{0}},
serviceDefinition {
{
/* Device Information Service */
{/* Device Information Service */
.type = BLE_GATT_SVC_TYPE_PRIMARY,
.uuid = (ble_uuid_t*) &ctsUuid,
.characteristics = characteristicDefinition
.characteristics = characteristicDefinition},
{0},
},
{
0
},
}, m_dateTimeController{dateTimeController} {
m_dateTimeController {dateTimeController} {
}

@ -16,22 +16,15 @@ namespace Pinetime {
CurrentTimeService(DateTime& dateTimeController);
void Init();
int OnTimeAccessed(uint16_t conn_handle, uint16_t attr_handle,
struct ble_gatt_access_ctxt *ctxt);
int OnTimeAccessed(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt);
private:
static constexpr uint16_t ctsId {0x1805};
static constexpr uint16_t ctsCharId {0x2a2b};
static constexpr ble_uuid16_t ctsUuid {
.u { .type = BLE_UUID_TYPE_16 },
.value = ctsId
};
static constexpr ble_uuid16_t ctsUuid {.u {.type = BLE_UUID_TYPE_16}, .value = ctsId};
static constexpr ble_uuid16_t ctChrUuid {
.u { .type = BLE_UUID_TYPE_16 },
.value = ctsCharId
};
static constexpr ble_uuid16_t ctChrUuid {.u {.type = BLE_UUID_TYPE_16}, .value = ctsCharId};
struct ble_gatt_chr_def characteristicDefinition[2];
struct ble_gatt_svc_def serviceDefinition[2];

@ -10,7 +10,6 @@ constexpr ble_uuid16_t DeviceInformationService::deviceInfoUuid;
constexpr ble_uuid16_t DeviceInformationService::hwRevisionUuid;
constexpr ble_uuid16_t DeviceInformationService::swRevisionUuid;
int DeviceInformationCallback(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt, void* arg) {
auto deviceInformationService = static_cast<DeviceInformationService*>(arg);
return deviceInformationService->OnDeviceInfoRequested(conn_handle, attr_handle, ctxt);
@ -25,9 +24,7 @@ void DeviceInformationService::Init() {
ASSERT(res == 0);
}
int DeviceInformationService::OnDeviceInfoRequested(uint16_t conn_handle, uint16_t attr_handle,
struct ble_gatt_access_ctxt *ctxt) {
int DeviceInformationService::OnDeviceInfoRequested(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt) {
const char* str;
switch (ble_uuid_u16(ctxt->chr->uuid)) {
@ -57,9 +54,8 @@ int DeviceInformationService::OnDeviceInfoRequested(uint16_t conn_handle, uint16
return (res == 0) ? 0 : BLE_ATT_ERR_INSUFFICIENT_RES;
}
DeviceInformationService::DeviceInformationService() :
characteristicDefinition{
{
DeviceInformationService::DeviceInformationService()
: characteristicDefinition {{
.uuid = (ble_uuid_t*) &manufacturerNameUuid,
.access_cb = DeviceInformationCallback,
.arg = this,
@ -95,22 +91,12 @@ DeviceInformationService::DeviceInformationService() :
.arg = this,
.flags = BLE_GATT_CHR_F_READ,
},
{
0
}
},
{0}},
serviceDefinition {
{
/* Device Information Service */
{/* Device Information Service */
.type = BLE_GATT_SVC_TYPE_PRIMARY,
.uuid = (ble_uuid_t*) &deviceInfoUuid,
.characteristics = characteristicDefinition
},
{
0
},
.characteristics = characteristicDefinition},
{0},
} {
}
{
}

@ -13,8 +13,7 @@ namespace Pinetime {
DeviceInformationService();
void Init();
int OnDeviceInfoRequested(uint16_t conn_handle, uint16_t attr_handle,
struct ble_gatt_access_ctxt *ctxt);
int OnDeviceInfoRequested(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt);
private:
static constexpr uint16_t deviceInfoId {0x180a};
@ -32,46 +31,22 @@ namespace Pinetime {
static constexpr const char* fwRevision = Version::VersionString();
static constexpr const char* swRevision = "InfiniTime";
static constexpr ble_uuid16_t deviceInfoUuid {.u {.type = BLE_UUID_TYPE_16}, .value = deviceInfoId};
static constexpr ble_uuid16_t deviceInfoUuid {
.u { .type = BLE_UUID_TYPE_16 },
.value = deviceInfoId
};
static constexpr ble_uuid16_t manufacturerNameUuid {.u {.type = BLE_UUID_TYPE_16}, .value = manufacturerNameId};
static constexpr ble_uuid16_t manufacturerNameUuid {
.u { .type = BLE_UUID_TYPE_16 },
.value = manufacturerNameId
};
static constexpr ble_uuid16_t modelNumberUuid {.u {.type = BLE_UUID_TYPE_16}, .value = modelNumberId};
static constexpr ble_uuid16_t modelNumberUuid {
.u { .type = BLE_UUID_TYPE_16 },
.value = modelNumberId
};
static constexpr ble_uuid16_t serialNumberUuid {.u {.type = BLE_UUID_TYPE_16}, .value = serialNumberId};
static constexpr ble_uuid16_t serialNumberUuid {
.u { .type = BLE_UUID_TYPE_16 },
.value = serialNumberId
};
static constexpr ble_uuid16_t fwRevisionUuid {.u {.type = BLE_UUID_TYPE_16}, .value = fwRevisionId};
static constexpr ble_uuid16_t fwRevisionUuid {
.u { .type = BLE_UUID_TYPE_16 },
.value = fwRevisionId
};
static constexpr ble_uuid16_t hwRevisionUuid {.u {.type = BLE_UUID_TYPE_16}, .value = hwRevisionId};
static constexpr ble_uuid16_t hwRevisionUuid {
.u {.type = BLE_UUID_TYPE_16},
.value = hwRevisionId
};
static constexpr ble_uuid16_t swRevisionUuid {
.u {.type = BLE_UUID_TYPE_16},
.value = swRevisionId
};
static constexpr ble_uuid16_t swRevisionUuid {.u {.type = BLE_UUID_TYPE_16}, .value = swRevisionId};
struct ble_gatt_chr_def characteristicDefinition[7];
struct ble_gatt_svc_def serviceDefinition[2];
};
}
}

@ -11,8 +11,7 @@ constexpr ble_uuid128_t DfuService::controlPointCharacteristicUuid;
constexpr ble_uuid128_t DfuService::revisionCharacteristicUuid;
constexpr ble_uuid128_t DfuService::packetCharacteristicUuid;
int DfuServiceCallback(uint16_t conn_handle, uint16_t attr_handle,
struct ble_gatt_access_ctxt *ctxt, void *arg) {
int DfuServiceCallback(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt, void* arg) {
auto dfuService = static_cast<DfuService*>(arg);
return dfuService->OnServiceData(conn_handle, attr_handle, ctxt);
}
@ -27,13 +26,13 @@ void TimeoutTimerCallback(TimerHandle_t xTimer) {
dfuService->OnTimeout();
}
DfuService::DfuService(Pinetime::System::SystemTask &systemTask, Pinetime::Controllers::Ble &bleController,
Pinetime::Drivers::SpiNorFlash &spiNorFlash) :
systemTask{systemTask},
DfuService::DfuService(Pinetime::System::SystemTask& systemTask,
Pinetime::Controllers::Ble& bleController,
Pinetime::Drivers::SpiNorFlash& spiNorFlash)
: systemTask {systemTask},
bleController {bleController},
dfuImage {spiNorFlash},
characteristicDefinition{
{
characteristicDefinition {{
.uuid = (ble_uuid_t*) &packetCharacteristicUuid,
.access_cb = DfuServiceCallback,
.arg = this,
@ -55,21 +54,15 @@ DfuService::DfuService(Pinetime::System::SystemTask &systemTask, Pinetime::Contr
.val_handle = &revision,
},
{
0
}
{0}
},
serviceDefinition {
{
/* Device Information Service */
{/* Device Information Service */
.type = BLE_GATT_SVC_TYPE_PRIMARY,
.uuid = (ble_uuid_t*) &serviceUuid,
.characteristics = characteristicDefinition
},
{
0
},
.characteristics = characteristicDefinition},
{0},
} {
timeoutTimer = xTimerCreate("notificationTimer", 10000, pdFALSE, this, TimeoutTimerCallback);
}
@ -88,26 +81,25 @@ int DfuService::OnServiceData(uint16_t connectionHandle, uint16_t attributeHandl
xTimerStart(timeoutTimer, 0);
}
ble_gatts_find_chr((ble_uuid_t *) &serviceUuid, (ble_uuid_t *) &packetCharacteristicUuid, nullptr,
&packetCharacteristicHandle);
ble_gatts_find_chr((ble_uuid_t *) &serviceUuid, (ble_uuid_t *) &controlPointCharacteristicUuid, nullptr,
&controlPointCharacteristicHandle);
ble_gatts_find_chr((ble_uuid_t *) &serviceUuid, (ble_uuid_t *) &revisionCharacteristicUuid, nullptr,
&revisionCharacteristicHandle);
ble_gatts_find_chr((ble_uuid_t*) &serviceUuid, (ble_uuid_t*) &packetCharacteristicUuid, nullptr, &packetCharacteristicHandle);
ble_gatts_find_chr((ble_uuid_t*) &serviceUuid, (ble_uuid_t*) &controlPointCharacteristicUuid, nullptr, &controlPointCharacteristicHandle);
ble_gatts_find_chr((ble_uuid_t*) &serviceUuid, (ble_uuid_t*) &revisionCharacteristicUuid, nullptr, &revisionCharacteristicHandle);
if (attributeHandle == packetCharacteristicHandle) {
if (context->op == BLE_GATT_ACCESS_OP_WRITE_CHR)
return WritePacketHandler(connectionHandle, context->om);
else return 0;
else
return 0;
} else if (attributeHandle == controlPointCharacteristicHandle) {
if (context->op == BLE_GATT_ACCESS_OP_WRITE_CHR)
return ControlPointHandler(connectionHandle, context->om);
else return 0;
else
return 0;
} else if (attributeHandle == revisionCharacteristicHandle) {
if (context->op == BLE_GATT_ACCESS_OP_READ_CHR)
return SendDfuRevision(context->om);
else return 0;
else
return 0;
} else {
NRF_LOG_INFO("[DFU] Unknown Characteristic : %d", attributeHandle);
return 0;
@ -126,8 +118,8 @@ int DfuService::WritePacketHandler(uint16_t connectionHandle, os_mbuf *om) {
bootloaderSize = om->om_data[4] + (om->om_data[5] << 8) + (om->om_data[6] << 16) + (om->om_data[7] << 24);
applicationSize = om->om_data[8] + (om->om_data[9] << 8) + (om->om_data[10] << 16) + (om->om_data[11] << 24);
bleController.FirmwareUpdateTotalBytes(applicationSize);
NRF_LOG_INFO("[DFU] -> Start data received : SD size : %d, BT size : %d, app size : %d", softdeviceSize,
bootloaderSize, applicationSize);
NRF_LOG_INFO(
"[DFU] -> Start data received : SD size : %d, BT size : %d, app size : %d", softdeviceSize, bootloaderSize, applicationSize);
dfuImage.Erase();
@ -139,19 +131,22 @@ int DfuService::WritePacketHandler(uint16_t connectionHandle, os_mbuf *om) {
case States::Init: {
uint16_t deviceType = om->om_data[0] + (om->om_data[1] << 8);
uint16_t deviceRevision = om->om_data[2] + (om->om_data[3] << 8);
uint32_t applicationVersion =
om->om_data[4] + (om->om_data[5] << 8) + (om->om_data[6] << 16) + (om->om_data[7] << 24);
uint32_t applicationVersion = om->om_data[4] + (om->om_data[5] << 8) + (om->om_data[6] << 16) + (om->om_data[7] << 24);
uint16_t softdeviceArrayLength = om->om_data[8] + (om->om_data[9] << 8);
uint16_t sd[softdeviceArrayLength];
for (int i = 0; i < softdeviceArrayLength; i++) {
sd[i] = om->om_data[10 + (i * 2)] + (om->om_data[10 + (i * 2) + 1] << 8);
}
expectedCrc =
om->om_data[10 + (softdeviceArrayLength * 2)] + (om->om_data[10 + (softdeviceArrayLength * 2) + 1] << 8);
expectedCrc = om->om_data[10 + (softdeviceArrayLength * 2)] + (om->om_data[10 + (softdeviceArrayLength * 2) + 1] << 8);
NRF_LOG_INFO(
"[DFU] -> Init data received : deviceType = %d, deviceRevision = %d, applicationVersion = %d, nb SD = %d, First SD = %d, CRC = %u",
deviceType, deviceRevision, applicationVersion, softdeviceArrayLength, sd[0], expectedCrc);
deviceType,
deviceRevision,
applicationVersion,
softdeviceArrayLength,
sd[0],
expectedCrc);
return 0;
}
@ -164,8 +159,10 @@ int DfuService::WritePacketHandler(uint16_t connectionHandle, os_mbuf *om) {
if ((nbPacketReceived % nbPacketsToNotify) == 0 && bytesReceived != applicationSize) {
uint8_t data[5] {static_cast<uint8_t>(Opcodes::PacketReceiptNotification),
(uint8_t) (bytesReceived & 0x000000FFu), (uint8_t) (bytesReceived >> 8u),
(uint8_t) (bytesReceived >> 16u), (uint8_t) (bytesReceived >> 24u)};
(uint8_t) (bytesReceived & 0x000000FFu),
(uint8_t) (bytesReceived >> 8u),
(uint8_t) (bytesReceived >> 16u),
(uint8_t) (bytesReceived >> 24u)};
NRF_LOG_INFO("[DFU] -> Send packet notification: %d bytes received", bytesReceived);
notificationManager.Send(connectionHandle, controlPointCharacteristicHandle, data, 5);
}
@ -214,8 +211,7 @@ int DfuService::ControlPointHandler(uint16_t connectionHandle, os_mbuf *om) {
NRF_LOG_INFO("[DFU] -> Start DFU, mode %d not supported!", imageType);
return 0;
}
}
break;
} break;
case Opcodes::InitDFUParameters: {
if (state != States::Init) {
NRF_LOG_INFO("[DFU] -> Init DFU requested, but we are not in Init state");
@ -225,11 +221,9 @@ int DfuService::ControlPointHandler(uint16_t connectionHandle, os_mbuf *om) {
NRF_LOG_INFO("[DFU] -> Init DFU parameters %s", isInitComplete ? " complete" : " not complete");
if (isInitComplete) {
uint8_t data[3] {
static_cast<uint8_t>(Opcodes::Response),
uint8_t data[3] {static_cast<uint8_t>(Opcodes::Response),
static_cast<uint8_t>(Opcodes::InitDFUParameters),
(isInitComplete ? uint8_t{1} : uint8_t{0})
};
(isInitComplete ? uint8_t {1} : uint8_t {0})};
notificationManager.AsyncSend(connectionHandle, controlPointCharacteristicHandle, data, 3);
return 0;
}
@ -262,21 +256,17 @@ int DfuService::ControlPointHandler(uint16_t connectionHandle, os_mbuf *om) {
bleController.State(Pinetime::Controllers::Ble::FirmwareUpdateStates::Validated);
NRF_LOG_INFO("Image OK");
uint8_t data[3] {
static_cast<uint8_t>(Opcodes::Response),
uint8_t data[3] {static_cast<uint8_t>(Opcodes::Response),
static_cast<uint8_t>(Opcodes::ValidateFirmware),
static_cast<uint8_t>(ErrorCodes::NoError)
};
static_cast<uint8_t>(ErrorCodes::NoError)};
notificationManager.AsyncSend(connectionHandle, controlPointCharacteristicHandle, data, 3);
} else {
bleController.State(Pinetime::Controllers::Ble::FirmwareUpdateStates::Error);
NRF_LOG_INFO("Image Error : bad CRC");
uint8_t data[3] {
static_cast<uint8_t>(Opcodes::Response),
uint8_t data[3] {static_cast<uint8_t>(Opcodes::Response),
static_cast<uint8_t>(Opcodes::ValidateFirmware),
static_cast<uint8_t>(ErrorCodes::CrcError)
};
static_cast<uint8_t>(ErrorCodes::CrcError)};
notificationManager.AsyncSend(connectionHandle, controlPointCharacteristicHandle, data, 3);
}
@ -354,7 +344,8 @@ void DfuService::NotificationManager::Reset() {
}
void DfuService::DfuImage::Init(size_t chunkSize, size_t totalSize, uint16_t expectedCrc) {
if(chunkSize != 20) return;
if (chunkSize != 20)
return;
this->chunkSize = chunkSize;
this->totalSize = totalSize;
this->expectedCrc = expectedCrc;
@ -362,7 +353,8 @@ void DfuService::DfuImage::Init(size_t chunkSize, size_t totalSize, uint16_t exp
}
void DfuService::DfuImage::Append(uint8_t* data, size_t size) {
if(!ready) return;
if (!ready)
return;
ASSERT(size <= 20);
std::memcpy(tempBuffer + bufferWriteIndex, data, size);
@ -383,7 +375,8 @@ void DfuService::DfuImage::Append(uint8_t *data, size_t size) {
}
void DfuService::DfuImage::WriteMagicNumber() {
uint32_t magic[4] = { // TODO When this variable is a static constexpr, the values written to the memory are not correct. Why?
uint32_t magic[4] = {
// TODO When this variable is a static constexpr, the values written to the memory are not correct. Why?
0xf395c277,
0x7fefd260,
0x0f505235,
@ -436,6 +429,7 @@ uint16_t DfuService::DfuImage::ComputeCrc(uint8_t const *p_data, uint32_t size,
}
bool DfuService::DfuImage::IsComplete() {
if(!ready) return false;
if (!ready)
return false;
return totalWriteIndex == totalSize;
}

@ -21,7 +21,8 @@ namespace Pinetime {
class DfuService {
public:
DfuService(Pinetime::System::SystemTask &systemTask, Pinetime::Controllers::Ble &bleController,
DfuService(Pinetime::System::SystemTask& systemTask,
Pinetime::Controllers::Ble& bleController,
Pinetime::Drivers::SpiNorFlash& spiNorFlash);
void Init();
int OnServiceData(uint16_t connectionHandle, uint16_t attributeHandle, ble_gatt_access_ctxt* context);
@ -33,19 +34,22 @@ namespace Pinetime {
NotificationManager();
bool AsyncSend(uint16_t connection, uint16_t charactHandle, uint8_t* data, size_t size);
void Send(uint16_t connection, uint16_t characteristicHandle, const uint8_t* data, const size_t s);
private:
TimerHandle_t timer;
uint16_t connectionHandle = 0;
uint16_t characteristicHandle = 0;
size_t size = 0;
uint8_t buffer[10];
public:
void OnNotificationTimer();
void Reset();
};
class DfuImage {
public:
DfuImage(Pinetime::Drivers::SpiNorFlash& spiNorFlash) : spiNorFlash{spiNorFlash} {}
DfuImage(Pinetime::Drivers::SpiNorFlash& spiNorFlash) : spiNorFlash {spiNorFlash} {
}
void Init(size_t chunkSize, size_t totalSize, uint16_t expectedCrc);
void Erase();
void Append(uint8_t* data, size_t size);
@ -67,7 +71,6 @@ namespace Pinetime {
void WriteMagicNumber();
uint16_t ComputeCrc(uint8_t const* p_data, uint32_t size, uint16_t const* p_crc);
};
private:
@ -85,27 +88,19 @@ namespace Pinetime {
static constexpr ble_uuid128_t serviceUuid {
.u {.type = BLE_UUID_TYPE_128},
.value = {0x23, 0xD1, 0xBC, 0xEA, 0x5F, 0x78, 0x23, 0x15,
0xDE, 0xEF, 0x12, 0x12, 0x30, 0x15, 0x00, 0x00}
};
.value = {0x23, 0xD1, 0xBC, 0xEA, 0x5F, 0x78, 0x23, 0x15, 0xDE, 0xEF, 0x12, 0x12, 0x30, 0x15, 0x00, 0x00}};
static constexpr ble_uuid128_t packetCharacteristicUuid {
.u {.type = BLE_UUID_TYPE_128},
.value = {0x23, 0xD1, 0xBC, 0xEA, 0x5F, 0x78, 0x23, 0x15,
0xDE, 0xEF, 0x12, 0x12, 0x32, 0x15, 0x00, 0x00}
};
.value = {0x23, 0xD1, 0xBC, 0xEA, 0x5F, 0x78, 0x23, 0x15, 0xDE, 0xEF, 0x12, 0x12, 0x32, 0x15, 0x00, 0x00}};
static constexpr ble_uuid128_t controlPointCharacteristicUuid {
.u {.type = BLE_UUID_TYPE_128},
.value = {0x23, 0xD1, 0xBC, 0xEA, 0x5F, 0x78, 0x23, 0x15,
0xDE, 0xEF, 0x12, 0x12, 0x31, 0x15, 0x00, 0x00}
};
.value = {0x23, 0xD1, 0xBC, 0xEA, 0x5F, 0x78, 0x23, 0x15, 0xDE, 0xEF, 0x12, 0x12, 0x31, 0x15, 0x00, 0x00}};
static constexpr ble_uuid128_t revisionCharacteristicUuid {
.u {.type = BLE_UUID_TYPE_128},
.value = {0x23, 0xD1, 0xBC, 0xEA, 0x5F, 0x78, 0x23, 0x15,
0xDE, 0xEF, 0x12, 0x12, 0x34, 0x15, 0x00, 0x00}
};
.value = {0x23, 0xD1, 0xBC, 0xEA, 0x5F, 0x78, 0x23, 0x15, 0xDE, 0xEF, 0x12, 0x12, 0x34, 0x15, 0x00, 0x00}};
struct ble_gatt_chr_def characteristicDefinition[4];
struct ble_gatt_svc_def serviceDefinition[2];
@ -113,9 +108,7 @@ namespace Pinetime {
uint16_t controlPointCharacteristicHandle;
uint16_t revisionCharacteristicHandle;
enum class States : uint8_t {
Idle, Init, Start, Data, Validate, Validated
};
enum class States : uint8_t { Idle, Init, Start, Data, Validate, Validated };
States state = States::Idle;
enum class ImageTypes : uint8_t {

@ -15,31 +15,21 @@ namespace {
}
// TODO Refactoring - remove dependency to SystemTask
HeartRateService::HeartRateService(Pinetime::System::SystemTask &system, Controllers::HeartRateController& heartRateController) :
system{system},
HeartRateService::HeartRateService(Pinetime::System::SystemTask& system, Controllers::HeartRateController& heartRateController)
: system {system},
heartRateController {heartRateController},
characteristicDefinition{
{
.uuid = (ble_uuid_t *) &heartRateMeasurementUuid,
characteristicDefinition {{.uuid = (ble_uuid_t*) &heartRateMeasurementUuid,
.access_cb = HeartRateServiceServiceCallback,
.arg = this,
.flags = BLE_GATT_CHR_F_READ | BLE_GATT_CHR_F_NOTIFY,
.val_handle = &heartRateMeasurementHandle
},
{
0
}
},
.val_handle = &heartRateMeasurementHandle},
{0}},
serviceDefinition {
{
/* Device Information Service */
{/* Device Information Service */
.type = BLE_GATT_SVC_TYPE_PRIMARY,
.uuid = (ble_uuid_t*) &heartRateServiceUuid,
.characteristics = characteristicDefinition
},
{
0
},
.characteristics = characteristicDefinition},
{0},
} {
// TODO refactor to prevent this loop dependency (service depends on controller and controller depends on service)
heartRateController.SetService(this);
@ -54,8 +44,7 @@ void HeartRateService::Init() {
ASSERT(res == 0);
}
int HeartRateService::OnHeartRateRequested(uint16_t connectionHandle, uint16_t attributeHandle,
ble_gatt_access_ctxt *context) {
int HeartRateService::OnHeartRateRequested(uint16_t connectionHandle, uint16_t attributeHandle, ble_gatt_access_ctxt* context) {
if (attributeHandle == heartRateMeasurementHandle) {
NRF_LOG_INFO("HEARTRATE : handle = %d", heartRateMeasurementHandle);
uint8_t buffer[2] = {0, heartRateController.HeartRate()}; // [0] = flags, [1] = hr value

@ -24,21 +24,14 @@ namespace Pinetime {
static constexpr uint16_t heartRateServiceId {0x180D};
static constexpr uint16_t heartRateMeasurementId {0x2A37};
static constexpr ble_uuid16_t heartRateServiceUuid {
.u {.type = BLE_UUID_TYPE_16},
.value = heartRateServiceId
};
static constexpr ble_uuid16_t heartRateServiceUuid {.u {.type = BLE_UUID_TYPE_16}, .value = heartRateServiceId};
static constexpr ble_uuid16_t heartRateMeasurementUuid {
.u {.type = BLE_UUID_TYPE_16},
.value = heartRateMeasurementId
};
static constexpr ble_uuid16_t heartRateMeasurementUuid {.u {.type = BLE_UUID_TYPE_16}, .value = heartRateMeasurementId};
struct ble_gatt_chr_def characteristicDefinition[3];
struct ble_gatt_svc_def serviceDefinition[2];
uint16_t heartRateMeasurementHandle;
};
}
}

@ -16,42 +16,35 @@ namespace {
const char* ToString(ImmediateAlertService::Levels level) {
switch (level) {
case ImmediateAlertService::Levels::NoAlert: return "Alert : None";
case ImmediateAlertService::Levels::HighAlert: return "Alert : High";
case ImmediateAlertService::Levels::MildAlert: return "Alert : Mild";
default: return "";
case ImmediateAlertService::Levels::NoAlert:
return "Alert : None";
case ImmediateAlertService::Levels::HighAlert:
return "Alert : High";
case ImmediateAlertService::Levels::MildAlert:
return "Alert : Mild";
default:
return "";
}
}
}
ImmediateAlertService::ImmediateAlertService(Pinetime::System::SystemTask& systemTask,
Pinetime::Controllers::NotificationManager &notificationManager) :
systemTask{systemTask},
Pinetime::Controllers::NotificationManager& notificationManager)
: systemTask {systemTask},
notificationManager {notificationManager},
characteristicDefinition{
{
.uuid = (ble_uuid_t *) &alertLevelUuid,
characteristicDefinition {{.uuid = (ble_uuid_t*) &alertLevelUuid,
.access_cb = AlertLevelCallback,
.arg = this,
.flags = BLE_GATT_CHR_F_WRITE_NO_RSP,
.val_handle = &alertLevelHandle
},
{
0
}
},
.val_handle = &alertLevelHandle},
{0}},
serviceDefinition {
{
/* Device Information Service */
{/* Device Information Service */
.type = BLE_GATT_SVC_TYPE_PRIMARY,
.uuid = (ble_uuid_t*) &immediateAlertServiceUuid,
.characteristics = characteristicDefinition
},
{
0
},
.characteristics = characteristicDefinition},
{0},
} {
}
void ImmediateAlertService::Init() {

@ -13,14 +13,9 @@ namespace Pinetime {
class NotificationManager;
class ImmediateAlertService {
public:
enum class Levels : uint8_t {
NoAlert = 0,
MildAlert = 1,
HighAlert = 2
};
enum class Levels : uint8_t { NoAlert = 0, MildAlert = 1, HighAlert = 2 };
ImmediateAlertService(Pinetime::System::SystemTask &systemTask,
Pinetime::Controllers::NotificationManager &notificationManager);
ImmediateAlertService(Pinetime::System::SystemTask& systemTask, Pinetime::Controllers::NotificationManager& notificationManager);
void Init();
int OnAlertLevelChanged(uint16_t connectionHandle, uint16_t attributeHandle, ble_gatt_access_ctxt* context);
@ -31,15 +26,9 @@ namespace Pinetime {
static constexpr uint16_t immediateAlertServiceId {0x1802};
static constexpr uint16_t alertLevelId {0x2A06};
static constexpr ble_uuid16_t immediateAlertServiceUuid {
.u {.type = BLE_UUID_TYPE_16},
.value = immediateAlertServiceId
};
static constexpr ble_uuid16_t immediateAlertServiceUuid {.u {.type = BLE_UUID_TYPE_16}, .value = immediateAlertServiceId};
static constexpr ble_uuid16_t alertLevelUuid {
.u {.type = BLE_UUID_TYPE_16},
.value = alertLevelId
};
static constexpr ble_uuid16_t alertLevelUuid {.u {.type = BLE_UUID_TYPE_16}, .value = alertLevelId};
struct ble_gatt_chr_def characteristicDefinition[3];
struct ble_gatt_svc_def serviceDefinition[2];

@ -91,75 +91,44 @@ Pinetime::Controllers::MusicService::MusicService(Pinetime::System::SystemTask &
.access_cb = MSCallback,
.arg = this,
.flags = BLE_GATT_CHR_F_NOTIFY,
.val_handle = &eventHandle
};
characteristicDefinition[1] = {.uuid = (ble_uuid_t *) (&msStatusCharUuid),
.access_cb = MSCallback,
.arg = this,
.flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ
};
characteristicDefinition[2] = {.uuid = (ble_uuid_t *) (&msTrackCharUuid),
.access_cb = MSCallback,
.arg = this,
.flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ
};
characteristicDefinition[3] = {.uuid = (ble_uuid_t *) (&msArtistCharUuid),
.access_cb = MSCallback,
.arg = this,
.flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ
};
characteristicDefinition[4] = {.uuid = (ble_uuid_t *) (&msAlbumCharUuid),
.access_cb = MSCallback,
.arg = this,
.flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ
};
characteristicDefinition[5] = {.uuid = (ble_uuid_t *) (&msPositionCharUuid),
.access_cb = MSCallback,
.arg = this,
.flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ
};
.val_handle = &eventHandle};
characteristicDefinition[1] = {
.uuid = (ble_uuid_t*) (&msStatusCharUuid), .access_cb = MSCallback, .arg = this, .flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ};
characteristicDefinition[2] = {
.uuid = (ble_uuid_t*) (&msTrackCharUuid), .access_cb = MSCallback, .arg = this, .flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ};
characteristicDefinition[3] = {
.uuid = (ble_uuid_t*) (&msArtistCharUuid), .access_cb = MSCallback, .arg = this, .flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ};
characteristicDefinition[4] = {
.uuid = (ble_uuid_t*) (&msAlbumCharUuid), .access_cb = MSCallback, .arg = this, .flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ};
characteristicDefinition[5] = {
.uuid = (ble_uuid_t*) (&msPositionCharUuid), .access_cb = MSCallback, .arg = this, .flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ};
characteristicDefinition[6] = {.uuid = (ble_uuid_t*) (&msTotalLengthCharUuid),
.access_cb = MSCallback,
.arg = this,
.flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ
};
.flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ};
characteristicDefinition[7] = {.uuid = (ble_uuid_t*) (&msTotalLengthCharUuid),
.access_cb = MSCallback,
.arg = this,
.flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ
};
.flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ};
characteristicDefinition[8] = {.uuid = (ble_uuid_t*) (&msTrackNumberCharUuid),
.access_cb = MSCallback,
.arg = this,
.flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ
};
.flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ};
characteristicDefinition[9] = {.uuid = (ble_uuid_t*) (&msTrackTotalCharUuid),
.access_cb = MSCallback,
.arg = this,
.flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ
};
.flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ};
characteristicDefinition[10] = {.uuid = (ble_uuid_t*) (&msPlaybackSpeedCharUuid),
.access_cb = MSCallback,
.arg = this,
.flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ
};
characteristicDefinition[11] = {.uuid = (ble_uuid_t *) (&msRepeatCharUuid),
.access_cb = MSCallback,
.arg = this,
.flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ
};
characteristicDefinition[12] = {.uuid = (ble_uuid_t *) (&msShuffleCharUuid),
.access_cb = MSCallback,
.arg = this,
.flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ
};
.flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ};
characteristicDefinition[11] = {
.uuid = (ble_uuid_t*) (&msRepeatCharUuid), .access_cb = MSCallback, .arg = this, .flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ};
characteristicDefinition[12] = {
.uuid = (ble_uuid_t*) (&msShuffleCharUuid), .access_cb = MSCallback, .arg = this, .flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ};
characteristicDefinition[13] = {0};
serviceDefinition[0] = {
.type = BLE_GATT_SVC_TYPE_PRIMARY,
.uuid = (ble_uuid_t *) &msUuid,
.characteristics = characteristicDefinition
};
serviceDefinition[0] = {.type = BLE_GATT_SVC_TYPE_PRIMARY, .uuid = (ble_uuid_t*) &msUuid, .characteristics = characteristicDefinition};
serviceDefinition[1] = {0};
artistName = "Waiting for";
@ -182,8 +151,7 @@ void Pinetime::Controllers::MusicService::Init() {
ASSERT(res == 0);
}
int Pinetime::Controllers::MusicService::OnCommand(uint16_t conn_handle, uint16_t attr_handle,
struct ble_gatt_access_ctxt *ctxt) {
int Pinetime::Controllers::MusicService::OnCommand(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt) {
if (ctxt->op == BLE_GATT_ACCESS_OP_WRITE_CHR) {
size_t notifSize = OS_MBUF_PKTLEN(ctxt->om);
@ -257,4 +225,3 @@ int Pinetime::Controllers::MusicService::getProgress() {
int Pinetime::Controllers::MusicService::getTrackLength() {
return trackLength;
}

@ -27,7 +27,8 @@
#undef min
// 00000000-78fc-48fe-8e23-433b3a1942d0
#define MUSIC_SERVICE_UUID_BASE {0xd0, 0x42, 0x19, 0x3a, 0x3b, 0x43, 0x23, 0x8e, 0xfe, 0x48, 0xfc, 0x78, 0x00, 0x00, 0x00, 0x00}
#define MUSIC_SERVICE_UUID_BASE \
{ 0xd0, 0x42, 0x19, 0x3a, 0x3b, 0x43, 0x23, 0x8e, 0xfe, 0x48, 0xfc, 0x78, 0x00, 0x00, 0x00, 0x00 }
namespace Pinetime {
namespace System {
@ -41,8 +42,7 @@ namespace Pinetime {
void Init();
int OnCommand(uint16_t conn_handle, uint16_t attr_handle,
struct ble_gatt_access_ctxt *ctxt);
int OnCommand(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt);
void event(char event);
@ -68,10 +68,8 @@ namespace Pinetime {
static const char EVENT_MUSIC_VOLUP = 0x05;
static const char EVENT_MUSIC_VOLDOWN = 0x06;
enum MusicStatus {
NotPlaying = 0x00,
Playing = 0x01
};
enum MusicStatus { NotPlaying = 0x00, Playing = 0x01 };
private:
static constexpr uint8_t msId[2] = {0x00, 0x00};
static constexpr uint8_t msEventCharId[2] = {0x01, 0x00};
@ -87,59 +85,20 @@ namespace Pinetime {
static constexpr uint8_t msRepeatCharId[2] = {0x0b, 0x00};
static constexpr uint8_t msShuffleCharId[2] = {0x0c, 0x00};
ble_uuid128_t msUuid{
.u = {.type = BLE_UUID_TYPE_128},
.value = MUSIC_SERVICE_UUID_BASE
};
ble_uuid128_t msUuid {.u = {.type = BLE_UUID_TYPE_128}, .value = MUSIC_SERVICE_UUID_BASE};
ble_uuid128_t msEventCharUuid{
.u = {.type = BLE_UUID_TYPE_128},
.value = MUSIC_SERVICE_UUID_BASE
};
ble_uuid128_t msStatusCharUuid{
.u = {.type = BLE_UUID_TYPE_128},
.value = MUSIC_SERVICE_UUID_BASE
};
ble_uuid128_t msArtistCharUuid{
.u = {.type = BLE_UUID_TYPE_128},
.value = MUSIC_SERVICE_UUID_BASE
};
ble_uuid128_t msTrackCharUuid{
.u = {.type = BLE_UUID_TYPE_128},
.value = MUSIC_SERVICE_UUID_BASE
};
ble_uuid128_t msAlbumCharUuid{
.u = {.type = BLE_UUID_TYPE_128},
.value = MUSIC_SERVICE_UUID_BASE
};
ble_uuid128_t msPositionCharUuid{
.u = {.type = BLE_UUID_TYPE_128},
.value = MUSIC_SERVICE_UUID_BASE
};
ble_uuid128_t msTotalLengthCharUuid{
.u = {.type = BLE_UUID_TYPE_128},
.value = MUSIC_SERVICE_UUID_BASE
};
ble_uuid128_t msTrackNumberCharUuid{
.u = {.type = BLE_UUID_TYPE_128},
.value = MUSIC_SERVICE_UUID_BASE
};
ble_uuid128_t msTrackTotalCharUuid{
.u = {.type = BLE_UUID_TYPE_128},
.value = MUSIC_SERVICE_UUID_BASE
};
ble_uuid128_t msPlaybackSpeedCharUuid{
.u = {.type = BLE_UUID_TYPE_128},
.value = MUSIC_SERVICE_UUID_BASE
};
ble_uuid128_t msRepeatCharUuid{
.u = {.type = BLE_UUID_TYPE_128},
.value = MUSIC_SERVICE_UUID_BASE
};
ble_uuid128_t msShuffleCharUuid{
.u = {.type = BLE_UUID_TYPE_128},
.value = MUSIC_SERVICE_UUID_BASE
};
ble_uuid128_t msEventCharUuid {.u = {.type = BLE_UUID_TYPE_128}, .value = MUSIC_SERVICE_UUID_BASE};
ble_uuid128_t msStatusCharUuid {.u = {.type = BLE_UUID_TYPE_128}, .value = MUSIC_SERVICE_UUID_BASE};
ble_uuid128_t msArtistCharUuid {.u = {.type = BLE_UUID_TYPE_128}, .value = MUSIC_SERVICE_UUID_BASE};
ble_uuid128_t msTrackCharUuid {.u = {.type = BLE_UUID_TYPE_128}, .value = MUSIC_SERVICE_UUID_BASE};
ble_uuid128_t msAlbumCharUuid {.u = {.type = BLE_UUID_TYPE_128}, .value = MUSIC_SERVICE_UUID_BASE};
ble_uuid128_t msPositionCharUuid {.u = {.type = BLE_UUID_TYPE_128}, .value = MUSIC_SERVICE_UUID_BASE};
ble_uuid128_t msTotalLengthCharUuid {.u = {.type = BLE_UUID_TYPE_128}, .value = MUSIC_SERVICE_UUID_BASE};
ble_uuid128_t msTrackNumberCharUuid {.u = {.type = BLE_UUID_TYPE_128}, .value = MUSIC_SERVICE_UUID_BASE};
ble_uuid128_t msTrackTotalCharUuid {.u = {.type = BLE_UUID_TYPE_128}, .value = MUSIC_SERVICE_UUID_BASE};
ble_uuid128_t msPlaybackSpeedCharUuid {.u = {.type = BLE_UUID_TYPE_128}, .value = MUSIC_SERVICE_UUID_BASE};
ble_uuid128_t msRepeatCharUuid {.u = {.type = BLE_UUID_TYPE_128}, .value = MUSIC_SERVICE_UUID_BASE};
ble_uuid128_t msShuffleCharUuid {.u = {.type = BLE_UUID_TYPE_128}, .value = MUSIC_SERVICE_UUID_BASE};
struct ble_gatt_chr_def characteristicDefinition[14];
struct ble_gatt_svc_def serviceDefinition[2];
@ -166,4 +125,3 @@ namespace Pinetime {
};
}
}

@ -49,35 +49,25 @@ Pinetime::Controllers::NavigationService::NavigationService(Pinetime::System::Sy
navProgressCharUuid.value[14] = navId[0];
navProgressCharUuid.value[15] = navId[1];
characteristicDefinition[0] = {.uuid = (ble_uuid_t *) (&navFlagCharUuid),
.access_cb = NAVCallback,
.arg = this,
.flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ
};
characteristicDefinition[0] = {
.uuid = (ble_uuid_t*) (&navFlagCharUuid), .access_cb = NAVCallback, .arg = this, .flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ};
characteristicDefinition[1] = {.uuid = (ble_uuid_t*) (&navNarrativeCharUuid),
.access_cb = NAVCallback,
.arg = this,
.flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ
};
.flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ};
characteristicDefinition[2] = {.uuid = (ble_uuid_t*) (&navManDistCharUuid),
.access_cb = NAVCallback,
.arg = this,
.flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ
};
.flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ};
characteristicDefinition[3] = {.uuid = (ble_uuid_t*) (&navProgressCharUuid),
.access_cb = NAVCallback,
.arg = this,
.flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ
};
.flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ};
characteristicDefinition[4] = {0};
serviceDefinition[0] = {
.type = BLE_GATT_SVC_TYPE_PRIMARY,
.uuid = (ble_uuid_t *) &navUuid,
.characteristics = characteristicDefinition
};
serviceDefinition[0] = {.type = BLE_GATT_SVC_TYPE_PRIMARY, .uuid = (ble_uuid_t*) &navUuid, .characteristics = characteristicDefinition};
serviceDefinition[1] = {0};
m_progress = 0;
@ -92,8 +82,7 @@ void Pinetime::Controllers::NavigationService::Init() {
ASSERT(res == 0);
}
int Pinetime::Controllers::NavigationService::OnCommand(uint16_t conn_handle, uint16_t attr_handle,
struct ble_gatt_access_ctxt *ctxt) {
int Pinetime::Controllers::NavigationService::OnCommand(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt) {
if (ctxt->op == BLE_GATT_ACCESS_OP_WRITE_CHR) {
size_t notifSize = OS_MBUF_PKTLEN(ctxt->om);
@ -114,23 +103,18 @@ int Pinetime::Controllers::NavigationService::OnCommand(uint16_t conn_handle, ui
return 0;
}
std::string Pinetime::Controllers::NavigationService::getFlag()
{
std::string Pinetime::Controllers::NavigationService::getFlag() {
return m_flag;
}
std::string Pinetime::Controllers::NavigationService::getNarrative()
{
std::string Pinetime::Controllers::NavigationService::getNarrative() {
return m_narrative;
}
std::string Pinetime::Controllers::NavigationService::getManDist()
{
std::string Pinetime::Controllers::NavigationService::getManDist() {
return m_manDist;
}
int Pinetime::Controllers::NavigationService::getProgress()
{
int Pinetime::Controllers::NavigationService::getProgress() {
return m_progress;
}

@ -27,7 +27,8 @@
#undef min
// c7e60000-78fc-48fe-8e23-433b3a1942d0
#define NAVIGATION_SERVICE_UUID_BASE {0xd0, 0x42, 0x19, 0x3a, 0x3b, 0x43, 0x23, 0x8e, 0xfe, 0x48, 0xfc, 0x78, 0x00, 0x00, 0x00, 0x00}
#define NAVIGATION_SERVICE_UUID_BASE \
{ 0xd0, 0x42, 0x19, 0x3a, 0x3b, 0x43, 0x23, 0x8e, 0xfe, 0x48, 0xfc, 0x78, 0x00, 0x00, 0x00, 0x00 }
namespace Pinetime {
namespace System {
@ -41,8 +42,7 @@ namespace Pinetime {
void Init();
int OnCommand(uint16_t conn_handle, uint16_t attr_handle,
struct ble_gatt_access_ctxt *ctxt);
int OnCommand(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt);
std::string getFlag();
@ -59,27 +59,12 @@ namespace Pinetime {
static constexpr uint8_t navManDistCharId[2] = {0x03, 0x00};
static constexpr uint8_t navProgressCharId[2] = {0x04, 0x00};
ble_uuid128_t navUuid{
.u = {.type = BLE_UUID_TYPE_128},
.value = NAVIGATION_SERVICE_UUID_BASE
};
ble_uuid128_t navUuid {.u = {.type = BLE_UUID_TYPE_128}, .value = NAVIGATION_SERVICE_UUID_BASE};
ble_uuid128_t navFlagCharUuid{
.u = {.type = BLE_UUID_TYPE_128},
.value = NAVIGATION_SERVICE_UUID_BASE
};
ble_uuid128_t navNarrativeCharUuid{
.u = {.type = BLE_UUID_TYPE_128},
.value = NAVIGATION_SERVICE_UUID_BASE
};
ble_uuid128_t navManDistCharUuid{
.u = {.type = BLE_UUID_TYPE_128},
.value = NAVIGATION_SERVICE_UUID_BASE
};
ble_uuid128_t navProgressCharUuid{
.u = {.type = BLE_UUID_TYPE_128},
.value = NAVIGATION_SERVICE_UUID_BASE
};
ble_uuid128_t navFlagCharUuid {.u = {.type = BLE_UUID_TYPE_128}, .value = NAVIGATION_SERVICE_UUID_BASE};
ble_uuid128_t navNarrativeCharUuid {.u = {.type = BLE_UUID_TYPE_128}, .value = NAVIGATION_SERVICE_UUID_BASE};
ble_uuid128_t navManDistCharUuid {.u = {.type = BLE_UUID_TYPE_128}, .value = NAVIGATION_SERVICE_UUID_BASE};
ble_uuid128_t navProgressCharUuid {.u = {.type = BLE_UUID_TYPE_128}, .value = NAVIGATION_SERVICE_UUID_BASE};
struct ble_gatt_chr_def characteristicDefinition[5];
struct ble_gatt_svc_def serviceDefinition[2];
@ -93,4 +78,3 @@ namespace Pinetime {
};
}
}

@ -23,8 +23,8 @@ NimbleController::NimbleController(Pinetime::System::SystemTask& systemTask,
Pinetime::Controllers::NotificationManager& notificationManager,
Controllers::Battery& batteryController,
Pinetime::Drivers::SpiNorFlash& spiNorFlash,
Controllers::HeartRateController& heartRateController) :
systemTask{systemTask},
Controllers::HeartRateController& heartRateController)
: systemTask {systemTask},
bleController {bleController},
dateTimeController {dateTimeController},
notificationManager {notificationManager},
@ -48,7 +48,8 @@ int GAPEventCallback(struct ble_gap_event *event, void *arg) {
}
void NimbleController::Init() {
while (!ble_hs_synced()) {}
while (!ble_hs_synced()) {
}
ble_svc_gap_init();
ble_svc_gatt_init();
@ -81,7 +82,8 @@ void NimbleController::Init() {
}
void NimbleController::StartAdvertising() {
if(bleController.IsConnected() || ble_gap_conn_active() || ble_gap_adv_active()) return;
if (bleController.IsConnected() || ble_gap_conn_active() || ble_gap_adv_active())
return;
ble_svc_gap_device_name_set(deviceName);
@ -101,8 +103,7 @@ void NimbleController::StartAdvertising() {
adv_params.conn_mode = BLE_GAP_CONN_MODE_UND;
adv_params.disc_mode = BLE_GAP_DISC_MODE_GEN;
fields.flags = BLE_HS_ADV_F_DISC_GEN |
BLE_HS_ADV_F_BREDR_UNSUP;
fields.flags = BLE_HS_ADV_F_DISC_GEN | BLE_HS_ADV_F_BREDR_UNSUP;
// fields.uuids128 = BLE_UUID128(BLE_UUID128_DECLARE(
// 0x00, 0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77,
// 0x88, 0x99, 0xaa, 0xbb, 0xcc, 0xdd, 0xee, 0xff));
@ -121,8 +122,7 @@ void NimbleController::StartAdvertising() {
ble_gap_adv_rsp_set_fields(&rsp_fields);
// ASSERT(res == 0);
ble_gap_adv_start(addrType, NULL, 180000,
&adv_params, GAPEventCallback, this);
ble_gap_adv_start(addrType, NULL, 180000, &adv_params, GAPEventCallback, this);
// ASSERT(res == 0);// TODO I've disabled these ASSERT as they sometime asserts and reset the mcu.
// For now, the advertising is restarted as soon as it ends. There may be a race condition
// that prevent the advertising from restarting reliably.
@ -141,8 +141,7 @@ int NimbleController::OnGAPEvent(ble_gap_event *event) {
NRF_LOG_INFO("Advertising event : BLE_GAP_EVENT_CONNECT");
/* A new connection was established or a connection attempt failed. */
NRF_LOG_INFO("connection %s; status=%d ", event->connect.status == 0 ? "established" : "failed",
event->connect.status);
NRF_LOG_INFO("connection %s; status=%d ", event->connect.status == 0 ? "established" : "failed", event->connect.status);
if (event->connect.status != 0) {
/* Connection failed; resume advertising. */
@ -154,8 +153,7 @@ int NimbleController::OnGAPEvent(ble_gap_event *event) {
connectionHandle = event->connect.conn_handle;
// Service discovery is deffered via systemtask
}
}
break;
} break;
case BLE_GAP_EVENT_DISCONNECT:
NRF_LOG_INFO("Advertising event : BLE_GAP_EVENT_DISCONNECT");
NRF_LOG_INFO("disconnect; reason=%d", event->disconnect.reason);
@ -187,10 +185,7 @@ int NimbleController::OnGAPEvent(ble_gap_event *event) {
event->subscribe.prev_indicate);
return 0;
case BLE_GAP_EVENT_MTU:
NRF_LOG_INFO("mtu update event; conn_handle=%d cid=%d mtu=%d\n",
event->mtu.conn_handle,
event->mtu.channel_id,
event->mtu.value);
NRF_LOG_INFO("mtu update event; conn_handle=%d cid=%d mtu=%d\n", event->mtu.conn_handle, event->mtu.channel_id, event->mtu.value);
return 0;
case BLE_GAP_EVENT_REPEAT_PAIRING: {
@ -216,9 +211,7 @@ int NimbleController::OnGAPEvent(ble_gap_event *event) {
NRF_LOG_INFO("received %s; conn_handle=%d attr_handle=%d "
"attr_len=%d",
event->notify_rx.indication ?
"indication" :
"notification",
event->notify_rx.indication ? "indication" : "notification",
event->notify_rx.conn_handle,
event->notify_rx.attr_handle,
notifSize);
@ -239,8 +232,6 @@ void NimbleController::StartDiscovery() {
serviceDiscovery.StartDiscovery(connectionHandle);
}
uint16_t NimbleController::connHandle() {
return connectionHandle;
}

@ -37,28 +37,37 @@ namespace Pinetime {
class NimbleController {
public:
NimbleController(Pinetime::System::SystemTask& systemTask, Pinetime::Controllers::Ble& bleController,
DateTime& dateTimeController, Pinetime::Controllers::NotificationManager& notificationManager,
Controllers::Battery& batteryController, Pinetime::Drivers::SpiNorFlash& spiNorFlash,
NimbleController(Pinetime::System::SystemTask& systemTask,
Pinetime::Controllers::Ble& bleController,
DateTime& dateTimeController,
Pinetime::Controllers::NotificationManager& notificationManager,
Controllers::Battery& batteryController,
Pinetime::Drivers::SpiNorFlash& spiNorFlash,
Controllers::HeartRateController& heartRateController);
void Init();
void StartAdvertising();
int OnGAPEvent(ble_gap_event* event);
int OnDiscoveryEvent(uint16_t i, const ble_gatt_error* pError, const ble_gatt_svc* pSvc);
int OnCTSCharacteristicDiscoveryEvent(uint16_t connectionHandle, const ble_gatt_error *error,
const ble_gatt_chr *characteristic);
int OnANSCharacteristicDiscoveryEvent(uint16_t connectionHandle, const ble_gatt_error *error,
const ble_gatt_chr *characteristic);
int OnCTSCharacteristicDiscoveryEvent(uint16_t connectionHandle, const ble_gatt_error* error, const ble_gatt_chr* characteristic);
int OnANSCharacteristicDiscoveryEvent(uint16_t connectionHandle, const ble_gatt_error* error, const ble_gatt_chr* characteristic);
int OnCurrentTimeReadResult(uint16_t connectionHandle, const ble_gatt_error* error, ble_gatt_attr* attribute);
int OnANSDescriptorDiscoveryEventCallback(uint16_t connectionHandle, const ble_gatt_error *error,
uint16_t characteristicValueHandle, const ble_gatt_dsc *descriptor);
int OnANSDescriptorDiscoveryEventCallback(uint16_t connectionHandle,
const ble_gatt_error* error,
uint16_t characteristicValueHandle,
const ble_gatt_dsc* descriptor);
void StartDiscovery();
Pinetime::Controllers::MusicService& music() {return musicService;};
Pinetime::Controllers::NavigationService& navigation() {return navService;};
Pinetime::Controllers::AlertNotificationService& alertService() {return anService;};
Pinetime::Controllers::MusicService& music() {
return musicService;
};
Pinetime::Controllers::NavigationService& navigation() {
return navService;
};
Pinetime::Controllers::AlertNotificationService& alertService() {
return anService;
};
uint16_t connHandle();
@ -87,9 +96,7 @@ namespace Pinetime {
ble_uuid128_t dfuServiceUuid {
.u {.type = BLE_UUID_TYPE_128},
.value = {0x23, 0xD1, 0xBC, 0xEA, 0x5F, 0x78, 0x23, 0x15,
0xDE, 0xEF, 0x12, 0x12, 0x30, 0x15, 0x00, 0x00}
};
.value = {0x23, 0xD1, 0xBC, 0xEA, 0x5F, 0x78, 0x23, 0x15, 0xDE, 0xEF, 0x12, 0x12, 0x30, 0x15, 0x00, 0x00}};
ServiceDiscovery serviceDiscovery;
};

@ -6,7 +6,6 @@ using namespace Pinetime::Controllers;
constexpr uint8_t NotificationManager::MessageSize;
void NotificationManager::Push(NotificationManager::Notification&& notif) {
notif.id = GetNextId();
notif.valid = true;
@ -14,7 +13,8 @@ void NotificationManager::Push(NotificationManager::Notification &&notif) {
writeIndex = (writeIndex + 1 < TotalNbNotifications) ? writeIndex + 1 : 0;
if (!empty)
readIndex = (readIndex + 1 < TotalNbNotifications) ? readIndex + 1 : 0;
else empty = false;
else
empty = false;
newNotification = true;
}
@ -30,8 +30,11 @@ NotificationManager::Notification::Id NotificationManager::GetNextId() {
}
NotificationManager::Notification NotificationManager::GetNext(NotificationManager::Notification::Id id) {
auto currentIterator = std::find_if(notifications.begin(), notifications.end(), [id](const Notification& n){return n.valid && n.id == id;});
if(currentIterator == notifications.end() || currentIterator->id != id) return Notification{};
auto currentIterator = std::find_if(notifications.begin(), notifications.end(), [id](const Notification& n) {
return n.valid && n.id == id;
});
if (currentIterator == notifications.end() || currentIterator->id != id)
return Notification {};
auto& lastNotification = notifications[readIndex];
@ -42,15 +45,19 @@ NotificationManager::Notification NotificationManager::GetNext(NotificationManag
else
result = *(currentIterator + 1);
if(result.id <= id) return {};
if (result.id <= id)
return {};
result.index = (lastNotification.id - result.id) + 1;
return result;
}
NotificationManager::Notification NotificationManager::GetPrevious(NotificationManager::Notification::Id id) {
auto currentIterator = std::find_if(notifications.begin(), notifications.end(), [id](const Notification& n){return n.valid && n.id == id;});
if(currentIterator == notifications.end() || currentIterator->id != id) return Notification{};
auto currentIterator = std::find_if(notifications.begin(), notifications.end(), [id](const Notification& n) {
return n.valid && n.id == id;
});
if (currentIterator == notifications.end() || currentIterator->id != id)
return Notification {};
auto& lastNotification = notifications[readIndex];
@ -61,7 +68,8 @@ NotificationManager::Notification NotificationManager::GetPrevious(NotificationM
else
result = *(currentIterator - 1);
if(result.id >= id) return {};
if (result.id >= id)
return {};
result.index = (lastNotification.id - result.id) + 1;
return result;
@ -84,7 +92,9 @@ bool NotificationManager::ClearNewNotificationFlag() {
}
size_t NotificationManager::NbNotifications() const {
return std::count_if(notifications.begin(), notifications.end(), [](const Notification& n){ return n.valid;});
return std::count_if(notifications.begin(), notifications.end(), [](const Notification& n) {
return n.valid;
});
}
const char* NotificationManager::Notification::Message() const {

@ -9,7 +9,19 @@ namespace Pinetime {
namespace Controllers {
class NotificationManager {
public:
enum class Categories {Unknown, SimpleAlert, Email, News, IncomingCall, MissedCall, Sms, VoiceMail, Schedule, HighProriotyAlert, InstantMessage };
enum class Categories {
Unknown,
SimpleAlert,
Email,
News,
IncomingCall,
MissedCall,
Sms,
VoiceMail,
Schedule,
HighProriotyAlert,
InstantMessage
};
static constexpr uint8_t MessageSize {100};
struct Notification {
@ -35,7 +47,9 @@ namespace Pinetime {
bool IsVibrationEnabled();
void ToggleVibrations();
static constexpr size_t MaximumMessageSize() { return MessageSize; };
static constexpr size_t MaximumMessageSize() {
return MessageSize;
};
size_t NbNotifications() const;
private:

@ -5,7 +5,6 @@
using namespace Pinetime::Controllers;
ServiceDiscovery::ServiceDiscovery(std::array<BleClient*, 2>&& clients) : clients {clients} {
}
void ServiceDiscovery::StartDiscovery(uint16_t connectionHandle) {

@ -13,7 +13,6 @@ namespace Pinetime {
void StartDiscovery(uint16_t connectionHandle);
private:
BleClient** clientIterator;
std::array<BleClient*, 2> clients;

@ -4,7 +4,6 @@
using namespace Pinetime::Controllers;
void BrightnessController::Init() {
nrf_gpio_cfg_output(pinLcdBacklight1);
nrf_gpio_cfg_output(pinLcdBacklight2);
@ -41,19 +40,33 @@ void BrightnessController::Set(BrightnessController::Levels level) {
void BrightnessController::Lower() {
switch (level) {
case Levels::High: Set(Levels::Medium); break;
case Levels::Medium: Set(Levels::Low); break;
case Levels::Low: Set(Levels::Off); break;
default: break;
case Levels::High:
Set(Levels::Medium);
break;
case Levels::Medium:
Set(Levels::Low);
break;
case Levels::Low:
Set(Levels::Off);
break;
default:
break;
}
}
void BrightnessController::Higher() {
switch (level) {
case Levels::Off: Set(Levels::Low); break;
case Levels::Low: Set(Levels::Medium); break;
case Levels::Medium: Set(Levels::High); break;
default: break;
case Levels::Off:
Set(Levels::Low);
break;
case Levels::Low:
Set(Levels::Medium);
break;
case Levels::Medium:
Set(Levels::High);
break;
default:
break;
}
}
@ -71,28 +84,43 @@ void BrightnessController::Restore() {
void BrightnessController::Step() {
switch (level) {
case Levels::Low: Set(Levels::Medium); break;
case Levels::Medium: Set(Levels::High); break;
case Levels::High: Set(Levels::Low); break;
default: break;
case Levels::Low:
Set(Levels::Medium);
break;
case Levels::Medium:
Set(Levels::High);
break;
case Levels::High:
Set(Levels::Low);
break;
default:
break;
}
}
const char* BrightnessController::GetIcon() {
switch (level) {
case Levels::Medium: return Applications::Screens::Symbols::brightnessMedium;
case Levels::High: return Applications::Screens::Symbols::brightnessHigh;
default: break;
case Levels::Medium:
return Applications::Screens::Symbols::brightnessMedium;
case Levels::High:
return Applications::Screens::Symbols::brightnessHigh;
default:
break;
}
return Applications::Screens::Symbols::brightnessLow;
}
const char* BrightnessController::ToString() {
switch (level) {
case Levels::Off: return "Off";
case Levels::Low: return "Low";
case Levels::Medium: return "Medium";
case Levels::High: return "High";
default : return "???";
case Levels::Off:
return "Off";
case Levels::Low:
return "Low";
case Levels::Medium:
return "Medium";
case Levels::High:
return "High";
default:
return "???";
}
}

@ -6,13 +6,12 @@
using namespace Pinetime::Controllers;
DateTime::DateTime(System::SystemTask& systemTask) : systemTask {systemTask} {
}
void DateTime::SetTime(uint16_t year, uint8_t month, uint8_t day, uint8_t dayOfWeek, uint8_t hour, uint8_t minute,
uint8_t second, uint32_t systickCounter) {
std::tm tm = { /* .tm_sec = */ second,
void DateTime::SetTime(
uint16_t year, uint8_t month, uint8_t day, uint8_t dayOfWeek, uint8_t hour, uint8_t minute, uint8_t second, uint32_t systickCounter) {
std::tm tm = {
/* .tm_sec = */ second,
/* .tm_min = */ minute,
/* .tm_hour = */ hour,
/* .tm_mday = */ day,
@ -105,95 +104,17 @@ const char *DateTime::DayOfWeekShortToStringLow() {
return DateTime::DaysStringShortLow[(uint8_t) dayOfWeek];
}
char const* DateTime::DaysStringLow[] = {"--", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday", "Sunday"};
char const *DateTime::DaysStringLow[] = {
"--",
"Monday",
"Tuesday",
"Wednesday",
"Thursday",
"Friday",
"Saturday",
"Sunday"
};
char const* DateTime::DaysStringShortLow[] = {"--", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat", "Sun"};
char const *DateTime::DaysStringShortLow[] = {
"--",
"Mon",
"Tue",
"Wed",
"Thu",
"Fri",
"Sat",
"Sun"
};
char const* DateTime::DaysStringShort[] = {"--", "MON", "TUE", "WED", "THU", "FRI", "SAT", "SUN"};
char const *DateTime::DaysStringShort[] = {
"--",
"MON",
"TUE",
"WED",
"THU",
"FRI",
"SAT",
"SUN"
};
char const* DateTime::DaysString[] = {"--", "MONDAY", "TUESDAY", "WEDNESDAY", "THURSDAY", "FRIDAY", "SATURDAY", "SUNDAY"};
char const *DateTime::DaysString[] = {
"--",
"MONDAY",
"TUESDAY",
"WEDNESDAY",
"THURSDAY",
"FRIDAY",
"SATURDAY",
"SUNDAY"
};
char const* DateTime::MonthsString[] = {"--", "JAN", "FEB", "MAR", "APR", "MAY", "JUN", "JUL", "AUG", "SEP", "OCT", "NOV", "DEC"};
char const *DateTime::MonthsString[] = {
"--",
"JAN",
"FEB",
"MAR",
"APR",
"MAY",
"JUN",
"JUL",
"AUG",
"SEP",
"OCT",
"NOV",
"DEC"
};
char const *DateTime::MonthsStringLow[] = {
"--",
"Jan",
"Feb",
"Mar",
"Apr",
"May",
"Jun",
"Jul",
"Aug",
"Sep",
"Oct",
"Nov",
"Dec"
};
char const* DateTime::MonthsStringLow[] = {"--", "Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"};
char const* DateTime::MonthsLow[] = {
"--",
"January",
"February",
"March",
"April",
"May",
"June",
"July",
"August",
"September",
"October",
"November",
"December"
};
"--", "January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"};

@ -11,19 +11,54 @@ namespace Pinetime {
class DateTime {
public:
enum class Days : uint8_t { Unknown, Monday, Tuesday, Wednesday, Thursday, Friday, Saturday, Sunday };
enum class Months : uint8_t {Unknown, January, February, March, April, May, June, July, August, September, October, November, December};
enum class Months : uint8_t {
Unknown,
January,
February,
March,
April,
May,
June,
July,
August,
September,
October,
November,
December
};
DateTime(System::SystemTask& systemTask);
void SetTime(uint16_t year, uint8_t month, uint8_t day, uint8_t dayOfWeek, uint8_t hour, uint8_t minute, uint8_t second, uint32_t systickCounter);
void SetTime(uint16_t year,
uint8_t month,
uint8_t day,
uint8_t dayOfWeek,
uint8_t hour,
uint8_t minute,
uint8_t second,
uint32_t systickCounter);
void UpdateTime(uint32_t systickCounter);
uint16_t Year() const { return year; }
Months Month() const { return month; }
uint8_t Day() const { return day; }
Days DayOfWeek() const { return dayOfWeek; }
uint8_t Hours() const { return hour; }
uint8_t Minutes() const { return minute; }
uint8_t Seconds() const { return second; }
uint16_t Year() const {
return year;
}
Months Month() const {
return month;
}
uint8_t Day() const {
return day;
}
Days DayOfWeek() const {
return dayOfWeek;
}
uint8_t Hours() const {
return hour;
}
uint8_t Minutes() const {
return minute;
}
uint8_t Seconds() const {
return second;
}
const char* MonthShortToString();
const char* MonthShortToStringLow();
@ -33,8 +68,13 @@ namespace Pinetime {
const char* DayOfWeekToStringLow();
const char* DayOfWeekShortToStringLow();
std::chrono::time_point<std::chrono::system_clock, std::chrono::nanoseconds> CurrentDateTime() const { return currentDateTime; }
std::chrono::seconds Uptime() const { return uptime; }
std::chrono::time_point<std::chrono::system_clock, std::chrono::nanoseconds> CurrentDateTime() const {
return currentDateTime;
}
std::chrono::seconds Uptime() const {
return uptime;
}
private:
System::SystemTask& systemTask;
uint16_t year = 0;
@ -58,7 +98,6 @@ namespace Pinetime {
static char const* MonthsString[];
static char const* MonthsStringLow[];
static char const* MonthsLow[];
};
}
}

@ -10,6 +10,7 @@ namespace Pinetime {
bool IsValidated() const;
void Reset();
private:
static constexpr uint32_t validBitAdress {0x7BFE8};
static constexpr uint32_t validBitValue {1};

@ -6,7 +6,6 @@ Gfx::Gfx(Pinetime::Drivers::St7789 &lcd) : lcd{lcd} {
}
void Gfx::Init() {
}
void Gfx::ClearScreen() {
@ -20,7 +19,6 @@ void Gfx::ClearScreen() {
lcd.DrawBuffer(0, 0, width, height, reinterpret_cast<const uint8_t*>(buffer), width * 2);
WaitTransferFinished();
}
void Gfx::FillRectangle(uint8_t x, uint8_t y, uint8_t w, uint8_t h, uint16_t color) {
@ -101,8 +99,7 @@ void Gfx::DrawChar(const FONT_INFO *font, uint8_t c, uint8_t *x, uint8_t y, uint
for (uint8_t k = 0; k < 8; k++) {
if ((1 << (7 - k)) & font->data[font->charInfo[char_idx].offset + j]) {
buffer[(j * 8) + k] = color;
}
else {
} else {
buffer[(j * 8) + k] = bg;
}
}
@ -142,7 +139,8 @@ void Gfx::SetBackgroundColor(uint16_t color) {
}
bool Gfx::GetNextBuffer(uint8_t** data, size_t& size) {
if(!state.busy) return false;
if (!state.busy)
return false;
state.remainingIterations--;
if (state.remainingIterations == 0) {
state.busy = false;
@ -162,8 +160,7 @@ bool Gfx::GetNextBuffer(uint8_t **data, size_t &size) {
for (uint8_t k = 0; k < 8; k++) {
if ((1 << (7 - k)) & state.font->data[state.font->charInfo[char_idx].offset + ((state.currentIteration + 1) * bytes_in_line) + j]) {
buffer[(j * 8) + k] = state.color;
}
else {
} else {
buffer[(j * 8) + k] = bg;
}
}

@ -23,20 +23,19 @@ namespace Pinetime {
void SetScrollArea(uint16_t topFixedLines, uint16_t scrollLines, uint16_t bottomFixedLines);
void SetScrollStartLine(uint16_t line);
void Sleep();
void Wakeup();
bool GetNextBuffer(uint8_t** buffer, size_t& size) override;
void pixel_draw(uint8_t x, uint8_t y, uint16_t color);
private:
static constexpr uint8_t width = 240;
static constexpr uint8_t height = 240;
enum class Action { None, FillRectangle, DrawChar };
struct State {
State() : busy{false}, action{Action::None}, remainingIterations{0}, currentIteration{0} {}
State() : busy {false}, action {Action::None}, remainingIterations {0}, currentIteration {0} {
}
volatile bool busy;
volatile Action action;
volatile uint16_t remainingIterations;

@ -10,7 +10,6 @@ using namespace Pinetime::Controllers;
/** Original implementation from wasp-os : https://github.com/daniel-thompson/wasp-os/blob/master/wasp/ppg.py */
Biquad::Biquad(float b0, float b1, float b2, float a1, float a2) : b0 {b0}, b1 {b1}, b2 {b2}, a1 {a1}, a2 {a2} {
}
float Biquad::Step(float x) {

@ -5,10 +5,8 @@
using namespace Pinetime::Controllers;
HeartRateController::HeartRateController(Pinetime::System::SystemTask& systemTask) : systemTask {systemTask} {
}
void HeartRateController::Update(HeartRateController::States newState, uint8_t heartRate) {
this->state = newState;
if (this->heartRate != heartRate) {
@ -38,4 +36,3 @@ void HeartRateController::SetHeartRateTask(Pinetime::Applications::HeartRateTask
void HeartRateController::SetService(Pinetime::Controllers::HeartRateService* service) {
this->service = service;
}

@ -22,8 +22,12 @@ namespace Pinetime {
void Update(States newState, uint8_t heartRate);
void SetHeartRateTask(Applications::HeartRateTask* task);
States State() const { return state; }
uint8_t HeartRate() const { return heartRate; }
States State() const {
return state;
}
uint8_t HeartRate() const {
return heartRate;
}
void SetService(Pinetime::Controllers::HeartRateService* service);

@ -38,11 +38,11 @@ namespace {
}
}
Ppg::Ppg(float spl) : offset{spl},
Ppg::Ppg(float spl)
: offset {spl},
hpf {0.87033078, -1.74066156, 0.87033078, -1.72377617, 0.75754694},
agc {20, 0.971, 2},
lpf {0.11595249, 0.23190498, 0.11595249, -0.72168143, 0.18549138} {
}
int Ppg::Preprocess(float spl) {

@ -24,7 +24,6 @@ namespace Pinetime {
Ptagc agc;
Biquad lpf;
float ProcessHeartRate();
};
}

@ -11,7 +11,6 @@ using namespace Pinetime::Controllers;
/** Original implementation from wasp-os : https://github.com/daniel-thompson/wasp-os/blob/master/wasp/ppg.py */
Ptagc::Ptagc(float start, float decay, float threshold) : peak {start}, decay {decay}, boost {1.0f / decay}, threshold {threshold} {
}
float Ptagc::Step(float spl) {

@ -12,7 +12,6 @@ namespace Pinetime {
float decay;
float boost;
float threshold;
};
}
}

@ -8,14 +8,24 @@ namespace Pinetime {
public:
void Update(int16_t x, int16_t y, int16_t z, uint32_t nbSteps);
uint16_t X() const { return x; }
uint16_t Y() const { return y; }
uint16_t Z() const { return z; }
uint32_t NbSteps() const { return nbSteps; }
uint16_t X() const {
return x;
}
uint16_t Y() const {
return y;
}
uint16_t Z() const {
return z;
}
uint32_t NbSteps() const {
return nbSteps;
}
bool ShouldWakeUp(bool isSleeping);
void IsSensorOk(bool isOk);
bool IsSensorOk() const { return isSensorOk; }
bool IsSensorOk() const {
return isSensorOk;
}
private:
uint32_t nbSteps;

@ -7,7 +7,8 @@ APP_TIMER_DEF(vibTimer);
using namespace Pinetime::Controllers;
MotorController::MotorController( Controllers::Settings &settingsController ) : settingsController{settingsController} {}
MotorController::MotorController(Controllers::Settings& settingsController) : settingsController {settingsController} {
}
void MotorController::Init() {
nrf_gpio_cfg_output(pinMotor);
@ -18,7 +19,8 @@ void MotorController::Init() {
void MotorController::SetDuration(uint8_t motorDuration) {
if ( settingsController.GetVibrationStatus() == Controllers::Settings::Vibration::OFF ) return;
if (settingsController.GetVibrationStatus() == Controllers::Settings::Vibration::OFF)
return;
nrf_gpio_pin_clear(pinMotor);
/* Start timer for motorDuration miliseconds and timer triggers vibrate() when it finishes*/

@ -3,7 +3,6 @@
using namespace Pinetime::Tools;
RleDecoder::RleDecoder(const uint8_t* buffer, size_t size) : buffer {buffer}, size {size} {
}
RleDecoder::RleDecoder(const uint8_t* buffer, size_t size, uint16_t foregroundColor, uint16_t backgroundColor) : RleDecoder {buffer, size} {
@ -11,7 +10,6 @@ RleDecoder::RleDecoder(const uint8_t *buffer, size_t size, uint16_t foregroundCo
this->backgroundColor = backgroundColor;
}
void RleDecoder::DecodeNext(uint8_t* output, size_t maxBytes) {
for (; encodedBufferIndex < size; encodedBufferIndex++) {
uint8_t rl = buffer[encodedBufferIndex] - processedCount;
@ -36,4 +34,3 @@ void RleDecoder::DecodeNext(uint8_t *output, size_t maxBytes) {
color = backgroundColor;
}
}

@ -11,14 +11,13 @@ struct SettingsHeader {
#define HEADER_SIZE sizeof(SettingsHeader)
Settings::Settings( Pinetime::Drivers::SpiNorFlash &spiNorFlash ) : spiNorFlash{spiNorFlash} {}
Settings::Settings(Pinetime::Drivers::SpiNorFlash& spiNorFlash) : spiNorFlash {spiNorFlash} {
}
void Settings::Init() {
// Load default settings from Flash
LoadSettingsFromFlash();
}
void Settings::SaveSettings() {
@ -30,7 +29,6 @@ void Settings::SaveSettings() {
settingsChanged = false;
}
bool Settings::FindHeader() {
SettingsHeader settingsHeader;
uint8_t bufferHead[sizeof(settingsHeader)];
@ -66,7 +64,6 @@ void Settings::SetHeader( bool state ) {
std::memcpy(bufferHead, &settingsHeader, sizeof(settingsHeader));
spiNorFlash.Write(settingsBaseAddr + (settingsFlashBlock * 0x1000), bufferHead, sizeof(settingsHeader));
}
void Settings::SaveSettingsData() {
@ -89,7 +86,6 @@ void Settings::LoadSettingsFromFlash() {
// never used :)
ReadSettingsData();
}
}
void Settings::SaveSettingsToFlash() {
@ -106,7 +102,8 @@ void Settings::SaveSettingsToFlash() {
}
settingsFlashBlock++;
if ( settingsFlashBlock > 9 ) settingsFlashBlock = 0;
if (settingsFlashBlock > 9)
settingsFlashBlock = 0;
EraseBlock();
SetHeader(true);

@ -19,49 +19,74 @@ namespace Pinetime {
void SaveSettings();
void SetClockFace(uint8_t face) {
if ( face != settings.clockFace ) settingsChanged = true;
if (face != settings.clockFace)
settingsChanged = true;
settings.clockFace = face;
};
uint8_t GetClockFace() const { return settings.clockFace; };
uint8_t GetClockFace() const {
return settings.clockFace;
};
void SetAppMenu( uint8_t menu ) { appMenu = menu; };
uint8_t GetAppMenu() { return appMenu; };
void SetAppMenu(uint8_t menu) {
appMenu = menu;
};
uint8_t GetAppMenu() {
return appMenu;
};
void SetSettingsMenu( uint8_t menu ) { settingsMenu = menu; };
uint8_t GetSettingsMenu() const { return settingsMenu; };
void SetSettingsMenu(uint8_t menu) {
settingsMenu = menu;
};
uint8_t GetSettingsMenu() const {
return settingsMenu;
};
void SetClockType(ClockType clocktype) {
if ( clocktype != settings.clockType ) settingsChanged = true;
if (clocktype != settings.clockType)
settingsChanged = true;
settings.clockType = clocktype;
};
ClockType GetClockType() const { return settings.clockType; };
ClockType GetClockType() const {
return settings.clockType;
};
void SetVibrationStatus(Vibration status) {
if ( status != settings.vibrationStatus ) settingsChanged = true;
if (status != settings.vibrationStatus)
settingsChanged = true;
settings.vibrationStatus = status;
};
Vibration GetVibrationStatus() const { return settings.vibrationStatus; };
Vibration GetVibrationStatus() const {
return settings.vibrationStatus;
};
void SetScreenTimeOut(uint32_t timeout) {
if ( timeout != settings.screenTimeOut ) settingsChanged = true;
if (timeout != settings.screenTimeOut)
settingsChanged = true;
settings.screenTimeOut = timeout;
};
uint32_t GetScreenTimeOut() const { return settings.screenTimeOut; };
uint32_t GetScreenTimeOut() const {
return settings.screenTimeOut;
};
void setWakeUpMode(WakeUpMode wakeUp) {
if ( wakeUp != settings.wakeUpMode ) settingsChanged = true;
if (wakeUp != settings.wakeUpMode)
settingsChanged = true;
settings.wakeUpMode = wakeUp;
};
WakeUpMode getWakeUpMode() const { return settings.wakeUpMode; };
WakeUpMode getWakeUpMode() const {
return settings.wakeUpMode;
};
void SetBrightness(Controllers::BrightnessController::Levels level) {
if ( level != settings.brightLevel ) settingsChanged = true;
if (level != settings.brightLevel)
settingsChanged = true;
settings.brightLevel = level;
};
Controllers::BrightnessController::Levels GetBrightness() const { return settings.brightLevel; };
Controllers::BrightnessController::Levels GetBrightness() const {
return settings.brightLevel;
};
private:
Pinetime::Drivers::SpiNorFlash& spiNorFlash;
struct SettingsData {
@ -76,7 +101,6 @@ namespace Pinetime {
WakeUpMode wakeUpMode = WakeUpMode::None;
Controllers::BrightnessController::Levels brightLevel = Controllers::BrightnessController::Levels::Medium;
};
SettingsData settings;
@ -99,7 +123,6 @@ namespace Pinetime {
void SaveSettingsData();
void LoadSettingsFromFlash();
void SaveSettingsToFlash();
};
}
}

@ -3,9 +3,30 @@
namespace Pinetime {
namespace Applications {
enum class Apps {
None, Launcher, Clock, SysInfo, FirmwareUpdate, FirmwareValidation, NotificationsPreview, Notifications, FlashLight, BatteryInfo,
Music, Paint, Paddle, Twos, HeartRate, Navigation, StopWatch, Motion,
QuickSettings, Settings, SettingWatchFace, SettingTimeFormat, SettingDisplay, SettingWakeUp
None,
Launcher,
Clock,
SysInfo,
FirmwareUpdate,
FirmwareValidation,
NotificationsPreview,
Notifications,
FlashLight,
BatteryInfo,
Music,
Paint,
Paddle,
Twos,
HeartRate,
Navigation,
StopWatch,
Motion,
QuickSettings,
Settings,
SettingWatchFace,
SettingTimeFormat,
SettingDisplay,
SettingWakeUp
};
}
}

@ -40,15 +40,19 @@
using namespace Pinetime::Applications;
using namespace Pinetime::Applications::Display;
DisplayApp::DisplayApp(Drivers::St7789 &lcd, Components::LittleVgl &lvgl, Drivers::Cst816S &touchPanel,
Controllers::Battery &batteryController, Controllers::Ble &bleController,
Controllers::DateTime &dateTimeController, Drivers::WatchdogView &watchdog,
DisplayApp::DisplayApp(Drivers::St7789& lcd,
Components::LittleVgl& lvgl,
Drivers::Cst816S& touchPanel,
Controllers::Battery& batteryController,
Controllers::Ble& bleController,
Controllers::DateTime& dateTimeController,
Drivers::WatchdogView& watchdog,
System::SystemTask& systemTask,
Pinetime::Controllers::NotificationManager& notificationManager,
Pinetime::Controllers::HeartRateController& heartRateController,
Controllers::Settings& settingsController,
Pinetime::Controllers::MotionController& motionController) :
lcd{lcd},
Pinetime::Controllers::MotionController& motionController)
: lcd {lcd},
lvgl {lvgl},
touchPanel {touchPanel},
batteryController {batteryController},
@ -129,7 +133,8 @@ void DisplayApp::Refresh() {
systemTask.PushMessage(System::SystemTask::Messages::UpdateTimeOut);
break;
case Messages::UpdateBleConnection:
// clockScreen.SetBleConnectionState(bleController.IsConnected() ? Screens::Clock::BleConnectionStates::Connected : Screens::Clock::BleConnectionStates::NotConnected);
// clockScreen.SetBleConnectionState(bleController.IsConnected() ? Screens::Clock::BleConnectionStates::Connected :
// Screens::Clock::BleConnectionStates::NotConnected);
break;
case Messages::UpdateBatteryLevel:
batteryController.Update();
@ -138,7 +143,8 @@ void DisplayApp::Refresh() {
LoadApp(Apps::NotificationsPreview, DisplayApp::FullRefreshDirections::Down);
break;
case Messages::TouchEvent: {
if (state != States::Running) break;
if (state != States::Running)
break;
auto gesture = OnTouchEvent();
if (!currentScreen->OnTouchEvent(gesture)) {
if (currentApp == Apps::Clock) {
@ -162,8 +168,7 @@ void DisplayApp::Refresh() {
LoadApp(returnToApp, returnDirection);
}
}
}
break;
} break;
case Messages::ButtonPushed:
if (currentApp == Apps::Clock) {
systemTask.PushMessage(System::SystemTask::Messages::GoToSleep);
@ -225,7 +230,14 @@ void DisplayApp::LoadApp(Apps app, DisplayApp::FullRefreshDirections direction)
break;
case Apps::None:
case Apps::Clock:
currentScreen = std::make_unique<Screens::Clock>(this, dateTimeController, batteryController, bleController, notificationManager, settingsController, heartRateController, motionController);
currentScreen = std::make_unique<Screens::Clock>(this,
dateTimeController,
batteryController,
bleController,
notificationManager,
settingsController,
heartRateController,
motionController);
break;
case Apps::FirmwareValidation:
@ -237,17 +249,20 @@ void DisplayApp::LoadApp(Apps app, DisplayApp::FullRefreshDirections direction)
break;
case Apps::Notifications:
currentScreen = std::make_unique<Screens::Notifications>(this, notificationManager, systemTask.nimble().alertService(), Screens::Notifications::Modes::Normal);
currentScreen = std::make_unique<Screens::Notifications>(
this, notificationManager, systemTask.nimble().alertService(), Screens::Notifications::Modes::Normal);
returnApp(Apps::Clock, FullRefreshDirections::Up, TouchEvents::SwipeUp);
break;
case Apps::NotificationsPreview:
currentScreen = std::make_unique<Screens::Notifications>(this, notificationManager, systemTask.nimble().alertService(), Screens::Notifications::Modes::Preview);
currentScreen = std::make_unique<Screens::Notifications>(
this, notificationManager, systemTask.nimble().alertService(), Screens::Notifications::Modes::Preview);
returnApp(Apps::Clock, FullRefreshDirections::Up, TouchEvents::SwipeUp);
break;
// Settings
case Apps::QuickSettings:
currentScreen = std::make_unique<Screens::QuickSettings>(this, batteryController, dateTimeController, brightnessController, settingsController);
currentScreen =
std::make_unique<Screens::QuickSettings>(this, batteryController, dateTimeController, brightnessController, settingsController);
returnApp(Apps::Clock, FullRefreshDirections::LeftAnim, TouchEvents::SwipeLeft);
break;
case Apps::Settings:
@ -275,7 +290,8 @@ void DisplayApp::LoadApp(Apps app, DisplayApp::FullRefreshDirections direction)
returnApp(Apps::Settings, FullRefreshDirections::Down, TouchEvents::SwipeDown);
break;
case Apps::SysInfo:
currentScreen = std::make_unique<Screens::SystemInfo>(this, dateTimeController, batteryController, brightnessController, bleController, watchdog);
currentScreen =
std::make_unique<Screens::SystemInfo>(this, dateTimeController, batteryController, brightnessController, bleController, watchdog);
returnApp(Apps::Settings, FullRefreshDirections::Down, TouchEvents::SwipeDown);
break;
//
@ -313,7 +329,6 @@ void DisplayApp::LoadApp(Apps app, DisplayApp::FullRefreshDirections direction)
}
void DisplayApp::IdleState() {
}
void DisplayApp::PushMessage(Messages msg) {
@ -374,11 +389,11 @@ void DisplayApp::SetFullRefresh(DisplayApp::FullRefreshDirections direction) {
case DisplayApp::FullRefreshDirections::RightAnim:
lvgl.SetFullRefresh(Components::LittleVgl::FullRefreshDirections::RightAnim);
break;
default: break;
default:
break;
}
}
void DisplayApp::SetTouchMode(DisplayApp::TouchModes mode) {
touchMode = mode;
}

@ -40,15 +40,18 @@ namespace Pinetime {
enum class FullRefreshDirections { None, Up, Down, Left, Right, LeftAnim, RightAnim };
enum class TouchModes { Gestures, Polling };
DisplayApp(Drivers::St7789 &lcd, Components::LittleVgl &lvgl, Drivers::Cst816S &,
Controllers::Battery &batteryController, Controllers::Ble &bleController,
Controllers::DateTime &dateTimeController, Drivers::WatchdogView &watchdog,
DisplayApp(Drivers::St7789& lcd,
Components::LittleVgl& lvgl,
Drivers::Cst816S&,
Controllers::Battery& batteryController,
Controllers::Ble& bleController,
Controllers::DateTime& dateTimeController,
Drivers::WatchdogView& watchdog,
System::SystemTask& systemTask,
Pinetime::Controllers::NotificationManager& notificationManager,
Pinetime::Controllers::HeartRateController& heartRateController,
Controllers::Settings& settingsController,
Pinetime::Controllers::MotionController& motionController
);
Pinetime::Controllers::MotionController& motionController);
void Start();
void PushMessage(Display::Messages msg);
@ -58,7 +61,6 @@ namespace Pinetime {
void SetTouchMode(TouchModes mode);
private:
Pinetime::Drivers::St7789& lcd;
Pinetime::Components::LittleVgl& lvgl;
Pinetime::Drivers::Cst816S& touchPanel;
@ -100,9 +102,6 @@ namespace Pinetime {
void Refresh();
void returnApp(Apps app, DisplayApp::FullRefreshDirections direction, TouchEvents touchEvent);
void LoadApp(Apps app, DisplayApp::FullRefreshDirections direction);
};
}
}

@ -7,17 +7,20 @@
using namespace Pinetime::Applications;
DisplayApp::DisplayApp(Drivers::St7789 &lcd, Components::LittleVgl &lvgl, Drivers::Cst816S &touchPanel,
Controllers::Battery &batteryController, Controllers::Ble &bleController,
Controllers::DateTime &dateTimeController, Drivers::WatchdogView &watchdog,
DisplayApp::DisplayApp(Drivers::St7789& lcd,
Components::LittleVgl& lvgl,
Drivers::Cst816S& touchPanel,
Controllers::Battery& batteryController,
Controllers::Ble& bleController,
Controllers::DateTime& dateTimeController,
Drivers::WatchdogView& watchdog,
System::SystemTask& systemTask,
Pinetime::Controllers::NotificationManager& notificationManager,
Pinetime::Controllers::HeartRateController& heartRateController,
Pinetime::Controllers::Settings& settingsController,
Pinetime::Controllers::MotionController& motionController):
lcd{lcd}, bleController{bleController} {
Pinetime::Controllers::MotionController& motionController)
: lcd {lcd}, bleController {bleController} {
msgQueue = xQueueCreate(queueSize, itemSize);
}
void DisplayApp::Start() {
@ -61,8 +64,9 @@ void DisplayApp::Refresh() {
}
if (bleController.IsFirmwareUpdating()) {
uint8_t percent = (static_cast<float>(bleController.FirmwareUpdateCurrentBytes()) /
static_cast<float>(bleController.FirmwareUpdateTotalBytes())) * 100.0f;
uint8_t percent =
(static_cast<float>(bleController.FirmwareUpdateCurrentBytes()) / static_cast<float>(bleController.FirmwareUpdateTotalBytes())) *
100.0f;
switch (bleController.State()) {
case Controllers::Ble::FirmwareUpdateStates::Running:
DisplayOtaProgress(percent, colorWhite);

@ -30,9 +30,13 @@ namespace Pinetime {
namespace Applications {
class DisplayApp {
public:
DisplayApp(Drivers::St7789 &lcd, Components::LittleVgl &lvgl, Drivers::Cst816S &,
Controllers::Battery &batteryController, Controllers::Ble &bleController,
Controllers::DateTime &dateTimeController, Drivers::WatchdogView &watchdog,
DisplayApp(Drivers::St7789& lcd,
Components::LittleVgl& lvgl,
Drivers::Cst816S&,
Controllers::Battery& batteryController,
Controllers::Ble& bleController,
Controllers::DateTime& dateTimeController,
Drivers::WatchdogView& watchdog,
System::SystemTask& systemTask,
Pinetime::Controllers::NotificationManager& notificationManager,
Pinetime::Controllers::HeartRateController& heartRateController,
@ -66,10 +70,6 @@ namespace Pinetime {
static constexpr uint16_t colorRedSwapped = 0x00ff;
static constexpr uint16_t colorBlack = 0x0000;
uint8_t displayBuffer[displayWidth * bytesPerPixel];
};
}
}

@ -11,20 +11,23 @@ namespace Pinetime {
class LittleVgl {
public:
enum class FullRefreshDirections { None, Up, Down };
LittleVgl(Pinetime::Drivers::St7789& lcd, Pinetime::Drivers::Cst816S& touchPanel) {}
LittleVgl(Pinetime::Drivers::St7789& lcd, Pinetime::Drivers::Cst816S& touchPanel) {
}
LittleVgl(const LittleVgl&) = delete;
LittleVgl& operator=(const LittleVgl&) = delete;
LittleVgl(LittleVgl&&) = delete;
LittleVgl& operator=(LittleVgl&&) = delete;
void FlushDisplay(const lv_area_t * area, lv_color_t * color_p) {}
bool GetTouchPadInfo(lv_indev_data_t *ptr) {return false;}
void SetFullRefresh(FullRefreshDirections direction) {}
void SetNewTapEvent(uint16_t x, uint16_t y) {}
void FlushDisplay(const lv_area_t* area, lv_color_t* color_p) {
}
bool GetTouchPadInfo(lv_indev_data_t* ptr) {
return false;
}
void SetFullRefresh(FullRefreshDirections direction) {
}
void SetNewTapEvent(uint16_t x, uint16_t y) {
}
};
}
}

@ -21,7 +21,8 @@ bool touchpad_read(lv_indev_drv_t * indev_drv, lv_indev_data_t * data) {
return lvgl->GetTouchPadInfo(data);
}
LittleVgl::LittleVgl(Pinetime::Drivers::St7789& lcd, Pinetime::Drivers::Cst816S& touchPanel) : lcd{lcd}, touchPanel{touchPanel}, previousClick{0,0} {
LittleVgl::LittleVgl(Pinetime::Drivers::St7789& lcd, Pinetime::Drivers::Cst816S& touchPanel)
: lcd {lcd}, touchPanel {touchPanel}, previousClick {0, 0} {
lv_init();
InitTheme();
InitDisplay();
@ -203,13 +204,7 @@ bool LittleVgl::GetTouchPadInfo(lv_indev_data_t *ptr) {
void LittleVgl::InitTheme() {
lv_theme_t* th = lv_pinetime_theme_init(
LV_COLOR_WHITE, LV_COLOR_SILVER,
0,
&jetbrains_mono_bold_20,
&jetbrains_mono_bold_20,
&jetbrains_mono_bold_20,
&jetbrains_mono_bold_20);
LV_COLOR_WHITE, LV_COLOR_SILVER, 0, &jetbrains_mono_bold_20, &jetbrains_mono_bold_20, &jetbrains_mono_bold_20, &jetbrains_mono_bold_20);
lv_theme_set_act(th);
}

@ -29,11 +29,9 @@ namespace Pinetime {
void InitTouchpad();
void InitTheme();
Pinetime::Drivers::St7789& lcd;
Pinetime::Drivers::Cst816S& touchPanel;
lv_disp_buf_t disp_buf_2;
lv_color_t buf2_1[LV_HOR_RES_MAX * 4];
lv_color_t buf2_2[LV_HOR_RES_MAX * 4];
@ -45,7 +43,9 @@ namespace Pinetime {
static constexpr uint8_t nbWriteLines = 4;
static constexpr uint16_t totalNbLines = 320;
static constexpr uint16_t visibleNbLines = 240;
static constexpr uint8_t MaxScrollOffset() { return LV_VER_RES_MAX - nbWriteLines; }
static constexpr uint8_t MaxScrollOffset() {
return LV_VER_RES_MAX - nbWriteLines;
}
FullRefreshDirections scrollDirection = FullRefreshDirections::None;
uint16_t writeOffset = 0;
uint16_t scrollOffset = 0;
@ -56,4 +56,3 @@ namespace Pinetime {
};
}
}

@ -3,8 +3,16 @@ namespace Pinetime {
namespace Applications {
namespace Display {
enum class Messages : uint8_t {
GoToSleep, GoToRunning, UpdateDateTime, UpdateBleConnection, UpdateBatteryLevel, TouchEvent, ButtonPushed,
NewNotification, BleFirmwareUpdateStarted, UpdateTimeOut
GoToSleep,
GoToRunning,
UpdateDateTime,
UpdateBleConnection,
UpdateBatteryLevel,
TouchEvent,
ButtonPushed,
NewNotification,
BleFirmwareUpdateStarted,
UpdateTimeOut
};
}
}

@ -0,0 +1,44 @@
# Fonts
* [Jetbrains Mono](https://www.jetbrains.com/fr-fr/lp/mono/)
* [Awesome font from LVGL](https://lvgl.io/assets/others/FontAwesome5-Solid+Brands+Regular.woff)
## Generate the fonts:
* Open the [LVGL font converter](https://lvgl.io/tools/fontconverter)
* Name : jetbrains_mono_bold_20
* Size : 20
* Bpp : 1 bit-per-pixel
* Do not enable font compression and horizontal subpixel hinting
* Load the file `JetBrainsMono-Bold.tff` and specify the following range : `0x20-0x7f, 0x410-0x44f`
* Add a 2nd font, load the file `FontAwesome5-Solid+Brands+Regular.woff` and specify the following
range : `0xf293, 0xf294, 0xf244, 0xf240, 0xf242, 0xf243, 0xf241, 0xf54b, 0xf21e, 0xf1e6, 0xf54b, 0xf017, 0xf129, 0xf03a, 0xf185, 0xf560, 0xf001, 0xf3fd, 0xf069, 0xf1fc, 0xf45d, 0xf59f, 0xf5a0, 0xf029, 0xf027, 0xf028, 0xf6a9, 0xf04b, 0xf04c, 0xf048, 0xf051, 0xf095, 0xf3dd, 0xf04d, 0xf2f2, 0xf024`
* Click on Convert, and download the file `jetbrains_mono_bold_20.c` and copy it in `src/DisplayApp/Fonts`
Add new symbols:
* Browse the [cheatsheet](https://fontawesome.com/cheatsheet/free/solid) and find your new symbols
* For each symbol, add its hex code (0xf641 for the 'Ad' icon, for example) to the *Range* list (Remember to keep this
readme updated with newest range list)
* Convert this hex value into a UTF-8 code
using [this site](http://www.ltg.ed.ac.uk/~richard/utf-8.cgi?input=f185&mode=hex)
* Define the new symbols in `src/DisplayApp/Screens/Symbols.h`:
```
static constex char* newSymbol = "\xEF\x86\x85";
```
#### Navigation font
To create the navigtion.ttf I use the web app [icomoon](https://icomoon.io/app)
this app can import the svg files from the folder *src/displayapp/icons/navigation/unique* and creat a ttf file the
project for the site is *lv_font_navi_80.json* you can import it to add or remove icons
You can also use the online LVGL tool to create the .c
ttf file : navigation.ttf name : lv_font_navi_80 size : 80px Bpp : 2 bit-per-pixel range : 0xe900-0xe929
$lv_font_conv --font navigation.ttf -r '0xe900-0xe929' --size 80 --format lvgl --bpp 2 --no-prefilter -o
lv_font_navi_80.c
#### I use the method above to create the other ttf

@ -1,41 +0,0 @@
#Fonts
* [Jetbrains Mono](https://www.jetbrains.com/fr-fr/lp/mono/)
* [Awesome font from LVGL](https://lvgl.io/assets/others/FontAwesome5-Solid+Brands+Regular.woff)
## Generate the fonts:
* Open the [LVGL font converter](https://lvgl.io/tools/fontconverter)
* Name : jetbrains_mono_bold_20
* Size : 20
* Bpp : 1 bit-per-pixel
* Do not enable font compression and horizontal subpixel hinting
* Load the file `JetBrainsMono-Bold.tff` and specify the following range : `0x20-0x7f, 0x410-0x44f`
* Add a 2nd font, load the file `FontAwesome5-Solid+Brands+Regular.woff` and specify the following range : `0xf293, 0xf294, 0xf244, 0xf240, 0xf242, 0xf243, 0xf241, 0xf54b, 0xf21e, 0xf1e6, 0xf54b, 0xf017, 0xf129, 0xf03a, 0xf185, 0xf560, 0xf001, 0xf3fd, 0xf069, 0xf1fc, 0xf45d, 0xf59f, 0xf5a0, 0xf029, 0xf027, 0xf028, 0xf6a9, 0xf04b, 0xf04c, 0xf048, 0xf051, 0xf095, 0xf3dd, 0xf04d, 0xf2f2, 0xf024`
* Click on Convert, and download the file `jetbrains_mono_bold_20.c` and copy it in `src/DisplayApp/Fonts`
Add new symbols:
* Browse the [cheatsheet](https://fontawesome.com/cheatsheet/free/solid) and find your new symbols
* For each symbol, add its hex code (0xf641 for the 'Ad' icon, for example) to the *Range* list (Remember to keep this readme updated with newest range list)
* Convert this hex value into a UTF-8 code using [this site](http://www.ltg.ed.ac.uk/~richard/utf-8.cgi?input=f185&mode=hex)
* Define the new symbols in `src/DisplayApp/Screens/Symbols.h`:
```
static constex char* newSymbol = "\xEF\x86\x85";
```
#### Navigation font
To create the navigtion.ttf I use the web app [icomoon](https://icomoon.io/app)
this app can import the svg files from the folder *src/displayapp/icons/navigation/unique* and creat a ttf file
the project for the site is *lv_font_navi_80.json* you can import it to add or remove icons
You can also use the online LVGL tool to create the .c
ttf file : navigation.ttf
name : lv_font_navi_80
size : 80px
Bpp : 2 bit-per-pixel
range : 0xe900-0xe929
$lv_font_conv --font navigation.ttf -r '0xe900-0xe929' --size 80 --format lvgl --bpp 2 --no-prefilter -o lv_font_navi_80.c
#### I use the method above to create the other ttf

@ -67,15 +67,14 @@ static bool inited;
* STATIC FUNCTIONS
**********************/
static void style_init_reset(lv_style_t * style)
{
if(inited) lv_style_reset(style);
else lv_style_init(style);
static void style_init_reset(lv_style_t* style) {
if (inited)
lv_style_reset(style);
else
lv_style_init(style);
}
static void basic_init(void)
{
static void basic_init(void) {
style_init_reset(&style_pad);
lv_style_set_pad_top(&style_pad, LV_STATE_DEFAULT, LV_VER_RES / 30);
@ -103,7 +102,6 @@ static void basic_init(void)
lv_style_set_border_color(&style_box_border, LV_STATE_DEFAULT, LV_PINETIME_GRAY);
lv_style_set_text_color(&style_box, LV_STATE_DEFAULT, LV_PINETIME_BLUE);
style_init_reset(&style_title);
lv_style_set_text_color(&style_title, LV_STATE_DEFAULT, LV_PINETIME_WHITE);
lv_style_set_text_font(&style_title, LV_STATE_DEFAULT, theme.font_subtitle);
@ -301,10 +299,8 @@ static void basic_init(void)
lv_style_set_pad_right(&style_cb_bullet, LV_STATE_DEFAULT, LV_DPX(8));
lv_style_set_pad_top(&style_cb_bullet, LV_STATE_DEFAULT, LV_DPX(8));
lv_style_set_pad_bottom(&style_cb_bullet, LV_STATE_DEFAULT, LV_DPX(8));
}
/**********************
* GLOBAL FUNCTIONS
**********************/
@ -320,10 +316,13 @@ static void basic_init(void)
* @param font_title pointer to a extra large font
* @return a pointer to reference this theme later
*/
lv_theme_t * lv_pinetime_theme_init(lv_color_t color_primary, lv_color_t color_secondary, uint32_t flags,
const lv_font_t * font_small, const lv_font_t * font_normal, const lv_font_t * font_subtitle,
const lv_font_t * font_title)
{
lv_theme_t* lv_pinetime_theme_init(lv_color_t color_primary,
lv_color_t color_secondary,
uint32_t flags,
const lv_font_t* font_small,
const lv_font_t* font_normal,
const lv_font_t* font_subtitle,
const lv_font_t* font_title) {
theme.color_primary = color_primary;
theme.color_secondary = color_secondary;
theme.font_small = font_small;
@ -341,9 +340,7 @@ lv_theme_t * lv_pinetime_theme_init(lv_color_t color_primary, lv_color_t color_s
return &theme;
}
static void theme_apply(lv_obj_t * obj, lv_theme_style_t name)
{
static void theme_apply(lv_obj_t* obj, lv_theme_style_t name) {
lv_style_list_t* list;
/*To avoid warnings*/
@ -442,7 +439,6 @@ static void theme_apply(lv_obj_t * obj, lv_theme_style_t name)
_lv_style_list_add_style(list, &style_list_btn);
break;
case LV_THEME_ARC:
lv_obj_clean_style_list(obj, LV_ARC_PART_BG);
list = lv_obj_get_style_list(obj, LV_ARC_PART_BG);
@ -453,7 +449,6 @@ static void theme_apply(lv_obj_t * obj, lv_theme_style_t name)
_lv_style_list_add_style(list, &style_arc_indic);
break;
case LV_THEME_SWITCH:
lv_obj_clean_style_list(obj, LV_SWITCH_PART_BG);
list = lv_obj_get_style_list(obj, LV_SWITCH_PART_BG);
@ -526,15 +521,11 @@ static void theme_apply(lv_obj_t * obj, lv_theme_style_t name)
_lv_style_list_add_style(list, &style_cb_bullet);
break;
default:
break;
}
lv_obj_refresh_style(obj, LV_OBJ_PART_ALL, LV_STYLE_PROP_ALL);
}
/**********************

@ -31,12 +31,10 @@ extern "C" {
* TYPEDEFS
**********************/
/**********************
* GLOBAL PROTOTYPES
**********************/
/**
* Initialize the default
* @param color_primary the primary color of the theme
@ -48,8 +46,12 @@ extern "C" {
* @param font_title pointer to a extra large font
* @return a pointer to reference this theme later
*/
lv_theme_t * lv_pinetime_theme_init(lv_color_t color_primary, lv_color_t color_secondary, uint32_t flags,
const lv_font_t * font_small, const lv_font_t * font_normal, const lv_font_t * font_subtitle,
lv_theme_t* lv_pinetime_theme_init(lv_color_t color_primary,
lv_color_t color_secondary,
uint32_t flags,
const lv_font_t* font_small,
const lv_font_t* font_normal,
const lv_font_t* font_subtitle,
const lv_font_t* font_title);
/**********************
* MACROS

@ -11,21 +11,24 @@ using namespace Pinetime::Applications::Screens;
ApplicationList::ApplicationList(Pinetime::Applications::DisplayApp* app,
Pinetime::Controllers::Settings& settingsController,
Pinetime::Controllers::Battery& batteryController,
Controllers::DateTime& dateTimeController) :
Screen(app),
Controllers::DateTime& dateTimeController)
: Screen(app),
settingsController {settingsController},
batteryController {batteryController},
dateTimeController {dateTimeController},
screens {app,
settingsController.GetAppMenu(),
{
[this]() -> std::unique_ptr<Screen> { return CreateScreen1(); },
[this]() -> std::unique_ptr<Screen> { return CreateScreen2(); },
[this]() -> std::unique_ptr<Screen> {
return CreateScreen1();
},
[this]() -> std::unique_ptr<Screen> {
return CreateScreen2();
},
//[this]() -> std::unique_ptr<Screen> { return CreateScreen3(); }
},
Screens::ScreenListModes::UpDown
} {}
Screens::ScreenListModes::UpDown} {
}
ApplicationList::~ApplicationList() {
lv_obj_clean(lv_scr_act());
@ -42,31 +45,27 @@ bool ApplicationList::OnTouchEvent(Pinetime::Applications::TouchEvents event) {
}
std::unique_ptr<Screen> ApplicationList::CreateScreen1() {
std::array<Screens::Tile::Applications, 6> applications {
{
std::array<Screens::Tile::Applications, 6> applications {{
{Symbols::stopWatch, Apps::StopWatch},
{Symbols::music, Apps::Music},
{Symbols::map, Apps::Navigation},
{Symbols::shoe, Apps::Motion},
{Symbols::heartBeat, Apps::HeartRate},
{"", Apps::None},
}
};
}};
return std::make_unique<Screens::Tile>(0, 2, app, settingsController, batteryController, dateTimeController, applications);
}
std::unique_ptr<Screen> ApplicationList::CreateScreen2() {
std::array<Screens::Tile::Applications, 6> applications {
{
std::array<Screens::Tile::Applications, 6> applications {{
{Symbols::paintbrush, Apps::Paint},
{Symbols::paddle, Apps::Paddle},
{"2", Apps::Twos},
{"", Apps::None},
{"", Apps::None},
{"", Apps::None},
}
};
}};
return std::make_unique<Screens::Tile>(1, 2, app, settingsController, batteryController, dateTimeController, applications);
}
@ -84,4 +83,3 @@ std::unique_ptr<Screen> ApplicationList::CreateScreen2() {
return std::make_unique<Screens::Tile>(2, 3, app, settingsController, batteryController, dateTimeController, applications);
}*/

@ -20,8 +20,8 @@ namespace Pinetime {
~ApplicationList() override;
bool Refresh() override;
bool OnTouchEvent(TouchEvents event) override;
private:
private:
Controllers::Settings& settingsController;
Pinetime::Controllers::Battery& batteryController;
Controllers::DateTime& dateTimeController;

@ -4,10 +4,14 @@
using namespace Pinetime::Applications::Screens;
const char* BatteryIcon::GetBatteryIcon(int batteryPercent) {
if(batteryPercent > 90) return Symbols::batteryFull;
if(batteryPercent > 75) return Symbols::batteryThreeQuarter;
if(batteryPercent > 50) return Symbols::batteryHalf;
if(batteryPercent > 25) return Symbols::batteryOneQuarter;
if (batteryPercent > 90)
return Symbols::batteryFull;
if (batteryPercent > 75)
return Symbols::batteryThreeQuarter;
if (batteryPercent > 50)
return Symbols::batteryHalf;
if (batteryPercent > 25)
return Symbols::batteryOneQuarter;
return Symbols::batteryEmpty;
}
@ -18,5 +22,6 @@ const char* BatteryIcon::GetUnknownIcon() {
const char* BatteryIcon::GetPlugIcon(bool isCharging) {
if (isCharging)
return Symbols::plug;
else return "";
else
return "";
}

@ -14,12 +14,8 @@ static void lv_anim_task(struct _lv_task_t *task) {
user_data->UpdateAnim();
}
BatteryInfo::BatteryInfo(
Pinetime::Applications::DisplayApp *app,
Pinetime::Controllers::Battery& batteryController) :
Screen(app),
batteryController{batteryController}
{
BatteryInfo::BatteryInfo(Pinetime::Applications::DisplayApp* app, Pinetime::Controllers::Battery& batteryController)
: Screen(app), batteryController {batteryController} {
batteryPercent = batteryController.PercentRemaining();
batteryVoltage = batteryController.Voltage();
@ -53,7 +49,8 @@ BatteryInfo::BatteryInfo(
// hack to not use the flot functions from printf
uint8_t batteryVoltageBytes[2];
batteryVoltageBytes[1] = static_cast<uint8_t>(batteryVoltage); // truncate whole numbers
batteryVoltageBytes[0] = static_cast<uint8_t>((batteryVoltage - batteryVoltageBytes[1]) * 100); //remove whole part of flt and shift 2 places over
batteryVoltageBytes[0] =
static_cast<uint8_t>((batteryVoltage - batteryVoltageBytes[1]) * 100); // remove whole part of flt and shift 2 places over
//
voltage = lv_label_create(lv_scr_act(), nullptr);
@ -73,7 +70,6 @@ BatteryInfo::BatteryInfo(
UpdateScreen();
}
BatteryInfo::~BatteryInfo() {
lv_task_del(taskUpdate);
lv_task_del(taskAnim);
@ -136,14 +132,13 @@ void BatteryInfo::UpdateScreen() {
// hack to not use the flot functions from printf
uint8_t batteryVoltageBytes[2];
batteryVoltageBytes[1] = static_cast<uint8_t>(batteryVoltage); // truncate whole numbers
batteryVoltageBytes[0] = static_cast<uint8_t>((batteryVoltage - batteryVoltageBytes[1]) * 100); //remove whole part of flt and shift 2 places over
batteryVoltageBytes[0] =
static_cast<uint8_t>((batteryVoltage - batteryVoltageBytes[1]) * 100); // remove whole part of flt and shift 2 places over
//
lv_label_set_text_fmt(voltage, "%1i.%02i volts", batteryVoltageBytes[1], batteryVoltageBytes[0]);
}
bool BatteryInfo::Refresh() {
return running;
}

@ -6,7 +6,6 @@
#include "Screen.h"
#include <lvgl/lvgl.h>
namespace Pinetime {
namespace Controllers {
class Battery;
@ -17,18 +16,15 @@ namespace Pinetime {
class BatteryInfo : public Screen {
public:
BatteryInfo(DisplayApp* app,
Pinetime::Controllers::Battery& batteryController);
BatteryInfo(DisplayApp* app, Pinetime::Controllers::Battery& batteryController);
~BatteryInfo() override;
bool Refresh() override;
void UpdateScreen();
void UpdateAnim();
private:
Pinetime::Controllers::Battery& batteryController;
lv_obj_t* voltage;
@ -42,7 +38,6 @@ namespace Pinetime {
int8_t animation = 0;
int8_t batteryPercent = -1;
float batteryVoltage = 0.0f;
};
}
}

@ -3,6 +3,8 @@
using namespace Pinetime::Applications::Screens;
const char* BleIcon::GetIcon(bool isConnected) {
if(isConnected) return Symbols::bluetooth;
else return "";
if (isConnected)
return Symbols::bluetooth;
else
return "";
}

@ -10,7 +10,8 @@ void slider_event_cb(lv_obj_t * slider, lv_event_t event) {
}
}
Brightness::Brightness(Pinetime::Applications::DisplayApp *app, Controllers::BrightnessController& brightness) : Screen(app), brightness{brightness} {
Brightness::Brightness(Pinetime::Applications::DisplayApp* app, Controllers::BrightnessController& brightness)
: Screen(app), brightness {brightness} {
slider = lv_slider_create(lv_scr_act(), nullptr);
lv_obj_set_user_data(slider, this);
lv_obj_set_width(slider, LV_DPI * 2);
@ -35,11 +36,16 @@ bool Brightness::Refresh() {
const char* Brightness::LevelToString(Pinetime::Controllers::BrightnessController::Levels level) {
switch (level) {
case Pinetime::Controllers::BrightnessController::Levels::Off: return "Off";
case Pinetime::Controllers::BrightnessController::Levels::Low: return "Low";
case Pinetime::Controllers::BrightnessController::Levels::Medium: return "Medium";
case Pinetime::Controllers::BrightnessController::Levels::High: return "High";
default : return "???";
case Pinetime::Controllers::BrightnessController::Levels::Off:
return "Off";
case Pinetime::Controllers::BrightnessController::Levels::Low:
return "Low";
case Pinetime::Controllers::BrightnessController::Levels::Medium:
return "Medium";
case Pinetime::Controllers::BrightnessController::Levels::High:
return "High";
default:
return "???";
}
}
@ -49,20 +55,31 @@ void Brightness::OnValueChanged() {
void Brightness::SetValue(uint8_t value) {
switch (value) {
case 0: brightness.Set(Controllers::BrightnessController::Levels::Low); break;
case 1: brightness.Set(Controllers::BrightnessController::Levels::Medium); break;
case 2: brightness.Set(Controllers::BrightnessController::Levels::High); break;
case 0:
brightness.Set(Controllers::BrightnessController::Levels::Low);
break;
case 1:
brightness.Set(Controllers::BrightnessController::Levels::Medium);
break;
case 2:
brightness.Set(Controllers::BrightnessController::Levels::High);
break;
}
lv_label_set_text(slider_label, LevelToString(brightness.Level()));
}
uint8_t Brightness::LevelToInt(Pinetime::Controllers::BrightnessController::Levels level) {
switch (level) {
case Pinetime::Controllers::BrightnessController::Levels::Off: return 0;
case Pinetime::Controllers::BrightnessController::Levels::Low: return 0;
case Pinetime::Controllers::BrightnessController::Levels::Medium: return 1;
case Pinetime::Controllers::BrightnessController::Levels::High: return 2;
default : return 0;
case Pinetime::Controllers::BrightnessController::Levels::Off:
return 0;
case Pinetime::Controllers::BrightnessController::Levels::Low:
return 0;
case Pinetime::Controllers::BrightnessController::Levels::Medium:
return 1;
case Pinetime::Controllers::BrightnessController::Levels::High:
return 2;
default:
return 0;
}
}

@ -17,8 +17,8 @@ namespace Pinetime {
bool OnTouchEvent(TouchEvents event) override;
void OnValueChanged();
private:
private:
Controllers::BrightnessController& brightness;
lv_obj_t* slider_label;

@ -15,7 +15,6 @@
#include "WatchFaceDigital.h"
#include "WatchFaceAnalog.h"
using namespace Pinetime::Applications::Screens;
Clock::Clock(DisplayApp* app,
@ -25,33 +24,37 @@ Clock::Clock(DisplayApp* app,
Controllers::NotificationManager& notificatioManager,
Controllers::Settings& settingsController,
Controllers::HeartRateController& heartRateController,
Controllers::MotionController& motionController) : Screen(app),
dateTimeController{dateTimeController}, batteryController{batteryController},
bleController{bleController}, notificatioManager{notificatioManager},
Controllers::MotionController& motionController)
: Screen(app),
dateTimeController {dateTimeController},
batteryController {batteryController},
bleController {bleController},
notificatioManager {notificatioManager},
settingsController {settingsController},
heartRateController {heartRateController},
motionController {motionController},
screens {app,
settingsController.GetClockFace(),
{
[this]() -> std::unique_ptr<Screen> { return WatchFaceDigitalScreen(); },
[this]() -> std::unique_ptr<Screen> { return WatchFaceAnalogScreen(); },
[this]() -> std::unique_ptr<Screen> {
return WatchFaceDigitalScreen();
},
[this]() -> std::unique_ptr<Screen> {
return WatchFaceAnalogScreen();
},
// Examples for more watch faces
//[this]() -> std::unique_ptr<Screen> { return WatchFaceMinimalScreen(); },
//[this]() -> std::unique_ptr<Screen> { return WatchFaceCustomScreen(); }
},
Screens::ScreenListModes::LongPress
} {
Screens::ScreenListModes::LongPress} {
settingsController.SetAppMenu(0);
}
Clock::~Clock() {
lv_obj_clean(lv_scr_act());
}
bool Clock::Refresh() {
screens.Refresh();
return running;
@ -62,20 +65,30 @@ bool Clock::OnTouchEvent(Pinetime::Applications::TouchEvents event) {
}
std::unique_ptr<Screen> Clock::WatchFaceDigitalScreen() {
return std::make_unique<Screens::WatchFaceDigital>(app, dateTimeController, batteryController, bleController, notificatioManager, settingsController, heartRateController, motionController);
return std::make_unique<Screens::WatchFaceDigital>(app,
dateTimeController,
batteryController,
bleController,
notificatioManager,
settingsController,
heartRateController,
motionController);
}
std::unique_ptr<Screen> Clock::WatchFaceAnalogScreen() {
return std::make_unique<Screens::WatchFaceAnalog>(app, dateTimeController, batteryController, bleController, notificatioManager, settingsController);
return std::make_unique<Screens::WatchFaceAnalog>(
app, dateTimeController, batteryController, bleController, notificatioManager, settingsController);
}
/*
// Examples for more watch faces
std::unique_ptr<Screen> Clock::WatchFaceMinimalScreen() {
return std::make_unique<Screens::WatchFaceMinimal>(app, dateTimeController, batteryController, bleController, notificatioManager, settingsController);
return std::make_unique<Screens::WatchFaceMinimal>(app, dateTimeController, batteryController, bleController, notificatioManager,
settingsController);
}
std::unique_ptr<Screen> Clock::WatchFaceCustomScreen() {
return std::make_unique<Screens::WatchFaceCustom>(app, dateTimeController, batteryController, bleController, notificatioManager, settingsController);
return std::make_unique<Screens::WatchFaceCustom>(app, dateTimeController, batteryController, bleController, notificatioManager,
settingsController);
}
*/

@ -39,7 +39,6 @@ namespace Pinetime {
bool OnTouchEvent(TouchEvents event) override;
private:
Controllers::DateTime& dateTimeController;
Controllers::Battery& batteryController;
Controllers::Ble& bleController;
@ -48,7 +47,6 @@ namespace Pinetime {
Controllers::HeartRateController& heartRateController;
Controllers::MotionController& motionController;
ScreenList<2> screens;
std::unique_ptr<Screen> WatchFaceDigitalScreen();
std::unique_ptr<Screen> WatchFaceAnalogScreen();
@ -56,9 +54,6 @@ namespace Pinetime {
// Examples for more watch faces
// std::unique_ptr<Screen> WatchFaceMinimalScreen();
// std::unique_ptr<Screen> WatchFaceCustomScreen();
};
}
}

@ -8,7 +8,8 @@ using namespace Pinetime::Applications::Screens;
DropDownDemo::DropDownDemo(Pinetime::Applications::DisplayApp* app) : Screen(app) {
// Create the dropdown object, with many item, and fix its height
ddlist = lv_ddlist_create(lv_scr_act(), nullptr);
lv_ddlist_set_options(ddlist, "Apple\n"
lv_ddlist_set_options(ddlist,
"Apple\n"
"Banana\n"
"Orange\n"
"Melon\n"
@ -54,4 +55,3 @@ bool DropDownDemo::OnTouchEvent(Pinetime::Applications::TouchEvents event) {
return false;
}
}

@ -5,9 +5,8 @@
using namespace Pinetime::Applications::Screens;
FirmwareUpdate::FirmwareUpdate(Pinetime::Applications::DisplayApp *app, Pinetime::Controllers::Ble& bleController) :
Screen(app), bleController{bleController} {
FirmwareUpdate::FirmwareUpdate(Pinetime::Applications::DisplayApp* app, Pinetime::Controllers::Ble& bleController)
: Screen(app), bleController {bleController} {
lv_obj_t * backgroundLabel = lv_label_create(lv_scr_act(), nullptr);
lv_label_set_long_mode(backgroundLabel, LV_LABEL_LONG_CROP);

@ -17,7 +17,6 @@ namespace Pinetime {
bool Refresh() override;
private:
enum class States { Idle, Running, Validated, Error };
Pinetime::Controllers::Ble& bleController;

@ -7,23 +7,20 @@
using namespace Pinetime::Applications::Screens;
namespace {
static void ButtonEventHandler(lv_obj_t * obj, lv_event_t event)
{
static void ButtonEventHandler(lv_obj_t* obj, lv_event_t event) {
FirmwareValidation* screen = static_cast<FirmwareValidation*>(obj->user_data);
screen->OnButtonEvent(obj, event);
}
}
FirmwareValidation::FirmwareValidation(Pinetime::Applications::DisplayApp *app,
Pinetime::Controllers::FirmwareValidator &validator)
FirmwareValidation::FirmwareValidation(Pinetime::Applications::DisplayApp* app, Pinetime::Controllers::FirmwareValidator& validator)
: Screen {app}, validator {validator} {
labelVersionInfo = lv_label_create(lv_scr_act(), nullptr);
lv_obj_align(labelVersionInfo, nullptr, LV_ALIGN_IN_TOP_LEFT, 0, 0);
lv_label_set_text(labelVersionInfo, "Version : ");
lv_label_set_align(labelVersionInfo, LV_LABEL_ALIGN_LEFT);
labelVersionValue = lv_label_create(lv_scr_act(), nullptr);
lv_obj_align(labelVersionValue, labelVersionInfo, LV_ALIGN_OUT_RIGHT_MID, 0, 0);
lv_label_set_recolor(labelVersionValue, true);
@ -39,8 +36,7 @@ FirmwareValidation::FirmwareValidation(Pinetime::Applications::DisplayApp *app,
if (validator.IsValidated())
lv_label_set_text(labelIsValidated, "You have already\n#00ff00 validated# this firmware#");
else {
lv_label_set_text(labelIsValidated,
"Please #00ff00 Validate# this version or\n#ff0000 Reset# to rollback to the previous version.");
lv_label_set_text(labelIsValidated, "Please #00ff00 Validate# this version or\n#ff0000 Reset# to rollback to the previous version.");
buttonValidate = lv_btn_create(lv_scr_act(), nullptr);
lv_obj_align(buttonValidate, NULL, LV_ALIGN_IN_BOTTOM_LEFT, 0, 0);
@ -62,7 +58,6 @@ FirmwareValidation::FirmwareValidation(Pinetime::Applications::DisplayApp *app,
}
}
FirmwareValidation::~FirmwareValidation() {
lv_obj_clean(lv_scr_act());
}
@ -78,5 +73,4 @@ void FirmwareValidation::OnButtonEvent(lv_obj_t *object, lv_event_t event) {
} else if (object == buttonReset && event == LV_EVENT_PRESSED) {
validator.Reset();
}
}

@ -18,7 +18,6 @@ namespace Pinetime {
bool Refresh() override;
void OnButtonEvent(lv_obj_t* object, lv_event_t event);
private:
@ -32,7 +31,6 @@ namespace Pinetime {
lv_obj_t* labelButtonValidate;
lv_obj_t* buttonReset;
lv_obj_t* labelButtonReset;
};
}
}

@ -11,11 +11,10 @@ namespace {
}
}
FlashLight::FlashLight(
Pinetime::Applications::DisplayApp *app,
FlashLight::FlashLight(Pinetime::Applications::DisplayApp* app,
System::SystemTask& systemTask,
Controllers::BrightnessController& brightness) :
Screen(app),
Controllers::BrightnessController& brightness)
: Screen(app),
systemTask {systemTask},
brightness {brightness}
@ -41,10 +40,8 @@ FlashLight::FlashLight(
lv_obj_set_event_cb(backgroundAction, event_handler);
systemTask.PushMessage(Pinetime::System::SystemTask::Messages::DisableSleeping);
}
FlashLight::~FlashLight() {
lv_obj_clean(lv_scr_act());
lv_obj_set_style_local_bg_color(lv_scr_act(), LV_OBJ_PART_MAIN, LV_STATE_DEFAULT, lv_color_hex(0x000000));
@ -64,7 +61,6 @@ void FlashLight::OnClickEvent(lv_obj_t *obj, lv_event_t event) {
lv_obj_set_style_local_bg_color(lv_scr_act(), LV_OBJ_PART_MAIN, LV_STATE_DEFAULT, lv_color_hex(0x000000));
lv_obj_set_style_local_text_color(flashLight, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, lv_color_hex(0xFFFFFF));
}
}
}
}
@ -76,4 +72,3 @@ bool FlashLight::Refresh() {
bool FlashLight::OnTouchEvent(Pinetime::Applications::TouchEvents event) {
return true;
}

@ -6,7 +6,6 @@
#include "systemtask/SystemTask.h"
#include "components/brightness/BrightnessController.h"
namespace Pinetime {
namespace Applications {
@ -29,7 +28,6 @@ namespace Pinetime {
lv_obj_t* flashLight;
lv_obj_t* backgroundAction;
bool isOn = true;
};
}
}

@ -27,8 +27,10 @@ namespace {
}
}
HeartRate::HeartRate(Pinetime::Applications::DisplayApp *app, Controllers::HeartRateController& heartRateController, System::SystemTask &systemTask) :
Screen(app), heartRateController{heartRateController}, systemTask{systemTask} {
HeartRate::HeartRate(Pinetime::Applications::DisplayApp* app,
Controllers::HeartRateController& heartRateController,
System::SystemTask& systemTask)
: Screen(app), heartRateController {heartRateController}, systemTask {systemTask} {
bool isHrRunning = heartRateController.State() != Controllers::HeartRateController::States::Stopped;
label_hr = lv_label_create(lv_scr_act(), nullptr);
@ -95,8 +97,7 @@ void HeartRate::OnStartStopEvent(lv_event_t event) {
UpdateStartStopButton(heartRateController.State() != Controllers::HeartRateController::States::Stopped);
systemTask.PushMessage(Pinetime::System::SystemTask::Messages::DisableSleeping);
lv_obj_set_style_local_text_color(label_hr, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, LV_COLOR_GREEN);
}
else {
} else {
heartRateController.Stop();
UpdateStartStopButton(heartRateController.State() != Controllers::HeartRateController::States::Stopped);
systemTask.PushMessage(Pinetime::System::SystemTask::Messages::EnableSleeping);

@ -33,9 +33,6 @@ namespace Pinetime {
lv_obj_t* label_status;
lv_obj_t* btn_startStop;
lv_obj_t* label_startStop;
};
}
}

@ -72,4 +72,3 @@ bool InfiniPaint::OnTouchEvent(uint16_t x, uint16_t y) {
lvgl.FlushDisplay(&area, b);
return true;
}

@ -31,7 +31,6 @@ namespace Pinetime {
lv_color_t b[bufferSize];
lv_color_t selectColor = LV_COLOR_WHITE;
uint8_t color = 2;
};
}
}

@ -2,10 +2,8 @@
using namespace Pinetime::Applications::Screens;
Label::Label(uint8_t screenID, uint8_t numScreens,
Pinetime::Applications::DisplayApp *app, lv_obj_t* labelText) :
Screen(app),
labelText{labelText} {
Label::Label(uint8_t screenID, uint8_t numScreens, Pinetime::Applications::DisplayApp* app, lv_obj_t* labelText)
: Screen(app), labelText {labelText} {
if (numScreens > 1) {
pageIndicatorBasePoints[0].x = 240 - 1;
@ -19,7 +17,6 @@ Label::Label(uint8_t screenID, uint8_t numScreens,
lv_obj_set_style_local_line_rounded(pageIndicatorBase, LV_LINE_PART_MAIN, LV_STATE_DEFAULT, true);
lv_line_set_points(pageIndicatorBase, pageIndicatorBasePoints, 2);
uint16_t indicatorSize = 228 / numScreens;
uint16_t indicatorPos = indicatorSize * screenID;
@ -34,7 +31,6 @@ Label::Label(uint8_t screenID, uint8_t numScreens,
lv_obj_set_style_local_line_rounded(pageIndicator, LV_LINE_PART_MAIN, LV_STATE_DEFAULT, true);
lv_line_set_points(pageIndicator, pageIndicatorPoints, 2);
}
}
Label::~Label() {

@ -9,15 +9,12 @@ namespace Pinetime {
class Label : public Screen {
public:
Label( uint8_t screenID, uint8_t numScreens,
DisplayApp* app, lv_obj_t* labelText );
Label(uint8_t screenID, uint8_t numScreens, DisplayApp* app, lv_obj_t* labelText);
~Label() override;
bool Refresh() override;
private:
bool running = true;
lv_obj_t* labelText = nullptr;

@ -12,13 +12,12 @@ namespace {
}
List::List(uint8_t screenID, uint8_t numScreens,
List::List(uint8_t screenID,
uint8_t numScreens,
DisplayApp* app,
Controllers::Settings& settingsController,
std::array<Applications, MAXLISTITEMS>& applications) :
Screen(app),
settingsController{settingsController}
{
std::array<Applications, MAXLISTITEMS>& applications)
: Screen(app), settingsController {settingsController} {
// Set the background to Black
lv_obj_set_style_local_bg_color(lv_scr_act(), LV_OBJ_PART_MAIN, LV_STATE_DEFAULT, lv_color_make(0, 0, 0));
@ -37,7 +36,6 @@ List::List(uint8_t screenID, uint8_t numScreens,
lv_obj_set_style_local_line_rounded(pageIndicatorBase, LV_LINE_PART_MAIN, LV_STATE_DEFAULT, true);
lv_line_set_points(pageIndicatorBase, pageIndicatorBasePoints, 2);
uint16_t indicatorSize = 228 / numScreens;
uint16_t indicatorPos = indicatorSize * screenID;
@ -53,7 +51,6 @@ List::List(uint8_t screenID, uint8_t numScreens,
lv_line_set_points(pageIndicator, pageIndicatorPoints, 2);
}
lv_obj_t* container1 = lv_cont_create(lv_scr_act(), nullptr);
// lv_obj_set_style_local_bg_color(container1, LV_CONT_PART_MAIN, LV_STATE_DEFAULT, lv_color_hex(0x111111));
@ -91,7 +88,6 @@ List::List(uint8_t screenID, uint8_t numScreens,
labelBt = lv_label_create(itemApps[i], nullptr);
lv_label_set_text_fmt(labelBt, " %s", applications[i].name);
}
}
@ -100,7 +96,6 @@ List::List(uint8_t screenID, uint8_t numScreens,
lv_obj_set_size(backgroundLabel, LV_HOR_RES, LV_VER_RES);
lv_obj_set_pos(backgroundLabel, 0, 0);
lv_label_set_text_static(backgroundLabel, "");
}
List::~List() {
@ -123,4 +118,3 @@ void List::OnButtonEvent(lv_obj_t * object, lv_event_t event) {
}
}
}

@ -20,7 +20,8 @@ namespace Pinetime {
Pinetime::Applications::Apps application;
};
explicit List(uint8_t screenID, uint8_t numScreens,
explicit List(uint8_t screenID,
uint8_t numScreens,
DisplayApp* app,
Controllers::Settings& settingsController,
std::array<Applications, MAXLISTITEMS>& applications);
@ -28,11 +29,9 @@ namespace Pinetime {
bool Refresh() override;
void OnButtonEvent(lv_obj_t* object, lv_event_t event);
private:
Controllers::Settings& settingsController;
Pinetime::Applications::Apps apps[MAXLISTITEMS];
@ -42,7 +41,6 @@ namespace Pinetime {
lv_point_t pageIndicatorPoints[2];
lv_obj_t* pageIndicatorBase;
lv_obj_t* pageIndicator;
};
}
}

@ -4,7 +4,6 @@
using namespace Pinetime::Applications::Screens;
Meter::Meter(Pinetime::Applications::DisplayApp* app) : Screen(app) {
/*Create a line meter */
@ -21,18 +20,17 @@ Meter::Meter(Pinetime::Applications::DisplayApp *app) : Screen(app) {
lv_obj_set_size(lmeter, 200, 200);
lv_obj_align(lmeter, nullptr, LV_ALIGN_CENTER, 0, 0);
}
Meter::~Meter() {
lv_obj_clean(lv_scr_act());
}
bool Meter::Refresh() {
lv_linemeter_set_value(lmeter, value++); /*Set the current value*/
if(value>=60) value = 0;
if (value >= 60)
value = 0;
return running;
}

@ -21,8 +21,6 @@ namespace Pinetime {
lv_obj_t* lmeter;
uint32_t value = 0;
};
}
}

@ -6,8 +6,8 @@ using namespace Pinetime::Applications::Screens;
extern lv_font_t jetbrains_mono_extrabold_compressed;
extern lv_font_t jetbrains_mono_bold_20;
Motion::Motion(Pinetime::Applications::DisplayApp *app, Controllers::MotionController& motionController) : Screen(app), motionController{motionController} {
Motion::Motion(Pinetime::Applications::DisplayApp* app, Controllers::MotionController& motionController)
: Screen(app), motionController {motionController} {
chart = lv_chart_create(lv_scr_act(), NULL);
lv_obj_set_size(chart, 240, 240);
lv_obj_align(chart, NULL, LV_ALIGN_IN_TOP_MID, 0, 0);

@ -32,7 +32,6 @@ namespace Pinetime {
static constexpr uint8_t nbStepsBufferSize = 9;
char nbStepsBuffer[nbStepsBufferSize + 1];
bool running = true;
};
}
}

@ -125,7 +125,6 @@ Music::Music(Pinetime::Applications::DisplayApp *app, Pinetime::Controllers::Mus
lv_obj_set_width(txtArtist, LV_HOR_RES - 12);
lv_label_set_text(txtArtist, "Artist Name");
txtTrack = lv_label_create(lv_scr_act(), nullptr);
lv_label_set_long_mode(txtTrack, LV_LABEL_LONG_SROLL_CIRC);
lv_label_set_anim_speed(txtTrack, 1);
@ -202,8 +201,8 @@ bool Music::Refresh() {
frameB = !frameB;
if (currentLength < totalLength) {
currentLength += static_cast<int>((static_cast<float>(xTaskGetTickCount() - lastIncrement) / 1024.0f) *
musicService.getPlaybackSpeed());
currentLength +=
static_cast<int>((static_cast<float>(xTaskGetTickCount() - lastIncrement) / 1024.0f) * musicService.getPlaybackSpeed());
} else {
// Let's assume the getTrack finished, paused when the timer ends
// and there's no new getTrack being sent to us
@ -226,21 +225,21 @@ void Music::UpdateLength() {
lv_label_set_text(txtTrackDuration, "Inf/Inf");
} else if (totalLength > (99 * 60)) {
char timer[12];
sprintf(timer, "%02d:%02d/%02d:%02d",
sprintf(timer,
"%02d:%02d/%02d:%02d",
(currentLength / (60 * 60)) % 100,
((currentLength % (60 * 60)) / 60) % 100,
(totalLength / (60 * 60)) % 100,
((totalLength % (60 * 60)) / 60) % 100
);
((totalLength % (60 * 60)) / 60) % 100);
lv_label_set_text(txtTrackDuration, timer);
} else {
char timer[12];
sprintf(timer, "%02d:%02d/%02d:%02d",
sprintf(timer,
"%02d:%02d/%02d:%02d",
(currentLength / 60) % 100,
(currentLength % 60) % 100,
(totalLength / 60) % 100,
(totalLength % 60) % 100
);
(totalLength % 60) % 100);
lv_label_set_text(txtTrackDuration, timer);
}
}
@ -272,7 +271,6 @@ void Music::OnObjectEvent(lv_obj_t *obj, lv_event_t event) {
}
}
bool Music::OnTouchEvent(Pinetime::Applications::TouchEvents event) {
switch (event) {
case TouchEvents::SwipeUp: {

@ -37,8 +37,6 @@ namespace Pinetime {
bool Refresh() override;
void OnObjectEvent(lv_obj_t* obj, lv_event_t event);
private:
@ -81,7 +79,6 @@ namespace Pinetime {
bool playing;
/** Watchapp */
};
}
}

@ -28,7 +28,8 @@ LV_FONT_DECLARE(lv_font_navi_80)
* Navigation watchapp
*
*/
Navigation::Navigation(Pinetime::Applications::DisplayApp *app, Pinetime::Controllers::NavigationService &nav) : Screen(app), navService(nav) {
Navigation::Navigation(Pinetime::Applications::DisplayApp* app, Pinetime::Controllers::NavigationService& nav)
: Screen(app), navService(nav) {
imgFlag = lv_label_create(lv_scr_act(), nullptr);
lv_obj_set_style_local_text_font(imgFlag, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, &lv_font_navi_80);
@ -36,7 +37,6 @@ Navigation::Navigation(Pinetime::Applications::DisplayApp *app, Pinetime::Contro
lv_label_set_text(imgFlag, iconForName("flag"));
lv_obj_align(imgFlag, nullptr, LV_ALIGN_CENTER, 0, -60);
txtNarrative = lv_label_create(lv_scr_act(), nullptr);
lv_label_set_long_mode(txtNarrative, LV_LABEL_LONG_BREAK);
lv_obj_set_width(txtNarrative, LV_HOR_RES);

@ -23,7 +23,6 @@
#include "Screen.h"
#include <array>
namespace Pinetime {
namespace Controllers {
class NavigationService;
@ -39,7 +38,6 @@ namespace Pinetime {
bool Refresh() override;
private:
lv_obj_t* imgFlag;
lv_obj_t* txtNarrative;
lv_obj_t* txtManDist;

@ -3,6 +3,8 @@
using namespace Pinetime::Applications::Screens;
const char* NotificationIcon::GetIcon(bool newNotificationAvailable) {
if(newNotificationAvailable) return Symbols::info;
else return "";
if (newNotificationAvailable)
return Symbols::info;
else
return "";
}

Some files were not shown because too many files have changed in this diff Show More