多线程问题,好晕!!!只有这么多分数了(63分)

  • 主题发起人 主题发起人 liwowo
  • 开始时间 开始时间
L

liwowo

Unregistered / Unconfirmed
GUEST, unregistred user!
我作了一个多线程的图片浏览的程序
文件分三个单元 主窗体,线程, 读文件的一个类(就是多个Tliststring存放文件名的相关信息)
在主窗体上我使用了一个listview, 一个imagelist中
在目录改变时,我将图片一个个的加载到imagelist中,然后再将它放到listview中显示出来
但我操作的时候,如果反复点击几个有图片的文件夹 ,就会发生
project project1.exe raised exception EOutOfResources with message ‘存储空间不足,无法处理此命令。’ 过程。 Process stopped use step or run to continue.
这是怎么回事,我一直怀疑是不是我的程序中在更新目录时没有将相应的东东清空,但我在改变目录时,一个个清空了,怎么还会出现存储空间不足?
 
把代码贴出来吧.
 
兄弟你邮箱多少 我把代友发到你邮箱吧 我用delphi 7调试的
 
这是线程
unit Unit_readImage;
interface
uses
Classes;
type
TreadImage = class(TThread)
private
{ Private declarations }
protected
procedure Execute;
override;
end;

implementation
uses unit1;
{ Important: Methods and properties of objects in visual components can only be
used in a method called using Synchronize, for example,
Synchronize(UpdateCaption);
and UpdateCaption could look like,
procedure readImage.UpdateCaption;
begin
Form1.Caption := 'Updated in a thread';
end;
}
{ readImage }
procedure TreadImage.Execute;
begin
try
form1.ShellTreeView1.Enabled:=false;
Form1.ShellTreeView1Change2(form1.shelltreeview1.path);
form1.ShellTreeView1.Enabled:=true;
finally
form1.ShellTreeView1.Enabled:=true;
// ProgressBar1.Visible:=false;
// listview2.Items.EndUpdate;
end;
freeonterminate:=true;
{ Place thread code here }
end;

end.
 
主窗体
unit Unit1;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, ExtCtrls, ComCtrls, ShellCtrls, ImgList, commctrl, jpeg,imagefilelist,filectrl,Unit_readImage;
type
TForm1 = class(TForm)
ScrollBox1: TScrollBox;
ShellTreeView1: TShellTreeView;
Splitter1: TSplitter;
Panel1: TPanel;
Splitter2: TSplitter;
Panel2: TPanel;
Image1: TImage;
ImageList1: TImageList;
ListView1: TListView;
StatusBar1: TStatusBar;
procedure FormCreate(Sender: TObject);
procedure ShellTreeView1Change(Sender: TObject;
Node: TTreeNode);
procedure FormDestroy(Sender: TObject);
private
PreviewBmp,originalbmp,Thumbbmp:Tbitmap;
PreviewJpg,Thumbjpg:Tjpegimage;
IsRefreshImageFinshi:boolean;
{ Private declarations }
public
progressbar_one:Tprogressbar;
procedure ShellTreeView1Change2(dir:string);
procedure RefreshImage;
{ Public declarations}
end;

const
RaisedPanel=1;
LoweredPanel=2;
var
Form1: TForm1;
imagefilelist:Timagefilelist;
readImage:TreadImage;

implementation
{$R *.dfm}
//在canvas上画一个Panel
procedure DrawPanel(canvas:TCanvas;Left,Top,Width,Height:integer;PanelType:integer);
var
Right,Bottom:integer;
LeftTopColor,RightBottomColor:TColor;
begin
//凸起的panel
if PanelType=RaisedPanel then
begin
LeftTopColor:=clwhite;
RightBottomColor:=clgray;
end
else
//凹下去的panel
begin

LeftTopColor:=clgray;
RightBottomColor:=clwhite;
end;
Right:=Left+width;
Bottom:=Top+Height;
Canvas.Pen.Width:=1;
Canvas.Pen.Color:=LeftTopColor;
Canvas.MoveTo(Right,Top);
Canvas.lineTo(Left,Top);
Canvas.LineTo(Left,bottom);
Canvas.Pen.Color:=RightBottomColor;
Canvas.lineTo(Right,Bottom);
Canvas.lineTo(Right,Top);
end;

