Monday, 19 September 2011

Getting a Bitmap out of a Zip file in Android (or Java in general)

The following function will extract an image from a zip file stored anywhere on the filesystem (for as long as the application has access to it).

It will return a bitmap object if the image is found or null otherwise. This function should work in pure java as well with minor alterations (replacing the Log calls with system.outs).


public Bitmap getBtimapFromZip(final String zipFilePath, final String imageFileInZip){
	Log.d(TAG, "Getting image '" + imageFileInZip + "' from '" + zipFilePath +"'");
	Bitmap result = null;
	try {
		FileInputStream fis = new FileInputStream(zipFilePath);
		ZipInputStream zis = new ZipInputStream(fis);
		ZipEntry ze = null;
		while ((ze = zis.getNextEntry()) != null) {
			if (ze.getName().equals(imageFileInZip)) {
				result = BitmapFactory.decodeStream(zis);
				break;
			}
		}
	} catch (FileNotFoundException e) {
		Log.e(Constants.TAG, "Extracting file: Error opening zip file - FileNotFoundException: ", e);
		e.printStackTrace();
	} catch (IOException e) {
		Log.e(Constants.TAG, "Extracting file: Error opening zip file - IOException: ", e);
		e.printStackTrace();
	}
	return result;
}

If you you use a wrapper function like this:
private void loadImage(ImageButton button, String image){
	// Use this drawable by default
	Drawable d = context.getResources().getDrawable(R.drawable.no_image);
	Bitmap b = getBtimapFromZip("path_to_zip_file", image);
	
	if(b != null){ // if the bitmap is not null, load that instead.
		d = new BitmapDrawable(b);
	}
	
	button.setImageDrawable(d);
}

you can have a fallback drawable to display if something goes wrong (the above bit is Android specific).

A few things to keep in mind:
  1. To get the image out of the zip file you are scanning through all records in the archive sequentially. This could be a performance hit if you have many images. 
  2. If the function returns null but you know that the image is in there, check that you havent accidentally archived the top directory along with the images when creating the zip.

Thursday, 11 August 2011

Sending emails via Gmail (and others) in Java.

The following class will send emails from a java program. It definitely works on Gmail accounts and if you know the settings it should work on others as well. Keep in mind that it needs the javax.mail jar in your classpath.

You can use it like this:

private static void sendEmail(){  
     String[] toRecipients = {"he@it.com", "you@yes.you", "hey@there.com"};  
     String[] ccRecipients = {"this@concerns.you", "and@you.too"};  
     EmailSender es = new EmailSender("smtp.gmail.com", 465, "myEmail@gmail.com", "myPassword");  
     boolean res = es.sendEmail("myEmail@gmail.com", toRecipients, ccRecipients, "Hey guys!", "I can automate email sending now!");  
     if(res){  
          System.out.println("Woohoo!");  
     } else {  
          System.err.println("Hmmmm... Something went wrong...");  
     }  
}  
And here is the class:

Monday, 27 June 2011

Fixing the "Error getting final archive: Debug certificate expired on xx/xx/xxxx" problem

If you are developing Android applications for a while on the same computer (specifically for more than 365 days) you should be familiar with the "Error getting final archive: Debug certificate expired" error which will stop you from testing your applications.

When the Android SDK is installed, it creates a Debug Key which is used to automatically sign applications when you hit the run button and upload them to the Emulator/Test device. The certificate is only valid for 365 days after which you get the error above.

There are two ways to tackle this issue:
  1. You can either get the Android SDK to recreate a debug key - and repeat this every 1 year.
  2. You can create your own key and set the expiry date yourself.

Friday, 24 June 2011

Downloading and Parsing Vendor IDS files to CSV in VB.Net

The following function will parse an ids file and produce an equivalent CSV file. It has been tested with the following two ids files:
  1. The PCI ven/dev list: http://pciids.sourceforge.net/v2.2/pci.ids
  2. The USB ven/dev list: http://www.linux-usb.org/usb.ids
