commit
39a297c8a8
@ -50,7 +50,9 @@
|
|||||||
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads}""/>
|
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads/common}""/>
|
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads/common}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads/master}""/>
|
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads/master}""/>
|
||||||
|
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads/user_interface}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc:/${ProjName}/src/threads/rotary}""/>
|
<listOptionValue builtIn="false" value=""${workspace_loc:/${ProjName}/src/threads/rotary}""/>
|
||||||
|
<listOptionValue builtIn="false" value=""${workspace_loc:/${ProjName}/src/threads/manager}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/peripherals}""/>
|
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/peripherals}""/>
|
||||||
</option>
|
</option>
|
||||||
<option id="com.crt.advproject.cpp.misc.dialect.4036734" name="Language standard" superClass="com.crt.advproject.cpp.misc.dialect" useByScannerDiscovery="true" value="com.crt.advproject.misc.dialect.cpp17" valueType="enumerated"/>
|
<option id="com.crt.advproject.cpp.misc.dialect.4036734" name="Language standard" superClass="com.crt.advproject.cpp.misc.dialect" useByScannerDiscovery="true" value="com.crt.advproject.misc.dialect.cpp17" valueType="enumerated"/>
|
||||||
@ -82,6 +84,7 @@
|
|||||||
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads}""/>
|
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads/common}""/>
|
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads/common}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads/master}""/>
|
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads/master}""/>
|
||||||
|
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads/user_interface}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/peripherals}""/>
|
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/peripherals}""/>
|
||||||
</option>
|
</option>
|
||||||
<option id="com.crt.advproject.c.misc.dialect.82852045" name="Language standard" superClass="com.crt.advproject.c.misc.dialect" useByScannerDiscovery="true" value="com.crt.advproject.misc.dialect.c17" valueType="enumerated"/>
|
<option id="com.crt.advproject.c.misc.dialect.82852045" name="Language standard" superClass="com.crt.advproject.c.misc.dialect" useByScannerDiscovery="true" value="com.crt.advproject.misc.dialect.c17" valueType="enumerated"/>
|
||||||
@ -101,6 +104,7 @@
|
|||||||
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads}""/>
|
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads/common}""/>
|
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads/common}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads/master}""/>
|
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads/master}""/>
|
||||||
|
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads/user_interface}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/peripherals}""/>
|
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/peripherals}""/>
|
||||||
</option>
|
</option>
|
||||||
<inputType id="cdt.managedbuild.tool.gnu.assembler.input.1836378919" superClass="cdt.managedbuild.tool.gnu.assembler.input"/>
|
<inputType id="cdt.managedbuild.tool.gnu.assembler.input.1836378919" superClass="cdt.managedbuild.tool.gnu.assembler.input"/>
|
||||||
@ -199,6 +203,7 @@
|
|||||||
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/peripherals}""/>
|
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/peripherals}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/FreeRTOSCPP}""/>
|
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/FreeRTOSCPP}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads/common}""/>
|
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads/common}""/>
|
||||||
|
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads/user_interface}""/>
|
||||||
</option>
|
</option>
|
||||||
<inputType id="com.crt.advproject.compiler.cpp.input.903614193" superClass="com.crt.advproject.compiler.cpp.input"/>
|
<inputType id="com.crt.advproject.compiler.cpp.input.903614193" superClass="com.crt.advproject.compiler.cpp.input"/>
|
||||||
</tool>
|
</tool>
|
||||||
@ -228,6 +233,7 @@
|
|||||||
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/peripherals}""/>
|
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/peripherals}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/FreeRTOSCPP}""/>
|
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/FreeRTOSCPP}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads/common}""/>
|
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads/common}""/>
|
||||||
|
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads/user_interface}""/>
|
||||||
</option>
|
</option>
|
||||||
<option id="com.crt.advproject.c.misc.dialect.1008527937" name="Language standard" superClass="com.crt.advproject.c.misc.dialect" useByScannerDiscovery="true" value="com.crt.advproject.misc.dialect.c17" valueType="enumerated"/>
|
<option id="com.crt.advproject.c.misc.dialect.1008527937" name="Language standard" superClass="com.crt.advproject.c.misc.dialect" useByScannerDiscovery="true" value="com.crt.advproject.misc.dialect.c17" valueType="enumerated"/>
|
||||||
<inputType id="com.crt.advproject.compiler.input.246185412" superClass="com.crt.advproject.compiler.input"/>
|
<inputType id="com.crt.advproject.compiler.input.246185412" superClass="com.crt.advproject.compiler.input"/>
|
||||||
@ -248,6 +254,7 @@
|
|||||||
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/peripherals}""/>
|
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/peripherals}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/FreeRTOSCPP}""/>
|
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/FreeRTOSCPP}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads/common}""/>
|
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads/common}""/>
|
||||||
|
<listOptionValue builtIn="false" value=""${workspace_loc:/shoh/src/threads/user_interface}""/>
|
||||||
</option>
|
</option>
|
||||||
<inputType id="cdt.managedbuild.tool.gnu.assembler.input.1117166373" superClass="cdt.managedbuild.tool.gnu.assembler.input"/>
|
<inputType id="cdt.managedbuild.tool.gnu.assembler.input.1117166373" superClass="cdt.managedbuild.tool.gnu.assembler.input"/>
|
||||||
<inputType id="com.crt.advproject.assembler.input.2071009798" name="Additional Assembly Source Files" superClass="com.crt.advproject.assembler.input"/>
|
<inputType id="com.crt.advproject.assembler.input.2071009798" name="Additional Assembly Source Files" superClass="com.crt.advproject.assembler.input"/>
|
||||||
|
|||||||
@ -3,13 +3,13 @@
|
|||||||
#include "FreeRTOS.h"
|
#include "FreeRTOS.h"
|
||||||
#include "task.h"
|
#include "task.h"
|
||||||
#include <cr_section_macros.h>
|
#include <cr_section_macros.h>
|
||||||
|
#include "retarget_uart.h"
|
||||||
|
|
||||||
#include "ThreadCommon.h"
|
#include "ThreadCommon.h"
|
||||||
#include "Master.h"
|
#include "Master.h"
|
||||||
#include "Rotary.h"
|
#include "Rotary.h"
|
||||||
#include "retarget_uart.h"
|
#include "Manager.h"
|
||||||
#include "LiquidCrystal.h"
|
#include "UserInterface.h"
|
||||||
|
|
||||||
void lcd_starting();
|
|
||||||
|
|
||||||
int main(void)
|
int main(void)
|
||||||
{
|
{
|
||||||
@ -20,19 +20,30 @@ int main(void)
|
|||||||
|
|
||||||
printf("Hello there!\r\n");
|
printf("Hello there!\r\n");
|
||||||
|
|
||||||
lcd_starting();
|
|
||||||
|
|
||||||
ThreadCommon::ThreadManager* manager = new ThreadCommon::ThreadManager;
|
ThreadCommon::ThreadManager* manager = new ThreadCommon::ThreadManager;
|
||||||
ThreadCommon::QueueManager* qmanager = new ThreadCommon::QueueManager;
|
ThreadCommon::QueueManager* qmanager = new ThreadCommon::QueueManager;
|
||||||
//Creating queues
|
//Creating queues
|
||||||
qmanager->createQueue(100,
|
qmanager->createQueue(100,
|
||||||
sizeof(Event),
|
sizeof(Event),
|
||||||
ThreadCommon::QueueManager::master_event_all);
|
ThreadCommon::QueueManager::master_event_all);
|
||||||
|
qmanager->createQueue(20,
|
||||||
|
sizeof(Event),
|
||||||
|
ThreadCommon::QueueManager::manager_event_master);
|
||||||
|
qmanager->createQueue(20,
|
||||||
|
sizeof(UserInterface::InterfaceWithData),
|
||||||
|
ThreadCommon::QueueManager::ui_event_manager);
|
||||||
|
|
||||||
//Creating tasks
|
//Creating tasks
|
||||||
manager->createTask(master_thread, "master",
|
manager->createTask(thread_master, "master",
|
||||||
configMINIMAL_STACK_SIZE * 10,tskIDLE_PRIORITY + 1UL,
|
configMINIMAL_STACK_SIZE * 10,tskIDLE_PRIORITY + 1UL,
|
||||||
static_cast<void*>(qmanager));
|
static_cast<void*>(qmanager));
|
||||||
manager->createTask(rotary_thread, "rotary",
|
manager->createTask(thread_manager, "manager",
|
||||||
|
configMINIMAL_STACK_SIZE * 10,tskIDLE_PRIORITY + 1UL,
|
||||||
|
static_cast<void*>(qmanager));
|
||||||
|
manager->createTask(thread_rotary, "rotary",
|
||||||
|
configMINIMAL_STACK_SIZE * 10,tskIDLE_PRIORITY + 1UL,
|
||||||
|
static_cast<void*>(qmanager));
|
||||||
|
manager->createTask(thread_user_interface, "user_interface",
|
||||||
configMINIMAL_STACK_SIZE * 10,tskIDLE_PRIORITY + 1UL,
|
configMINIMAL_STACK_SIZE * 10,tskIDLE_PRIORITY + 1UL,
|
||||||
static_cast<void*>(qmanager));
|
static_cast<void*>(qmanager));
|
||||||
|
|
||||||
@ -41,44 +52,3 @@ int main(void)
|
|||||||
|
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief While we don't have UI, this should do for LCD.
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
void lcd_starting() {
|
|
||||||
// LCD pins init.
|
|
||||||
//Well, this lpc is a bit different with those. Table 83 from UM10732-11u68.pdf
|
|
||||||
DigitalIoPin *rs = new DigitalIoPin(1, 9, false);
|
|
||||||
Chip_IOCON_PinMuxSet (LPC_IOCON, 1, 9, (IOCON_FUNC0 | IOCON_MODE_INACT | IOCON_DIGMODE_EN));
|
|
||||||
|
|
||||||
DigitalIoPin *en = new DigitalIoPin(0, 14, false);
|
|
||||||
Chip_IOCON_PinMuxSet (LPC_IOCON, 0, 14, (IOCON_FUNC1 | IOCON_MODE_INACT | IOCON_DIGMODE_EN));
|
|
||||||
|
|
||||||
DigitalIoPin *d4 = new DigitalIoPin(0, 13, false);
|
|
||||||
Chip_IOCON_PinMuxSet (LPC_IOCON, 0, 13, (IOCON_FUNC1 | IOCON_MODE_INACT | IOCON_DIGMODE_EN));
|
|
||||||
|
|
||||||
DigitalIoPin *d5 = new DigitalIoPin(0, 12, false);
|
|
||||||
Chip_IOCON_PinMuxSet (LPC_IOCON, 0, 12, (IOCON_FUNC1 | IOCON_MODE_INACT | IOCON_DIGMODE_EN));
|
|
||||||
|
|
||||||
DigitalIoPin *d6 = new DigitalIoPin(0, 23, false);
|
|
||||||
Chip_IOCON_PinMuxSet (LPC_IOCON, 0, 23, (IOCON_FUNC0 | IOCON_MODE_INACT | IOCON_DIGMODE_EN));
|
|
||||||
|
|
||||||
DigitalIoPin *d7 = new DigitalIoPin(0, 11, false);
|
|
||||||
Chip_IOCON_PinMuxSet (LPC_IOCON, 0, 11, (IOCON_FUNC1 | IOCON_MODE_INACT | IOCON_DIGMODE_EN));
|
|
||||||
|
|
||||||
rs->write(false);
|
|
||||||
en->write(false);
|
|
||||||
d4->write(false);
|
|
||||||
d5->write(false);
|
|
||||||
d6->write(false);
|
|
||||||
d7->write(false);
|
|
||||||
// LCD init.
|
|
||||||
LiquidCrystal *lcd = new LiquidCrystal(rs, en, d4, d5, d6, d7);
|
|
||||||
// LCD configure display geometry.
|
|
||||||
lcd->begin(16, 2);
|
|
||||||
lcd->setCursor (0, 0);
|
|
||||||
lcd->print("Hello there");
|
|
||||||
lcd->setCursor (0, 1);
|
|
||||||
lcd->print("Starting...");
|
|
||||||
}
|
|
||||||
|
|||||||
@ -18,6 +18,12 @@ DigitalIoPin::DigitalIoPin (int port, int pin, bool input, bool pullup,
|
|||||||
_io._invert = invert;
|
_io._invert = invert;
|
||||||
_io.IOCON_mode = IOCON_MODE_INACT;
|
_io.IOCON_mode = IOCON_MODE_INACT;
|
||||||
_io.IOCON_inv = IOCON_FUNC0;
|
_io.IOCON_inv = IOCON_FUNC0;
|
||||||
|
//Table 83 from UM10732-11u68.pdf
|
||||||
|
if(port == 0 && ((pin >= 10 && pin <= 15) || pin == 0))
|
||||||
|
_io.IOFunction = IOCON_FUNC1;
|
||||||
|
else
|
||||||
|
_io.IOFunction = IOCON_FUNC0;
|
||||||
|
|
||||||
if (isr){
|
if (isr){
|
||||||
_io.isr_i = isr_index;
|
_io.isr_i = isr_index;
|
||||||
setIsr();
|
setIsr();
|
||||||
@ -48,7 +54,7 @@ DigitalIoPin::setIoPin ()
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
Chip_IOCON_PinMuxSet (LPC_IOCON, _io._port, _io._pin,
|
Chip_IOCON_PinMuxSet (LPC_IOCON, _io._port, _io._pin,
|
||||||
(_io.IOCON_mode | _io.DigitalEn | _io.IOCON_inv));
|
(_io.IOFunction | _io.IOCON_mode | _io.DigitalEn | _io.IOCON_inv));
|
||||||
/** False direction equals input */
|
/** False direction equals input */
|
||||||
Chip_GPIO_SetPinDIR (LPC_GPIO, _io._port, _io._pin, direction);
|
Chip_GPIO_SetPinDIR (LPC_GPIO, _io._port, _io._pin, direction);
|
||||||
}
|
}
|
||||||
@ -75,9 +81,9 @@ DigitalIoPin::setIsr ()
|
|||||||
Chip_Clock_SetIOCONFiltClockDiv(0, 64);
|
Chip_Clock_SetIOCONFiltClockDiv(0, 64);
|
||||||
|
|
||||||
Chip_IOCON_PinMuxSet (LPC_IOCON, _io._port, _io._pin,
|
Chip_IOCON_PinMuxSet (LPC_IOCON, _io._port, _io._pin,
|
||||||
(_io.IOCON_mode | _io.DigitalEn
|
(_io.IOFunction | _io.IOCON_mode
|
||||||
| _io.IOCON_inv | IOCON_CLKDIV(0)
|
| _io.DigitalEn | _io.IOCON_inv
|
||||||
| IOCON_S_MODE(3)));
|
| IOCON_CLKDIV(0) | IOCON_S_MODE(3)));
|
||||||
/** False direction equals input */
|
/** False direction equals input */
|
||||||
Chip_GPIO_SetPinDIR (LPC_GPIO, _io._port, _io._pin, direction);
|
Chip_GPIO_SetPinDIR (LPC_GPIO, _io._port, _io._pin, direction);
|
||||||
|
|
||||||
|
|||||||
@ -23,6 +23,7 @@ typedef struct DigitalIOConfigStruct
|
|||||||
uint32_t IOCON_mode;
|
uint32_t IOCON_mode;
|
||||||
uint32_t IOCON_inv;
|
uint32_t IOCON_inv;
|
||||||
uint32_t DigitalEn;
|
uint32_t DigitalEn;
|
||||||
|
uint32_t IOFunction;
|
||||||
IRQn_Type isr_i;
|
IRQn_Type isr_i;
|
||||||
} DigitalIOConfigStruct;
|
} DigitalIOConfigStruct;
|
||||||
|
|
||||||
|
|||||||
@ -104,6 +104,8 @@ LiquidCrystal::LiquidCrystal(DigitalIoPin *rs, DigitalIoPin *enable,
|
|||||||
begin(16, 2); // default to 16x2 display
|
begin(16, 2); // default to 16x2 display
|
||||||
}
|
}
|
||||||
|
|
||||||
|
LiquidCrystal::~LiquidCrystal() {}
|
||||||
|
|
||||||
void LiquidCrystal::begin(uint8_t cols, uint8_t lines, uint8_t dotsize) {
|
void LiquidCrystal::begin(uint8_t cols, uint8_t lines, uint8_t dotsize) {
|
||||||
if (lines > 1) {
|
if (lines > 1) {
|
||||||
_displayfunction |= LCD_2LINE;
|
_displayfunction |= LCD_2LINE;
|
||||||
@ -193,15 +195,17 @@ void LiquidCrystal::home()
|
|||||||
|
|
||||||
void LiquidCrystal::print(std::string const &s)
|
void LiquidCrystal::print(std::string const &s)
|
||||||
{
|
{
|
||||||
print(s.c_str());
|
print(s.c_str());
|
||||||
}
|
}
|
||||||
|
|
||||||
void LiquidCrystal::print(const char *s)
|
void LiquidCrystal::print(const char *s)
|
||||||
{
|
{
|
||||||
while(*s) {
|
for (uint8_t i = 0; *s != '\0' && i <= 1; i++) {
|
||||||
write(*s);
|
for (size_t q = 0; *s != '\0' && q < 16; q++, s++) {
|
||||||
++s;
|
this->setCursor(q, i);
|
||||||
}
|
this->write(*s);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void LiquidCrystal::setCursor(uint8_t col, uint8_t row)
|
void LiquidCrystal::setCursor(uint8_t col, uint8_t row)
|
||||||
|
|||||||
@ -50,6 +50,8 @@ public:
|
|||||||
LiquidCrystal(DigitalIoPin *rs, DigitalIoPin *enable,
|
LiquidCrystal(DigitalIoPin *rs, DigitalIoPin *enable,
|
||||||
DigitalIoPin *d0, DigitalIoPin *d1, DigitalIoPin *d2, DigitalIoPin *d3);
|
DigitalIoPin *d0, DigitalIoPin *d1, DigitalIoPin *d2, DigitalIoPin *d3);
|
||||||
|
|
||||||
|
virtual ~LiquidCrystal();
|
||||||
|
|
||||||
void begin(uint8_t cols, uint8_t rows, uint8_t charsize = LCD_5x8DOTS);
|
void begin(uint8_t cols, uint8_t rows, uint8_t charsize = LCD_5x8DOTS);
|
||||||
|
|
||||||
void clear();
|
void clear();
|
||||||
|
|||||||
@ -23,9 +23,16 @@ public:
|
|||||||
Rotary,
|
Rotary,
|
||||||
InternalTemp,
|
InternalTemp,
|
||||||
ExternalTemp,
|
ExternalTemp,
|
||||||
SetPoint
|
SetPoint,
|
||||||
|
NotifyUI
|
||||||
};
|
};
|
||||||
|
|
||||||
|
typedef struct _EventPair
|
||||||
|
{
|
||||||
|
EventRawData rd;
|
||||||
|
EventType et;
|
||||||
|
} EventPair;
|
||||||
|
|
||||||
Event(Event::EventType type, EventRawData data)
|
Event(Event::EventType type, EventRawData data)
|
||||||
{
|
{
|
||||||
events.insert({type, data});
|
events.insert({type, data});
|
||||||
|
|||||||
102
source/shoh/src/threads/manager/Counter.h
Normal file
102
source/shoh/src/threads/manager/Counter.h
Normal file
@ -0,0 +1,102 @@
|
|||||||
|
/*
|
||||||
|
* Counter.h
|
||||||
|
*
|
||||||
|
* Created on: Sep 1, 2022
|
||||||
|
* Author: tylen
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef COUNTER_H_
|
||||||
|
#define COUNTER_H_
|
||||||
|
|
||||||
|
#include "chip.h"
|
||||||
|
|
||||||
|
template <class CounterDataType> class Counter
|
||||||
|
{
|
||||||
|
|
||||||
|
public:
|
||||||
|
Counter (CounterDataType lower_boundary, CounterDataType upper_boundary,
|
||||||
|
CounterDataType step);
|
||||||
|
void inc ();
|
||||||
|
void dec ();
|
||||||
|
CounterDataType getCurrent ();
|
||||||
|
void setCurrent (CounterDataType num);
|
||||||
|
~Counter () = default;
|
||||||
|
|
||||||
|
private:
|
||||||
|
CounterDataType init;
|
||||||
|
CounterDataType up_lim;
|
||||||
|
CounterDataType down_lim;
|
||||||
|
CounterDataType _step;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
template <class CounterDataType>
|
||||||
|
void
|
||||||
|
Counter<CounterDataType>::inc ()
|
||||||
|
{
|
||||||
|
if ((init + _step) <= up_lim)
|
||||||
|
{
|
||||||
|
init += _step;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
template <class CounterDataType>
|
||||||
|
void
|
||||||
|
Counter<CounterDataType>::dec ()
|
||||||
|
{
|
||||||
|
if (init - _step >= down_lim)
|
||||||
|
{
|
||||||
|
init -= _step;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
template <class CounterDataType>
|
||||||
|
CounterDataType
|
||||||
|
Counter<CounterDataType>::getCurrent ()
|
||||||
|
{
|
||||||
|
return this->init;
|
||||||
|
}
|
||||||
|
|
||||||
|
template <class CounterDataType>
|
||||||
|
Counter<CounterDataType>::Counter (CounterDataType lower_boundary,
|
||||||
|
CounterDataType upper_boundary,
|
||||||
|
CounterDataType step)
|
||||||
|
{
|
||||||
|
up_lim = upper_boundary;
|
||||||
|
down_lim = lower_boundary;
|
||||||
|
_step = step;
|
||||||
|
if (down_lim > up_lim)
|
||||||
|
{
|
||||||
|
init = up_lim;
|
||||||
|
}
|
||||||
|
else if (down_lim < 0)
|
||||||
|
{
|
||||||
|
init = 0;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
init = down_lim;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
template <class CounterDataType>
|
||||||
|
void
|
||||||
|
Counter<CounterDataType>::setCurrent (CounterDataType num)
|
||||||
|
{
|
||||||
|
if (num > up_lim)
|
||||||
|
{
|
||||||
|
init = up_lim;
|
||||||
|
}
|
||||||
|
else if (num < down_lim)
|
||||||
|
{
|
||||||
|
init = down_lim;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
init = num;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
#endif /* COUNTER_H_ */
|
||||||
54
source/shoh/src/threads/manager/Manager.cpp
Normal file
54
source/shoh/src/threads/manager/Manager.cpp
Normal file
@ -0,0 +1,54 @@
|
|||||||
|
/*
|
||||||
|
* Manager.cpp
|
||||||
|
*
|
||||||
|
* Created on: 29 Apr 2023
|
||||||
|
* Author: dave
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "Manager.h"
|
||||||
|
#include "ThreadCommon.h"
|
||||||
|
|
||||||
|
Manager::Manager(ThreadCommon::QueueManager* qm)
|
||||||
|
: _qm(qm), _menu{qm}
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
Manager::~Manager()
|
||||||
|
{
|
||||||
|
// TODO Auto-generated destructor stub
|
||||||
|
}
|
||||||
|
|
||||||
|
Event::EventPair Manager::parseEvent(Event* e)
|
||||||
|
{
|
||||||
|
EventRawData raw_data;
|
||||||
|
for(Event::EventType i :
|
||||||
|
{Event::Rotary, Event::InternalTemp,
|
||||||
|
Event::ExternalTemp})
|
||||||
|
{
|
||||||
|
raw_data = e->getDataOf(i);
|
||||||
|
if(raw_data != ERROR_RETURN)
|
||||||
|
{
|
||||||
|
Event::EventPair p = {raw_data, i};
|
||||||
|
return p;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return {ERROR_RETURN, Event::Null};
|
||||||
|
}
|
||||||
|
|
||||||
|
void Manager::taskFunction()
|
||||||
|
{
|
||||||
|
Event data(Event::Null, 0);
|
||||||
|
Event::EventPair event_pair = {0, Event::EventType::Null};
|
||||||
|
for(;;)
|
||||||
|
{
|
||||||
|
_qm->receive<Event>(ThreadCommon::QueueManager::manager_event_master, &data, portMAX_DELAY);
|
||||||
|
event_pair= this->parseEvent(&data);
|
||||||
|
_menu.HandleEventPair(&event_pair);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void thread_manager(void* pvParams)
|
||||||
|
{
|
||||||
|
Manager m(static_cast<ThreadCommon::QueueManager*>(pvParams));
|
||||||
|
m.taskFunction();
|
||||||
|
}
|
||||||
32
source/shoh/src/threads/manager/Manager.h
Normal file
32
source/shoh/src/threads/manager/Manager.h
Normal file
@ -0,0 +1,32 @@
|
|||||||
|
/*
|
||||||
|
* Manager.h
|
||||||
|
*
|
||||||
|
* Created on: 29 Apr 2023
|
||||||
|
* Author: dave
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef THREADS_MANAGER_MANAGER_H_
|
||||||
|
#define THREADS_MANAGER_MANAGER_H_
|
||||||
|
|
||||||
|
#include "ThreadCommon.h"
|
||||||
|
#include "Event.h"
|
||||||
|
#include "Counter.h"
|
||||||
|
#include "Menu.h"
|
||||||
|
|
||||||
|
|
||||||
|
class Manager {
|
||||||
|
public:
|
||||||
|
Manager(ThreadCommon::QueueManager* qm);
|
||||||
|
virtual ~Manager();
|
||||||
|
void taskFunction();
|
||||||
|
private:
|
||||||
|
Event::EventPair parseEvent(Event* e);
|
||||||
|
ThreadCommon::QueueManager* _qm;
|
||||||
|
Menu _menu;
|
||||||
|
|
||||||
|
EventRawData rotary_action;
|
||||||
|
};
|
||||||
|
|
||||||
|
void thread_manager(void* pvParams);
|
||||||
|
|
||||||
|
#endif /* THREADS_MANAGER_MANAGER_H_ */
|
||||||
182
source/shoh/src/threads/manager/Menu.cpp
Normal file
182
source/shoh/src/threads/manager/Menu.cpp
Normal file
@ -0,0 +1,182 @@
|
|||||||
|
/*
|
||||||
|
* Menu.cpp
|
||||||
|
*
|
||||||
|
* Created on: 29 Apr 2023
|
||||||
|
* Author: dave
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "Menu.h"
|
||||||
|
#include <assert.h>
|
||||||
|
#include "UserInterface.h"
|
||||||
|
|
||||||
|
Menu::Menu(ThreadCommon::QueueManager* qm): _qm(qm),
|
||||||
|
current(&Menu::sInitView), ext_temp(-99, 99, 1), set_point(-99, 99, 1),
|
||||||
|
main_text ("CURRENT %3d DESIRED %3d "),
|
||||||
|
set_point_text("CURRENT %3d DESIRED[%3d] ")
|
||||||
|
{
|
||||||
|
this->SetState(&Menu::sInitView);
|
||||||
|
ext_temp.setCurrent(0);
|
||||||
|
set_point.setCurrent(0);
|
||||||
|
}
|
||||||
|
|
||||||
|
Menu::~Menu()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
void Menu::HandleEventPair (Event::EventPair *ep)
|
||||||
|
{
|
||||||
|
switch(ep->et/*EventType*/)
|
||||||
|
{
|
||||||
|
case Event::Rotary:
|
||||||
|
// can be wrapped in a function, but this was found to be more clear solution,
|
||||||
|
// since we are still handling eventpair here, although nested
|
||||||
|
switch(static_cast<ThreadCommon::RotaryAction>(ep->rd)/*RawData*/)
|
||||||
|
{
|
||||||
|
case ThreadCommon::RotaryAction::Right:
|
||||||
|
this->HandleObj(MenuObjEvent (MenuObjEvent::eRollClockWise));
|
||||||
|
break;
|
||||||
|
case ThreadCommon::RotaryAction::Left:
|
||||||
|
this->HandleObj(MenuObjEvent (MenuObjEvent::eRollCClockWise));
|
||||||
|
break;
|
||||||
|
case ThreadCommon::RotaryAction::Press:
|
||||||
|
this->HandleObj(MenuObjEvent (MenuObjEvent::eClick));
|
||||||
|
break;
|
||||||
|
case ThreadCommon::RotaryAction::Idle:
|
||||||
|
/*I guess this is left for debugging purposes ;D*/
|
||||||
|
this->HandleObj(MenuObjEvent (MenuObjEvent::eRefresh));
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
assert(0);
|
||||||
|
/* Pretty damn bad code if reached here */
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case Event::ExternalTemp:
|
||||||
|
//Change ExternalTemp value. -99 <= ext_temp <= 99
|
||||||
|
this->ext_temp.setCurrent(ep->rd);
|
||||||
|
//Refresh the menu screen.
|
||||||
|
this->HandleObj(MenuObjEvent (MenuObjEvent::eRefresh));
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
assert(0);
|
||||||
|
/* Manager has big issues... */
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* States */
|
||||||
|
void Menu::sInitView(const MenuObjEvent &e)
|
||||||
|
{
|
||||||
|
switch (e.type)
|
||||||
|
{
|
||||||
|
case MenuObjEvent::eFocus:
|
||||||
|
this->NotifyAndRefreshUI("Loading...");
|
||||||
|
break;
|
||||||
|
case MenuObjEvent::eUnFocus:
|
||||||
|
printf("NOTE: leave sInitView\n");
|
||||||
|
this->NotifyAndRefreshUI("");
|
||||||
|
break;
|
||||||
|
case MenuObjEvent::eRollClockWise:
|
||||||
|
break;
|
||||||
|
case MenuObjEvent::eRollCClockWise:
|
||||||
|
break;
|
||||||
|
case MenuObjEvent::eClick:
|
||||||
|
this->SetState(&Menu::sMainView);
|
||||||
|
break;
|
||||||
|
case MenuObjEvent::eRefresh:
|
||||||
|
printf("NOTE: sInitView handled eRefresh.\n");
|
||||||
|
this->SetState(&Menu::sMainView);
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void Menu::sMainView(const MenuObjEvent &e)
|
||||||
|
{
|
||||||
|
static char screen_text[64];
|
||||||
|
switch (e.type)
|
||||||
|
{
|
||||||
|
case MenuObjEvent::eFocus:
|
||||||
|
sprintf(screen_text, main_text, this->ext_temp.getCurrent(),
|
||||||
|
this->set_point.getCurrent());
|
||||||
|
this->NotifyAndRefreshUI(screen_text);
|
||||||
|
break;
|
||||||
|
case MenuObjEvent::eUnFocus:
|
||||||
|
this->NotifyAndRefreshUI("");
|
||||||
|
break;
|
||||||
|
case MenuObjEvent::eRollClockWise:
|
||||||
|
break;
|
||||||
|
case MenuObjEvent::eRollCClockWise:
|
||||||
|
break;
|
||||||
|
case MenuObjEvent::eClick:
|
||||||
|
this->SetState(&Menu::sSetPointMod);
|
||||||
|
break;
|
||||||
|
case MenuObjEvent::eRefresh:
|
||||||
|
sprintf(screen_text, main_text, this->ext_temp.getCurrent(),
|
||||||
|
this->set_point.getCurrent());
|
||||||
|
this->NotifyAndRefreshUI(screen_text);
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void Menu::sSetPointMod(const MenuObjEvent &e)
|
||||||
|
{
|
||||||
|
static char screen_text[64];
|
||||||
|
switch (e.type)
|
||||||
|
{
|
||||||
|
case MenuObjEvent::eFocus:
|
||||||
|
sprintf(screen_text, set_point_text, this->ext_temp.getCurrent(),
|
||||||
|
this->set_point.getCurrent());
|
||||||
|
this->NotifyAndRefreshUI(screen_text);
|
||||||
|
break;
|
||||||
|
case MenuObjEvent::eUnFocus:
|
||||||
|
this->NotifyAndRefreshUI("");
|
||||||
|
break;
|
||||||
|
case MenuObjEvent::eRollClockWise:
|
||||||
|
set_point.inc();
|
||||||
|
sprintf(screen_text, set_point_text, this->ext_temp.getCurrent(),
|
||||||
|
this->set_point.getCurrent());
|
||||||
|
this->NotifyAndRefreshUI(screen_text);
|
||||||
|
break;
|
||||||
|
case MenuObjEvent::eRollCClockWise:
|
||||||
|
set_point.dec();
|
||||||
|
sprintf(screen_text, set_point_text, this->ext_temp.getCurrent(),
|
||||||
|
this->set_point.getCurrent());
|
||||||
|
this->NotifyAndRefreshUI(screen_text);
|
||||||
|
break;
|
||||||
|
case MenuObjEvent::eClick:
|
||||||
|
this->SetState(&Menu::sMainView);
|
||||||
|
break;
|
||||||
|
case MenuObjEvent::eRefresh:
|
||||||
|
sprintf(screen_text, set_point_text, this->ext_temp.getCurrent(),
|
||||||
|
this->set_point.getCurrent());
|
||||||
|
this->NotifyAndRefreshUI(screen_text);
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void Menu::SetState (p_state new_state)
|
||||||
|
{
|
||||||
|
(this->*current) (MenuObjEvent (MenuObjEvent::eUnFocus));
|
||||||
|
current = new_state;
|
||||||
|
(this->*current) (MenuObjEvent (MenuObjEvent::eFocus));
|
||||||
|
}
|
||||||
|
|
||||||
|
void Menu::HandleObj (const MenuObjEvent &event)
|
||||||
|
{
|
||||||
|
(this->*current) (event);
|
||||||
|
}
|
||||||
|
|
||||||
|
void Menu::NotifyAndRefreshUI (const char *str)
|
||||||
|
{
|
||||||
|
//Send string on a queue to UI task.
|
||||||
|
UserInterface::InterfaceWithData ud = {UserInterface::LCD1, str};
|
||||||
|
this->_qm->send<UserInterface::InterfaceWithData>(
|
||||||
|
ThreadCommon::QueueManager::ui_event_manager, &ud, portMAX_DELAY);
|
||||||
|
}
|
||||||
44
source/shoh/src/threads/manager/Menu.h
Normal file
44
source/shoh/src/threads/manager/Menu.h
Normal file
@ -0,0 +1,44 @@
|
|||||||
|
/*
|
||||||
|
* Menu.h
|
||||||
|
*
|
||||||
|
* Created on: 29 Apr 2023
|
||||||
|
* Author: dave
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef THREADS_MANAGER_MENU_H_
|
||||||
|
#define THREADS_MANAGER_MENU_H_
|
||||||
|
|
||||||
|
#include "Counter.h"
|
||||||
|
#include "MenuObjEvent.h"
|
||||||
|
#include "ThreadCommon.h"
|
||||||
|
#include "Event.h"
|
||||||
|
|
||||||
|
class Menu;
|
||||||
|
typedef void (Menu::*p_state) (const MenuObjEvent &);
|
||||||
|
|
||||||
|
class Menu
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
Menu (ThreadCommon::QueueManager* qm);
|
||||||
|
virtual ~Menu ();
|
||||||
|
void HandleEventPair (Event::EventPair *ep);
|
||||||
|
|
||||||
|
private:
|
||||||
|
/* Variables and objects */
|
||||||
|
ThreadCommon::QueueManager* _qm;
|
||||||
|
p_state current;
|
||||||
|
Counter<EventRawData> ext_temp;
|
||||||
|
Counter<EventRawData> set_point;
|
||||||
|
const char main_text[64];
|
||||||
|
const char set_point_text[64];
|
||||||
|
/* States */
|
||||||
|
void sInitView(const MenuObjEvent &e);
|
||||||
|
void sMainView(const MenuObjEvent &e);
|
||||||
|
void sSetPointMod(const MenuObjEvent &e);
|
||||||
|
/* Methods */
|
||||||
|
void SetState (p_state new_state);
|
||||||
|
void HandleObj (const MenuObjEvent &event);
|
||||||
|
void NotifyAndRefreshUI (const char *str);
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif /* THREADS_MANAGER_MENU_H_ */
|
||||||
37
source/shoh/src/threads/manager/MenuObjEvent.h
Normal file
37
source/shoh/src/threads/manager/MenuObjEvent.h
Normal file
@ -0,0 +1,37 @@
|
|||||||
|
/*
|
||||||
|
* MenuObjEvent.h
|
||||||
|
*
|
||||||
|
* Created on: Dec 11, 2022
|
||||||
|
* Author: tylen
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef MENU_MENUOBJEVENT_H_
|
||||||
|
#define MENU_MENUOBJEVENT_H_
|
||||||
|
|
||||||
|
class MenuObjEvent
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
virtual ~MenuObjEvent (){};
|
||||||
|
|
||||||
|
enum EventType
|
||||||
|
{
|
||||||
|
/** Start of the event */
|
||||||
|
eFocus,
|
||||||
|
/** End of the event*/
|
||||||
|
eUnFocus,
|
||||||
|
/** Refresh event */
|
||||||
|
eRefresh,
|
||||||
|
/** Button toggle event type */
|
||||||
|
eClick,
|
||||||
|
/** Rotary clockwise */
|
||||||
|
eRollClockWise,
|
||||||
|
/** Rotary counter clockwise */
|
||||||
|
eRollCClockWise,
|
||||||
|
};
|
||||||
|
MenuObjEvent (EventType e = eFocus) : type (e){};
|
||||||
|
EventType type;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
#endif /* MENU_MENUOBJEVENT_H_ */
|
||||||
@ -16,24 +16,29 @@ void Master::taskFunction() {
|
|||||||
Event data(Event::Null, 0);
|
Event data(Event::Null, 0);
|
||||||
bool LedState = true;
|
bool LedState = true;
|
||||||
for (;;) {
|
for (;;) {
|
||||||
_qm->receive<Event>(ThreadCommon::QueueManager::master_event_all, &data, portMAX_DELAY);
|
if(!_qm->receive<Event>(ThreadCommon::QueueManager::master_event_all, &data, 10000))
|
||||||
|
data.setDataOf(Event::Rotary, ThreadCommon::RotaryAction::Idle);
|
||||||
switch(data.getDataOf(Event::Rotary))
|
switch(data.getDataOf(Event::Rotary))
|
||||||
{
|
{
|
||||||
case ThreadCommon::RotaryAction::Right:
|
case ThreadCommon::RotaryAction::Right:
|
||||||
Board_LED_Set(ThreadCommon::RotaryAction::Right, LedState);
|
Board_LED_Set(ThreadCommon::RotaryAction::Right, LedState);
|
||||||
printf("Right\r\n");
|
printf("Right\r\n");
|
||||||
|
_qm->send<Event>(ThreadCommon::QueueManager::manager_event_master, &data, 0);
|
||||||
break;
|
break;
|
||||||
case ThreadCommon::RotaryAction::Left:
|
case ThreadCommon::RotaryAction::Left:
|
||||||
Board_LED_Set(ThreadCommon::RotaryAction::Left, LedState);
|
Board_LED_Set(ThreadCommon::RotaryAction::Left, LedState);
|
||||||
printf("Left\r\n");
|
printf("Left\r\n");
|
||||||
|
_qm->send<Event>(ThreadCommon::QueueManager::manager_event_master, &data, 0);
|
||||||
break;
|
break;
|
||||||
case ThreadCommon::RotaryAction::Press:
|
case ThreadCommon::RotaryAction::Press:
|
||||||
Board_LED_Set(ThreadCommon::RotaryAction::Press, LedState);
|
Board_LED_Set(ThreadCommon::RotaryAction::Press, LedState);
|
||||||
printf("Press\r\n");
|
printf("Press\r\n");
|
||||||
|
_qm->send<Event>(ThreadCommon::QueueManager::manager_event_master, &data, 0);
|
||||||
break;
|
break;
|
||||||
case ThreadCommon::RotaryAction::Idle:
|
case ThreadCommon::RotaryAction::Idle:
|
||||||
Board_LED_Set(ThreadCommon::RotaryAction::Right, LedState);
|
//Board_LED_Set(ThreadCommon::RotaryAction::Right, LedState);
|
||||||
printf("Idle\r\n");
|
printf("Idle\r\n");
|
||||||
|
_qm->send<Event>(ThreadCommon::QueueManager::manager_event_master, &data, 0);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
LedState = !LedState;
|
LedState = !LedState;
|
||||||
@ -41,7 +46,7 @@ void Master::taskFunction() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void master_thread(void* pvParams) {
|
void thread_master(void* pvParams) {
|
||||||
Master m(static_cast<ThreadCommon::QueueManager*>(pvParams));
|
Master m(static_cast<ThreadCommon::QueueManager*>(pvParams));
|
||||||
m.taskFunction();
|
m.taskFunction();
|
||||||
}
|
}
|
||||||
|
|||||||
@ -26,7 +26,7 @@ private:
|
|||||||
ThreadCommon::QueueManager* _qm;
|
ThreadCommon::QueueManager* _qm;
|
||||||
};
|
};
|
||||||
|
|
||||||
void master_thread(void* pvParams);
|
void thread_master(void* pvParams);
|
||||||
|
|
||||||
|
|
||||||
#endif /* THREADS_MASTER_MASTER_H_ */
|
#endif /* THREADS_MASTER_MASTER_H_ */
|
||||||
|
|||||||
@ -64,7 +64,7 @@ void Rotary::taskFunction()
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void rotary_thread(void* pvParams)
|
void thread_rotary(void* pvParams)
|
||||||
{
|
{
|
||||||
// Special case for ISR
|
// Special case for ISR
|
||||||
QueueHandle_t rotary_isr_q = xQueueCreate(15, sizeof(char));
|
QueueHandle_t rotary_isr_q = xQueueCreate(15, sizeof(char));
|
||||||
|
|||||||
@ -25,6 +25,6 @@ private:
|
|||||||
{ 1, 8, true, false, false, true, PIN_INT2_IRQn} };
|
{ 1, 8, true, false, false, true, PIN_INT2_IRQn} };
|
||||||
};
|
};
|
||||||
|
|
||||||
void rotary_thread(void* pvParams);
|
void thread_rotary(void* pvParams);
|
||||||
|
|
||||||
#endif /* THREADS_ROTARY_ROTARY_H_ */
|
#endif /* THREADS_ROTARY_ROTARY_H_ */
|
||||||
|
|||||||
97
source/shoh/src/threads/user_interface/UserInterface.cpp
Normal file
97
source/shoh/src/threads/user_interface/UserInterface.cpp
Normal file
@ -0,0 +1,97 @@
|
|||||||
|
/*
|
||||||
|
* UserInterface.cpp
|
||||||
|
*
|
||||||
|
* Created on: 8 May 2023
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "UserInterface.h"
|
||||||
|
#include <cstring>
|
||||||
|
|
||||||
|
UserInterface::UserInterface(ThreadCommon::QueueManager* qm) :
|
||||||
|
_qm(qm), lcd1(nullptr)
|
||||||
|
{
|
||||||
|
this->initLCD1();
|
||||||
|
}
|
||||||
|
|
||||||
|
UserInterface::~UserInterface()
|
||||||
|
{
|
||||||
|
delete this->lcd1;
|
||||||
|
delete this->lcd1_rs;
|
||||||
|
delete this->lcd1_en;
|
||||||
|
delete this->lcd1_d4;
|
||||||
|
delete this->lcd1_d5;
|
||||||
|
delete this->lcd1_d6;
|
||||||
|
delete this->lcd1_d7;
|
||||||
|
}
|
||||||
|
|
||||||
|
void UserInterface::taskFunction()
|
||||||
|
{
|
||||||
|
InterfaceWithData ui_with_data;
|
||||||
|
|
||||||
|
for (;;)
|
||||||
|
{
|
||||||
|
this->_qm->receive<UserInterface::InterfaceWithData>(ThreadCommon::QueueManager::ui_event_manager, &ui_with_data, portMAX_DELAY);
|
||||||
|
this->handleEvent(&ui_with_data);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
void UserInterface::handleEvent(InterfaceWithData* ui_data)
|
||||||
|
{
|
||||||
|
switch (ui_data->display)
|
||||||
|
{
|
||||||
|
case LCD1:
|
||||||
|
this->handleLCD(this->lcd1, ui_data->data.str);
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
//Should never happen.
|
||||||
|
printf("WARNING: [UserInterface::handleEvent] executed default case.\n");
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/******************************/
|
||||||
|
/*Interface specific functions*/
|
||||||
|
/******************************/
|
||||||
|
|
||||||
|
void UserInterface::handleLCD(LiquidCrystal *lcd, const char *str)
|
||||||
|
{
|
||||||
|
//Interpret empty string as clear.
|
||||||
|
if(!strlen(str))
|
||||||
|
lcd->clear();
|
||||||
|
//Print the text otherwise.
|
||||||
|
else
|
||||||
|
{
|
||||||
|
lcd->setCursor(0, 0);
|
||||||
|
lcd->print(str);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void UserInterface::initLCD1()
|
||||||
|
{
|
||||||
|
this->lcd1_rs = new DigitalIoPin(1, 9, false);
|
||||||
|
this->lcd1_en = new DigitalIoPin(0, 14, false);
|
||||||
|
this->lcd1_d4 = new DigitalIoPin(0, 13, false);
|
||||||
|
this->lcd1_d5 = new DigitalIoPin(0, 12, false);
|
||||||
|
this->lcd1_d6 = new DigitalIoPin(0, 23, false);
|
||||||
|
this->lcd1_d7 = new DigitalIoPin(0, 11, false);
|
||||||
|
|
||||||
|
this->lcd1_rs->write(false);
|
||||||
|
this->lcd1_en->write(false);
|
||||||
|
this->lcd1_d4->write(false);
|
||||||
|
this->lcd1_d5->write(false);
|
||||||
|
this->lcd1_d6->write(false);
|
||||||
|
this->lcd1_d7->write(false);
|
||||||
|
// LCD init.
|
||||||
|
this->lcd1 = new LiquidCrystal(this->lcd1_rs, this->lcd1_en, this->lcd1_d4,
|
||||||
|
this->lcd1_d5, this->lcd1_d6, this->lcd1_d7);
|
||||||
|
// LCD configure display geometry.
|
||||||
|
this->lcd1->begin(16, 2);
|
||||||
|
this->lcd1->setCursor (0, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
void thread_user_interface(void* pvParams)
|
||||||
|
{
|
||||||
|
UserInterface ui(static_cast<ThreadCommon::QueueManager*>(pvParams));
|
||||||
|
ui.taskFunction();
|
||||||
|
}
|
||||||
52
source/shoh/src/threads/user_interface/UserInterface.h
Normal file
52
source/shoh/src/threads/user_interface/UserInterface.h
Normal file
@ -0,0 +1,52 @@
|
|||||||
|
/*
|
||||||
|
* UserInterface.h
|
||||||
|
*
|
||||||
|
* Created on: 8 May 2023
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef THREADS_USER_INTERFACE_USERINTERFACE_H_
|
||||||
|
#define THREADS_USER_INTERFACE_USERINTERFACE_H_
|
||||||
|
|
||||||
|
#include "ThreadCommon.h"
|
||||||
|
#include "Event.h"
|
||||||
|
#include "LiquidCrystal.h"
|
||||||
|
|
||||||
|
class UserInterface {
|
||||||
|
public:
|
||||||
|
UserInterface(ThreadCommon::QueueManager* qm);
|
||||||
|
virtual ~UserInterface();
|
||||||
|
|
||||||
|
enum Interface
|
||||||
|
{
|
||||||
|
LCD1
|
||||||
|
};
|
||||||
|
|
||||||
|
union InterfaceData
|
||||||
|
{
|
||||||
|
const char* str;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct InterfaceWithData
|
||||||
|
{
|
||||||
|
Interface display;
|
||||||
|
InterfaceData data;
|
||||||
|
};
|
||||||
|
|
||||||
|
void taskFunction();
|
||||||
|
private:
|
||||||
|
/* Variables */
|
||||||
|
ThreadCommon::QueueManager* _qm;
|
||||||
|
LiquidCrystal* lcd1;
|
||||||
|
DigitalIoPin *lcd1_rs, *lcd1_en, *lcd1_d4, *lcd1_d5, *lcd1_d6, *lcd1_d7;
|
||||||
|
|
||||||
|
/* Methods */
|
||||||
|
void handleEvent(InterfaceWithData* ui_data);
|
||||||
|
|
||||||
|
//UIs
|
||||||
|
void handleLCD(LiquidCrystal *lcd, const char *str);
|
||||||
|
void initLCD1();
|
||||||
|
};
|
||||||
|
|
||||||
|
void thread_user_interface(void* pvParams);
|
||||||
|
|
||||||
|
#endif /* THREADS_USER_INTERFACE_USERINTERFACE_H_ */
|
||||||
Loading…
x
Reference in New Issue
Block a user