lugl4313820 发表于 2024-10-19 16:28

【STM32H7S78-DK】手撸一个数字键盘

<div class='showpostmsg'> 本帖最后由 lugl4313820 于 2024-10-20 16:07 编辑

<p>【前言】</p>

<p>touchgfx 是一个优秀的图形界面,在用户交互中,数字键盘非常重要,本篇是基于STM32H7S78的TouchGFX实现的一款数字键盘。</p>

<p>【开发工具】</p>

<p>TouchGFX Desiger 4.24.1</p>

<p>【开发步骤】</p>

<p>1、打开TouchGFX Desiger 新建一个基于STM32H7S78-DK的基础工程:</p>

<p>&nbsp; 2、新建一个自定义容器,命名为Keyboard:</p>

<p>&nbsp; 3、准备一张数字键盘的背景图片,将他放入工程目录:\KeyBoard\Appli\TouchGFX\assets\images之下。</p>

<p>&nbsp; 4、添加一张图片,图片指向这张背图片:</p>

<p>&nbsp; 5、添加一个box控件到1上面,并把透明度调到0。</p>

<p>&nbsp; 6、复制这个box,分别放到对应的数字键盘之上。并按下图所示重命名box的名称:</p>

<p> &nbsp;</p>

<p>&nbsp; 7、添加一个textArear到Keyboard界面,并按下图重命名为textNum,用于存放输出结果:</p>

<p>&nbsp; 8、钩选ClickListener,使能可以捕捉box的事件。</p>

<p> &nbsp;</p>

<p>9、在screen1的界面把这个keyboard添加进桌面。并同时添加两个box,用于捕捉按键,再添加两个textArea用于显示输入数据的结果。</p>

<p>10、添加OK按下后事件发送函数,实现与其他窗体的交互:</p>

<p> &nbsp;&nbsp;&nbsp;</p>

<p>11、生成工程后使用模拟器观察无误:</p>

<p> &nbsp;</p>

<p>【用户代码实现】</p>

<p>1、首先需要设定回调函数,以及将操作对象绑定到相应的控件上面。首先需要在keyboard.hpp文件中添加函数的声明,以及一些变量的声明,在KeyBoard.hpp上添加代码如下:</p>

<pre>
<code>    virtual void ButtonClickHandle(const Box&amp; box,const ClickEvent&amp; evt);//
                Callback&lt;KeyBoard, const Box&amp;, const ClickEvent&amp;&gt; ButtonCallBack;
                int key_value;
      uint8_t set_index;</code></pre>

<p>2、在Keyboard.cpp中添加实现回调函数的注册代码:</p>

<pre>
<code>KeyBoard::KeyBoard():
ButtonCallBack(this, &amp;KeyBoard::ButtonClickHandle)
{

}
</code></pre>

<p>3、接下来我们来分析一下在这个回调函数里面我们需要做点什么,第一点,你需要判断是哪一个按键摁下,不同的按键有不同的事件处理机制,其次你还要将输入的键值显示在设定的input text上面,同时你还需要考虑怎么实现错误删除,以及清空等操作!其实现代码如下:</p>

<pre>
<code>
void KeyBoard::ButtonClickHandle(const Box&amp; box,const ClickEvent&amp; evt)
{
    static uint8_t index;
    static uint32_t num_value;
    touchgfx::ClickEvent::ClickEventType type = evt.getType();
        if(type == touchgfx::ClickEvent::PRESSED)      //这里是判断事件类型,EVENT_CLICK属于点击事件
      {

            if(&amp;box == &amp;num1)
            {
                key_value = 1;
            }else if(&amp;box == &amp;num2){
                key_value = 2;
            }else if(&amp;box == &amp;num3){
                key_value = 3;
            }else if(&amp;box == &amp;num4){
                key_value = 4;
            }else if(&amp;box == &amp;num5){
                key_value = 5;
            }else if(&amp;box == &amp;num6){
                key_value = 6;
            }else if(&amp;box == &amp;num7){
                key_value = 7;
            }else if(&amp;box == &amp;num8){
                key_value = 8;
            }else if(&amp;box == &amp;num9){
                key_value = 9;
            }else if(&amp;box == &amp;num0){
                key_value = 0;
            }else if(&amp;box == &amp;num_del){
                key_value = -1;
            }else if(&amp;box == &amp;num_ok){
                key_value = -2;
            }else if(&amp;box == &amp;num_cancel){
                key_value = -3;
            }else if(&amp;box == &amp;num_dot){
                key_value = -5;
            }

            if(key_value &gt;= 0){
                if(index&lt;5){
                  num_value =num_value*10 + key_value;
                  Unicode::snprintf(textNumBuffer, TEXTNUM_SIZE, "%d",num_value);
                  textNum.invalidate();
                }
            }else if(key_value == -1)
            {
                num_value = num_value/10;
                Unicode::snprintf(textNumBuffer, TEXTNUM_SIZE, "%d",num_value);
                textNum.invalidate();
            }else if(key_value == -3)
            {
                num_value = 0;
                Unicode::snprintf(textNumBuffer, TEXTNUM_SIZE, "%d",num_value);
                textNum.invalidate();
            }else if(key_value == -2)
            {
                emitKeyValueTransforCallback(num_value);
            }

      }

}
</code></pre>

<p>4、在初始时注册box的按下回调函数,代码如下:</p>

