Can I save (write to file) UIImage
object as bitmap file (.bmp extension) in iPhone’s document directory?
我可以在iPhone的文档目录中保存(写入文件)UIImage对象作为位图文件(.bmp扩展名)吗?
Thanks in advance.
提前致谢。
4 个解决方案
#1
3
I don’t think BMP is supported on iPhone. Maybe somebody wrote a category for UIImage
that does saving into BMP, but I don’t know about any. I guess You’ll have to get the bitmap data from the UIImage
and write them yourself, BMP is quite a simple file format. All you have to do is write out the header and then the uncompressed data. The header is a structure called BITMAPINFOHEADER
, see MSDN. Getting the bitmap data of an UIImage
is described in Apple’s Technical Q&A1509.
我不认为iPhone支持BMP。也许有人为UIImage编写了一个保存到BMP中的类别,但我不知道任何类别。我想你必须从UIImage获取位图数据并自己编写,BMP是一种非常简单的文件格式。您所要做的就是写出标题然后写出未压缩的数据。标头是一个名为BITMAPINFOHEADER的结构,请参阅MSDN。获取UIImage的位图数据在Apple的技术Q&A1509中有所描述。
#2
2
Right now I am not concerned about the size. Just want to know can I write image data as .bmp file.
现在我不关心大小。只是想知道我可以将图像数据写为.bmp文件。
#3
1
Realize this is an old post, but in case someone finds it like I did looking for a solution. I basically needed to FTP UIImage as a small BMP, so I hacked this crude class in MonoTouch. I borrowed from zxing.Bitmap.cs and Example 1 from wikipedia BMP article. It appears to work. Might have been slicker to do an extension like AsBMP() or something like that. (I don't know what the objective-c equivalent is, but hopefully this is helpful to someone.)
意识到这是一个老帖子,但万一有人发现它像我一样寻找解决方案。我基本上需要将FTP UIImage作为一个小型BMP,所以我在MonoTouch中破解了这个原始类。我借用了wikipedia BMP文章中的zxing.Bitmap.cs和例1。它似乎工作。像AsBMP(或类似的东西)这样的扩展可能会更加流畅。 (我不知道Objective-c的等价物是什么,但希望这对某人有帮助。)
using System;
using System.Drawing;
using System.Runtime.InteropServices;
using MonoTouch.Foundation;
using MonoTouch.UIKit;
using MonoTouch.CoreGraphics;
public class BitmapFileRGBA8888
{
public byte[] Data; // data needs to be BGRA
public const int PixelDataOffset = 54;
public BitmapFileRGBA8888(UIImage image)
{
CGImage imageRef = image.CGImage;
int width = imageRef.Width;
int height = imageRef.Height;
Initialize((uint)width, (uint)height);
CGColorSpace colorSpace = CGColorSpace.CreateDeviceRGB();
IntPtr rawData = Marshal.AllocHGlobal(height*width*4);
CGContext context = new CGBitmapContext(
rawData, width, height, 8, 4*width, colorSpace, CGImageAlphaInfo.PremultipliedLast
);
context.DrawImage(new RectangleF(0.0f,0.0f,(float)width,(float)height),imageRef); // RGBA
byte[] pixelData = new byte[height*width*4];
Marshal.Copy(rawData,pixelData,0,pixelData.Length);
Marshal.FreeHGlobal(rawData);
int di = PixelDataOffset;
int si;
for (int y = 0; y < height; y++)
{
si = (height-y-1) * 4 * width;
for (int x = 0; x < width; x++)
{
CopyFlipPixel(pixelData, si, Data, di);
di += 4; // destination marchs forward
si += 4;
}
}
}
private void CopyFlipPixel(byte[] Src, int Src_offset, byte[] Dst, int Dst_offset)
{
int S = Src_offset;
int D = Dst_offset + 2;
Dst[D--] = Src[S++]; // R
Dst[D--] = Src[S++]; // G
Dst[D--] = Src[S++]; // B
Dst[Dst_offset+3] = Src[S]; // alpha
}
private void Initialize(uint W, uint H)
{
uint RawPixelDataSize = W * H * 4;
uint Size = RawPixelDataSize + 14 + 40;
Data = new byte[Size];
Data[0] = 0x42; Data[1] = 0x4D; // BITMAPFILEHEADER "BM"
SetLong(0x2, Size); // file size
SetLong(0xA, PixelDataOffset); // offset to pixel data
SetLong(0xE, 40); // bytes in DIB header (BITMAPINFOHEADER)
SetLong(0x12, W);
SetLong(0x16, H);
SetShort(0x1A, 1); // 1 plane
SetShort(0x1C, 32); // 32 bits
SetLong(0x22, RawPixelDataSize);
SetLong(0x26, 2835); // h/v pixels per meter device resolution
SetLong(0x2A, 2835);
}
private void SetShort(int Offset, UInt16 V)
{
var byts = BitConverter.GetBytes(V);
if (!BitConverter.IsLittleEndian) Array.Reverse(byts);
Array.Copy(byts,0,Data,Offset,byts.Length);
}
private void SetLong(int Offset, UInt32 V)
{
var byts = BitConverter.GetBytes(V);
if (!BitConverter.IsLittleEndian) Array.Reverse(byts);
Array.Copy(byts,0,Data,Offset,byts.Length);
}
} // END CLASS
Basically
var Bmp = new BitmapFileRGBA8888(TempImage);
FTP.UploadBin(Bmp.Data, "test.bmp"); // or just write as binary file
#4
0
Since BMP is not a compressed format, is this a good idea?
由于BMP不是压缩格式,这是个好主意吗?
Presumably, image size is even more important on portable devices.
据推测,图像尺寸在便携式设备上更为重要。
#1
3
I don’t think BMP is supported on iPhone. Maybe somebody wrote a category for UIImage
that does saving into BMP, but I don’t know about any. I guess You’ll have to get the bitmap data from the UIImage
and write them yourself, BMP is quite a simple file format. All you have to do is write out the header and then the uncompressed data. The header is a structure called BITMAPINFOHEADER
, see MSDN. Getting the bitmap data of an UIImage
is described in Apple’s Technical Q&A1509.
我不认为iPhone支持BMP。也许有人为UIImage编写了一个保存到BMP中的类别,但我不知道任何类别。我想你必须从UIImage获取位图数据并自己编写,BMP是一种非常简单的文件格式。您所要做的就是写出标题然后写出未压缩的数据。标头是一个名为BITMAPINFOHEADER的结构,请参阅MSDN。获取UIImage的位图数据在Apple的技术Q&A1509中有所描述。
#2
2
Right now I am not concerned about the size. Just want to know can I write image data as .bmp file.
现在我不关心大小。只是想知道我可以将图像数据写为.bmp文件。
#3
1
Realize this is an old post, but in case someone finds it like I did looking for a solution. I basically needed to FTP UIImage as a small BMP, so I hacked this crude class in MonoTouch. I borrowed from zxing.Bitmap.cs and Example 1 from wikipedia BMP article. It appears to work. Might have been slicker to do an extension like AsBMP() or something like that. (I don't know what the objective-c equivalent is, but hopefully this is helpful to someone.)
意识到这是一个老帖子,但万一有人发现它像我一样寻找解决方案。我基本上需要将FTP UIImage作为一个小型BMP,所以我在MonoTouch中破解了这个原始类。我借用了wikipedia BMP文章中的zxing.Bitmap.cs和例1。它似乎工作。像AsBMP(或类似的东西)这样的扩展可能会更加流畅。 (我不知道Objective-c的等价物是什么,但希望这对某人有帮助。)
using System;
using System.Drawing;
using System.Runtime.InteropServices;
using MonoTouch.Foundation;
using MonoTouch.UIKit;
using MonoTouch.CoreGraphics;
public class BitmapFileRGBA8888
{
public byte[] Data; // data needs to be BGRA
public const int PixelDataOffset = 54;
public BitmapFileRGBA8888(UIImage image)
{
CGImage imageRef = image.CGImage;
int width = imageRef.Width;
int height = imageRef.Height;
Initialize((uint)width, (uint)height);
CGColorSpace colorSpace = CGColorSpace.CreateDeviceRGB();
IntPtr rawData = Marshal.AllocHGlobal(height*width*4);
CGContext context = new CGBitmapContext(
rawData, width, height, 8, 4*width, colorSpace, CGImageAlphaInfo.PremultipliedLast
);
context.DrawImage(new RectangleF(0.0f,0.0f,(float)width,(float)height),imageRef); // RGBA
byte[] pixelData = new byte[height*width*4];
Marshal.Copy(rawData,pixelData,0,pixelData.Length);
Marshal.FreeHGlobal(rawData);
int di = PixelDataOffset;
int si;
for (int y = 0; y < height; y++)
{
si = (height-y-1) * 4 * width;
for (int x = 0; x < width; x++)
{
CopyFlipPixel(pixelData, si, Data, di);
di += 4; // destination marchs forward
si += 4;
}
}
}
private void CopyFlipPixel(byte[] Src, int Src_offset, byte[] Dst, int Dst_offset)
{
int S = Src_offset;
int D = Dst_offset + 2;
Dst[D--] = Src[S++]; // R
Dst[D--] = Src[S++]; // G
Dst[D--] = Src[S++]; // B
Dst[Dst_offset+3] = Src[S]; // alpha
}
private void Initialize(uint W, uint H)
{
uint RawPixelDataSize = W * H * 4;
uint Size = RawPixelDataSize + 14 + 40;
Data = new byte[Size];
Data[0] = 0x42; Data[1] = 0x4D; // BITMAPFILEHEADER "BM"
SetLong(0x2, Size); // file size
SetLong(0xA, PixelDataOffset); // offset to pixel data
SetLong(0xE, 40); // bytes in DIB header (BITMAPINFOHEADER)
SetLong(0x12, W);
SetLong(0x16, H);
SetShort(0x1A, 1); // 1 plane
SetShort(0x1C, 32); // 32 bits
SetLong(0x22, RawPixelDataSize);
SetLong(0x26, 2835); // h/v pixels per meter device resolution
SetLong(0x2A, 2835);
}
private void SetShort(int Offset, UInt16 V)
{
var byts = BitConverter.GetBytes(V);
if (!BitConverter.IsLittleEndian) Array.Reverse(byts);
Array.Copy(byts,0,Data,Offset,byts.Length);
}
private void SetLong(int Offset, UInt32 V)
{
var byts = BitConverter.GetBytes(V);
if (!BitConverter.IsLittleEndian) Array.Reverse(byts);
Array.Copy(byts,0,Data,Offset,byts.Length);
}
} // END CLASS
Basically
var Bmp = new BitmapFileRGBA8888(TempImage);
FTP.UploadBin(Bmp.Data, "test.bmp"); // or just write as binary file
#4
0
Since BMP is not a compressed format, is this a good idea?
由于BMP不是压缩格式,这是个好主意吗?
Presumably, image size is even more important on portable devices.
据推测,图像尺寸在便携式设备上更为重要。