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

STemWin 树形文件 目录 执行 初始化速度 和 内存优化

[复制链接]
lovewyufeng 发布时间:2014-12-12 17:35
本帖最后由 lovewyufeng 于 2014-12-12 17:55 编辑 # X- j" s' R  i5 m+ l$ t& |) S
+ b7 P, J; X5 z4 V8 w( J
不知道大家有没有  这样的应用,需要将磁盘上面的文件以列表方式显示出来。,0 o- w% z' t/ t7 \5 Y7 `

+ u8 q8 D4 E, d0 J/ F. q0 C6 _TREEVIEW 无疑是最佳选择了,可是 假如存在这样一种情况,你的设备经常需要保存文件,  比如每个小时保存一个 文件  每天或者每个月一个文件夹; ]! _6 V  d5 n+ p/ j5 }
也许没这么频繁,但是无论如何  设备使用到一定时间  磁盘里面的文件数量将不可估量。
+ N/ k  y/ z. y/ {, }那么问题来了# v8 X/ J, x% L9 l& U

; H( m" j' n# ~5 D( ~第一、 树形目录  一个节点消耗100字节  一个树叶 消耗  50字节 当你的文件成千上万的时候  你的内存消耗得起么?
( Q9 B) g3 e, @7 o第二、众所周知磁盘操作速度很慢的,就算你获取文件名  同样需要操作磁盘   当你的文件成千上万的时候 你初始化这个 树形结构 可能都需要10多秒甚至更多。, t* z9 p3 j; I! Y  f8 K
         别认为没那么慢,笔者曾经在 NAND FLASH上使用JFFS2文件系统  从文件一个有500个子文件的文件夹中  遍历检索第  100-103 4个文件花的时间长达2s    8 W: C' \' E" ]! [, w2 z
         当然这个 JFFS2这个文件系统有关系, 后来使用FATFS文件系统  就快了起来   但是第一点依然是很严重的问题' x7 t7 x" l6 i( c: O; M  X

- w' ^' ]% G0 c$ K( n/ N8 O! f% @5 u, b7 `2 B  x
为解决这个问题   笔者提出一个方案。0 [) r- {* ?& d5 b5 [0 M
初始化 TREE的时候只将第一层  节点添加进去,对于文件夹, 在节点内添加一个占位 叶节点,这样看起来这个节点前面就有一个 +号可以被打开。, o/ u2 o6 }4 v! X( I9 V7 L* _
当打开这个节点的时候查看子节点是否为预添加的占位符, 如果是 再去遍历   对应的文件夹,同时删除占位符,添加节点。. G4 n7 k. `/ j9 {' n1 J! K' Y
如此  遍历的时间由单个文件夹的文件数量决定,不会因为总数量 庞大而慢。, g  H$ [+ Y8 L3 b5 J- Z/ Z
内存则由 打开过的文件决定, 甚至  当系统内存不足的是否可以 删除被关闭的  节点内容 再次添加占位符。释放内存。" g( ]( {& p& c( u& J: U- u

! g  N! J8 Q+ I5 M: d1 K/ i; ]$ R8 J7 |( o

8 f( w  y7 k- k+ R. e
$ U. l2 T2 h% Z. ?6 [0 r! J9 C# m# c2 i
2 ?+ O, t5 I0 D: U5 f4 L& L
那么现在方案有了  具体怎么实现呢?1 A, n- J0 ?$ Q' `; L

- `) v# Q2 Q, A; j9 E7 J
9 ?( D1 B/ g/ D6 _# W这里笔者提供一个已经实现的  回调函数  callback6 m  y3 _0 C9 h% I9 Q3 K

: {. i5 B% R7 `! Z( |4 X9 m

* D6 X3 a# s1 P  H9 X2 a

  1. * C% m  S# g) g8 L9 r
  2. + J1 D( I' a) d1 |+ n
  3. TREEVIEW_ITEM_Handle Item_get_next(TREEVIEW_ITEM_Handle hItem)//用到辅助函数' Q0 E9 C7 V/ v' Q+ q: c
  4. {
    : f) |3 P5 Q. a
  5.     TREEVIEW_ITEM_OBJ *itemobj;
    " M# K! \. O/ t- K( i
  6.     if(hItem)' o) G$ A: {/ {7 e  o
  7.     {
    - Y; r6 _: P, g& ^7 o4 v' y
  8.         itemobj=(TREEVIEW_ITEM_OBJ*)GUI_ALLOC_h2p(hItem);
    + I' D) t1 _! C: o% V1 P' L
  9.         return itemobj->hNext;) Z1 o- ]) f2 y5 z7 [
  10.     }
    5 }) W1 N( u* s. K6 I$ y. g: t
  11.     return 0;
    9 {( ?# M% I% e; N! c
  12. }  [2 @# H7 p; N1 D
  13. 5 t9 w4 }# {4 k% \
  14. void _cbtree(WM_MESSAGE * pMsg)& D. @) s8 d. b0 K" u) ^$ F, P5 _
  15. {
    $ P" f) I: M6 C/ p+ _1 W
  16.     int Id, NCode;
    0 Q5 H$ P- P9 {" ~" h1 n/ |- L  R
  17.     TREEVIEW_ITEM_Handle hItem,fristitem;
    9 {: h) Q: N! y2 i$ J
  18.     char buf[20];
    & C- h  y( e$ l  G% a
  19.     int num[2]={1,2000};+ U( \! J5 f- P8 W2 C: H9 C9 l9 @
  20.     TREEVIEW_ITEM_INFO info;; @- I- A+ Q2 b  A* K/ s/ ~
  21.     switch (pMsg->MsgId) * }& {' ~8 ~- a$ e) g
  22.     {: G1 p! _! b+ o$ z# S- W
  23.     case WM_KEY://拦截 按键消息
      R  v: k- R# {: u6 [
  24.         {
    # q$ i+ l0 M# L% r4 \
  25.             int pressed;
    ) J- l* c% T2 }6 a, X
  26.             pressed=((WM_KEY_INFO*)(pMsg->Data.p))->PressedCnt;  ~. r/ G3 H# x
  27.             NCode = ((WM_KEY_INFO*)(pMsg->Data.p))->Key;
    5 x% g9 l4 d5 P. ]; @

  28. ' J4 _4 H9 x+ s+ i5 n+ `$ p: Z
  29.             switch(NCode)
    ; ?& @( B2 O1 H" H5 j( D  L; ?4 [
  30.             {6 m, N, h+ I  q9 _
  31.             default:# Q2 n* e- n& {9 ]' J( t
  32.                 if(pressed)3 h, S, _7 Z$ K, z
  33.                 {
    ' j% F# w. x5 ~, \+ w% ~! |9 t
  34.                     if (NCode==GUI_KEY_RIGHT)// 树默认right 键打开节点,再打开前  添加节点9 j) o9 v4 H" l  Q
  35.                     {7 `  V3 x: J4 X9 k7 r
  36.                         hItem=TREEVIEW_GetSel(pMsg->hWin);# d' \% X# ~! J1 L, t" G
  37.                         TREEVIEW_ITEM_GetInfo(hItem,&info);
    7 V- l: n, i' B' K9 u0 E4 w8 Z1 {' f5 ?
  38.                         if(info.IsNode)
      B2 E5 M/ J1 @( b" e  h* F
  39.                         {: \- S7 h0 ?( I
  40.                             fristitem=TREEVIEW_GetItem(pMsg->hWin,hItem,TREEVIEW_GET_FIRST_CHILD);
    ( a0 T: ]% V1 n0 [  q
  41.                             TREEVIEW_ITEM_GetText(fristitem,(uint8_t*)buf,20);
    0 _1 `+ F* T  q3 X; d
  42.                             if(strcmp("space",buf)==0)//比较是否为占位符4 D3 r0 w8 O" X# ~7 Y
  43.                             {  ?. V6 H0 l4 l5 J1 P
  44.                                 TREEVIEW_ITEM_Delete(fristitem);
    & n' t6 o" n- c0 B8 k! ]
  45.                                 tree_add_filelist(num,0,pMsg->hWin,hItem);//这个函数将  遍历磁盘文件添加到树 指定节点
    7 }% Y& t; H! H
  46.                             }, T6 |+ q! c5 O8 C/ o0 h
  47.                         }
    ( V- b9 k; w# O2 [( [
  48.   v: L2 H2 {8 U6 e
  49.                     }
    & u1 E" q' T$ ~! o6 e2 N% g4 q6 w3 y
  50.                 }8 P) Q5 R2 T5 ~: }* @
  51.                 else
    * R) C/ w- B+ g
  52.                 {
    - Z$ Z8 o0 ~% a5 d9 {
  53.                     ((WM_KEY_INFO*)(pMsg->Data.p))->PressedCnt=1;
    % G* b1 Q$ J1 z9 X! ]3 ]: c
  54.                     TREEVIEW_Callback(pMsg);6 Z$ Y. O) t9 I, Q/ }* n( }
  55.                 }
    ; V7 ~( v. Z( v/ l
  56.                 break;& a3 a+ ~: V. M; P( L7 t
  57.             }4 L  ?0 S3 H4 h# D# B
  58.         }
    ) `& \6 \% u" k: @& i  Y
  59.         break;
    $ q  r7 |' H& E: p3 [+ w
  60.     case WM_TOUCH:// 这个是处理触摸事件   比较麻烦一点  主要是获得触摸的地方, 遍历TREE 取得被点击的节点  判断是否为 节点  然后的操作就和  按键一样了
    0 y, I2 T  ?  ?+ Q
  61.         {
    3 d4 r  b% M& N$ p4 {' H/ R5 T& ]% D7 N
  62.             TREEVIEW_ITEM_Handle hNode;+ g+ K  X6 h" _* r! w
  63.             GUI_PID_STATE* pState;) D! n# i9 @6 D5 t: f
  64.             TREEVIEW_OBJ *treeobj;4 N$ k$ S% a3 V

  65. 5 V3 M5 s( L; e6 q. d2 I% _: x8 e
  66.             pState     = (GUI_PID_STATE*)pMsg->Data.p;8 e0 K7 I  C# J8 G
  67.             treeobj       = (TREEVIEW_OBJ*)GUI_ALLOC_h2p(pMsg->hWin);
    8 y! T4 b3 G8 @6 q" g& e
  68.             if(pState->y/treeobj->Props.MinItemHeight<treeobj->NumVisItems+1)3 v  K8 \8 p% |$ U  g% r8 w
  69.             {8 n. y0 X3 o" p# C5 M( b
  70.                 hNode=TREEVIEW_GetItem(pMsg->hWin,0,TREEVIEW_GET_FIRST);
    - o/ i5 Q6 a' z
  71.                 if(hNode)# e$ ^: c1 u2 T6 s  c6 S) p
  72.                 {3 @) e& k6 X# m* Q3 o: m' w9 ]
  73.                     int num=pState->y/treeobj->Props.MinItemHeight +((pState->y%treeobj->Props.MinItemHeight)>0 ?1:0)-1;//计算被点击的是第几个节点
    7 C9 F% P4 w0 ~7 |% t( J# q1 v& ^
  74.                     if(treeobj->ScrollStateV.v>0)4 T6 n+ [8 O$ i) X
  75.                         num+=treeobj->ScrollStateV.v;
    2 e) k! b# z, P8 P

  76.   k0 ~( t, {4 x
  77.                     while(num--)//这个while  遍历得到被点击的  节点handle
    - p  H! {- o: ~9 l6 x2 y% D3 W5 g$ ]0 p
  78.                     {
    # A/ ~. }! Q5 F* O# `! n
  79.                         TREEVIEW_ITEM_GetInfo(hNode,&info);& `; x" f1 h' b  |7 {- Z/ k" e
  80.                         if(info.IsNode)2 `7 k! V7 s8 U  z) H( {
  81.                         {+ d" }3 y1 E6 V6 Y1 R
  82.                             if(info.IsExpanded)
    3 M. C' {$ p, w0 W, L2 I
  83.                             {
    4 i9 @$ _+ q9 T9 r- i  x
  84.                                 hNode=TREEVIEW_GetItem(pMsg->hWin,hNode,TREEVIEW_GET_FIRST_CHILD);' P% Z$ H: ^( j
  85.                             }5 O2 a7 l4 b# Q6 q4 B' `
  86.                             else
      N/ V, L9 _) F( Y% J
  87.                             {
    1 U3 |& g* W- b# `
  88.                                 hNode=TREEVIEW_GetItem(pMsg->hWin,hNode,TREEVIEW_GET_NEXT_SIBLING);
    4 I, l: t( Z. h- v  I
  89.                             }1 i* L* D& j7 h. w5 T* _( v

  90. ) C1 ^% Z7 P4 o) Z9 ]
  91.                         }* {  V8 L  u1 R4 |
  92.                         else
    / |7 L5 S# c3 `: o! y3 ?
  93.                         {
    $ R. a, s" i" ?. x
  94.                             hNode=Item_get_next(hNode);
    1 I$ v1 @1 O) o* @8 s- y% L
  95.                         }% u1 H, Y( Z) k; v7 m* f
  96.                     }( {9 \* n) W* X
  97.                 }
    3 t9 O) f7 x, o# u! q
  98.                 TREEVIEW_ITEM_GetInfo(hNode,&info);2 n$ ?$ ^& V/ v% A; R3 a/ p
  99.                 if(info.IsExpanded==0)
    $ z/ M+ E9 M1 ^# {3 @7 e2 B
  100.                 {! \- J* e: e" t% l5 ?
  101.                     if(info.IsNode&&(pState->x<((info.Level+1)*treeobj->Props.Indent-treeobj->ScrollStateH.v))&&8 c& N% _0 t  \- q, q' p
  102.                         pState->x>((info.Level)*treeobj->Props.Indent-treeobj->ScrollStateH.v)4 _8 |, {' u* ?: `
  103.                         )7 d7 p5 z  `5 Z% T5 C
  104.                     {: t4 ~7 Z& `9 n/ F  R
  105.                         fristitem=TREEVIEW_GetItem(pMsg->hWin,hNode,TREEVIEW_GET_FIRST_CHILD);
    9 W8 {3 f# A( w  x5 ^6 R
  106.                         TREEVIEW_ITEM_GetText(fristitem,(uint8_t*)buf,20);
    % T% l, h- m$ @" e% k/ R2 Y6 Q2 w
  107.                         if(strcmp("space",buf)==0)
    ) F9 L$ U4 H  w  m' n
  108.                         {
    8 e1 N# }% M. |! `9 U4 q7 L8 F, y
  109.                             TREEVIEW_ITEM_Delete(fristitem);
    + ]7 l3 Y% V9 O: W$ `" E8 p
  110.                             tree_add_filelist(num,0,pMsg->hWin,hNode);
    $ G* E1 }" B8 L9 M3 Y$ b- C
  111.                         }# d& U2 g2 H1 P  Z' s
  112.                     }
    ! T/ z) I7 j) ^, D+ q: N, Y3 y5 ]
  113.                 }
    . ^" ?( |% S8 _: U% k1 a4 ^7 R
  114.                 else
    * s+ F1 q/ z- ~9 g
  115.                 {
    9 X+ n8 N+ T5 r& c# A. }, h. N
  116. ! p7 S6 k' S( H
  117.                 }
    5 v8 O3 \  w+ D$ e8 Y
  118.                 TREEVIEW_Callback(pMsg);
    5 O' [. t! Z5 _+ F; n( H
  119.             }0 c$ c$ i  x* R+ u  J; K1 A; N2 W
  120. % ~/ b1 m5 T2 `4 O9 D, R. c2 i
  121.         }+ X6 C5 M- N$ y: h& A  J4 s
  122.         break;4 u% c# ?1 m/ C( q8 r! M' J
  123.     default:  ^, r; c8 J8 f7 x
  124.         TREEVIEW_Callback(pMsg);3 }2 b) B& j/ N) {
  125.         break;
    % u% `) M" \, d! B
  126.     }
    " s" f5 ?4 h( B8 v$ a6 ~5 \/ t

  127. 8 h+ s+ n4 r6 O
  128. }* a% O% D( k1 k* F% I

  129. ! e! \4 W( ~7 K: a
  130. 6 x% Z, o) ?' `) h8 u
