导航:
论坛 -> DELPHI技术
斑竹:liumazi,sephil
作者:
2017/4/22 1:46:23
标题:
使用匿名线程CreateAnonymousThread方法卡死的问题
浏览:1978
加入我的收藏
楼主:
使用匿名线程加载一个50M的大图片,希望程序能不卡死,为什么匿名线程明明是成功的,为什么还卡呢?要怎么解决? procedure TForm1.FormClick(Sender: TObject); begin TThread.CreateAnonymousThread(procedure begin TThread.Synchronize(nil, procedure begin image1.Picture.LoadFromFile('C:\Users\Administrator\Desktop\大图片\735296906189813293.jpg'); end); end).Start; end;
----------------------------------------------
-
作者:
bdl1 (bdl1)
▲▲▲▲▲
-
普通会员
2017/4/22 8:08:47
1楼:
这跟不用线程有什么区别?
----------------------------------------------
-我的博客
作者:
a5824 (Return)
★☆☆☆☆
-
普通会员
2017/4/22 8:27:18
2楼:
先读到流里,再加载吧,你这个没有区别的,或者看看你的image1有没有别的地方使用,如果没有,就不要Synchronize了
----------------------------------------------
-
作者:
2017/4/22 13:16:44
3楼:
Synchronize 改成 Queue 试试
----------------------------------------------
http://mcool.appinn.me/
作者:
2017/4/22 22:00:01
4楼:
都试了,还是卡的死,高手指点下
----------------------------------------------
-
作者:
2017/4/23 9:36:55
5楼:
匿名线程有Bug,我也碰到过的 能不用就不用
----------------------------------------------
樵夫的大马甲
作者:
2017/4/23 10:44:29
6楼:
樵总,有啥bug,举个例?
----------------------------------------------
-
作者:
2017/4/23 18:27:51
7楼:
楼主已经举了
----------------------------------------------
樵夫的大马甲
作者:
2017/4/23 18:36:18
8楼:
1:线程中,不要写和ui相关的代码。 2:你既然都直接同步了,还要线程做什么?
----------------------------------------------
--
作者:
2017/4/24 13:22:07
9楼:
是image1把程序卡死了吧
----------------------------------------------
-
作者:
pame (鱼子酱)
▲▲▲▲△
-
普通会员
2017/4/24 13:38:49
10楼:
你这里开了一个线程,然后线程里同步回主线程,然后在主线程操作。这就跟不用匿名线程一样了。 但是不管怎么说对UI的操作肯定是要在主线程里的。 这里应该先把图片数据读到内存里然后 Timage在 Synchroniz里从内存里画到界面上。 或者直接在线程里开个bitmap加载图片(这个还没到界面上所以是线程安全的),然后在Synchroniz里弄到界面上。 另外@jopher3 显然这个情况并不是匿名线程的bug。
----------------------------------------------
-我的网站: http://vbox.vlabpro.com/ 几个中学生用Delphi 制作的软件平台(现在已经上大学了...岁月不饶人啊QAQ)
作者:
pame (鱼子酱)
▲▲▲▲△
-
普通会员
2017/4/24 13:42:17
11楼:
哦对了3楼的方法也是不对的,Synchroniz 和 Queue 是一样的,都是在线程里传回主线程运行,只是顺序和方式不同 http://docwiki.embarcadero.com/Libraries/Berlin/en/System.Classes.TThread.Queue “Asynchronously executes a method call within the main thread. Queue causes the call specified by AMethod to be executed using the main thread, thereby avoiding multi-thread conflicts.”
----------------------------------------------
-我的网站: http://vbox.vlabpro.com/ 几个中学生用Delphi 制作的软件平台(现在已经上大学了...岁月不饶人啊QAQ)
作者:
2017/4/24 13:44:33
12楼:
其实,我也爱写楼主这样的代码,省了一个 TIMER 。
----------------------------------------------
(C)(P)Flying Wang
作者:
2017/4/24 15:12:05
13楼:
顶10楼
----------------------------------------------
http://mcool.appinn.me/
作者:
a5824 (Return)
★☆☆☆☆
-
普通会员
2017/4/24 15:17:58
13楼:
var jpg: TJPEGImage; begin TThread.CreateAnonymousThread(procedure begin jpg := TJPEGImage.Create; jpg.LoadFromFile('122.jpg'); img1.Picture.Bitmap.Assign(jpg); jpg.Free; end).Start; end; 就这样就可以了,别整那么多华丽花哨的
----------------------------------------------
-
作者:
pame (鱼子酱)
▲▲▲▲△
-
普通会员
2017/4/24 15:38:42
14楼:
@a5824 img1.Picture.Bitmap.Assign(jpg); 这步应该在 Synchroniz 里,在非主线程里操作UI是危险的。
----------------------------------------------
-我的网站: http://vbox.vlabpro.com/ 几个中学生用Delphi 制作的软件平台(现在已经上大学了...岁月不饶人啊QAQ)
作者:
2017/4/24 15:45:48
15楼:
之前一个同事写的这种异步调用也是卡死,发现是因为Synchroniz是在主线程执行,而他主线程又有等待,两边卡住了。 看看你有没有类似的代码干扰
----------------------------------------------
武稀松http://www.raysoftware.cn
作者:
a5824 (Return)
★☆☆☆☆
-
普通会员
2017/4/24 15:59:58
16楼:
var jpg: TJPEGImage; bmp:Tbitmap; begin TThread.CreateAnonymousThread(procedure begin jpg := TJPEGImage.Create; jpg.LoadFromFile('122.jpg'); bmp:=Tbitmap.create; bmp.assign(jpg); TThread.Synchronize ( nil, procedure begin img1.Picture.Bitmap.Assign(bmp); end ); bmp.Free; jpg.Free; end).Start; end; 那就这样,如果image有操作,就这样同步,数据加载完,给image得了
----------------------------------------------
-
作者:
2017/4/24 17:18:11
17楼:
@武稀松大侠 关于安卓音乐播放器有什么建议?mcool 基于bass 库开发,按下home 键后,播放会卡顿,有什么解决方法?源码在这里 https://sourceforge.net/projects/mcool/
此帖子包含附件: 大小: 8.8K
----------------------------------------------
http://mcool.appinn.me/
作者:
2017/4/24 17:51:40
18楼:
我用第三方播放器,播放如果返回到桌面,会停一下。感觉是切换播放方式。 因为,有时候,播放的位置,也差了不到2秒。
----------------------------------------------
(C)(P)Flying Wang
作者:
2017/4/24 18:49:51
19楼:
@Flying Wang 我有个想法,基于你的 fmx QQ 群足够牛逼,能否利用大家的力量,把mcool 搞成跨全平台?现在我真是力不从心了
----------------------------------------------
http://mcool.appinn.me/
作者:
2017/4/24 19:12:42
20楼:
@diystar 是Android的APP吗,我没看你的代码。如果是Activity被切换到后台,应该是保存状态。想要一直不卡顿的播放,至少切换到后台应该是用服务来播放。 因为没读你的代码,所以不知道你的APP被切换到的后台是还用主线程播放还是用服务播放了。
----------------------------------------------
武稀松http://www.raysoftware.cn
作者:
2017/4/24 19:18:37
21楼:
原来是需要用服务来播放,这个对我来说复杂了点..
----------------------------------------------
http://mcool.appinn.me/
作者:
2017/4/24 21:30:43
22楼:
@武大侠 记得樊一鹏前辈曾经是你的同事,你知道他的近况么?airplay可是相当牛逼的啊..桌面版是他独力开发的么?据说他已放弃airplay,到顺德发展去了?
----------------------------------------------
http://mcool.appinn.me/
作者:
2017/4/25 17:46:41
23楼:
@diystar 刚刚回了一大段说我是违法,没发出去。 总之樊一鹏非常厉害,AirPlay是他一人之力的作品。他跟大家很少联系,据说是做木器去了,很可惜。
----------------------------------------------
武稀松http://www.raysoftware.cn
作者:
2017/4/25 18:19:17
24楼:
AirPlay 是什么?搜了,但是没明白啊。
----------------------------------------------
只有偏执狂才能生存!
作者:
2017/4/25 21:51:31
25楼:
是windows下的音乐播放器,你搜windows airplay就知道了
----------------------------------------------
http://mcool.appinn.me/
作者:
hexi (Hexi)
★☆☆☆☆
-
盒子活跃会员
2017/4/27 10:50:36
26楼:
TThread.Synchronize是同步到主线程执行的。如果这个过程执行时间太长,界面就会卡死。 16楼的方法是可行的。 但是如果图片太大 TThread.Synchronize ( nil, procedure begin img1.Picture.Bitmap.Assign(bmp); end ); 都要卡顿界面的话, 建议将img1分解成n*n的图片矩阵可用TGridLayout,将原来的大图片切割成小的。 for i:=0 to n-1 do begin for j:=0 to n-1 do begin TThread.Synchronize ( nil, procedure begin img[i][j].Picture.Bitmap.Canvas.BrushCopy(...); end ; Sleep(1); end; end;
----------------------------------------------
-
作者:
akay (akay)
★☆☆☆☆
-
普通会员
2017/4/27 13:43:04
27楼:
学习了,谢谢各位的讨论。
----------------------------------------------
-