|
jpg, gif, png, bmp 之间的格式转换 |
• jpg, png, bmp 转 gif 动画 |
• jpg 转 gif, png, bmp |
• gif 转 jpg, png, bmp, 每一帧存为一个图片 |
• png 转 jpg, gif, bmp |
• bmp 转 jpg, gif, png |
本文内容用到的头文件:
类/模板 |
描述 |
头文件 (XE2 之后) |
头文件 (XE 之前) |
TGIFImage |
.gif 图片/动画 |
#include <Vcl.Imaging.GIFImg.hpp> |
#include <GIFImg.hpp> |
TJPEGImage |
.jpg 图片/JPEG 图片 |
#include <Vcl.Imaging.jpeg.hpp> |
#include <jpeg.hpp> |
TPngImage |
.png 图片 |
#include <Vcl.Imaging.pngimage.hpp> |
#include <pngimage.hpp> |
TBitmap |
.bmp 图片/位图 |
#include <Vcl.Graphics.hpp> |
#include <Graphics.hpp> |
TPicture |
支持加载 .gif, .jpg, .png, .bmp, .emf, .tif 等 |
#include <Vcl.Graphics.hpp> |
#include <Graphics.hpp> |
std::auto_ptr |
自动指针 |
#include <memory> |
#include <memory> |
TGIFImage, TJPEGImage, TPngImage, TBitmap 都是从 TGraphic 继承来的,他们之间可以通过 Assign 方法来互相复制显示的内容。
jpg, png, bmp 转 gif 动画
• 这个例子是把 jpg, png, bmp 等几张图片合成一个 gif 动画,相当于循环播放这些图片的效果
• 如果是单张图片,就是静态的 gif 图片,如果要指定透明颜色,请参考这两个例子
void __fastcall TForm1::Button1Click(TObject *Sender)
{
std::auto_ptr<TPicture>picture(new TPicture);
std::auto_ptr<TGIFImage>gif(new TGIFImage);
std::auto_ptr<TStringList>slFiles(new TStringList);
// 图片文件名,显示时间 (时间单位为 0.01 秒)
slFiles->AddPair(L"d:\\a.png", 20); // 第 1 帧:a.png, 显示时间:20 个单位 = 0.2 秒
slFiles->AddPair(L"d:\\b.bmp", 30); // 第 2 帧:b.bmp, 显示时间:30 个单位 = 0.3 秒
slFiles->AddPair(L"d:\\c.jpg", 50); // 第 3 帧:c.jpg, 显示时间:50 个单位 = 0.5 秒
slFiles->AddPair(L"d:\\d.png", 50); // 第 4 帧:d.png, 显示时间:50 个单位 = 0.5 秒
for(int i=0; i<slFiles->Count; i++)
{
TGIFFrame *lpFrame = new TGIFFrame(gif.get()); // gif 里面新增一个空白帧 lpFrame
picture->LoadFromFile(slFiles->Names[i]); // 加载第 i 个 图片文件
lpFrame->Assign(picture->Graphic); // 把图片的内容复制到 lpFrame 帧里面
if(i==0) // 第一帧要添加 gif 循环播放的次数
{
TGIFAppExtNSLoop *loop = new TGIFAppExtNSLoop(lpFrame);
loop->Loops = 0; // 0 为无限次循环,>0 为实际循环次数
}
// 给每一帧添加这一帧显示的时间 // uǝɥɔ ɹoʇɔıʌ - /ɯoɔ·suɐɟddɔ·ʍʍʍ//:dʇʇɥ
TGIFGraphicControlExtension *gce = new TGIFGraphicControlExtension(lpFrame);
gce->Delay = slFiles->ValueFromIndex[i].ToInt(); // 这一帧的显示时间为第 i 个图片的显示时间
}
gif->SaveToFile(L"d:\\test.gif"); // 保存 gif 到文件 d:\\test.gif
}
|
jpg 转 gif, png, bmp
void __fastcall TForm1::Button2Click(TObject *Sender)
{
std::auto_ptr<TJPEGImage>jpg(new TJPEGImage);
std::auto_ptr<TGIFImage>gif(new TGIFImage);
std::auto_ptr<TPngImage>png(new TPngImage);
std::auto_ptr<TBitmap>bmp(new TBitmap);
jpg->LoadFromFile(L"D:\\a.jpg"); // 加载 a.jpg 图片
bmp->Assign(jpg.get()); // jpg 转为 bmp
gif->Assign(bmp.get()); // 再由 bmp 转为 gif
png->Assign(bmp.get()); // 再由 bmp 转为 png
bmp->SaveToFile(L"d:\\test.bmp"); // 保存 bmp 到 test.bmp
gif->SaveToFile(L"d:\\test.gif"); // 保存 gif 到 test.gif
png->SaveToFile(L"d:\\test.png"); // 保存 png 到 test.png
}
|
gif 转 jpg, png, bmp, 每一帧存为一个图片
void __fastcall TForm1::Button3Click(TObject *Sender)
{
std::auto_ptr<TGIFImage>gif(new TGIFImage);
std::auto_ptr<TBitmap>bmp(new TBitmap);
std::auto_ptr<TPngImage>png(new TPngImage);
std::auto_ptr<TJPEGImage>jpg(new TJPEGImage);
// Copyright © Victor Chen, http://www.cppfans.com/
gif->LoadFromFile(L"D:\\a.gif"); // 加载 a.gif
for(int i=0; i<gif->Images->Count; i++) // 一共有 gif->Images->Count 帧
{
TGIFFrame *lpFrame = gif->Images->Frames[i]; // 第 i 帧
if(i==0)
bmp->Assign(lpFrame); // 第一帧是完整的图片
else // 之后的帧需要画在前一帧上才是完整的图片
lpFrame->Draw(bmp->Canvas,TRect(0,0,bmp->Width,bmp->Height),true,true);
bmp->SaveToFile(String().sprintf(L"d:\\b%02d.bmp",i)); // 第 i 帧存为第 i 个 bmp 文件
png->Assign(bmp.get());
png->SaveToFile(String().sprintf(L"d:\\p%02d.png",i)); // 第 i 帧存为第 i 个 png 文件
jpg->Assign(bmp.get());
jpg->SaveToFile(String().sprintf(L"d:\\j%02d.jpg",i)); // 第 i 帧存为第 i 个 jpg 文件
}
}
|
png 转 jpg, gif, bmp
void __fastcall TForm1::Button4Click(TObject *Sender)
{
std::auto_ptr<TPngImage>png(new TPngImage);
std::auto_ptr<TJPEGImage>jpg(new TJPEGImage);
std::auto_ptr<TGIFImage>gif(new TGIFImage);
std::auto_ptr<TBitmap>bmp(new TBitmap);
png->LoadFromFile(L"D:\\a.png"); // 加载 a.png 图片
// bmp->Assign(png.get()); // png 转为 bmp, 这句注释掉了,因为:
// 如果 png 有 Alpha 通道,是半透明的,那么直接 Assign 到 bmp 里面是黑背景的
// 如果需要指定一个背景颜色,就需要先把和 png 同样大小的 bmp 填充为指定的背景色
// 然后把 png 输出到背景色的 bmp 上,就达到了设定背景颜色的效果
// Copyright © Victor Chen, http://www.cppfans.com/
TColor clBkgnd = TColor(RGB(255,255,255)); // 背景色为白色 R=255, G=255, B=255
TRect rcBmp(0, 0, png->Width, png->Height); // bmp 的大小和 png 的大小相同
bmp->PixelFormat = pf32bit; // bmp 设定为 32 位像素格式
bmp->SetSize(rcBmp.Width(), rcBmp.Height()); // bmp 的大小和 png 的大小相同
bmp->Canvas->Brush->Style = bsSolid; // 用 bsSolid 刷子填充 bmp
bmp->Canvas->Brush->Color = clBkgnd; // 指定刷子的颜色为背景颜色
bmp->Canvas->FillRect(rcBmp); // bmp 填充为背景色
bmp->Canvas->Draw(0,0,png.get()); // 把 png 输出到背景颜色的 bmp 上
jpg->Assign(bmp.get()); // 再由 bmp 转为 jpg
gif->Assign(bmp.get()); // 再由 bmp 转为 gif
bmp->SaveToFile(L"d:\\test.bmp"); // 保存 bmp 到 test.bmp
jpg->SaveToFile(L"d:\\test.jpg"); // 保存 jpg 到 test.jpg
gif->SaveToFile(L"d:\\test.gif"); // 保存 gif 到 test.gif
}
|
bmp 转 jpg, gif, png
void __fastcall TForm1::Button15Click(TObject *Sender)
{
std::auto_ptr<TBitmap>bmp(new TBitmap);
std::auto_ptr<TJPEGImage>jpg(new TJPEGImage);
std::auto_ptr<TGIFImage>gif(new TGIFImage);
std::auto_ptr<TPngImage>png(new TPngImage);
bmp->LoadFromFile(L"D:\\a.bmp"); // 加载 a.bmp 图片
jpg->Assign(bmp.get()); // bmp 转为 jpg
gif->Assign(bmp.get()); // bmp 转为 gif
png->Assign(bmp.get()); // bmp 转为 png
jpg->SaveToFile(L"d:\\test.jpg"); // 保存 jpg 到 test.jpg
gif->SaveToFile(L"d:\\test.gif"); // 保存 gif 到 test.gif
png->SaveToFile(L"d:\\test.png"); // 保存 png 到 test.png
}
|
|
|
|
|