在实训的后半部分,对如何创建动态的GUI界面、如何显示表示进度的数字和图形、界面之间如何进行切换进行讲解和介绍。
TouchGFX设置动态文字和进度条显示
TouchGFX中的Text控件可以通过使用通配符来实现显示动态文字。首先设置文字控制的显示信息,设置其中的通配符信息。并开启文字控件的动画功能。


在左侧的Text选项卡中添加自定义字符串,可以设置字符串的标识符、字体以及具体的字符串内容。

添加一个圆形进度条用来以图形的方式表示当前的程序运行进度。



另外,新建一个新的界面,用于实现界面切换。

修改代码添加应用逻辑
点击生成代码。这时需要打开工程的代码,修改其中的内容。生成的代码分布在多个文件夹中。具体的文件分布如下。

和界面设计相关的文件主要分布在Appli/TouchGFX\
路径下的generated和gui文件夹中。
generated文件夹中的代码主要是根据用户使用TouchGFX图形工具在Canvas(画布)中设定的UI对象以及相关对象行为的代码。

gui文件夹中的源码是用户自定义的代码。

由于TouchGFX生成的代码是C++,所以用户代码中的类定义很少,需要到generated文件夹中查看相应基类的定义。比如窗口名字为“Welcome”,在用户代码中的定义在gui\src\welcome_screen\WelcomeView.cpp
和gui\include\gui\welcome_screen\WelcomeView.hpp
。
#ifndef WELCOMEVIEW_HPP
#define WELCOMEVIEW_HPP
#include <gui_generated/welcome_screen/WelcomeViewBase.hpp>
#include <gui/welcome_screen/WelcomePresenter.hpp>
class WelcomeView : public WelcomeViewBase
{
public:
WelcomeView();
virtual ~WelcomeView() {}
virtual void setupScreen();
virtual void tearDownScreen();
protected:
};
#endif // WELCOMEVIEW_HPP
其基类WelcomeViewBase
的定义在generated文件中,路径为generated\gui_generated\src\welcome_screen\WelcomeViewBase.cpp
和generated\gui_generated\include\gui_generated\welcome_screen\WelcomeViewBase.hpp
。其中可以找到添加的各种控件的成员变量的定义。
class WelcomeViewBase : public touchgfx::View<WelcomePresenter>
{
public:
WelcomeViewBase();
virtual ~WelcomeViewBase();
virtual void setupScreen();
virtual void handleKeyEvent(uint8_t key);
protected:
FrontendApplication& application() {
return *static_cast<FrontendApplication*>(touchgfx::Application::getInstance());
}
/*
* Member Declarations
*/
touchgfx::Box __background;
touchgfx::TiledImage tiledImage1;
touchgfx::TextArea textArea1;
touchgfx::TextArea textArea1_1;
touchgfx::FadeAnimator< touchgfx::MoveAnimator< touchgfx::TextAreaWithOneWildcard > > textArea2;
touchgfx::CircleProgress circleProgress1;
touchgfx::PainterRGB565 circleProgress1Painter;
/*
* Wildcard Buffers
*/
static const uint16_t TEXTAREA2_SIZE = 10;
touchgfx::Unicode::UnicodeChar textArea2Buffer[TEXTAREA2_SIZE];
private:
/*
* Canvas Buffer Size
*/
static const uint32_t CANVAS_BUFFER_SIZE = 12000;
uint8_t canvasBuffer[CANVAS_BUFFER_SIZE];
};
另外,在generated\texts\include\texts\TextKeysAndLanguages.hpp
可以看到自定的字符串信息,包含该头文件后,就可以使用自定义的字符串。
enum TEXTS
{
T_COUNTREADY,
T___SINGLEUSE_7Q5T,
T___SINGLEUSE_2G5S,
T___SINGLEUSE_QWNQ,
T___SINGLEUSE_8JBE,
T___SINGLEUSE_T5D5,
NUMBER_OF_TEXT_KEYS
};
由于TouchGFX工具生成代码的功能,用户可以借助其生成一些功能代码,减少编程工作量,加快应用验证速度。比如,跳转页面的代码可以通过借助TouchGFX工具生成。添加一个交互事件,定义其行为为跳转界面。

