I am trying to save a byte array (of an image) to the file system using C# and it isn't working using either method I have tried, here is code sample 1:
string path = @"c:\ppd" + g.ToString() + ".jpg";
using (MemoryStream inputStream = new MemoryStream(image))
{
Image returnImage = Image.FromStream(inputStream);
returnImage.Save(path, ImageFormat.Jpeg);
}
With this code I get 'Parameter is not valid' when sending the data to the service. So that's obviously the wrong code for the array, so I hit google and came up with this code:
string path = @"c:\ppd\" + g.ToString() + ".jpg";
using (MemoryStream inputStream = new MemoryStream(image))
{
using (Stream file = File.Create(path))
{
byte[] buffer = new byte[8 * 1024];
int len;
while ((len = inputStream.Read(buffer, 0, buffer.Length)) > 0)
{
file.Write(buffer, 0, len);
}
}
}
This code writes the file to the file system, but when you try to open it it helpfully says 'This is not a valid bitmap file, or it's format is not currently supported.
We get the byteArray from Flex using:
bitmapData.getPixels(0, 0, bitmapData.width, bitmapData.height);
And the bitmapData comes from the Android camera (via the Distriqt Camera ANE). The image displays fine in the app, but I have no idea where to go next with this, please help.
EDIT: The code in Flex to get the byteArray is:
<s:BitmapImage id="bitmapImage" width="100%"
maxHeight="{this.height/2}"
source="{profileModel.captureBitmapPreview}"
/>
<s:Button click="{dispatchEvent(new PictureEvent
(PictureEvent.UPLOAD,
0, pictureModel.captureBitmapPreview.getPixels(new Rectangle(0,0,pictureModel.captureBitmapPreview.width,pictureModel.captureBitmapPreview.height))))}"/>
/* this is the alternative which still doesn't work **/
<s:Button click="{dispatchEvent(new PictureEvent
(PictureEvent.UPLOAD,
0, bitmapImage.getPixels(new Rectangle(0,0,bitmapImage.width,bitmapImage.height))))}"/>
PictureEvent takes 3 parameters, type:String, id:int = 0, image:ByteArray = null.
SECOND EDIT: Here is the code that creates the bitmapData:
private function camera_capturedImageHandler(evt:CameraDataEvent):void
{
Camera.instance.setPresetMode(CameraMode.PRESET_MEDIUM);
Camera.instance.addEventListener(CameraEvent.VIDEO_FRAME, camera_videoFrameHandler, false, 0, true);
if (_captureBitmapData.width != evt.data.width || _captureBitmapData.height != evt.data.height)
{
_captureBitmapData = new BitmapData(evt.data.width, evt.data.height, false);
}
_captureBitmapData.draw(evt.data);
var tbd:BitmapData = new BitmapData(FlexGlobals.topLevelApplication.width, FlexGlobals.topLevelApplication.height, false)
tbd = applyOrientation(_bitmapData, "6");
profileModel.captureBitmapPreview.copyPixels(tbd, new Rectangle(0, ((FlexGlobals.topLevelApplication.height/2)-(FlexGlobals.topLevelApplication.height/4)), FlexGlobals.topLevelApplication.width, FlexGlobals.topLevelApplication.height/2), new Point(0, 0));
}
THIRD EDIT: I has done some testing and discovered that this code should work, it is a variation on the first block above that throws 'Parameter is not valid'
ImageConverter imageConverter = new ImageConverter();
Bitmap bm = (Bitmap)imageConverter.ConvertFrom(image);
if (bm != null && (bm.HorizontalResolution != (int)bm.HorizontalResolution || bm.VerticalResolution != (int)bm.VerticalResolution))
{
bm.SetResolution((int)(bm.HorizontalResolution + 0.5f),(int)(bm.VerticalResolution + 0.5f));
}
bm.Save(path, ImageFormat.Jpeg);
So now I am sure the error is with the byteArray, but I genuinely cannot see what I am doing wrong. I have the bitmapData and it is valid, and it looks like I am collecting the data I need, the written file is nearly 700Kb in size, but something is wrong. If someone could tell me what is wrong on the Flex side of this equation I would be forever grateful. I have the BitmapImage on the display list, it is bound to the model correctly and I have tried different ways of pointing to the source and drawing up the rectangle.