我一直在Delphi XE3上申请.我试图将值从数据库显示到放置在窗体上的TAdvStringGrid组件.我正在使用数据集在TAdvSTringGRid上显示结果(代码如下).除数据库中的图像外,所有其他值都显示完美.在预期显示图像的位置,它显示垃圾字符.如何在TAdvStringGrid上从DataBase完美地显示图像.
sqlConnection1: TsqlConnection;
sqlMonitor1: TsqlMonitor;
DataSource1: TDataSource;
ADOConnection1: TADOConnection;
ClientDataSet1: TClientDataSet;
AdvStringGrid1: TAdvStringGrid;
procedure Button1Click(Sender: TObject);
procedure ShowSelectResults(results: TDataSet; sg: TAdvSTringGrid);
procedure FormCreate(Sender: TObject);
procedure TForm2.FormCreate(Sender: TObject);
var
results: TDataSet;
begin
sqlConnection1.Params.Add('Database=E:\playdb.s3db');
try
sqlConnection1.Connected := true;
sqlMonitor1.Active := True;
sqlConnection1.Execute('Select * from plays',nil,results);
except
on E: EDatabaseError do
ShowMessage('Exception raised with message' + E.Message);
end;
ShowSelectResults(results,advstringgrid1);
end;
请致电下面的ShowSelectResult
procedure TForm2.ShowSelectResults(results: TDataSet; sg: TAdvStringGrid);
var
names: TStringList;
i,j,k,rc: Integer;
resultsfield: variant;
Field: TblobField;
Stream: TStream;
Jpg: TJPEGImage;
Picture: TPicture;
begin
if not results.IsEmpty then
//Prints Data in the TAdvStringGrid
results.First;
j := 1;
while not results.EOF do
begin
if (j>sg.rowcount) then
sg.rowcount := sg.rowcount + 1;
for i := 0 to results.fields.Count - 1 do
begin
if i=0 then
else if i = 4 then
//Here I want to display image from db
Field := TBlobField(results.FieldByName(names[i]).Asstring);
Stream := results.CreateBlobStream(Field,bmRead);
sg.CreatePicture(i,true,ShrinkWithAspectRatio,20,haCenter,vaAboveText).Picture
else
sg.cells[i,j] := results.FieldByName(names[i]).Asstring;
end;
results.Next;
inc(j);
end;
end;
如果在sg.CreatePicture中的上述代码中的i = 4循环(下面给出了CreatePicture过程的格式),问题出在else处,我想在该特定列中显示图像.
在TAdvStringGrid的手册中,他们提到了以下网格单元图像显示方法
Grid.CreatePicture(2,3,True,Shrink,haLeft,vaTop).LoadFromFile(‘TST.JPG’); procedure AddPicture(ACol,ARow: Integer;APicture:TPicture;transparent: Boolean; stretchmode:TStretchMode; padding: Integer; hal:TCellHalign; val:TCellValign); function GetPicture(ACol,ARow: Integer): TPicture; Grid.CreateFilePicture(2,vaTop).Filename := ‘TST.JPG’;
但是没有提到如何将它与DataSet一起使用.我正在搞乱TAdvStringGRid的CreatePicture过程,而不是使用DataSet来解决它.
最新发展
最后,我在Bummi等学者的帮助下找到方法将JPEG图像保存到内存流中,然后显示相同的内容.
我的最新代码如下
procedure TForm2.ShowSelectResults(results: TDataSet; sg: TAdvStringGrid);
var
names: TStringList;
Field: TblobField;
//Stream: TStream;
Stream: TMemoryStream;
//blobType := TBlobType;
Jpg: TJPEGImage;
Picture: TPicture;
Image: timage;
Graphic: TGraphic;
Begin
//k := results.FieldCount;
//sg.Rowcount := rc;
results.First;
j := 1;
while not results.EOF do
begin
if (j>sg.rowcount) then
sg.rowcount := sg.rowcount + 1;
for i := 0 to results.fields.Count - 1 do
begin
if i=0 then
else if i = 4 then // Column 5 for Image
begin
try
if ((results.FieldByName(names[i]).Asstring) <> '') then
Begin
Stream := TMemoryStream.Create;
Image := timage.Create(Self);
Jpg := TJPEGImage.Create;
Picture := TPicture.Create;
Field := TBlobField(results.FieldByName('image'));
Stream := results.CreateBlobStream(Field,bmReadWrite);
//Field.SavetoStream(Stream);
Stream.Position := 0;
Jpg.LoadFromStream(Stream);
Picture.Assign(Jpg);
//Jpg.LoadFromFile('C:\Sample Pictures\Cabo.jpg');
//Picture.Assign(Jpg);
sg.AddPicture(i,Picture,vaTop);
end;
finally
Jpg.Free;
Stream.Free;
end;
end
else
//Prints data in other columns
sg.cells[i.j] := results.FieldByName(names[i]).Asstring;
inc(j);
end;
end;
现在,根据我在Jpg.LoadFromStream(Stream)的行中,它正面临一些内存问题;
这是错误代码JPEG错误#53,我开始知道上面这样的错误代码只有当你试图通过内存流访问的图像被破坏时才会显示但是我确保图像没有被破坏并且在提取的其他软件的帮助下正确显示从类似的数据库.我也在数据库中更新了图像.仍然为什么我得到JPEG错误#53.问题主要在Jpg.LoadFromStream(Stream)
注意带有注释的代码
Jpg.LoadFromFile('C:\Sample Pictures\Cabo.jpg');
Picture.Assign(Jpg);
sg.AddPicture(i,vaTop);
当它从静态文件中提取时,它可以完美地工作.问题仅出在MemoryStream上.如何纠正这个错误?
解决方法
CreateBlobStream正在创建一个TStream对象,而不是TMemoryStream.
由于您不想将JPG写入数据库,因此应使用bmRead而不是bmReadWrite.
我不习惯sqlite,但你必须确保使用合适的二进制日期类型(BLOB).
由于您不想将JPG写入数据库,因此应使用bmRead而不是bmReadWrite.
我不习惯sqlite,但你必须确保使用合适的二进制日期类型(BLOB).
JPG := TJpegImage.Create;
Picture:= TPicture.Create;
try
st := results.CreateBlobStream(TBlobField(results.FieldByName('image')),bmRead);
try
JPG.LoadFromStream(st);
Picture.Assign(JPG);
sg.AddPicture(i,vaTop);
finally
st.Free;
end;
finally
JPG.Free;
Picture.Free;
end;
为了确保存储的图像真的是JPG,您应该编写JPG以进行测试,例如:
var
ms: TMemoryStream;
begin
ads.Open;
ads.Append;
ms := TMemoryStream.Create;
try
Image1.Picture.Graphic.SavetoStream(ms); // make sure having loaded a JPG
ms.Position := 0;
TBlobField(ads.FieldByName('image')).LoadFromStream(ms);
finally
ms.Free;
end;
ads.Post;
end;