Initial commit

This commit is contained in:
2023-11-26 20:13:49 +01:00
commit dc2dc5c58b
820 changed files with 258269 additions and 0 deletions

View File

@ -0,0 +1,24 @@
#ifndef FRONTENDAPPLICATION_HPP
#define FRONTENDAPPLICATION_HPP
#include <gui_generated/common/FrontendApplicationBase.hpp>
class FrontendHeap;
using namespace touchgfx;
class FrontendApplication : public FrontendApplicationBase
{
public:
FrontendApplication(Model& m, FrontendHeap& heap);
virtual ~FrontendApplication() { }
virtual void handleTickEvent()
{
model.tick();
FrontendApplicationBase::handleTickEvent();
}
private:
};
#endif // FRONTENDAPPLICATION_HPP

View File

@ -0,0 +1,74 @@
#ifndef FRONTENDHEAP_HPP
#define FRONTENDHEAP_HPP
#include <gui_generated/common/FrontendHeapBase.hpp>
class FrontendHeap : public FrontendHeapBase
{
public:
/* List any user-defined view types here*/
typedef touchgfx::meta::TypeList< touchgfx::meta::Nil, //Replace this with first user-defined type
touchgfx::meta::Nil //List must always end with meta::Nil !
> UserDefinedViewTypes;
/* List any user-defined presenter types here*/
typedef touchgfx::meta::TypeList< touchgfx::meta::Nil, //Replace this with first user-defined type
touchgfx::meta::Nil //List must always end with meta::Nil !
> UserDefinedPresenterTypes;
/* List any user-defined transition types here*/
typedef touchgfx::meta::TypeList< touchgfx::meta::Nil, //Replace this with first user-defined type
touchgfx::meta::Nil //List must always end with meta::Nil !
> UserDefinedTransitionTypes;
/* Calculate largest view, both from generated and user-defined typelists */
typedef touchgfx::meta::select_type_maxsize< UserDefinedViewTypes >::type MaxUserViewType;
typedef touchgfx::meta::TypeList< MaxGeneratedViewType,
touchgfx::meta::TypeList< MaxUserViewType,
touchgfx::meta::Nil
> > CombinedViewTypes;
typedef touchgfx::meta::select_type_maxsize< CombinedViewTypes >::type MaxViewType;
/* Calculate largest presenter, both from generated and user-defined typelists */
typedef touchgfx::meta::select_type_maxsize< UserDefinedPresenterTypes >::type MaxUserPresenterType;
typedef touchgfx::meta::TypeList< MaxGeneratedPresenterType,
touchgfx::meta::TypeList< MaxUserPresenterType,
touchgfx::meta::Nil
> > CombinedPresenterTypes;
typedef touchgfx::meta::select_type_maxsize< CombinedPresenterTypes >::type MaxPresenterType;
/* Calculate largest transition, both from generated and user-defined typelists */
typedef touchgfx::meta::select_type_maxsize< UserDefinedTransitionTypes >::type MaxUserTransitionType;
typedef touchgfx::meta::TypeList< MaxGeneratedTransitionType,
touchgfx::meta::TypeList< MaxUserTransitionType,
touchgfx::meta::Nil
> > CombinedTransitionTypes;
typedef touchgfx::meta::select_type_maxsize< CombinedTransitionTypes >::type MaxTransitionType;
static FrontendHeap& getInstance()
{
static FrontendHeap instance;
return instance;
}
touchgfx::Partition< CombinedPresenterTypes, 1 > presenters;
touchgfx::Partition< CombinedViewTypes, 1 > views;
touchgfx::Partition< CombinedTransitionTypes, 1 > transitions;
Model model;
FrontendApplication app;
private:
FrontendHeap() : FrontendHeapBase(presenters, views, transitions, app),
app(model, *this)
{
gotoStartScreen(app);
}
};
#endif // FRONTENDHEAP_HPP

View File