//转换jpg到bmp
procedure JpgToBmp(const JpgFileName:string;AJpg:TJpegImage;Abmp:Tbitmap);
begin
try
AJpg.LoadFromFile(JpgFileName);
Abmp.Assign(AJpg);
finally
end;
end;

//仅从扩展名上来判断是否是jpg格式的文件
function IsJpgFile(const FileName:string):boolean;
begin
result:=(LowerCase( ExtractFileExt(FileName))='.jpg') or (LowerCase( ExtractFileExt(FileName))='.jpeg');
end;

procedure TForm1.FormCreate(Sender: TObject);
begin

listview_seticonspacing(listview1.Handle,90,120);
//设置缩略图的间距
originalbmp:=Tbitmap.Create;
Thumbjpg:=Tjpegimage.Create;
previewbmp:=Tbitmap.Create;
previewjpg:=Tjpegimage.Create;
Thumbbmp:=Tbitmap.Create;
THumbbmp.Height:=80;
Thumbbmp.Width:=80;
Thumbbmp.PixelFormat:=pf24bit;
imagelist1.Height:=80;
imagelist1.Width:=80;
listview1.LargeImages:=imagelist1;
listview1.ViewStyle:=vsicon;
imagefilelist:=Timagefilelist.Create;
imagefilelist.Clear;
IsRefreshImageFinshi:=true;

progressbar_one:=Tprogressbar.Create(self);
progressbar_one.Parent:=statusbar1;
progressbar_one.Width:=200;
progressbar_one.Height:=statusbar1.Height-4;
progressbar_one.Left:=statusbar1.Width-progressbar_one.Width;
progressbar_one.Top:=2;

end;

procedure TForm1.ShellTreeView1Change(Sender: TObject;
Node: TTreeNode);
begin
readImage:=Treadimage.Create(false);

end;

procedure TForm1.ShellTreeView1Change2(dir:string);
begin
if not IsRefreshImageFinshi then
exit;
if not (directoryexists(dir)) then
exit;
if dir[length(dir)]='/' then
delete(dir,length(dir),1);
imagefilelist.Clear;
imagefilelist.ChangeDir(dir);
statusbar1.Panels[0].Text:='当前文件夹共有图片:'+inttostr(imagefilelist.GetFileCount)+'张';
screen.Cursor:=crHourGlass;
self.Enabled:=false;
RefreshImage;
self.Enabled:=true;
screen.Cursor:=crdefault;
end;

procedure TForm1.RefreshImage;
var
i:integer;
ImageFileName:string;
ThumbBmpLeft:integer;
ThumbBmpTop:integer;
ThumbBmpHeight:integer;
ThumbBmpWidth:integer;


IsErrorImage:boolean;
begin

screen.Cursor:=crHourGlass;
ProgressBar_one.Max:=ImageFileList.GetFileCount;
ProgressBar_one.Visible:=true;

listview1.Clear;
imagelist1.Clear;
try
listview1.Items.begin
Update;
for i:=0 to ImageFileList.GetFileCount-1do
begin
ImageFileList.SetIndex(i);
ImageFileName:=ImageFileList.GetCurFullFileName;

if IsJpgFile(ImageFileName) then
try
jpgtobmp(ImageFileList.GetCurFullFileName,ThumbJpg,OriginalBmp);
if OriginalBmp.Height>=OriginalBmp.Width then
begin
ThumbBmpWidth:=64*OriginalBmp.Width div OriginalBmp.Height;
ThumbBmpLeft:=(64-ThumbBmpWidth ) div 2;
ThumbBmp.Canvas.Brush.Color :=clBtnFace;
ThumbBmp.Canvas.FillRect(ThumbBmp.Canvas.ClipRect);
DrawPanel(ThumbBmp.Canvas,0,0,79,79,RaisedPanel);
DrawPanel(ThumbBmp.Canvas,7+ThumbBmpLeft,7,ThumbBmpWidth+1,64,LoweredPanel);
ThumbBmp.Canvas.StretchDraw(Rect(8+ThumbBmpLeft,8,8+ThumbBmpLeft+ThumbBmpWidth,71),OriginalBmp);
imagelist1.Add(ThumbBmp,nil);
end
else
begin
ThumbBmpHeight:=64*OriginalBmp.Height div OriginalBmp.Width;
ThumbBmpTop:=(64-ThumbBmpHeight ) div 2;
ThumbBmp.Canvas.Brush.Color :=clBtnFace;
ThumbBmp.Canvas.FillRect(ThumbBmp.Canvas.ClipRect);
DrawPanel(ThumbBmp.Canvas,0,0,79,79,RaisedPanel);
DrawPanel(ThumbBmp.Canvas,7,7+ThumbBmpTop,64,ThumbBmpHeight+1,LoweredPanel);
ThumbBmp.Canvas.StretchDraw(Rect(8,8+ThumbBmpTop,71,8+ThumbBmpTop+ThumbBmpHeight),OriginalBmp);
imagelist1.Add(ThumbBmp,nil);
end;