Ids files seem to have two sections; The first section contains the list of hardware and vendor IDs, while the second section has a list of known device classes, subclasses and programming interfaces. This function will only parse the first section. In principle, the only thing that one needs to do to add support for another ids, is to add a line telling the function when to stop parsing (see the idsToCsv() function below, at the beginning of the "Do While objReader.Peek()" loop).

It takes two parameters: "FileInPath" is the location of the OUI file and "FileOutPath" is the path of the CSVyou want to save to. If no file is there, one will be created automatically.

Tuesday, 21 June 2011

Checking if an Intent handler or Activity is present

Quite often in Android you need to call a 3rd party Intent or activity.
For example, to scan a barcode using the Barcode Scanner application, or to start the "hidden" Field Test application in HTC phones.

In order to make the life of a user easier, it is a good idea to check if the Intent Receiver/Activity exists before you attempt to invoke it. Some of the reasons being:
  1. If a non-existent intent, you application will force close.
  2. If the intent receiver is not present, you might want to redirect the user to the market to download the necessary application.
  3. Depending on the existence of an intent you might want to make menu options appear/disappear.
This post contains two functions (isIntentAvailable() and isActivityAvailable())which can perform the checking and return a boolean accordingly.

Sunday, 17 April 2011

Orange UK APN Settings

I've been flashing my phone quite often recently, and some ROMs do not contain the settings for the Orange UK APNs, so I am writing them here.

For the record, they are for Pay Monthly.

APN 1: Orange Internet
  • Name: Orange Internet
  • APN: orangeinternet
  • Proxy: <Not set>
  • Port: <Not set>
  • Username: <Not set>
  • Password: <Not set>
  • Server: <Not set>
  • MMSC: <Not set>
  • MMS proxy: <Not set>
  • MMS port: <Not set>
  • MMS protocol: WAP 2.0
  • MCC: 234
  • MNC: 33
  • Authentication Type: <Not set>
  • APN type: default
APN 2: Orange MMS
  • Name: Orange MMS
  • APN: orangemms
  • Proxy: <Not set>
  • Port: <Not set>
  • Username: <Not set>
  • Password: <Not set>
  • Server: <Not set>
  • MMSC: http://mms.orange.co.uk
  • MMS proxy: 192.168.224.010
  • MMS port: 8080
  • MMS protocol: WAP 2.0
  • MCC: 234
  • MNC: 33
  • Authentication Type: <Not set>
  • APN type: mms

Tuesday, 12 April 2011

Android Wifi password locations

The other day, I realised that I had forgotten my WiFi network password back at home.

The easy way to fix this would have been to use an already connected PC to access the router and change the password there, or to use an application like WirelessKeyView to recover the password of the said PC.

If I used method 1, I'd have to give the key to my housemates, which adds a bit of hassle.

When I tried method 2, the PC I was using was running XP I got a hex string which is not very user friendly (XP automatically converts WPA-PSK keys to a 64bit non-(easily?) reversible hash).

I then decided to try to get the key off my (rooted) Desire Z. Easy enough, the passwords are stored in plaintext in the following file:
/data/misc/wifi/wpa_supplicant.conf  

I then wrote a quick application to make the extraction a bit more painless (links at the bottom of the post), but when I was testing it on my Galaxy Tab, I realised that the file was not there. After a bit of digging around, I found the passwords here:
/data/wifi/bcm_supp.conf  

Also, here is the location of the file on the Streakroid ROM (this could be the default for all Dell Streaks, but as I don't have one I can't check):
/data/misc/wifi/wpa.conf  

The formatting of the files is identical and can be found here: http://linux.die.net/man/5/wpa_supplicant.conf, but the location is different (based on the whims of each developer/company I guess).

To access the files, you need root permissions.

Application Links:


If anyone has a device on which the app does not work, do two things:
  1. Make sure you are rooted.
  2. If you are certain you are rooted and it still does not work, email me (my email can be found here: http://aschillings.co.uk/html/contact.html).
I have no way to contact you if you post anonymously in the comments section!