<pre>
<code>void KeyBoard::initialize()
{
    KeyBoardBase::initialize();
    num0.setClickAction(ButtonCallBack);
    num1.setClickAction(ButtonCallBack);
    num2.setClickAction(ButtonCallBack);
    num3.setClickAction(ButtonCallBack);
    num4.setClickAction(ButtonCallBack);
    num5.setClickAction(ButtonCallBack);
    num6.setClickAction(ButtonCallBack);
    num7.setClickAction(ButtonCallBack);
    num8.setClickAction(ButtonCallBack);
    num9.setClickAction(ButtonCallBack);
    num_del.setClickAction(ButtonCallBack);
    num_ok.setClickAction(ButtonCallBack);
    num_cancel.setClickAction(ButtonCallBack);
    num_dot.setClickAction(ButtonCallBack);
}</code></pre>

<p>5、同样,在screenView.hpp中先定义虚拟函数与回调函数:</p>

<pre>
<code>    virtual void ButtonClickHandle(const Box&amp; box,const ClickEvent&amp; evt);
    Callback&lt;KeyBoard, const Box&amp;, const ClickEvent&amp;&gt; ButtonCallBack;
    virtual void setValue(uint32_t value);</code></pre>

<p>6、在screen1View.cpp的类中注册回调函数:</p>

<pre>
<code>SettingScreenView::SettingScreenView():
      ButtonCallBack(this, &amp;SettingScreenView::ButtonClickHandle)
{

}</code></pre>

<p>7、把box的按键事在屏幕载入时注册好:</p>

<pre>
<code>void Screen1View::setupScreen()
{
    Screen1ViewBase::setupScreen();
    box2.setClickAction(ButtonCallBack);
    box3.setClickAction(ButtonCallBack);
}</code></pre>

<p>8、添加按键回调函数的实现:</p>

<pre>
<code>void SettingScreenView::ButtonClickHandle(const Box&amp; box,const ClickEvent&amp; evt) {
    touchgfx::ClickEvent::ClickEventType type = evt.getType();
    if (type == touchgfx::ClickEvent::PRESSED)
    {
      if(&amp;box == &amp;box2)
      {
            keyBoard1.set_index = 1;
            keyBoard1.moveTo(0,0);
      }else if(&amp;box == &amp;box3)
      {
            keyBoard1.set_index = 2;
            keyBoard1.moveTo(0,0);
      }
    }
}</code></pre>

<p>9、在TouchGFX Designer中注册一个接收KeyBoard的函数:</p>

<p>&nbsp; 10、在回调中,把返回的数据更新到指定的textArear中</p>

<pre>
<code>void SettingScreenView::setValue(uint32_t value)
{
    if(keyBoard1.set_index == 1)
    {
      Unicode::snprintf(textArea1Buffer, 10, "%d", value);
      keyBoard1.moveTo(0,500);
      textArea1.invalidate();
    }
    else if(keyBoard1.set_index == 2)
    {
      Unicode::snprintf(textArea2Buffer, 10, "%d", value);
      keyBoard1.moveTo(0,500);
      textArea2.invalidate();
    }

}</code></pre>

<p>【实现效果】</p>

<p>在摸拟器中运行,结果如下:</p>

<p>&nbsp; 视频效果如下:</p>

<p>b1836b1791d60462b31c487a99411b73<br />
附工程源码如下:</p>

<p><a href="https://download.eeworld.com.cn/detail/lugl4313820/634590">STM32H7S78-DK TouchGFX数字键盘-嵌入式开发相关资料下载-EEWORLD下载中心</a></p>

<p>&nbsp;</p>
</div><script>                                        var loginstr = '<div class="locked">查看本帖全部内容,请<a href="javascript:;"   style="color:#e60000" class="loginf">登录</a>或者<a href="https://bbs.eeworld.com.cn/member.php?mod=register_eeworld.php&action=wechat" style="color:#e60000" target="_blank">注册</a></div>';
                                       
                                        if(parseInt(discuz_uid)==0){
                                                                                                (function($){
                                                        var postHeight = getTextHeight(400);
                                                        $(".showpostmsg").html($(".showpostmsg").html());
                                                        $(".showpostmsg").after(loginstr);
                                                        $(".showpostmsg").css({height:postHeight,overflow:"hidden"});
                                                })(jQuery);
                                        }                </script><script type="text/javascript">(function(d,c){var a=d.createElement("script"),m=d.getElementsByTagName("script"),eewurl="//counter.eeworld.com.cn/pv/count/";a.src=eewurl+c;m.parentNode.insertBefore(a,m)})(document,523)</script>

Jacktang 发表于 2024-10-20 08:58

<p>咋样,计算上有没有bug</p>

lugl4313820 发表于 2024-10-20 16:05

Jacktang 发表于 2024-10-20 08:58
咋样,计算上有没有bug

<p>只做了界面,计算还没有弄,只是记录了一下数据交互。</p>

jobszheng5 发表于 2024-10-22 23:44

<p>好厉害啊</p>

lugl4313820 发表于 2024-10-23 07:09

jobszheng5 发表于 2024-10-22 23:44
好厉害啊

<p>感谢大佬的肯定,touchGFX的界面设计还是非常有想法的。</p>

inkinessray 发表于 2024-10-23 12:24

<p>touchGFX&nbsp; &nbsp; 使用需要的资源多吗?STM32F207/407能不能用?</p>

lugl4313820 发表于 2024-10-23 14:36

inkinessray 发表于 2024-10-23 12:24
touchGFX&nbsp; &nbsp; 使用需要的资源多吗?STM32F207/407能不能用?

<p>都可以吧,资源小的不能驱动大屏。</p>
页: [1]
查看完整版本: 【STM32H7S78-DK】手撸一个数字键盘