with ListView1.Items.Add do
begin
ImageIndex:=imagelist1.Count-1;
caption:=ImageFileList.GetCurFileName;
end;

except
MessageDlg('读取文件:'+ImageFileList.GetCurFullFileName+'时发生错误!'+#13
+'该文件不是标准格式的文件,或者该文件已经被损坏!',mtError,[mbYes],0);
IsErrorImage:=true;
end
else
try
OriginalBmp.LoadFromFile(ImageFileList.GetCurFullFileName);
if OriginalBmp.Height>=OriginalBmp.Width then
begin
ThumbBmpWidth:=64*OriginalBmp.Width div OriginalBmp.Height;
ThumbBmpLeft:=(64-ThumbBmpWidth ) div 2;
ThumbBmp.Canvas.Brush.Color :=clBtnFace;
ThumbBmp.Canvas.FillRect(ThumbBmp.Canvas.ClipRect);
DrawPanel(ThumbBmp.Canvas,0,0,79,79,RaisedPanel);
DrawPanel(ThumbBmp.Canvas,7+ThumbBmpLeft,7,ThumbBmpWidth+1,64,LoweredPanel);
ThumbBmp.Canvas.StretchDraw(Rect(8+ThumbBmpLeft,8,8+ThumbBmpLeft+ThumbBmpWidth,71),OriginalBmp);
imagelist1.Add(ThumbBmp,nil);
end
else
begin
ThumbBmpHeight:=64*OriginalBmp.Height div OriginalBmp.Width;
ThumbBmpTop:=(64-ThumbBmpHeight ) div 2;
ThumbBmp.Canvas.Brush.Color :=clBtnFace;
ThumbBmp.Canvas.FillRect(ThumbBmp.Canvas.ClipRect);
DrawPanel(ThumbBmp.Canvas,0,0,79,79,RaisedPanel);
DrawPanel(ThumbBmp.Canvas,7,7+ThumbBmpTop,64,ThumbBmpHeight+1,LoweredPanel);
ThumbBmp.Canvas.StretchDraw(Rect(8,8+ThumbBmpTop,71,8+ThumbBmpTop+ThumbBmpHeight),OriginalBmp);
imagelist1.Add(ThumbBmp,nil);
end;

with ListView1.Items.Add do
begin
ImageIndex:=imagelist1.Count-1;
caption:=ImageFileList.GetCurFileName;
end;

except
MessageDlg('读取文件:'+ImageFileList.GetCurFullFileName+'时发生错误!'+#13
+'该文件不是标准格式的文件,或者该文件已经被损坏!',mtError,[mbYes],0);
IsErrorImage:=true;
end;
ProgressBar_one.Position:=i;
application.ProcessMessages;
end;
finally
listview1.Items.EndUpdate;
ProgressBar_one.Visible:=false;
end;
screen.Cursor:= crDefault;
end;

procedure TForm1.FormDestroy(Sender: TObject);
begin
PreviewBmp.Free;
originalbmp.free;
Thumbbmp.Free ;
PreviewJpg.Free;
Thumbjpg.free;

imagefilelist.Free;
end;

