Blackberry - how to resize image? - graphics

I wanted to know if we can resize an image. Suppose if we want to draw an image of 200x200 actual size with a size of 100 x 100 size on our blackberry screen.
Thanks

You can do this pretty simply using the EncodedImage.scaleImage32() method. You'll need to provide it with the factors by which you want to scale the width and height (as a Fixed32).
Here's some sample code which determines the scale factor for the width and height by dividing the original image size by the desired size, using RIM's Fixed32 class.
public static EncodedImage resizeImage(EncodedImage image, int newWidth, int newHeight) {
int scaleFactorX = Fixed32.div(Fixed32.toFP(image.getWidth()), Fixed32.toFP(newWidth));
int scaleFactorY = Fixed32.div(Fixed32.toFP(image.getHeight()), Fixed32.toFP(newHeight));
return image.scaleImage32(scaleFactorX, scaleFactorY);
}
If you're lucky enough to be developer for OS 5.0, Marc posted a link to the new APIs that are a lot clearer and more versatile than the one I described above. For example:
public static Bitmap resizeImage(Bitmap originalImage, int newWidth, int newHeight) {
Bitmap newImage = new Bitmap(newWidth, newHeight);
originalImage.scaleInto(newImage, Bitmap.FILTER_BILINEAR, Bitmap.SCALE_TO_FILL);
return newImage;
}
(Naturally you can substitute the filter/scaling options based on your needs.)

Just an alternative:
BlackBerry - draw image on the screen
BlackBerry - image 3D transform

I'm not a Blackberry programmer, but I believe some of these links will help you out:
Image Resizing Article
Resizing a Bitmap on the Blackberry
Blackberry Image Scaling Question

Keep in mind that the default image scaling done by BlackBerry is quite primitive and generally doesn't look very good. If you are building for 5.0 there is a new API to do much better image scaling using filters such as bilinear or Lanczos.

For BlackBerry JDE 5.0 or later, you can use the scaleInto API.

in this there is two bitmap.temp is holding the old bitmap.In this method you just pass
bitmap ,width,height.it return new bitmap of your choice.
Bitmap ImgResizer(Bitmap bitmap , int width , int height){
Bitmap temp=new Bitmap(width,height);
Bitmap resized_Bitmap = bitmap;
temp.createAlpha(Bitmap.HOURGLASS);
resized_Bitmap.scaleInto(temp , Bitmap.FILTER_LANCZOS);
return temp;
}

Here is the function or you can say method to resize image, use it as you want :
int olddWidth;
int olddHeight;
int dispplayWidth;
int dispplayHeight;
EncodedImage ei2 = EncodedImage.getEncodedImageResource("add2.png");
olddWidth = ei2.getWidth();
olddHeight = ei2.getHeight();
dispplayWidth = 40;\\here pass the width u want in pixels
dispplayHeight = 80;\\here pass the height u want in pixels again
int numeerator = net.rim.device.api.math.Fixed32.toFP(olddWidth);
int denoominator = net.rim.device.api.math.Fixed32.toFP(dispplayWidth);
int widtthScale = net.rim.device.api.math.Fixed32.div(numeerator, denoominator);
numeerator = net.rim.device.api.math.Fixed32.toFP(olddHeight);
denoominator = net.rim.device.api.math.Fixed32.toFP(dispplayHeight);
int heighhtScale = net.rim.device.api.math.Fixed32.div(numeerator, denoominator);
EncodedImage newEi2 = ei2.scaleImage32(widtthScale, heighhtScale);
Bitmap _add =newEi2.getBitmap();

I am posting this answers for newbie in Blackberry Application development. Below code is for processing Bitmap images from URL and Resizing them without loass of Aspect Ratio :
public static Bitmap imageFromServer(String url)
{
Bitmap bitmp = null;
try{
HttpConnection fcon = (HttpConnection)Connector.open(url);
int rc = fcon.getResponseCode();
if(rc!=HttpConnection.HTTP_OK)
{
throw new IOException("Http Response Code : " + rc);
}
InputStream httpInput = fcon.openDataInputStream();
InputStream inp = httpInput;
byte[] b = IOUtilities.streamToBytes(inp);
EncodedImage img = EncodedImage.createEncodedImage(b, 0, b.length);
bitmp = resizeImage(img.getBitmap(), 100, 100);
}
catch(Exception e)
{
Dialog.alert("Exception : " + e.getMessage());
}
return bitmp;
}
public static Bitmap resizeImage(Bitmap originalImg, int newWidth, int newHeight)
{
Bitmap scaledImage = new Bitmap(newWidth, newHeight);
originalImg.scaleInto(scaledImage, Bitmap.FILTER_BILINEAR, Bitmap.SCALE_TO_FIT);
return scaledImage;
}
The Method resizeImage is called inside the method imageFromServer(String url).
1) the image from server is processed using EncodedImage img.
2) Bitmap bitmp = resizeImage(img.getBitmap(), 100, 100);
parameters are passed to resizeImage() and the return value from resizeImage() is set to Bitmap bitmp.

