你的浏览器版本过低,可能导致网站不能正常访问!
为了你能正常使用网站功能,请使用这些浏览器。

【安富莱STemWin教程】第2章 STemWin5.xx详细移植步骤

[复制链接]
baiyongbin2009 发布时间:2015-1-8 18:14
本帖最后由 baiyongbin2009 于 2015-1-8 18:18 编辑
( A( q' d  x5 W  p, e
4 m% U' X2 q) N' D2 C/ ~4 n
特别说明:完整STemWin的1-60期教程和配套实例下载地址:链接
第2章  STemWin5.xx详细移植步骤
+ r. K8 Q- j( g3 ]9 a3 F
    本期教程开始带领大家学习STemWin的移植,对于初学者STemWin的移植不是必须要先学的,可以先学一些基本的应用,然后再来学习移植就方面很多了,考虑到教程正常的编排顺序,这里就把STemWin的移植放在了第二章。本章提供的移植方法可以自适应安富莱生产的3.0寸,4.3寸,5寸,7寸TFT屏。这里只讲STemWin在MDK上面的移植,在IAR上面的移植是类似的。开发板使用安富莱STM32-V5开发板,主芯片STM32F407IGT6。
    2.1 关于STemWin移植的重要说明
    2.2 移植前的准备工作
    2.3 STemWin的裸机移植
    2.4 STemWin带RTOS的移植
    2.5 总结

% d& Z" t6 N1 T( s0 q) x$ _
2.1  关于STemWin移植的重要说明
    关于STemWin的移植一定要明确以下几点:
1.     emWin手册里面有这样一句话:“驱动接口的改变始于emWin V5。不再支持针对emWin V4 或更早版本开发的老显示驱动”。
2.     如果不使用V5以后版本的新特性,基本和以前的版本使用是一样的,也就是说,大家用V5以前版本实现的功能,直接升级到现有的版本,基本可以正常运行。
3.     尽管emWin提供了大部分屏的驱动,但是不能包含所有,这篇移植文档就因此而生。不管是emWin已经支持的,还是没有提供支持的,均可采用这种方法。
4.     本章教程提供了一个非常好的触摸滤波方法,此方法可以有效的滤除飞点。
5.     使用STemWin的库,一定得记得开启CRC,使用MDK安装目录里面的emWin库,一定得注册MDK的RL-ARM。
2.2  移植前的准备工作
    这里分别讲一下MDK安装目录中emWin的移植和STemWin的移植,准备工作做好以后,剩下的移植步骤基本是一样的。只是使用的各自的库即可。
2.2.1      MDK安装目录中emWin移植
     第一步:我们以MDK5.10中emWin5.22库进行说明。安装目录中有如下几个文件(路径:C:\Keil5.10\ARM\Pack\Keil\MDK-Middleware\5.1.4\emWin,如果使用的是MDK4.73等4.xx版本,路径:C:\Keil4.73\ARM\Segger\emWin)。
2.1.jpg                               
库版本
说明
GUI_ARM_B.lib
大端模式的库
GUI_ARM_L.lib
小端模式的库
GUI_CM0.lib
M0内核
GUI_CM3.lib
M3内核
GUI_CM4F.lib
M4内核
    在这里有一个问题要跟大家说明,emWin的官方手册中有这样一句话:
2.2.png
% _; |# K0 W# }4 x7 f8 C& A
    其实这个是针对SEGGER自己做的emWin源码而言的,SEGGER授权给其它厂商后,芯片厂商都对源码进行了优化,要不FPU的存在就没有意义了。上面的GUI_CM4F.lib文件就是KEIL公司对emWin中需要使用浮点的地方进行了优化。
    第二步:注册RL-ARM,点击File->License Management
2.3.jpg

9 I. M- P, l4 H: Y3 H
    第三步:注册RL-ARM,点击File->License Management
2.4.jpg
9 j7 H3 E% d( a% u
    第四步:注册机的设置
2.5.png

7 d' S: J2 \" \' G4 T+ m
    这些准备工作做好后就可以开始移植工作了。
2.2.2      STemWin移植
     STemWin的移植准备工作比较简单,用户只需在初始化STemWin前使能CRC校验即可。STemWin的库文件如下:
2.6.jpg

2 i. q. e! m/ a* h8 A! C7 A2 o
    这里面含有KEIL,IAR和GCC三个版本的库。而且还区分带OS和不带OS版本。本教程讲的是不带OS版本的移植,带OS版本的移植也很简单,用户只需添加相应的文件即可。
    STemWin的下载地址:http://www.st.com/web/en/catalog/tools/PF259225#  (版本1.1.2)
    Lib文件所在的路径:STemWin_Library_V1.1.2\Libraries\STemWinLibrary522\Lib
( [2 z4 L2 ?- v  A* m
赞 收藏 评论19 发布时间:2015-1-8 18:14

举报

19个回答
baiyongbin2009 回答时间:2015-1-8 18:23:10
2.3  STemWin的裸机移植2.3.1      工程中添加的文件
    添加如图所示的几个文件:
2.7.png
                              
    这几个文件从上往下依次进行一下简单的说明:
1.     bsp_tft_lcd.c, LCD_RA887, LCD_SPFD5420.c是用户要实现的TFT驱动文件。
2.     bsp_touch.c是触摸文件,也是用户要实现的。
3.     GUIDRV_Template.c文件在ST官方提供的STemWin包里面没有,需要在MDK的安装目录里面找。
    比如在MDK4.73安装目录中查找位置是:C:\Keil4.73\ARM\Segger\emWin\Sample\DisplayDriver
2.8.png
4.    上面MDK工程目录中GUI_X中的几个文件在MDK安装目录和STemWin软件包中都有:
  Ø  STemWin软件包中路径如下:STemWin_Library_V1.1.2\Libraries\STemWinLibrary522\OS,只是STemWin软件包中相关文件比较少。
  Ø  MDK4.73安装目录中的如下路径中:C:\Keil4.73\ARM\Segger\emWin\Sample\GUI_X,这里文件夹里面的内容比较全。
5.    GUI和LCD配置文件所在位置:
    MDK4.73安装目录:C:\Keil4.73\ARM\Segger\emWin\Sample\Config
    STemWin软件包:STemWin_Library_V1.1.2\Libraries\STemWinLibrary522\Config
6.    GUI/DEMO中的函数需要用户实现,简单的写个程序即可。
7.    GUI/Lib里面是emWin,所在位置
    MDK4.73安装目录:C:\Keil4.73\ARM\Segger\emWin\Lib
    STemWin软件包:STemWin_Library_V1.1.2\Libraries\STemWinLibrary522\Lib
2.3.2      触摸屏滤波的实现
    这里提供了一种有效的滤波方法。具体函数在bsp_touch.c这个文件里面,得到触摸数值后供emWin中的函数GUI_TOUCH_X_MeasureX 和GUI_TOUCH_X_MeasureY两个函数的调用。
    特别注意这里改变触摸的滤波方法,以前的时候大家都是采用舍弃触摸数值的前几个点和后几个点,然后中间数值取平均的方法,效果并不理想,因为这种方法不能有效的滤除飞点,这里提供一个新的方法。1. 在STemWin里面使用触摸的中断方式,效果并不好,所以这里使用查询,查询此引脚的电平,这样可以避免不必要的读取触摸数据。
2. 触摸滤波,主要滤的是飞点,正是因为这些飞点的存在,才使得触摸很不稳定。
    下面的这个函数,大家应该很熟悉,就是滤除前几个点和后面几个点,然后中间几个点取平均
  1. /*+ \: Q/ ~, |9 a3 [7 k7 J. f
  2. *********************************************************************************************************
    1 {1 O5 G" z8 [* J2 p- ?
  3. *    函 数 名: TOUCH_DataFilter
    . n& b+ B- N2 O
  4. *    功能说明: 读取一个坐标值(x或者y)
    * k% ]: G+ n1 J6 m" \  U* i' w/ [
  5. *             连续读取XPT2046_READ_TIMES次数据,对这些数据升序排列,
    . o' K, {/ Z0 e/ v
  6. *             然后去掉最低和最高XPT2046_LOST_VAL个数,取平均值  z! M  y; ~' J# B6 b1 V% |& {
  7. *    形    参:无
    $ ~3 V6 m* N6 [9 A: L
  8. *    返 回 值: 读到的数据2 F) }4 r- Z/ f" g% J
  9. *********************************************************************************************************
    6 \1 m! K  p. [+ b4 H
  10. */7 L& q' w8 o8 m& q+ g
  11. /* 读取次数 */) v- m# k# W0 g( Z3 y! @
  12. #define XPT2046_READ_TIMES    5
    4 d! r1 N+ n0 J: r" s
  13. /* 丢弃值  */
    9 I4 y" Y! f7 u
  14. #define XPT2046_LOST_VAL      1     " {  I9 Y+ Z: L1 H& C
  15. uint16_t TOUCH_DataFilter(uint8_t _ucCh)( t# M& n+ d5 T% r" ^% A3 C
  16. {6 `7 T  c& C/ [, N
  17.      uint16_t i, j;" o  W# |* x8 J9 ]3 m- l
  18.      uint16_t buf[XPT2046_READ_TIMES];9 M6 Q; F; e+ D  w, |
  19.      uint16_t usSum;9 a/ C6 U) x1 v9 P3 e! z1 b
  20.      uint16_t usTemp;
    ; u: B! g' Q9 d. |. E9 n5 J. y
  21. ! |" j$ b+ Z6 V: e; r9 B  L; o, M
  22.      /* 读取READ_TIMES次数据*/1 H( P% L& y% k5 w( z5 N
  23.      for(i=0; i < XPT2046_READ_TIMES; i++)
    8 M( m1 Q9 u* q) T! \
  24.      {
    0 s# M: Q) c! S7 h) Q# |. s: A& v1 M$ v
  25.          if (g_ChipID == IC_8875)$ B' E6 g! e1 j2 T7 \5 h4 A
  26.          {$ q" ]; |9 e4 w7 g: k3 b" i& A
  27.               if(_ucCh == ADC_CH_X)
    ( _; d5 v/ n$ Q) L5 y- E
  28.               {. f- J% v1 f) x: ^; s6 r- Q6 F6 ?
  29.                    buf[i] = RA8875_TouchReadX();
    7 y( D/ u* N: M
  30.               }6 y  B. J% m% u/ g$ W9 h
  31.               else
    ; N8 I3 p/ r( d$ a1 `
  32.               {! V, t3 T) N: v) T
  33.                    buf[i] = RA8875_TouchReadY();   
    5 M- W8 [% v( Y/ a
  34.               }
    , W  J9 Y! s% l  b9 j8 V. i
  35.          }2 A+ u+ t8 z! d8 U, z
  36.          else* {3 w: x5 B8 P% n
  37.          {% f8 {$ u+ l/ I% s) e. L9 b% z& e
  38.               buf[i] = TSC2046_ReadAdc(_ucCh);' d% Q, g* m0 u+ c& B
  39.          }   
    ( ^0 Z$ y+ r& {# ]* Z3 m$ L; f1 o% e
  40.      }
    . H- {$ f/ p; K) j, E/ K- R+ b
  41.    
    ' ^9 X( |8 ^0 b* s: H
  42.      /* 升序排列 */                  
    # L" Q3 ^/ F8 J: z. f$ ?* f
  43.      for(i = 0; i < XPT2046_READ_TIMES - 1; i++)
    / h/ a3 J8 f! ^& F4 ^
  44.      {. k1 v1 E. u) t6 M4 t( ?/ z  f
  45.          for(j = i + 1; j < XPT2046_READ_TIMES; j++)
    5 _. j1 r* b9 h6 j, n) X; w
  46.          {8 h' u, T! y3 B  _) Z% n) c- D! |4 r
  47.               if(buf[i] > buf[j])
    + F7 r- ~$ |7 C: C4 a0 j& r2 X8 R
  48.               {; n) G: E- `3 a
  49.                    usTemp = buf[i];# ^2 d2 }0 O" o* g2 z, h: m
  50.                    buf[i] = buf[j];
    . y1 Q+ r+ i; v: K! X0 V+ p, {3 z
  51.                    buf[j] = usTemp;$ Y# @7 b9 A! a% ~, M
  52.               }
    & L" ~: u9 R: @
  53.          }/ K, ~6 f. n" I2 {# M
  54.      }
    + a  u. Y- J3 a, _4 N' w
  55.         4 Y. R! \7 n- Z! r1 |, [6 V+ o
  56.      usSum = 0;0 k* n+ f: z0 [

  57. # B* E2 n) x/ V% L( W
  58.      /*求和 */
    % Z$ @; S3 Q7 _4 k
  59.      for(i = XPT2046_LOST_VAL; i < XPT2046_READ_TIMES - XPT2046_LOST_VAL; i++)1 x9 N% {  Q4 o3 `' w4 C" |" K
  60.      {2 m; P; Z, e: s1 N0 _
  61.          usSum += buf[i];
    / G1 k  h4 Y7 v  d' Z
  62.      }
    0 Z& j# `0 \, u  a# L6 b6 T7 ]% Z) _
  63.      /*求平均 */) F' K2 E) x8 O) x: r) x' f" I3 _
  64.      usTemp = usSum / (XPT2046_READ_TIMES - 2 * XPT2046_LOST_VAL);
    ' B9 Y" o5 I! J0 ]% G" m0 }+ k

  65. ( E( H; n/ g- s( q+ y
  66.      return usTemp;
    7 s& ]& n6 O+ w+ b
  67. }
    # V& o1 B, D. W) `6 ?4 {
  68. % e0 K8 p: \9 {* k+ S2 ^2 k) k
  69. /*! y, h* z" I% O  x& H9 `
  70. *********************************************************************************************************# h, t' Z# x% W
  71. *    函 数 名: TOUCH_ReadAdcXY
    $ ?& G: v9 R! Y. b# w$ `
  72. *    功能说明: 连续2次读取触摸屏IC,且这两次的偏差不能超过' G- [  E/ ~# V( n
  73. *             ADC_ERR_RANGE,满足条件,则认为读数正确,否则读数错误.- J+ i: _" o  H% u/ h+ ]
  74. *             该函数能大大提高准确度
    - P8 _5 E7 \4 ], s9 F3 Q
  75. *    形    参:x,y:读取到的坐标值
    . r- z4 @4 I$ O: G  V: V0 G, C
  76. *    返 回 值: 0,失败;1,成功  K7 G2 _" F8 Y' w5 g7 J2 p. a
  77. *********************************************************************************************************2 R9 ^, r/ R+ T" N) c
  78. */! c' I4 Z8 M1 U. k
  79. /* 误差范围 */ # Y$ B' U8 t0 p+ D
  80. uint8_t ADC_ERR_RANGE = 5;
    5 O$ \, ?, H8 X# s1 b  q
  81. uint8_t TOUCH_ReadAdcXY(int16_t *_usX, int16_t *_usY)2 \! S, k2 J2 J/ P+ c
  82. {
    5 {9 j1 m2 U; y
  83.      uint16_t iX1, iY1;
    ; d$ a/ y  ~8 J+ P
  84.      uint16_t iX2, iY2;
    ! q% ~1 @. M* i: F' I
  85.      uint16_t iX, iY;. I- R$ u: R- I) v0 I) T
  86. ' L' t: X! u" g+ [' v& p
  87.      iX1 = TOUCH_DataFilter(ADC_CH_X);
    % y6 U- W7 W; q2 e0 e5 U
  88.      iY1 = TOUCH_DataFilter(ADC_CH_Y);
    3 r( v/ C' S7 `) R2 }/ u
  89.      iX2 = TOUCH_DataFilter(ADC_CH_X);
    " B( K- f1 S$ |+ c2 O+ E% [* ~2 f8 _6 s
  90.      iY2 = TOUCH_DataFilter(ADC_CH_Y);
    5 ?" G. P* h  s
  91.    
    0 U4 Y( G  x1 k/ R, s
  92.      iX = TOUCH_Abs(iX1 - iX2);
    + d* Q8 X% y8 I7 u- h7 S. [& M
  93.      iY = TOUCH_Abs(iY1 - iY2);
    2 ^+ c  Q( u) f4 L
  94.     3 @) p2 C8 u/ g7 h
  95.      /* 前后两次采样在+-ERR_RANGE内 */
      H; b& A& |, n3 [1 P: {
  96.     if ((iX <= ADC_ERR_RANGE) && (iY <= ADC_ERR_RANGE))
    ' ~: c# J4 d5 F. k& q& I
  97.     {        
    $ v& m& K0 H7 A/ ]7 {7 F" n  G7 }  W
  98.          *_usX = (iX1 + iX2) / 2;0 d; G+ s: \* I5 T8 q6 P1 w( z
  99.          *_usY = (iY1 + iY2) / 2;   4 G2 ?- U! Z2 S" y# y
  100. ( G( o7 q% d/ d
  101.          return 1;
    + y9 a" \: J6 H" f( \6 i
  102.     }
    0 S+ E8 W# ~" J, X  d
  103.      else4 o# X0 P9 g, x" ~: T) M
  104.      {1 J3 F: o! ?( _6 R# d6 t
  105.          return 0;
    0 h/ x* u+ w* }# `# I, ~
  106.      }   
    - B* n! e* A4 v* F  R3 Z
  107. }; F; f+ g  J. G- @

  108. ' J, u$ w4 D" c% _0 X/ W: e! ~$ B- l- `
  109. /*- |* R" \1 o9 _0 b, S
  110. *********************************************************************************************************
    6 i# M5 @0 R9 ~, @. _
  111. *    函 数 名: TOUCH_Scan
    7 F$ T( [% j; h* h
  112. *    功能说明: 触摸板事件检测程序。该函数被周期性调用,每ms调用1次. 见 bsp_Timer.c: L6 T* n1 u' C+ ?) V+ u  s2 v
  113. *    形    参:无
    4 J4 J; A3 G" ?; W: m0 Z" M: G9 |
  114. *    返 回 值: 无' H5 K9 {' l1 n" e# s- v, x
  115. *********************************************************************************************************
    8 e& {5 g( C/ v
  116. */
      X2 e8 I, c+ C/ L( @$ e; ^0 \
  117. void TOUCH_SCAN(void)) v% B9 s0 R& l  r6 [( a" X( b
  118. {- W# h9 K- e& a
  119.      uint8_t s_invalid_count = 0;( c8 J  P5 m( C+ ~6 G3 }, ~" o" E
  120.     ( m5 ^7 l4 _" r! [+ K" Y; P; \7 ?
  121.      if(TOUCH_PressValid == 0)
    6 z3 W3 w5 v* G  |
  122.      {            
    ' C- L4 Y( A1 X2 O( f
  123.          while(!TOUCH_ReadAdcXY(&g_tTP.usAdcNowX, &g_tTP.usAdcNowY)&&s_invalid_count < 20);
    8 D3 Y+ r% u' c" f* `6 E# ], |
  124.          {
      i, i2 ^' m# ?/ P9 D4 Z
  125.               s_invalid_count++;
    9 {! E  o- d9 H
  126.          }
    8 T# Q! w4 f1 k9 G. V
  127.          if(s_invalid_count >= 20)* i' R: N5 T" ]+ Z% r
  128.          {
    # f/ t) P/ G  R+ g
  129.               g_tTP.usAdcNowX = -1;7 |2 ~2 P6 C5 k" w- V
  130.               g_tTP.usAdcNowY = -1;
    7 }- a; A$ C' x5 a& O8 i
  131.          }, J) O6 [+ I. [, [3 t* V
  132.      }
    ) B2 r& i( l7 o2 z7 s
  133.      else! y9 v& f8 K5 D8 t% |: p* k+ Q
  134.      {2 Z' C# J& q8 j: {- H. b' e1 I
  135.          g_tTP.usAdcNowX = -1;2 Q# G& n: U5 h
  136.          g_tTP.usAdcNowY = -1; : s' Z( x+ x: P, j
  137.      }
    5 ?; b% I5 P7 x1 q
  138.              ! e+ k% K4 X" {, d4 {4 ]
  139. }
复制代码
    触摸的驱动就这些东西,详细的使用看例程级可以,然后在文件GUI_X_Touch_Analog.c里面调用就可以了。
  1. #include "GUI.h"
    4 f4 q+ v& H: t/ ^
  2. #include "LCD_RA8875.h"
    ' P% V8 M* B; C' u. q
  3. #include "bsp_touch.h"
    2 y0 p$ p" Z* j: g, _9 {% Y+ e
  4. ) T1 W# ?6 F2 I, X
  5. void GUI_TOUCH_X_ActivateX(void)
    ) [0 \9 T( x( T" L  |
  6. {
    0 \4 {) V! K% j# |8 U. @
  7. # ^' f1 d! c3 m: x5 L- r% ~+ D4 r
  8. }
    ) m9 l: @  M& K2 W
  9. # ?+ n/ a, B& X3 b
  10. void GUI_TOUCH_X_ActivateY(void)
    0 H7 s# i+ ?4 z- d6 }
  11. {3 H1 M2 S6 ]  f$ v% r. t

  12. 6 ^- q" c( Z- A# |/ Z7 t
  13. }* N6 K% J) {4 p8 S3 N9 V

  14. $ F7 K" r8 N/ P
  15. int  GUI_TOUCH_X_MeasureX(void)6 i) h2 o& ^/ t
  16. {
    4 x& M  @! o' C; @; A8 Q, Q  d  H
  17.      TOUCH_SCAN();1 y' Z, ]) C5 |- ?! ^  G6 U
  18.      return(g_tTP.usAdcNowX);        ) x, t' y2 j0 @1 [4 X
  19. }
    9 a  U' h; q* q0 P- x

  20. ) Q7 B% ^$ [5 j8 v
  21. int  GUI_TOUCH_X_MeasureY(void), N" \  S# M- B# n( Z9 m
  22. {   
    ) D" M& p' k8 Y; i
  23.      return(g_tTP.usAdcNowY);
    - A6 e$ k2 D$ v# R  W- x
  24. }
复制代码
% e4 l4 E2 t; O

1 G+ a" |- z" Q1 V5 D, q
baiyongbin2009 回答时间:2015-1-8 18:24:33
本帖最后由 baiyongbin2009 于 2015-1-8 18:28 编辑
2 G, M" q4 e# ]' y  K! [: J/ T* x* y0 |% g
2.3.3       底层驱动接口函数(GUIRV_Template)
    STemWin的底层驱动函数也很简单,用户只需提供打点和读点函数即可。但是这种没有经过优化的移植方式非常的影响STemWin的实际性能。这里就针对RA8875说一下需要优化的地方。
l  画水平线的函数
/*********************************************************************
*
*       _DrawHLine
*/
static void _DrawHLine  (GUI_DEVICE * pDevice, int x0, int y,  int x1) {
//  LCD_PIXELINDEX ColorIndex;
- x4 Q* n* U0 W# l* j) e
  if (GUI_pContext->DrawMode & LCD_DRAWMODE_XOR) {
    for (; x0 <= x1; x0++) {
      _XorPixel(pDevice, x0, y);
    }
  } else {
       #if emWin_Optimize
         //LCD8875_DrawHLine(x0, y, x1, LCD_COLORINDEX);
         s_ucRA8875BusyNow = 1;
         LCD_DrawLineH(x0, y, x1, LCD_COLORINDEX);
         s_ucRA8875BusyNow = 0;
       #else
         LCD_PIXELINDEX ColorIndex;
         ColorIndex = LCD__GetColorIndex();
         for (; x0 <= x1; x0++) {
           _SetPixelIndex(pDevice, x0, y, ColorIndex);

$ q% y9 C& [. T% t6 Q
         }
       #endif
    }
}
l  画垂直线的函数
/*********************************************************************
*
*       _DrawVLine
*/
static void _DrawVLine  (GUI_DEVICE * pDevice, int x, int y0,  int y1) {
//  LCD_PIXELINDEX ColorIndex;
; `3 c4 a0 [, j' g
  if (GUI_pContext->DrawMode & LCD_DRAWMODE_XOR) {
    for (; y0 <= y1; y0++) {
      _XorPixel(pDevice, x, y0);
    }
  } else {
    #if emWin_Optimize
         s_ucRA8875BusyNow = 1;
         LCD_DrawLineV(x, y0, y1, LCD_COLORINDEX);
         s_ucRA8875BusyNow = 0;
     #else
         LCD_PIXELINDEX ColorIndex;
         ColorIndex = LCD__GetColorIndex();
         for (; y0 <= y1; y0++) {
           _SetPixelIndex(pDevice, x, y0, ColorIndex);
         }
     #endif
  }
}
l  矩形填充函数
/*********************************************************************
*
*       _FillRect
*/
static void _FillRect(GUI_DEVICE * pDevice, int x0, int y0, int x1, int y1) {
#if emWin_Optimize
    if (g_ChipID == IC_8875)
     {
         s_ucRA8875BusyNow = 1;
         BTE_SetTarBlock(x0, y0, y1-y0+1, x1-x0+1, 0);/* 设置BTE位置和宽度高度 */
         BTE_SetOperateCode(0x0C);           /* 设定BTE 操作码和光栅运算码  REG[51h] Bit[3:0] = 0Ch */
         RA8875_SetFrontColor(LCD_COLORINDEX);    /* 设置BTE前景色 */
         BTE_Start();                        /* 开启BTE 功能 */
         BTE_Wait();                              /* 等待操作结束 */
         s_ucRA8875BusyNow = 0;    
     }
     else
     {
         for (; y0 <= y1; y0++)
         {
              _DrawHLine(pDevice, x0, y0, x1);
         }      
     }
8 V" Z# E* U' e( b. t) ?, X
#else
     for (; y0 <= y1; y0++)
     {
         _DrawHLine(pDevice, x0, y0, x1);
     }
#endif
}
l  绘制16BPP的函数
  1. /*******************************************************************************************************
    : E9 _7 }2 S6 B) S
  2. *
    : }5 Z% B5 ?0 P2 M* A
  3. * Draw Bitmap 16 BPP, not optimized; O/ D6 d6 }1 ~, v
  4. */
    . o/ a; H$ E& c2 n) c6 \% q
  5. static void _DrawBitLine16BPP(GUI_DEVICE * pDevice, int x, int y, U16 const GUI_UNI_PTR * p, int xsize) {- ?9 ~/ f8 d4 m- {/ [5 b1 i
  6. #if emWin_Optimize$ H2 ]: U2 K# O
  7. s_ucRA8875BusyNow = 1;% E1 ~0 N" v& S
  8. LCD_DrawHColorLine(x, y, xsize, (uint16_t *)p);( J% `1 ]* |2 n; C! G  d
  9. s_ucRA8875BusyNow = 0;4 q) l) p+ S8 k+ E
  10. #else$ P8 t+ t# o1 J6 m! s
  11. for (;xsize > 0; xsize--, x++, p++)
      \  z/ _; e! Z  ~* x; D/ m
  12. {: q; B! F+ d7 M4 ?) F( h
  13. _SetPixelIndex(pDevice, x, y, *p);
    2 I8 x7 a9 @. J+ c8 T
  14. }# O# L4 v, n! S5 [% c- a" I4 T/ j" m
  15. #endif
    7 B3 h! _# [8 T0 H7 j) Y
  16. }
复制代码
l  这里要根据实际的情况进行填写,不能填错,要不系统无法启动。
/*********************************************************************
*
*       _GetDevData
*/
static void * _GetDevData(GUI_DEVICE * pDevice, int Index) {
  GUI_USE_PARA(pDevice);
  #if GUI_SUPPORT_MEMDEV
    switch (Index) {
    case LCD_DEVDATA_MEMDEV:
// TBD: Has to be adapted to the right memory device depending on the used color depth!
      return (void *)&GUI_MEMDEV_DEVICE_16;
    }
  #else
    GUI_USE_PARA(Index);
  #endif
  return NULL;
}
    优化好上面四个地方即可。

7 x0 E* N5 X# d6 j3 R: {: F
baiyongbin2009 回答时间:2015-1-8 18:27:56
2.3.4       系统函数配置
    STemWin的底层驱动做好以后,就可以进行GUI和LCD的配置工作,这个是官方提供的配置流程:
2.9.png
1.    GUI的配置
    主要是配置STemWin所需的动态内存,下面的配置方式支持使用芯片内部存储器也支持使用外部存储器(比如:SRAM,SDRAM),使用外部存储器的话,一定要记得初始化相应器件。
  1. ----------------------------------------------------------------------# @( z4 g# l& N2 g
  2. File : GUIConf.c
    % W1 w% q% Z, M
  3. Purpose : Display controller initialization; A8 _6 G" i  @
  4. ---------------------------END-OF-HEADER------------------------------' E  c% B6 n3 A/ n# ^% ^
  5. */
      p: i* [% D/ Y" I+ U
  6. #include "GUI.h"
    ' a; `9 p- L! l+ A
  7. #include "bsp.h"
    8 h# [0 n8 E/ }( {# N0 w
  8. . q. {) n/ p' P+ A: ^* E3 r' e2 K
  9. /*: Z) T1 o; `" d" v: O) z
  10. **********************************************************************; ?: R/ [6 `% r2 ~; |, r
  11. *6 X, r3 i9 s8 c8 R9 _
  12. * Defines1 L! ]8 F  x3 @& K7 A- t& {/ s# Z
  13. *
    ( o( X8 S, @( M) p# J" a* V3 B
  14. **********************************************************************
    ' m3 c# Q* U7 j1 Z# G
  15. */
    " e+ g9 \7 H- w% A$ |0 V

  16.   C7 M/ Q9 T0 b5 ~( x
  17. /* Define the available number of bytes available for the GUI */
    , Q- E  S- S& X% I% ~- q
  18. //#define GUI_NUMBYTES (1024*105)- f; e+ r% e' \. @2 R
  19. #define GUI_NUMBYTES (1024*100)- s6 V9 z0 D6 [9 `) b' P/ E" {2 @
  20. /* Define the average block size *// F# n% \* X/ o
  21. #define GUI_BLOCKSIZE 0x80
    3 P. a) I# Y9 t: p0 V8 o

  22. ) T% t$ \2 N. Y! G) @6 I, ]
  23. /*********************************************************************
    6 z# R1 {- h% c3 q. g5 O, \
  24. *
    ; C0 S+ Z: M4 H1 o1 f$ f' b
  25. * GUI_X_Config. `) Z% t2 a0 o
  26. *
    4 b8 Q. x( \7 U1 @
  27. * Purpose:
    / f2 d3 L, d) h1 S
  28. * Called during the initialization process in order to set up the
    3 ^4 ]1 f! T6 D6 f$ N
  29. * available memory for the GUI." [! {& f  I6 |5 i  c2 s# O
  30. *********************************************************************** p# P. Z; i( s7 I. V5 Z6 O
  31. */$ L- D$ i# _  Y1 a- e# z/ T. Q
  32. void GUI_X_Config(void), k  h- ?1 f& {' H: m# ?
  33. {
    % |2 O! f2 l0 [/ @4 q; {4 h
  34. #if 1 //使用芯片内部内存
    # G3 s( O3 @  t' Y1 M; N
  35. /* 32 bit aligned memory area */) e5 W0 T' J; Z6 @/ W& M: f+ \
  36. static U32 aMemory[GUI_NUMBYTES / 4];  p2 N& e' ~/ F# U* |8 I

  37. : k/ q' E8 S3 |/ F6 D
  38. /* Assign memory to emWin */- s6 o% q4 w' v5 ?+ \3 r+ t- g
  39. GUI_ALLOC_AssignMemory(aMemory, GUI_NUMBYTES);4 [2 Q0 C, a0 h; I6 B( ~
  40. GUI_ALLOC_SetAvBlockSize(GUI_BLOCKSIZE);
    2 D1 `$ y9 P. e1 J3 Q0 f
  41. #else//使用外部内存
    8 F/ X% l! E% M! C5 E3 @8 [# p, {
  42. static U32 *aMemory;+ Q: v& `  a  D3 X, e  e& z
  43. aMemory = (U32 *)EXT_SRAM_ADDR;
    % ~) B' _1 ]5 {2 Q, q* a: d3 U: P
  44. /* Assign memory to emWin *// _, L* M# S! ?! J( e9 F% B, Q
  45. GUI_ALLOC_AssignMemory(aMemory, GUI_NUMBYTES);
      [) R( B5 E/ ^8 H, ^% S
  46. GUI_ALLOC_SetAvBlockSize(GUI_BLOCKSIZE);
    & u' ]( u7 a6 D) }- R! T
  47. #endif; g7 J( D% }2 e$ y/ Z0 E% i7 ^
  48. }
复制代码
2.    LCD的配置
    LCD的配置按照上面官方提供的驱动流程执行即可,下面是详细的代码。
  1. /*  N# t: m- u/ k8 c  x* a3 S5 ]* X
  2. ****************************************************************************" q7 o3 k; k5 r5 h) v( U
  3. *, b1 Z9 R2 ]3 a# `/ ?
  4. * LCD_X_Config7 X& Y( U- M  @. x
  5. *
    3 A  a1 Y! j4 x4 V* r# k
  6. * Purpose:
    0 B4 [. E' P, W) O* H
  7. * Called during the initialization process in order to set up the6 P+ ~- O2 s8 c* F2 p5 y* c4 V
  8. * display driver configuration.1 l# g7 i9 Y: Q% J* U  X. n4 j" n
  9. *
    " Y% p7 g1 G# E  l
  10. ****************************************************************************
    8 m4 I. r9 u# B) B8 b
  11. */
    8 L% |# L. C1 Q. e/ c' F- P) M3 H
  12. void LCD_X_Config(void)! t, d1 g# b( c4 Q  E. d" J& i& _. d
  13. {( Q' v' f0 ^. q0 {. m
  14. /* 读取EEPROM中的参数 */
    9 D. ]  c0 ^$ s
  15. ee_ReadBytes((uint8_t *)&g_tTPSL, 1024, sizeof(g_tTPSL));
    8 H" f4 A1 c$ c$ m7 q
  16. , P8 I) E" D4 u/ M3 z& F% Y
  17. /* Set display driver and color conversion for 1st layer */6 }8 W& `. Y0 R$ U6 F/ J
  18. GUI_DEVICE_CreateAndLink(DISPLAY_DRIVER, COLOR_CONVERSION, 0, 0);
    + }( S6 L& h& D! D+ J5 A: M, u

  19. 7 o0 W1 P0 ^6 q  K4 g: m' b
  20. if (g_ChipID == IC_8875)  W" o$ w5 G* ~) s
  21. {8 u' q2 c3 H* d" T. P) {
  22. if (g_ucGPIX == 1) /* GPIX = 1 4.3 480x272 */
    3 }8 P/ f8 C3 U( w$ X3 K1 Y
  23. {' ~  ], i+ R/ i& P8 d+ N8 Z
  24. /* Display driver configuration */0 F/ b9 ?- V& s( E8 q4 p# h
  25. LCD_SetSizeEx (0, 480, 272);
    % y! g8 G' v* H+ b
  26. LCD_SetVSizeEx (0, 480, 272);( I! z" D/ `! z8 u8 s7 f7 m1 d
  27. ; |, P' E7 P0 `& z/ `' w0 T
  28. /* Touch calibration */; D( L2 W& c$ |
  29. GUI_TOUCH_Calibrate(GUI_COORD_X, 0, 479, g_tTPSL.usAdcX1, g_tTPSL.usAdcX2);5 l( I/ ^! ]1 W8 I( O. w
  30. GUI_TOUCH_Calibrate(GUI_COORD_Y, 0, 271, g_tTPSL.usAdcY1, g_tTPSL.usAdcY2);* H. {& z: {  a6 z$ K4 p: s
  31. 5 D' t6 T( c8 M
  32. /* 查看是否需要切换X,Y*/$ a. }& ~4 F( e& \  z
  33. if(g_tTPSL.XYChange == 1)* R4 \2 a; Z* B! y; B+ n' m
  34. {( S& r: g# y$ ]( s7 f
  35. GUI_TOUCH_SetOrientation(GUI_SWAP_XY);
    ) D# {. a; ]- a+ o3 v3 L
  36. }+ E+ d+ M) L& ~6 I( @
  37. }
    3 I% z. `4 P5 i0 [  W; D% R/ ^# p
  38. else /* GPIX = 0 7 800*480 */
    . D3 s: U* ?* i: r2 A& [. T
  39. {$ |3 g) F0 f. A
  40. /* Display driver configuration */
    # v, X8 R9 J/ s0 k
  41. LCD_SetSizeEx (0, XSIZE_PHYS, YSIZE_PHYS);0 N. F* C' E+ }1 m7 g/ N
  42. LCD_SetVSizeEx (0, VXSIZE_PHYS, VYSIZE_PHYS);
    * U$ m; A* ?1 V

  43. 7 @: I% ]: Q; {* R. O# `, U: F
  44. GUI_TOUCH_Calibrate(GUI_COORD_X, 0, XSIZE_PHYS - 1, g_tTPSL.usAdcX1, g_tTPSL.usAdcX2);
    5 V! T8 ?  j( c" e$ F: s
  45. GUI_TOUCH_Calibrate(GUI_COORD_Y, 0, YSIZE_PHYS - 1, g_tTPSL.usAdcY1, g_tTPSL.usAdcY2); ) T. N5 `4 c; d4 `& y% e. c

  46. # |4 q( o. y! H. z/ A
  47. /* 查看是否需要切换X,Y*/7 W  @4 j8 m  @9 I
  48. if(g_tTPSL.XYChange == 1)( A( p0 G& _+ K1 [
  49. {/ J$ v$ S9 y5 `: H0 x
  50. GUI_TOUCH_SetOrientation(GUI_SWAP_XY);
    5 N" o0 n. [  a  I! X6 N  K
  51. }7 U  a6 p* I' h, b5 E
  52. }
    ) p: c& F, e& E. z
  53. }% n; ?' D& q: m5 O, s) {1 _3 @
  54. else7 Q- X. o3 w$ H9 D, T
  55. {8 d- ~7 M; o& A( s6 s
  56. LCD_SetSizeEx (0, 400, 240);: j: v; j2 @' B& A+ ^
  57. LCD_SetVSizeEx (0, 400, 240);
    ; [5 J, l* c& i3 e9 k0 [, X
  58. + B+ }! S! |* `. I, t4 {" \, p
  59. /* Touch calibration */3 T" b: I& F  E9 w
  60. GUI_TOUCH_Calibrate(GUI_COORD_X, 0, 399, 300, 3600);. w  z0 o7 g  \' [: C
  61. GUI_TOUCH_Calibrate(GUI_COORD_Y, 0, 239, 273, 3671);
    - i2 m. S5 ^: X: A- y! f
  62. }0 r$ W# _* Z9 b  \3 i

  63. 6 O0 x% o, [! `1 u- e0 C
  64. }
复制代码

' H: ~4 a. j" ]6 W0 f. C+ i
baiyongbin2009 回答时间:2015-1-8 18:30:51
2.4  STemWin带RTOS的移植
    带系统和不带系统的区别就是添加一个驱动文件并添加RTOS相关文件即可,STemWin软件包里面提供了一个FreeRTOS的驱动文件,而MDK安装目录里面提供了好几款RTOS的驱动。所在路径如下:
        MDK4.73安装目录:C:\Keil4.73\ARM\Segger\emWin\Sample\GUI_X
        STemWin软件包:STemWin_Library_V1.1.2\Libraries\STemWinLibrary522\OS
2.10.png
                              
    用户更具自己使用的OS,并添加此驱动即可,下面是FreeRTOS的工程目录。
2.11.png
2.5  总结
    整体来说,STemWin的移植不难,难的是底层驱动的优化,如何让它工作在最佳性能状态。这里有三个DEMO演示视频(分别是3.0寸,4.3寸和7寸的视频)供大家欣赏下:http://bbs.armfly.com/read.php?tid=1545。
4 l- ^& v' @5 D% d8 q% s" b* W
默默前行 回答时间:2015-1-8 18:32:52
感谢楼主分享。
moyanming2013 回答时间:2015-1-8 19:51:43
有没有STM32F429DIS的移植??谢谢!
那片清茶 回答时间:2015-1-8 20:05:48
楼主什么时候出数字信号的例程啊。。
zhous 回答时间:2015-1-8 20:11:28
点赞啊!!!
baiyongbin2009 回答时间:2015-1-8 20:12:02
moyanming2013 发表于 2015-1-8 19:51, \  `6 J; b$ @
有没有STM32F429DIS的移植??谢谢!

/ y4 o! Y; u. j4 `, d5 B4 J移植详解,是官方移植好的:http://bbs.armfly.com/read.php?tid=1958
baiyongbin2009 回答时间:2015-1-8 20:12:38
那片清茶 发表于 2015-1-8 20:05
1 L: a1 ~" G$ y4 p1 _2 p楼主什么时候出数字信号的例程啊。。

8 |, E+ N, F6 p* ?$ F0 X/ |# O很快了,这几天正在赶工,这个月15号前就发布。
moyanming2013 回答时间:2015-1-8 20:14:48
baiyongbin2009 发表于 2015-1-8 20:12& Y1 n) G: W4 U8 B7 I9 s/ _' p
移植详解,是官方移植好的:http://bbs.armfly.com/read.php?tid=1958
# t) g! w. b7 Y& o+ v, F
太好了,LZ有没有429或439的板子出?
boyubeiyu 回答时间:2015-1-8 20:21:21
安富莱的资料一向很给力
那片清茶 回答时间:2015-1-8 20:57:17
baiyongbin2009 发表于 2015-1-8 20:12& p3 D  U3 g& m0 y7 |
很快了,这几天正在赶工,这个月15号前就发布。

0 l& I* B( ^+ k有没有图像处理的例程,也可以共享出来。
baiyongbin2009 回答时间:2015-1-8 23:13:46
moyanming2013 发表于 2015-1-8 20:14" W: {3 Z( M/ ~4 x% U
太好了,LZ有没有429或439的板子出?
' V& h( c3 t! b2 R! c% b- p+ L% Y
这个得春节后了。
12下一页
关于
我们是谁
投资者关系
意法半导体可持续发展举措
创新与技术
意法半导体官网
联系我们
联系ST分支机构
寻找销售人员和分销渠道
社区
媒体中心
活动与培训
隐私策略
隐私策略
Cookies管理
行使您的权利
官方最新发布
人形机器人运动控制、感知与智能配电
半导体创新技术与应用方向
EE架构与软件定义汽车
12V/48V 汽车智能配电(SPD)
区域控制单元(ZCU)与分区架构
关注我们
st-img 微信公众号
st-img 手机版