end.

 
//image操作的类
unit imagefilelist;
interface
uses shellctrls,Classes,sysUtils;
type
TImageFileList=class
private
FStrListFile:TStringList;
FIndex:integer;
{ Private declarations }
public
OtherFileList:Tstringlist;
//添加一个文件
procedure Add(FullFileName:string);
//清空文件列表
procedure Clear;
//删除一个文件
procedure Delete(Index:integer);
//当目录改变时,调用此过程会把该目录下所有图片文件
//添加到文件列表中
procedure ChangeDir(dir:string);
//返回文件数目
function GetFileCount:integer;
//设置索引
procedure SetIndex(AIndex:integer);
//返回文件索引
function GetIndex:integer;
//返回当前完整文件名
function GetCurFullFileName:string;
//返回当前文件名
function GetCurFileName:string;
//返回下一个文件的文件名
function GetNextFileName:string;
//返回上一个文件的文件名
function GetPreFileName:string;
procedure CopyStrListFile(SrcFileNameList:TStringList);
constructor Create;
destructor Destroy;
override;
{ Public declarations }
end;

var
OtherFileList:Tstringlist;
implementation

procedure TImageFileList.Add(FullFileName: string);
//添加一个文件
begin
FStrListFile.Add(FullFileName);
end;

procedure TImageFileList.Clear;
//清空文件列表
begin
FStrListFile.Clear;
Findex:=-1;
end;

procedure TImageFileList.Delete(Index: integer);
//删除一个文件
begin
FStrListFile.Delete(Index);
SetIndex(Index-1);
//
end;

procedure TImageFileList.ChangeDir(dir: string);
var
SearchRec : TSearchRec;
Attr : integer;
Found : integer;
ExtFileName:string;
temstr:string;
begin
clear;
OtherFileList.Clear;
temstr:=dir+'/*.*';
Attr := faAnyFile;
Found := FindFirst(temstr, Attr, SearchRec);
while Found = 0do
begin
// SearchRec.Attr
ExtFileName:=LowerCase(ExtractFileExt(SearchRec.Name));
if (ExtFileName='.bmp') or (ExtFileName='.jpg') or ((ExtFileName='.jpeg')) then
Add(dir+'/'+SearchRec.Name)
else
if SearchRec.Attr=faDirectory then
begin
if not ( (SearchRec.Name[length(SearchRec.Name)]='.') and (SearchRec.Name[length(SearchRec.Name)-1]<>'.' ) ) then
OtherFileList.Add('0#'+dir+'/'+SearchRec.Name)
end
else
if (ExtFileName='.txt') then
OtherFileList.Add('1#'+dir+'/'+SearchRec.Name)
else
if (ExtFileName='.htm') or (ExtFileName='.html') then
OtherFileList.Add('2#'+dir+'/'+SearchRec.Name)
else
if (ExtFileName='.pas') then
OtherFileList.Add('3#'+dir+'/'+SearchRec.Name)
else
if (ExtFileName='.exe') then
OtherFileList.Add('4#'+dir+'/'+SearchRec.Name)
else
if (ExtFileName='.dll') then
OtherFileList.Add('5#'+dir+'/'+SearchRec.Name)
else
if (ExtFileName='.ssp') then
OtherFileList.Add('6#'+dir+'/'+SearchRec.Name);

Found := FindNext(SearchRec);
end;
FindClose(SearchRec);
end;

function TImageFileList.GetFileCount: integer;
begin
result:=FStrListFile.Count;
end;

procedure TImageFileList.SetIndex(AIndex: integer);
begin
FIndex:=AIndex;
end;

function TImageFileList.GetIndex: integer;
begin
result:=FIndex;
end;

function TImageFileList.GetCurFullFileName: string;
begin
result:=FStrListFile.Strings[Findex];
end;

function TImageFileList.GetCurFileName: string;
begin
result:=ExtractFileName(FStrListFile.Strings[Findex]);
end;

function TImageFileList.GetNextFileName: string;
begin
if Findex=FStrListFile.Count-1 then
Findex:=0
else
inc(Findex);
result:=FStrListFile.Strings[Findex];
end;

function TImageFileList.GetPreFileName: string;
begin
if Findex=0 then
Findex:=FStrListFile.Count-1
else
dec(Findex);
result:=FStrListFile.Strings[Findex];
end;

procedure TImageFileList.CopyStrListFile(SrcFileNameList:TStringList);
begin
FStrListFile.Assign(SrcFileNameList);
end;

constructor TImageFileList.Create;
begin
FStrListFile:=TStringList.Create;
OtherFileList:=Tstringlist.create;
Findex:=-1;
end;

destructor TImageFileList.Destroy;
begin
FStrListFile.Free;
otherfilelist.Free;
inherited;
end;

end.
 
看半天也没看出什么东西只好帮你顶一下!
 
后退
顶部