Related

How do I change the background color of a tabbed page in Xamarin iOS?

I need to change the background color of the currently tabbed page in my UITabBarController. I've searched through every stackoverflow post I could find but nothing worked for me. I thought there would be something like UITabBar.Appearance.SelectedImageTintColor, just for the background color but it doesn't seem so.
For example, I want to change the color of that part when I am on the right tab:
Does someone know how to do that?
You could invoked the following code in your UITabBarController
public xxxTabBarController()
{
//...set ViewControllers
this.TabBar.BarTintColor = UIColor.Red;
}
Update
//3.0 here is if you have three child page in tab , set it as the current value in your project
//
var size = new CGSize(TabBar.Frame.Width / 3.0, IsFullScreen());
this.TabBar.SelectionIndicatorImage = ImageWithColor(size,UIColor.Green);
double IsFullScreen()
{
double height = 64;
if (UIDevice.CurrentDevice.CheckSystemVersion(11, 0))
{
if (UIApplication.SharedApplication.Delegate.GetWindow().SafeAreaInsets.Bottom > 0.0)
{
height = 84;
}
}
return height;
}
UIImage ImageWithColor(CGSize size, UIColor color)
{
var rect = new CGRect(0, 0, size.Width, size.Height);
UIGraphics.BeginImageContextWithOptions(size, false, 0);
CGContext context = UIGraphics.GetCurrentContext();
context.SetFillColor(color.CGColor);
context.FillRect(rect);
UIImage image = UIGraphics.GetImageFromCurrentImageContext();
UIGraphics.EndImageContext();
return image;
}
The trick is to use the SelectionIndicatorImage Property of the UITabBar and generate a completely filled image with your desired color using the following method:
private UIImage ImageWithColor(CGSize size)
{
CGRect rect = new CGRect(0, 0, size.Width, size.Height);
UIGraphics.BeginImageContext(size);
using (CGContext context = UIGraphics.GetCurrentContext())
{
context.SetFillColor(UIColor.Green); //change color if necessary
context.FillRect(rect);
}
UIImage image = UIGraphics.GetImageFromCurrentImageContext();
UIGraphics.EndImageContext();
return image;
}
To initialize everything we override ViewWillLayoutSubviews() like this:
public override void ViewWillLayoutSubviews()
{
base.ViewWillLayoutSubviews();
// The tabbar height will always be 49 unless we force it to reevaluate it's size on runtime ...
myTabBar.InvalidateIntrinsicContentSize();
double height = myTabBar.Frame.Height;
CGSize size = new CGSize(new nfloat(myTabBar.Frame.Width / myTabBar.Items.Length, height));
// Now get our all-green image...
UIImage image = ImageWithColor(size);
// And set it as the selection indicator
myTabBar.SelectionIndicatorImage = image;
}
As mentioned in this article (google translating it step by step when necessary lol) calling InvalidateIntrinsicContentSize() will force the UITabBar to reevaluate it's size and will get you the actual runtime height of the tab bar (instead of the constant 49 height value from XCode).

Memory Leak happens in Xamarin Forms Android while using Bitmap

While using bitmap in Xamarin Forms Android I'm getting out of memory error while loading images which are of higher than the usual size.
void getImage() {
-------
imageView.setImageBitmap(Bitmap.createScaledBitmap(getBitmapFromViewUpdated(_view), (int) width, (int) height, true));
tempView = imageView;
--------
}
public static Bitmap getBitmapFromView(final View view) {
view.setLayoutParams(new LayoutParams(view.getWidth(),
view.getHeight()));
view.measure(MeasureSpec.makeMeasureSpec(0, MeasureSpec.UNSPECIFIED),
MeasureSpec.makeMeasureSpec(0, MeasureSpec.UNSPECIFIED));
view.layout(0, 0, view.getMeasuredWidth(), view.getMeasuredHeight());
final Bitmap bitmap_ = Bitmap
.createBitmap(view.getMeasuredWidth(),
view.getMeasuredHeight(),
Bitmap.Config.ARGB_8888);
Canvas c = new Canvas(bitmap_);
view.draw(c);
return bitmap_;
}
Bitmap getBitmapFromViewUpdated(final View view) {
if (view.getWidth() == 0 || view.getHeight() == 0)
view.setLayoutParams(new LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT,
ViewGroup.LayoutParams.MATCH_PARENT));
else
view.setLayoutParams(new LayoutParams(view.getWidth(),
view.getHeight()));
view.measure(MeasureSpec.makeMeasureSpec(0, MeasureSpec.UNSPECIFIED),
MeasureSpec.makeMeasureSpec(0, MeasureSpec.UNSPECIFIED));
view.layout(0, 0, viewWidth, viewHeight);
final Bitmap bitmap_;
if(viewWidth>0 && viewHeight>0) {
bitmap_ = Bitmap
.createBitmap(viewWidth,
viewHeight, Bitmap.Config.ARGB_8888);
}
else
{
bitmap_= Bitmap
.createBitmap(view.getMeasuredWidth(),
view.getMeasuredHeight(),
Bitmap.Config.ARGB_8888);
}
Canvas c = new Canvas(bitmap_);
view.draw(c);
return bitmap_;
}
I have tried android:largeHeap=true, can achieve the result while using that but I need to know how to fix with bitmap resizing.
You can check these two links for efficient bitmap management in xamarin android
https://forums.xamarin.com/discussion/5716/disposing-of-bitmaps-properly
https://developer.xamarin.com/recipes/android/resources/general/load_large_bitmaps_efficiently/
GoodLuck!