@ -0,0 +1,57 @@
#ifndef MODEL_HPP
#define MODEL_HPP
#include <string>
#include <list>
#include "config/touchgfx-config.h"
#if defined(TOUCHGFX_ENABLED) && (TOUCHGFX_ENABLED != 0) // Used to get a compilable project for the students!
#include "mdw/button/buttoneventshandler.h"
#endif // TOUCHGFX_ENABLED
class ModelListener;
/**
* @brief Model containing data used by the GUI view(s).
*/
class Model
#if defined(TOUCHGFX_ENABLED) && (TOUCHGFX_ENABLED != 0) // Used to get a compilable project for the students!
: public interface::ButtonEventsHandlerObserver
#endif // TOUCHGFX_ENABLED
{
public:
Model();
void initialize(
#if defined(TOUCHGFX_ENABLED) && (TOUCHGFX_ENABLED != 0)
ButtonEventsHandler & buttonEventsHandler
#endif // TOUCHGFX_ENABLED
);
void bind(ModelListener* listener)
{
modelListener = listener;
}
void tick();
void addLogMessage(const std::string & logMessage);
void clearLogMessages();
#if defined(TOUCHGFX_ENABLED) && (TOUCHGFX_ENABLED != 0)
protected:
void onButtonShortPressed(ButtonIndex buttonIndex) override;
void onButtonLongPressed(ButtonIndex buttonIndex) override;
#endif // TOUCHGFX_ENABLED
protected:
ModelListener* modelListener;
static constexpr const uint32_t MAX_MESSAGES = 50;
std::list<std::string> logMessages_; ///< Log messages
std::string logTextTotal_; ///< String containing all log messages to display, provided to the model listener.
bool logTextChanged_; ///< True when one or more log messages were added.
};
#endif // MODEL_HPP

View File

@ -0,0 +1,25 @@
#ifndef MODELLISTENER_HPP
#define MODELLISTENER_HPP
#include <gui/model/Model.hpp>
class ModelListener
{
public:
ModelListener() : model(0) {}
virtual ~ModelListener() {}
void bind(Model* m)
{
model = m;
}
virtual void notifyLogTextChanged(const std::string & logText) =0;
virtual void notifyClearLogMessages() =0;
protected:
Model* model;
};
#endif // MODELLISTENER_HPP

View File

@ -0,0 +1,52 @@
#ifndef TERMINALPRESENTER_HPP
#define TERMINALPRESENTER_HPP
#include <gui/model/ModelListener.hpp>
#include <mvp/Presenter.hpp>
using namespace touchgfx;
class TerminalView;
class TerminalPresenter : public touchgfx::Presenter, public ModelListener
{
friend class TerminalView;
public:
TerminalPresenter(TerminalView& v);
/**
* The activate function is called automatically when this screen is "switched in"
* (ie. made active). Initialization logic can be placed here.
*/
virtual void activate();
/**
* The deactivate function is called automatically when this screen is "switched out"
* (ie. made inactive). Teardown functionality can be placed here.
*/
virtual void deactivate();
virtual ~TerminalPresenter() {};
protected:
void clearLogMessages();
/**
* Methods below are called by the associated view.
*/
void onButtonClearLogTextClicked();
/**
* Notify methods below are asynchronously called by the
* TouchGFX UI task to update the LCD display
*/
void notifyLogTextChanged(const std::string & logText) override;
void notifyClearLogMessages() override;
private:
TerminalPresenter();
TerminalView& view;
};
#endif // TERMINALPRESENTER_HPP

View File

@ -0,0 +1,31 @@
#ifndef TERMINALVIEW_HPP
#define TERMINALVIEW_HPP
#include <string>
#include <gui_generated/terminal_screen/TerminalViewBase.hpp>
#include <gui/terminal_screen/TerminalPresenter.hpp>
class TerminalView : public TerminalViewBase
{
friend class TerminalPresenter;
public:
TerminalView();
virtual ~TerminalView() {}
virtual void setupScreen();
virtual void tearDownScreen();
protected:
void onButtonClearLogTextClicked() override;
/**
* Methods below must only be called by the Presenter or
* the TouchGfx UI task.
*/
void updateLogText(const std::string & str);
void clearLogText();
protected:
bool autoScrollText_;
};
#endif // TERMINALVIEW_HPP

View File

@ -0,0 +1,7 @@
#include <gui/common/FrontendApplication.hpp>
FrontendApplication::FrontendApplication(Model& m, FrontendHeap& heap)
: FrontendApplicationBase(m, heap)
{
}

View File