生成代码后,在generated\gui_generated\include\gui_generated\common\FrontendApplicationBase.hpp
中可以看到实现跳转代码的函数声明
#ifndef FRONTENDAPPLICATIONBASE_HPP
#define FRONTENDAPPLICATIONBASE_HPP
#include <mvp/MVPApplication.hpp>
#include <gui/model/Model.hpp>
class FrontendHeap;
class FrontendApplicationBase : public touchgfx::MVPApplication
{
public:
FrontendApplicationBase(Model& m, FrontendHeap& heap);
virtual ~FrontendApplicationBase() { }
virtual void changeToStartScreen()
{
gotoWelcomeScreenNoTransition();
}
// Welcome
void gotoWelcomeScreenNoTransition();
// MainPage
void gotoMainPageScreenSlideTransitionWest();
protected:
touchgfx::Callback<FrontendApplicationBase> transitionCallback;
FrontendHeap& frontendHeap;
Model& model;
// Welcome
void gotoWelcomeScreenNoTransitionImpl();
// MainPage
void gotoMainPageScreenSlideTransitionWestImpl();
};
#endif // FRONTENDAPPLICATIONBASE_HPP
作为开发者,可以通过这种方式快速生成自己需要的代码,验证应用方案的可行性,熟悉TouchGFX代码的运行逻辑。
在gui\include\gui\welcome_screen\
目录中,修改窗口类的定义,对基类中handleTickEvent虚函数进行定义,添加成员变量用来表示当前的加载进度,变量tickCount表示计数值。
#ifndef WELCOMEVIEW_HPP
#define WELCOMEVIEW_HPP
#include <gui_generated/welcome_screen/WelcomeViewBase.hpp>
#include <gui/welcome_screen/WelcomePresenter.hpp>
class WelcomeView : public WelcomeViewBase
{
public:
WelcomeView();
virtual ~WelcomeView() {}
virtual void setupScreen();
virtual void tearDownScreen();
virtual void handleTickEvent();
protected:
int tickCount;
uint8_t currentPct;
const uint8_t ANIMATION_DURATION = 20;
};
#endif // WELCOMEVIEW_HPP
在gui\src\welcome_screen\WelcomeView.cpp
文件中添加成员变量的初始化以及handleTickEvent处理代码,在定时事件中动态改变界面中的进度条、圆环进度,并在进度变量达到100时,切换画面,实现GUI显示初始化的过程。
#include <gui/welcome_screen/WelcomeView.hpp>
#include <texts/TextKeysAndLanguages.hpp>
WelcomeView::WelcomeView()
{
}
void WelcomeView::setupScreen()
{
WelcomeViewBase::setupScreen();
currentPct = 0 ;
}
void WelcomeView::tearDownScreen()
{
WelcomeViewBase::tearDownScreen();
}
void WelcomeView::handleTickEvent()
{
const uint8_t ANIMATION_PRESCALER = 3;
if(currentPct <= 100 && tickCount > ANIMATION_PRESCALER*2)
{
if(!(tickCount % ANIMATION_PRESCALER))
{
Unicode::snprintf(textArea2Buffer,TEXTAREA2_SIZE,"%d", currentPct);
textArea2.invalidate();
currentPct++;
}
// Hide progress percentage
if (currentPct == 100)
{
textArea2.setFadeAnimationDelay(0);
textArea2.startFadeAnimation(0, ANIMATION_DURATION / 2);
textArea2.startMoveAnimation(textArea2.getX(), textArea2.getY() - 50, ANIMATION_DURATION / 2, EasingEquations::backEaseOut);
}
}
circleProgress1.setValue(currentPct * 10 + static_cast<int>((tickCount % ANIMATION_PRESCALER) * (10 / (ANIMATION_PRESCALER))));
// Show 'Ready' text
if (!textArea2.getAlpha() && textArea2.getY() < 150)
{
textArea2.setTypedText(T_COUNTREADY);
textArea2.setY(textArea2.getY() + 100);
textArea2.startFadeAnimation(255, ANIMATION_DURATION / 2);
textArea2.startMoveAnimation(270, 168, ANIMATION_DURATION / 2, EasingEquations::backEaseOut);
}
// Wait additional 60 ticks after animation before changing screen
if (tickCount == 100 * ANIMATION_PRESCALER + ANIMATION_DURATION * 2 + 60)
{
application().gotoMainPageScreenSlideTransitionWest();
}
tickCount++;
}
程序的仿真效果如图所示。

总结
使用TouchGFX设计界面,熟悉之后,可以很快地实现复杂的功能,并借助TouchGFX的代码生成功能,减少代码编辑的工作量。而且生成出来的代码易于理解,起到帮助开发者设计应用程序的作用。