复制代码
4 }6 y: t/ A: r& b7 }; x+ H

& j# a7 X6 z3 @( T# b" Z
赞 收藏 1 评论10 发布时间:2014-12-12 17:35

举报

10个回答
lovewyufeng 回答时间:2014-12-12 17:38:16
自己占沙发
aderson 回答时间:2014-12-12 17:41:54
石头板凳顶龙少
沐紫 回答时间:2014-12-12 17:41:58
赞赞赞!
lovewyufeng 回答时间:2014-12-12 17:47:26
adersonl 发表于 2014-12-12 17:41
% U& @6 b. e6 P  j石头板凳顶龙少

: z6 U$ ^$ `) o  m  i3Q  大家的肯定是我的动力
lovewyufeng 回答时间:2014-12-12 17:53:44
上传一张效果图片 QQ图片20141212175156.jpg
0 M+ s7 |* u6 R" q. q! Z! O& i0 r- ]/ ?
大器所成 回答时间:2014-12-12 21:00:42
太棒了!膜拜下
善良的女性 回答时间:2014-12-12 23:47:53
好复杂啊 好好学下
' z% |, A0 U; o% }* q. l) V
8 Z7 _1 G9 w2 a& z1 k5 w1 E+ O. o
9 m- R) H2 ?! n) f* _( k3 z5 e" t8 P% R% u; y# S3 K
Dylan疾风闪电 回答时间:2014-12-13 21:43:16
点赞,支持。
lovewyufeng 回答时间:2014-12-13 23:10:09
Dylan疾风闪电 发表于 2014-12-13 21:438 Z9 w# g7 |" Z. g3 E: ]* b! [1 t
点赞,支持。
4 D. a# K$ m* @, T2 \. H; |
这个控件不是很好用  改天介绍另一个   文件操作专用 小工具
yang 回答时间:2014-12-18 12:07:47
牛人, g: j1 C* O! v9 I* q" d
学习了
) x1 A0 P5 \* _
关于
我们是谁
投资者关系
意法半导体可持续发展举措
创新与技术
意法半导体官网
联系我们
联系ST分支机构
寻找销售人员和分销渠道
社区
媒体中心
活动与培训
隐私策略
隐私策略
Cookies管理
行使您的权利
官方最新发布
人形机器人运动控制、感知与智能配电
半导体创新技术与应用方向
EE架构与软件定义汽车
12V/48V 汽车智能配电(SPD)
区域控制单元(ZCU)与分区架构
关注我们
st-img 微信公众号
st-img 手机版