@ -0,0 +1,98 @@
#include "config/touchgfx-config.h"
#include <gui/model/Model.hpp>
#include <gui/model/ModelListener.hpp>
Model::Model() :
modelListener(0),
logTextChanged_(false)
{
}
void Model::initialize(
#if defined(TOUCHGFX_ENABLED) && (TOUCHGFX_ENABLED != 0) // Used to get a compilable project for the students!
ButtonEventsHandler & buttonEventsHandler
#endif // TOUCHGFX_ENABLED
)
{
#if defined(TOUCHGFX_ENABLED) && (TOUCHGFX_ENABLED != 0)
// Subscribe to button events
bool success = buttonEventsHandler.subscribe(this);
assert(success);
#endif // TOUCHGFX_ENABLED
}
/**
* The tick method is called regularly by the TouchGFX task
*/
void Model::tick()
{
if (logTextChanged_)
{
logTextChanged_ = false;
if (logMessages_.size() > 0)
{
logTextTotal_.clear();
// Add all log messages to logTextTotal_
// New messages are at the beginning of the list, but
// need to be at the end in logTextTotal_
for (std::string str : logMessages_)
{
logTextTotal_.insert(0, str);
}
modelListener->notifyLogTextChanged(logTextTotal_);
}
else
{
modelListener->notifyClearLogMessages();
}
}
}
void Model::addLogMessage(const std::string & logMessage)
{
logMessages_.push_front(logMessage);
// Remove an old message if list is too big
if (logMessages_.size() > MAX_MESSAGES)
{
logMessages_.pop_back();
}
// Tell UI task that logText did change
logTextChanged_ = true;
}
void Model::clearLogMessages()
{
logMessages_.clear();
logTextTotal_.clear();
// Tell UI task that logText did change
logTextChanged_ = true;
}
#if defined(TOUCHGFX_ENABLED) && (TOUCHGFX_ENABLED != 0)
void Model::onButtonShortPressed(ButtonIndex buttonIndex)
{
std::string logMessage("Button ");
logMessage += std::to_string(buttonIndex);
logMessage += " short pressed\n";
addLogMessage(logMessage);
}
void Model::onButtonLongPressed(ButtonIndex buttonIndex)
{
std::string logMessage("Button ");
logMessage += std::to_string(buttonIndex);
logMessage += " long pressed\n";
addLogMessage(logMessage);
}
#endif // TOUCHGFX_ENABLED

View File

@ -0,0 +1,38 @@
#include <gui/terminal_screen/TerminalView.hpp>
#include <gui/terminal_screen/TerminalPresenter.hpp>
TerminalPresenter::TerminalPresenter(TerminalView& v)
: view(v)
{
}
void TerminalPresenter::activate()
{
}
void TerminalPresenter::deactivate()
{
}
void TerminalPresenter::clearLogMessages()
{
model->clearLogMessages();
}
void TerminalPresenter::onButtonClearLogTextClicked()
{
clearLogMessages();
}
void TerminalPresenter::notifyLogTextChanged(const std::string & logText)
{
view.updateLogText(logText);
}
void TerminalPresenter::notifyClearLogMessages()
{
view.clearLogText();
}

View File

@ -0,0 +1,82 @@
#include <gui/terminal_screen/TerminalView.hpp>
TerminalView::TerminalView():
autoScrollText_(true)
{
}
void TerminalView::setupScreen()
{
TerminalViewBase::setupScreen();
}
void TerminalView::tearDownScreen()
{
TerminalViewBase::tearDownScreen();
}
void TerminalView::onButtonClearLogTextClicked()
{
// Forward event to presenter
presenter->onButtonClearLogTextClicked();
}
void TerminalView::updateLogText(const std::string & str)
{
Unicode::fromUTF8((const unsigned char *)str.c_str(), logText_Buffer, LOGTEXT__SIZE);
logText_.resizeToCurrentTextWithAlignment(); // Update height of text area
// Check if we always need to show the end of the logs (most recent logs)
if (autoScrollText_)
{
auto scrollHeight = scrollableTextArea_.getHeight();
auto textHeight = logText_.getTextHeight();
if (logText_.getRotation() == TEXT_ROTATE_0)
{
if (textHeight > scrollHeight)
{
logText_.startMoveAnimation(logText_.getX(), // X value to scroll to
-(textHeight - scrollHeight), // Y value to scroll to
2); // Animation duration in ticks
}
}
else if (logText_.getRotation() == TEXT_ROTATE_180)
{
if (textHeight > scrollHeight)
{
// Scroll to bottom is scrolling to y == 0
logText_.startMoveAnimation(logText_.getX(), 0, 2);
}
}
}
logText_.invalidate();
}
void TerminalView::clearLogText()
{
logText_Buffer[0] = '\0';
if (logText_.getRotation() == TEXT_ROTATE_0)
{
logText_.resizeHeightToCurrentText();
logText_.startMoveAnimation(logText_.getX(), // X value to scroll to
0, // Y value to scroll to
2); // Animation duration in ticks
}
else if (logText_.getRotation() == TEXT_ROTATE_180)
{
logText_.resizeToCurrentTextWithAlignment();
logText_.startMoveAnimation(logText_.getX(), // X value to scroll to
scrollableTextArea_.getHeight() - logText_.getHeight(), // Y value to scroll to (in respect with rotated text)
2); // Animation duration in ticks
}
logText_.invalidate();
scrollableTextArea_.invalidate();
}