Can you save a small bmp to an ini file?

Can you save a small bmp to an ini file?

Post by Harold Hol » Thu, 07 Oct 2004 01:15:17


I was wondering if it was possible to read/write small (32x32) icon bitmaps
to and from an INI file? I've poked around a bit and didn't see anything but
I thought I'd check here.
--
Best regards,
Harold Holmes
 
 
 

Can you save a small bmp to an ini file?

Post by Scott Pric » Thu, 07 Oct 2004 01:20:56

TCustomIniFile.WriteBinaryStream(const Section, Name: string; Value:
TStream);

You could use this to output some data, but I am not sure how much you
can write out. I think INI support has a fixed char line-length issue,
but my memory is a little vague on writing binary data to it. Only
ever used it to write out small records/structs.

Hope that helps.


Regards,

Scott :)

 
 
 

Can you save a small bmp to an ini file?

Post by Gary Willi » Thu, 07 Oct 2004 03:44:39


bitmaps
but

Obviously there is no reason this cannot be done, the real question is
whether there is a way to do it without writing new code. Unfortunately I
doubt a procedure already exists to do this.

I imagine the best way to do this would be to write a generic
stream-to-string converter, which outputs hex data, then break the string
into chunks of reasonable length and create a numbered key in the INI file
for each chunk. Also be sure to persist the number of key/value pairs, so
the reading mechanism will know when to stop.

I'd be willing to implement something like this tonight, just for the
novelty of it. It would only take a few minutes.

-Gary
 
 
 

Can you save a small bmp to an ini file?

Post by Nils Haec » Thu, 07 Oct 2004 05:38:26

If you would have the possibility to change from INI to XML, then check out
our XmlDocuments component (one unit to add to your "uses" clause).

It would go like this:

procedure AddBitmapToXml(const Filename: string; ABitmap: TBitmap);
Doc: TsdXmlDocument;
S: TStringStream;
begin
Doc := TsdXmlDocument.CreateName('Root');
S := TStringStream.Create('');
ABitmap.SaveToStream(S);
with Doc.Root.NodeNew('Bitmap') do
BinaryString := S.DataString;
S.Free;
Doc.SaveToFile(Filename);
Doc.Free;
end;

It puts the binary data in the form of BASE64 encoded data in the XML file.

Other tasks for which one normally uses INI can also be performed with
XmlDocuments, e.g.:

with ADoc.Root.NodeNew('MyObject') do begin
WriteString('Name', MyObject.Name);
WriteInteger('ID', MyObject.ID);
WriteBool('IsPerson', MyObject.IsPerson);
WriteFont('Font', MyObject.Font);
..etcetera
end;

It has the added advantage that XML has infinite levels instead of the usual
two in INI (section and items), so you can also easily store lists and
nested objects.

More info here:
http://www.yqcomputer.com/

Kind regards,

Nils Haeck
www.simdesign.nl





bitmaps
but
 
 
 

Can you save a small bmp to an ini file?

Post by Gary Willi » Thu, 07 Oct 2004 14:12:44

This may not be optimized or robust, but it works.

-Gary


uses
INIFiles, Math;

procedure WriteStreamToINIFile(const Stream: TStream;
const INIFile: TINIFile;
const Section: String);
const
MaxCharsPerKey = 64;
var
ChunkCount: Integer;
ChunkIndex: Integer;
ByteIndex: Integer;
S: String;
B: Byte;
begin
Assert(not(Odd(MaxCharsPerKey)));
ChunkCount := Ceil(Stream.Size / (MaxCharsPerKey div 2));
INIFile.WriteInteger(Section, 'ChunkCount', ChunkCount);

Stream.Position := 0;
for ChunkIndex := 1 to ChunkCount do
begin
S := '';
for ByteIndex := 1 to Min(MaxCharsPerKey div 2, Stream.Size -
Stream.Position) do
begin
Stream.Read(B, SizeOf(B));
S := S + IntToHex(B, 2);
end;

INIFile.WriteString(Section, IntToStr(ChunkIndex), S);
end;
end;

procedure ReadStreamFromINIFile(const Stream: TStream;
const INIFile: TINIFile;
const Section: String);
var
ChunkCount: Integer;
ChunkIndex: Integer;
S: String;
B: Byte;
I: Integer;
begin
ChunkCount := INIFile.ReadInteger(Section, 'ChunkCount', 0);
Stream.Size := 0; // can't call clear on a generic TStream
for ChunkIndex := 1 to ChunkCount do
begin
S := INIFile.ReadString(Section, IntToStr(ChunkIndex), '');
for I := 1 to Length(S) do
if (Odd(I)) then
begin
B := StrToInt('$' + Copy(S, I, 2));
Stream.Write(B, SizeOf(B));
end;
end;
end;

procedure TForm1.Button1Click(Sender: TObject);
var
INIFile: TINIFile;
Stream: TMemoryStream;
begin
INIFile := TINIFile.Create(ChangeFileExt(Application.EXEName, '.ini'));
Stream := TMemoryStream.Create;
try
Stream.LoadFromFile('C:\Program Files\Common Files\Borland
Shared\Images\Icons\chem16.bmp');
WriteStreamToINIFile(Stream, INIFile, 'Test');
finally
Stream.Free;
INIFile.Free;
end;
end;

procedure TForm1.Button2Click(Sender: TObject);
var
INIFile: TINIFile;
Stream: TMemoryStream;
begin
INIFile := TINIFile.Create(ChangeFileExt(Application.EXEName, '.ini'));
Stream := TMemoryStream.Create;
try
ReadStreamFromINIFile(Stream, INIFile, 'Test');
Stream.Position := 0;
Image1.Picture.Bitmap.LoadFromStream(Stream);
finally
Stream.Free;
INIFile.Free;
end;
end;
 
 
 

Can you save a small bmp to an ini file?

Post by Harold Hol » Sun, 10 Oct 2004 01:29:38


out

I couldn't get the INI/Binary stuff to work reliably but your XML control
came to the rescue. Thanks, will be ordering shortly! :-)
--
Best regards,
Harold Holmes