上次已经开启了Linux系统,并且有GUI桌面,虽然不是比较熟悉的Qt环境,但也是可以做个小应用感受下stm32mp135系列产品的特点。 首先要搭建开发环境,毫无疑问安装个SDK就行了,官方WiKi页面啥都有。 基于Ubuntu18系统,补充安装所需要的库和小工具 更新软件列表 安装python3 - sudo apt-get install gawk wget git diffstat unzip texinfo gcc-multilib chrpath socat cpio python3 python3-pip python3-pexpect
复制代码 其他工具- sudo apt-get install libssl-dev libgmp-dev libmpc-dev lz4 zstd
复制代码 编译器等组件 - sudo apt-get install build-essential libncurses-dev libyaml-dev libssl-dev
复制代码 默认使用python3 - sudo apt install python-is-python3
复制代码 其他有用的工具 - sudo apt-get install coreutils bsdmainutils sed curl bc lrzsz corkscrew cvs subversion mercurial nfs-common nfs-kernel-server libarchive-zip-perl dos2unix texi2html libxml2-utils
复制代码 执行完以上内容,就可以下载和安装SDK软件包了。从以下地址获取最新的SDK https://www.st.com/en/embedded-software/stm32mp1dev.html#get-software 我还是在windows下面下载的,然后拷贝到了虚拟机使用。使用tar xvf 解压该压缩包。chmod +x 赋予可执行权限。然后运行安装就行了,默认的目录是/opt/st/stm32mp1/,,这个路径就可以,直接继续安装。
% [; A1 r0 U4 T Y" l; x& V
+ G8 b2 |. H6 Y% u- _* t0 p* [8 y6 j 然后就学着官方文档的样子去验证下SDK是否安装成功
. \7 L; Y! Q) q* x# V' X
: k* \2 u1 S0 i; O) H% l 以上就完成了编译环境,至于说开发环境,一般还得有个IDE或者其他编辑器加调试工具。这里打算做的小程序使用gedit就行。 首先拷贝官方给的demo程序,基于GTK得hello world。 - #include <gtk/gtk.h>
) F) w- k! h% I \6 K - # m7 o0 o3 F0 M. u/ v0 y
- static void
+ j/ d4 ]6 O* M - print_hello (GtkWidget *widget,
% h7 h- v! g6 }% x% | - gpointer data)
6 i& l4 y8 ]1 @- Q - {
' K& J3 C3 N1 O' P. z# x - g_print ("Hello World\n");
& v. h7 I+ o+ ~) k. M8 ? - }
/ a6 a7 G0 N5 @5 M7 Q I% c6 H2 B - + q; |8 z' c0 x4 j7 f2 g
- static void; U; A) p' _, E; k9 n6 G: t6 B
- activate (GtkApplication *app,! X6 W. m2 \ I% S
- gpointer user_data)
& \6 `: V& @& H- L. W& P - {
8 x' K$ B3 v- n$ ?$ V c6 g5 I3 f0 h - GtkWidget *window;; ?. N" t& o; \
- GtkWidget *button;
- d2 k; p L$ X5 x1 e% T/ a4 o - GtkWidget *button_box;( } C" }! ^! n' H- s. i; {# t
- & Q8 T$ w4 a6 L" w5 j+ X
- window = gtk_application_window_new (app);
/ J4 C/ h) k- W9 G1 b" L( X - gtk_window_set_title (GTK_WINDOW (window), "Window");3 c/ ?3 t% @& n! }/ M: L- d% _
- gtk_window_set_default_size (GTK_WINDOW (window), 200, 200);
" T: d9 K! @8 L2 y
! W: B# Z+ R9 I9 l: |- button_box = gtk_button_box_new (GTK_ORIENTATION_HORIZONTAL);
4 k8 L. A% g) N& T - gtk_container_add (GTK_CONTAINER (window), button_box);" }) ~% @9 m" K. m0 t9 K
- f/ V# ?8 I1 ?# C: v' h- button = gtk_button_new_with_label ("Hello World");
# q. {7 ] _: |7 N) I+ I4 N - g_signal_connect (button, "clicked", G_CALLBACK (print_hello), NULL);
: _# a3 N# g# l; {4 F | - g_signal_connect_swapped (button, "clicked", G_CALLBACK (gtk_widget_destroy), window);6 `6 \8 _( r) a2 A- f$ I i0 i
- gtk_container_add (GTK_CONTAINER (button_box), button);# N: O3 L' f7 V' S# \! r
- ) G8 e' W" @% R' B0 n- D& J
- gtk_widget_show_all (window); X+ I, D% i/ D: h4 | ?
- }
. d7 E) R J* `& ~6 x5 g+ n5 ] - 6 Y4 j2 O$ y$ B; M6 H3 O) }7 `7 s- \
- int
5 } E' O, {4 J1 e. W, ]2 i" @/ v - main (int argc,7 Z3 x0 f4 C3 b4 o" J
- char **argv)
; g7 S( }# i& o4 A6 Q- ]4 T - {
; B( @( b2 x! i - GtkApplication *app;# S7 N3 _# N' y( x* B1 Q' g4 @9 Q( c
- int status;( K- a, V6 p3 K% ]. T! [6 r
! U3 K7 g5 R1 w8 b) o- app = gtk_application_new ("org.gtk.example", G_APPLICATION_DEFAULT_FLAGS);
9 M. G0 D2 Q0 Z9 C+ o% L+ R - g_signal_connect (app, "activate", G_CALLBACK (activate), NULL);
) v! C4 c1 j( ~+ O* Q - status = g_application_run (G_APPLICATION (app), argc, argv);
% m F8 F) u1 k5 l0 t - g_object_unref (app);* _0 p; {/ w) G/ v$ t
- ! R0 ^% p* }: v! j9 `: d9 v7 c: m
- return status;
+ u, T9 T( p5 F; k! { - }/ X4 O. l# _8 I& n% u" H8 b, y
复制代码 然后也复制一个makefile文件,其实单个文件,直接使用gcc命令也可以得。 4 S9 \ o) `$ R2 c0 O8 o
- PROG = gtk_hello_world' @) K$ n- @: H) E( v' G0 {
- SRCS = gtk_hello_world.c. @5 q- a, {) v
- 9 O3 ~! s. M; f2 U- f' x
- CLEANFILES = $(PROG)) u+ _* \, G. c; Y- L
/ |% d( \; \* j/ p s. c3 H- # Add / change option in CFLAGS and LDFLAGS; ^ k& q4 E0 [& ~5 d6 x
- CFLAGS += -Wall $(shell pkg-config --cflags gtk+-3.0)
0 u0 `( o3 l& D; Z% m2 k: m - LDFLAGS += $(shell pkg-config --libs gtk+-3.0)* f- Z8 v( B/ A+ _# |1 X( Q
7 ~& {7 q7 a) G; h/ k. C- all: $(PROG)
7 r0 V) J7 @0 X- j1 U
/ _9 `5 Y y8 P0 O& @- $(PROG): $(SRCS)0 C1 r9 o/ B3 B, e9 E& H" {/ |
- $(CC) -o $@ $^ $(CFLAGS) $(LDFLAGS)
$ A) e+ }* u" m6 V! ~( @/ {3 p( h
! k6 R$ l2 R( l; i6 W) P- u/ z) g- clean:
& X3 v* y: i7 B2 |2 m" U( ] - rm -f $(CLEANFILES) $(patsubst %.c,%.o, $(SRCS)); ]7 q9 ?* y* ]
复制代码 然后make,scp到开发板执行程序,就可以看到一个hello world窗口出现在之前得桌面上了。
4 a. \; v. C6 O9 a* ?# q 接下来改程序,说实话没用过gtk,不过看了下helloworld得程序可以看懂,所以也百度了一下,就基本做出来了。
; j/ g7 K" Y3 o$ \, g l
! M/ H& l" t' \) {: P0 A0 S
0 ]; i/ G8 i! t4 M- #include <gtk/gtk.h>
n/ i* a# ]7 r2 _0 ~3 s a - #include <stdio.h>& }, V+ E v% ` R+ x" @
- #include <string.h>
* _3 p# t! @+ V7 u0 [
5 w* B; m7 ^+ j" `0 s& V- char buf[50] = "";4 B; y% |( ^) k# O% R- }" g3 ]
- 1 Y9 @9 E8 ?) f7 A; B0 q6 o* `
- void calc(GtkButton *button, gpointer data)
# i( f; Y: g5 ~3 Y - {; j6 z; {: t' u4 w2 Z7 |
- const char *text = gtk_button_get_label(button);5 Y; S7 f0 x, I$ R
9 q6 X/ Y. Y P+ m: v# R- //退个操作; k# ~0 O7 M: e
- if (0 == strcmp(text, "c"))
1 Y9 p% a; ] j( J3 K2 C; c - {1 B! V3 q0 |0 U7 l/ P. s/ M
- buf[strlen(buf) - 1] = 0;$ X% C2 n6 G. I; j( [
- }else{
9 X: Q% A" s) p2 G6 | - & @0 k& A5 T- D
- int a = 0, b = 0;) B$ g' f" w) |/ J( L- |
- char c;: N: h |$ |! k1 Y
- strcat(buf,text);
. I% U- J! q! c1 A( X - $ K% y+ r1 N9 r% i+ l+ a
- if (0 == strcmp("=", text)) {
7 @; |6 Q2 W- f3 [. C4 L
6 d; y! O5 [0 G8 a* a- sscanf(buf, "%d%c%d", &a, &c, &b); O! Z! I! B* O+ H: i
- 0 s2 H2 T+ V& M6 ~
- if ('+' == c) {
& n7 [6 \/ j- _/ c J- _ - sprintf(buf,"%d", a+b);# a3 k3 j* ~8 D5 v
- }
2 b: d1 p, n4 w( l+ P* S- X% Z; i) D9 m- I - else if ('-' == c) {: r2 Q/ q7 E& i& v
- sprintf(buf, "%d", a-b); A+ S4 ~0 x3 M3 X. [: y; Q
- }
, _( ^0 G" M/ @) T/ i& h4 N - else if ('*' == c) {" F) r8 [8 i9 c! ^
- sprintf(buf, "%d", a*b);
7 b* _* b7 E3 z8 O( v" j - }+ Y& x& H4 H1 m+ ?4 X) z/ r/ X
- else if ('/' == c) {
7 q2 \# ^9 D( \, A8 R - sprintf(buf, "%d", a/b);
- M4 C; C+ y5 p- M - }
( H! u$ P' [+ w! X* |+ \ - 6 G2 D" T" F r% R( P5 p& y: t
- }
3 X8 F: \2 A' G8 r: t - }
/ D6 x% r( |- s$ V
4 n$ S, c6 Y, i1 s6 q3 W4 ^8 T- gtk_entry_set_text(GTK_ENTRY(data), buf);
' Y2 R$ E" A K - ; W0 Z# @; _ r% \) [! l
- return;
$ ?; ?% [# F& N - }
! }: c* ]7 E3 Y& ?
" _( D8 h0 v8 V/ V5 K- int main(int argc,char *argv[])" P8 J" R) ?% q- m' y* {# B
- {
& i7 i- e5 u* c: X/ c C% Y - % X% T& E( w7 m5 z* o
- gtk_init(&argc, &argv);+ I8 a! j/ A' E# z: r
- 5 A K2 M! y- n! ^9 U5 x
- - p) K O, e9 _6 w
- GtkWidget *window = gtk_window_new(GTK_WINDOW_TOPLEVEL);
* C2 h6 F, {2 @) R; o& ?. J - gtk_window_set_title (GTK_WINDOW (window), "calc");
7 q X- L* ^4 c; a; k - 7 K0 L5 d& E6 Q# a9 W0 L ^4 E6 [
- //创建一个表格容器5行4列
$ P* z, |3 [- G: g6 K - GtkWidget *table = gtk_table_new(5,4,TRUE);
; F" c+ ^1 Q6 l$ k- l6 c9 N2 d ? - 4 M4 @1 T7 Z+ X& F* |% ^2 f3 @- `! q
- gtk_container_add(GTK_CONTAINER(window), table);, z- l4 I4 ?( Q0 g8 t% B6 J2 ~
- - K( |6 u3 x8 R! o
- //创建一个行编辑* L0 q, C4 A4 | \! C, i
- GtkWidget *entry = gtk_entry_new();( `: g0 S: T& j& ]) D, O
- ' A7 Z, U# e# f% L( G
- gtk_entry_set_text(GTK_ENTRY(entry), "0");
% o( {4 ^7 z4 u3 Q8 V6 M6 P - / t. y0 d& g0 `
- gtk_editable_set_editable(GTK_EDITABLE(entry), FALSE);. j% F5 f( F% z4 u6 h0 |# D3 n% h' E
6 ~% j) s4 V7 j3 ?4 @- //创建多个按钮
2 `$ ^& G( s- j/ Q6 O6 h0 Z0 J - GtkWidget *button0 = gtk_button_new_with_label("0");6 ^4 y% S; o9 p7 k7 V- r3 Y
- GtkWidget *button1 = gtk_button_new_with_label("1");
4 v b5 J2 R. z- J - GtkWidget *button2 = gtk_button_new_with_label("2");; h8 `' Y/ F3 T( L/ I
- GtkWidget *button3 = gtk_button_new_with_label("3");
9 ~1 s w( q1 |- U - GtkWidget *button4 = gtk_button_new_with_label("4");
# x+ D1 u( {2 q! J: b8 M0 w - GtkWidget *button5 = gtk_button_new_with_label("5");- Z. l) N* h6 R* e. K/ Y4 G m
- GtkWidget *button6 = gtk_button_new_with_label("6");
4 h6 _) C. w! o# F - GtkWidget *button7 = gtk_button_new_with_label("7");- V/ m% x I) i" g7 Y
- GtkWidget *button8 = gtk_button_new_with_label("8");2 M) V. L/ q" I5 ]: g3 f% P" c
- GtkWidget *button9 = gtk_button_new_with_label("9");$ ]/ T; _5 ?; e; R; J
$ ]+ \: H5 |% \: P' d- GtkWidget *button_add = gtk_button_new_with_label("+");+ M/ i, H7 f9 B; R1 o( k! {
- GtkWidget *button_minus = gtk_button_new_with_label("-");% d3 ^' ^ n- M( ]! `5 z7 u
- GtkWidget *button_mul = gtk_button_new_with_label("*");( r% f; F. }; ^
- GtkWidget *button_div = gtk_button_new_with_label("/");
' T1 w$ @/ j- C- \/ v9 | - GtkWidget *button_equal = gtk_button_new_with_label("=");
|- @' s+ v" r' B - GtkWidget *button_delete = gtk_button_new_with_label("c");
: M0 z4 P4 y, n- g2 N
% r* R6 z# D3 l# x, m- 6 x8 G- b8 a3 N1 X
- gtk_table_attach_defaults(GTK_TABLE(table), entry, 0, 4, 0, 1);# m2 d7 n( O. Z/ d: P. H
- 7 z* w% a6 W3 F/ c2 {! `. a
- gtk_table_attach_defaults(GTK_TABLE(table), button0, 0, 1, 4, 5);+ p, p- E" s1 t! }9 o* R6 K
- gtk_table_attach_defaults(GTK_TABLE(table), button1, 0, 1, 3, 4);
! k9 `8 z: @; l" J- }) q( w - gtk_table_attach_defaults(GTK_TABLE(table), button2, 1, 2, 3, 4);7 }' l) r7 D1 H( M+ j
- gtk_table_attach_defaults(GTK_TABLE(table), button3, 2, 3, 3, 4);
8 K9 A; E6 L* D - gtk_table_attach_defaults(GTK_TABLE(table), button4, 0, 1, 2, 3);# v/ z2 J% G3 |" J8 Y: `2 F
- gtk_table_attach_defaults(GTK_TABLE(table), button5, 1, 2, 2, 3);
" M$ q" @* B4 Q' P6 j, ^ - gtk_table_attach_defaults(GTK_TABLE(table), button6, 2, 3, 2, 3);7 S8 K" f ]' X0 m4 k/ v* ?
- gtk_table_attach_defaults(GTK_TABLE(table), button7, 0, 1, 1, 2);
. d' ]# b4 O$ {& \- ^6 B - gtk_table_attach_defaults(GTK_TABLE(table), button8, 1, 2, 1, 2);% }& r. S- o& C: `) ^' R4 z# M$ L V& R
- gtk_table_attach_defaults(GTK_TABLE(table), button9, 2, 3, 1, 2);
% N: `$ X$ d& c# r" x% R y+ N
4 M$ \ ^; `; x) l- gtk_table_attach_defaults(GTK_TABLE(table), button_add, 1, 2, 4, 5);
, a- T3 y7 x/ y6 }# I, F - gtk_table_attach_defaults(GTK_TABLE(table), button_minus, 2, 3, 4, 5);
) i0 I9 \5 }& _6 ~ - gtk_table_attach_defaults(GTK_TABLE(table), button_mul , 3, 4, 2, 3);5 G; \, O1 U' ?9 _' q; z2 S }
- gtk_table_attach_defaults(GTK_TABLE(table), button_div, 3, 4, 3, 4);2 n, R- v5 \6 P, X* A% G5 N* N$ z
- gtk_table_attach_defaults(GTK_TABLE(table), button_equal, 3, 4, 4, 5);
( ?' ^/ K; v8 H6 l9 \: J' O G - gtk_table_attach_defaults(GTK_TABLE(table), button_delete, 3, 4, 1, 2);& U0 l' E6 x6 D! p2 Z4 ]" [( t" ?
- - D) k4 o" a) H
- //注册信号函数,calc()3 R5 ]! {$ A3 c! v* c9 D) F# u/ u
- g_signal_connect(button0, "pressed", G_CALLBACK(calc), entry);
+ S, n: Q: G6 `' v" q6 M; U8 f3 m - g_signal_connect(button1, "pressed", G_CALLBACK(calc), entry);0 C% S% W0 g2 D' h) [& k2 z( Q
- g_signal_connect(button2, "pressed", G_CALLBACK(calc), entry);
( M- O- c1 D2 h) B! c% M4 \7 R - g_signal_connect(button3, "pressed", G_CALLBACK(calc), entry);
?1 p3 J P* P9 q7 d$ `, t& @ - g_signal_connect(button4, "pressed", G_CALLBACK(calc), entry);
! f2 }) Y4 E/ o/ A - g_signal_connect(button5, "pressed", G_CALLBACK(calc), entry);$ ]' @2 O2 o. C* T8 C
- g_signal_connect(button6, "pressed", G_CALLBACK(calc), entry);
" h! {: w; p. l9 @7 v! m6 P - g_signal_connect(button7, "pressed", G_CALLBACK(calc), entry);
9 Y3 y% T4 O! z0 C - g_signal_connect(button8, "pressed", G_CALLBACK(calc), entry);. D% l9 x0 U+ [/ S
- g_signal_connect(button9, "pressed", G_CALLBACK(calc), entry);1 H% w3 t+ {$ `4 T; f
- ) Y) z2 @8 X% n; y; a& {: x
- g_signal_connect(button_add, "pressed", G_CALLBACK(calc), entry);
& n" X3 V- W j$ ` - g_signal_connect(button_mul, "pressed", G_CALLBACK(calc), entry);& a$ y+ ~( _$ K( }- H
- g_signal_connect(button_div, "pressed", G_CALLBACK(calc), entry);
/ {$ B' C7 u( [: p9 S - g_signal_connect(button_minus, "pressed", G_CALLBACK(calc), entry);
3 k& B! d% U- _5 `4 W7 _ - g_signal_connect(button_equal, "pressed", G_CALLBACK(calc), entry);& \+ s# O! J: J% c, @. P u }7 g
- g_signal_connect(button_delete, "pressed", G_CALLBACK(calc), entry);
" ~: a% B- l, x* Z N7 j - : t) H# E$ a! b; \4 ]
- 7 ]9 O. A0 K0 z8 n* i
- gtk_widget_show_all(window);
: \4 i5 \/ U% O! g, s1 `6 n0 v. ]1 i
2 n3 \( ?+ d, W, A8 F- //主事件循环
: B9 |- H: J4 g% s& K, I- d - gtk_main();$ |6 J# v& s8 t4 ?; s+ t5 O8 J
- / N# Q) Q8 a6 u9 N4 c
- return 0;9 r6 q- c* n7 X; K
- }
( H+ M/ X; u0 R" g
复制代码 以上程序,编译运行后,就可以有以下得效果
9 P) M( d$ s6 M7 k8 b' F. ^
! }4 x0 h+ f9 E) r% w, Q+ k 操作和UI都是比较简单得,就不演示过程了,系统得触摸驱动也是做好的,gtk只管做应用就好了。操作也算流畅,毕竟也没涉及到复杂的图表渲染。 搞到这里,发现其实不复杂得GUI程序用这套现成的框架倒也是挺方便。Linux系统下其实资源很丰富,软件开发方式也很多选择,所以不多做逗留了。这款开发板还有一大特点就是可以按照以往STM32单片机得方式进行使用,所以后面感受下1GHz的单片机开发方式。 |