Image getting zoomed and cut off when converting from binary data

I have some background images stored as binary data. I need to draw something on it based on data and then show it as a single image in the browser. The issue is that some of the images are getting zoomed in and some get zoomed out when I try to do this with the following code. Can anyone please tell where I am going wrong?
int imageWidth = 0, imageHeight=0;
Image bmpImg;
if (datatable.Rows.Count > 0)
{
bmpImg = Bitmap.FromStream(new MemoryStream((byte[])datatable.Rows[0]["data"]));
imageWidth = bmpImg.Width;
imageHeight= bmpImg.Height;
}
else{
bmpImg = null;
}
bitmap = new Bitmap(imageWidth, imageHeight);
//bitmap = new Bitmap(1000, 800);
renderer = SvgRenderer.FromImage(bitmap);
graphics = Graphics.FromImage(bitmap);
if(bmpImg != null)
{
graphics.DrawImage(bmpImg, 0, 0);
}
//perform other drawings using graphics
MemoryStream ms = new MemoryStream();
bitmap.Save(ms, ImageFormat.Png);
bitmap.Dispose();
renderer.Dispose();
After some searching, I got the answer from another question : Graphics.DrawImage unexpectedly resizing image
Basically you have to change this:
graphics.DrawImage(bmpImg, 0, 0);
to
graphics.DrawImage(bmpImg,new Rectangle(0,0,imageWidth,imageHeight));

how to write byte[] to Image with Landscape or Portrait properties?

I have a code which converts byte[] to image but my code always writes in Landscape mode even original image was Portrait. How can I detect original image's Page Orientation and write new Image with this properties? Any suggestions?
public void SendFax(byte[] file, string fileName)
{
try
{
MemoryStream ms = new MemoryStream(file);
Image imgSave = Image.FromStream(ms);
Bitmap bmSave = new Bitmap(imgSave);
Bitmap bmTemp = new Bitmap(bmSave);
Graphics grSave = Graphics.FromImage(bmTemp);
grSave.DrawImage(imgSave, 0, 0, imgSave.Width, imgSave.Height)
//Save Image to physical path
bmTemp.Save("C:/..." + fileName);
imgSave.Dispose();
bmSave.Dispose();
bmTemp.Dispose();
grSave.Dispose();
}
catch (Exception ex)
{
throw ex;
}
}
Try with this. Check for img height and width and based on the comparison decide portrait/landscape
int srcWidth = image.Width;
int srcHeight = image.Height;
int thumbWidth = width;
int thumbHeight;
Bitmap bmp;
if (srcHeight > srcWidth)
{
thumbHeight = (srcHeight / srcWidth) * thumbWidth;
bmp = new Bitmap(thumbWidth, thumbHeight);
}
else
{
thumbHeight = thumbWidth;
thumbWidth = (srcWidth / srcHeight) * thumbHeight;
bmp = new Bitmap(thumbWidth, thumbHeight);
}

Emulated docking the form is sized down, upon removing from dock the form only stays full size when it has focus with a mouse down

Calling module:
private void Indicator_Move(object sender, EventArgs e)
{
Sizer size = new Sizer();
int x = this.Location.X;
int y = this.Location.Y;
int width = this.Width;
int height = this.Height;
var screenWidth = Screen.PrimaryScreen.WorkingArea.Width - 130;
if (x >= screenWidth)
{
size.checkmove(x, y, width, height, this);
}
else if (width == 158 )
{
width = 235;
height = 223;
this.Size = new System.Drawing.Size(width, height);
}
}
Module to Dock and reduce size from Sizer class:
public void checkmove(int movex, int movey,int width, int height, Form mover)
{
var moverheight = mover.Height;
var screenWidth = Screen.PrimaryScreen.WorkingArea.Width - 130;
var screenHeight = Screen.PrimaryScreen.WorkingArea.Height;
var finalx = screenWidth;
if (movex > screenWidth)
{
mover.Size = new System.Drawing.Size(154, 45);
mover.Location = new Point(finalx, screenHeight - 600);
}
}
I actually found a different way to accomplish what I wanted by the double_click event on the form and just moving it out on to the desktop it full size, but I am still curious why it resizes back and forth to full size and reduced size while moving and appearing to flicker and ending up reduced and only showing full size when the mouse button is clicked on form and held down. I'm thinking it has to do with the resizeend call anytime the form is moved. And thanks Joran for the edit.

Resources