Wednesday 23 November 2011

SharedPreferences in eazy way

Its very easy to use SharedPreferences in our application. we can also do this steps through model wise.  for that we need to create one Preferences class with getter & setter. And initialized variable in strings.xml for storing the values.
Lets take an example of saving the user name and user id in SharedPreferences.
strings.xml

<string name="uname">user name</string>
<string name="uid">emp id</string>
<string name="prefSettings"> Pref Settings</string>
<string>
now create SharedPreferences class named Store

/*
 * This class store the application service related data.
 * Whether to enable or disable the Application Service
 */

public class Store {
   
    private SharedPreferences settingsPreference;
    private Context context;
   
    /**
     * Create the application Shared Preference.
     * @param context To access the Android System.
     */
   
    public Store(Context context) {
        this.context = context;
        settingsPreference = context.getSharedPreferences(context.getString(R.string.prefSettings),      Context.MODE_PRIVATE);
         }
   
public boolean setValues(String userName, int uID)
{
try {
            final SharedPreferences.Editor settingsEditor = settingsPreference.edit();
            settingsEditor.putString(context.getString(R.string.uname), userName);
            settingsEditor.putInt(context.getString(R.string.uid), uID);
            settingsEditor.commit();
            return true;

}
              catch (Exception e) {
               e.printStackTrace();
              return false;
        }
    }

public String getUserName() {
        return settingsPreference.getString(context.getString(R.string.uname), null);
    }

public int getUID() {
        return settingsPreference.getString(context.getString(R.string.uid), 0);
    }
}

Now we need to only create the object of Store class from any where in your application and with the use of setter method set the value and with the help of getter get the value.

Ex: new Store(MyActivity.this).setValues("jack", 101);
       int id =  new Store(MyActivity.this).getUID();
        

Lazy Load

Lazy loading is very common in android. When ever we make any server side app generally we download data with images from server. Everytime is downloading the data is not a good habit or when image take much time for download on that time we can display text so our user will not irritate ;)

Now our purpose is to display images with text with the help of lazyload:

Lets start with adapter: we will create custom adapter for our list

import android.app.Activity;
import android.content.Context;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.BaseAdapter;
import android.widget.ImageView;
import android.widget.TextView;

public class LazyAdapter extends BaseAdapter {
   
    private Activity activity;
    private String[] data;
    private static LayoutInflater inflater=null;
    public ImageLoader imageLoader;
   
    public LazyAdapter(Activity a, String[] d) {
        activity = a;
        data=d;
        inflater = (LayoutInflater)activity.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
        imageLoader=new ImageLoader(activity.getApplicationContext());
    }

    public int getCount() {
        return data.length;
    }

    public Object getItem(int position) {
        return position;
    }

    public long getItemId(int position) {
        return position;
    }
   
    public static class ViewHolder{
        public TextView text;
        public ImageView image;
    }

    public View getView(int position, View convertView, ViewGroup parent) {
        View vi=convertView;
        ViewHolder holder;
        if(convertView==null){
            vi = inflater.inflate(R.layout.item, null);
            holder=new ViewHolder();
            holder.text=(TextView)vi.findViewById(R.id.text);;
            holder.image=(ImageView)vi.findViewById(R.id.image);
            vi.setTag(holder);
        }
        else
            holder=(ViewHolder)vi.getTag();
       
        holder.text.setText("item "+position);
        holder.image.setTag(data[position]);
        imageLoader.DisplayImage(data[position], activity, holder.image);
        return vi;
    }
}

This is our adapter class.. but here we are also seeing one more class ImageLoader, This class has main role creating chache manage image


import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.URL;
import java.util.HashMap;
import java.util.Stack;
import android.app.Activity;
import android.content.Context;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.widget.ImageView;

public class ImageLoader {
   
    //the simplest in-memory cache implementation. This should be replaced with something like SoftReference or BitmapOptions.inPurgeable(since 1.6)
    private HashMap<String, Bitmap> cache=new HashMap<String, Bitmap>();
   
    private File cacheDir;
   
    public ImageLoader(Context context){
        //Make the background thead low priority. This way it will not affect the UI performance
        photoLoaderThread.setPriority(Thread.NORM_PRIORITY-1);
       
        //Find the dir to save cached images
        if (android.os.Environment.getExternalStorageState().equals(android.os.Environment.MEDIA_MOUNTED))
            cacheDir=new File(android.os.Environment.getExternalStorageDirectory(),"LazyList");
        else
            cacheDir=context.getCacheDir();
        if(!cacheDir.exists())
            cacheDir.mkdirs();
    }
   
    final int stub_id=R.drawable.stub;
    public void DisplayImage(String url, Activity activity, ImageView imageView)
    {
        if(cache.containsKey(url))
            imageView.setImageBitmap(cache.get(url));
        else
        {
            queuePhoto(url, activity, imageView);
            imageView.setImageResource(stub_id);
        }   
    }
       
    private void queuePhoto(String url, Activity activity, ImageView imageView)
    {
        //This ImageView may be used for other images before. So there may be some old tasks in the queue. We need to discard them.
        photosQueue.Clean(imageView);
        PhotoToLoad p=new PhotoToLoad(url, imageView);
        synchronized(photosQueue.photosToLoad){
            photosQueue.photosToLoad.push(p);
            photosQueue.photosToLoad.notifyAll();
        }
       
        //start thread if it's not started yet
        if(photoLoaderThread.getState()==Thread.State.NEW)
            photoLoaderThread.start();
    }
   
    private Bitmap getBitmap(String url)
    {
        //I identify images by hashcode. Not a perfect solution, good for the demo.
        String filename=String.valueOf(url.hashCode());
        File f=new File(cacheDir, filename);
       
        //from SD cache
        Bitmap b = decodeFile(f);
        if(b!=null)
            return b;
       
        //from web
        try {
            Bitmap bitmap=null;
            InputStream is=new URL(url).openStream();
            OutputStream os = new FileOutputStream(f);
            Utils.CopyStream(is, os);
            os.close();
            bitmap = decodeFile(f);
            return bitmap;
        } catch (Exception ex){
           ex.printStackTrace();
           return null;
        }
    }

    //decodes image and scales it to reduce memory consumption
    private Bitmap decodeFile(File f){
        try {
            //decode image size
            BitmapFactory.Options o = new BitmapFactory.Options();
            o.inJustDecodeBounds = true;
            BitmapFactory.decodeStream(new FileInputStream(f),null,o);
           
            //Find the correct scale value. It should be the power of 2.
            final int REQUIRED_SIZE=70;
            int width_tmp=o.outWidth, height_tmp=o.outHeight;
            int scale=1;
            while(true){
                if(width_tmp/2<REQUIRED_SIZE || height_tmp/2<REQUIRED_SIZE)
                    break;
                width_tmp/=2;
                height_tmp/=2;
                scale++;
            }
           
            //decode with inSampleSize
            BitmapFactory.Options o2 = new BitmapFactory.Options();
            o2.inSampleSize=scale;
            return BitmapFactory.decodeStream(new FileInputStream(f), null, o2);
        } catch (FileNotFoundException e) {}
        return null;
    }
   
    //Task for the queue
    private class PhotoToLoad
    {
        public String url;
        public ImageView imageView;
        public PhotoToLoad(String u, ImageView i){
            url=u;
            imageView=i;
        }
    }
   
    PhotosQueue photosQueue=new PhotosQueue();
   
    public void stopThread()
    {
        photoLoaderThread.interrupt();
    }
   
    //stores list of photos to download
    class PhotosQueue
    {
        private Stack<PhotoToLoad> photosToLoad=new Stack<PhotoToLoad>();
       
        //removes all instances of this ImageView
        public void Clean(ImageView image)
        {
            for(int j=0 ;j<photosToLoad.size();){
                if(photosToLoad.get(j).imageView==image)
                    photosToLoad.remove(j);
                else
                    ++j;
            }
        }
    }
   
    class PhotosLoader extends Thread {
        public void run() {
            try {
                while(true)
                {
                    //thread waits until there are any images to load in the queue
                    if(photosQueue.photosToLoad.size()==0)
                        synchronized(photosQueue.photosToLoad){
                            photosQueue.photosToLoad.wait();
                        }
                    if(photosQueue.photosToLoad.size()!=0)
                    {
                        PhotoToLoad photoToLoad;
                        synchronized(photosQueue.photosToLoad){
                            photoToLoad=photosQueue.photosToLoad.pop();
                        }
                        Bitmap bmp=getBitmap(photoToLoad.url);
                        cache.put(photoToLoad.url, bmp);
                        if(((String)photoToLoad.imageView.getTag()).equals(photoToLoad.url)){
                            BitmapDisplayer bd=new BitmapDisplayer(bmp, photoToLoad.imageView);
                            Activity a=(Activity)photoToLoad.imageView.getContext();
                            a.runOnUiThread(bd);
                        }
                    }
                    if(Thread.interrupted())
                        break;
                }
            } catch (InterruptedException e) {
                //allow thread to exit
            }
        }
    }
   
    PhotosLoader photoLoaderThread=new PhotosLoader();
   
    //Used to display bitmap in the UI thread
    class BitmapDisplayer implements Runnable
    {
        Bitmap bitmap;
        ImageView imageView;
        public BitmapDisplayer(Bitmap b, ImageView i){bitmap=b;imageView=i;}
        public void run()
        {
            if(bitmap!=null)
                imageView.setImageBitmap(bitmap);
            else
                imageView.setImageResource(stub_id);
        }
    }

    public void clearCache() {
        //clear memory cache
        cache.clear();
       
        //clear SD cache
        File[] files=cacheDir.listFiles();
        for(File f:files)
            f.delete();
    }

}

Common Method:
import java.io.InputStream;
import java.io.OutputStream;

public class Utils {
    public static void CopyStream(InputStream is, OutputStream os)
    {
        final int buffer_size=1024;
        try
        {
            byte[] bytes=new byte[buffer_size];
            for(;;)
            {
              int count=is.read(bytes, 0, buffer_size);
              if(count==-1)
                  break;
              os.write(bytes, 0, count);
            }
        }
        catch(Exception ex){}
    }
}

Now we are going to write the functionality of our main activity:

package com.fedorvlasov.lazylist;

import android.app.Activity;
import android.os.Bundle;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.ListView;

public class MainActivity extends Activity {
   
    ListView list;
    LazyAdapter adapter;

        @Override
    protected void onCreate(Bundle savedInstanceState) {
     requestWindowFeature(Window.FEATURE_NO_TITLE);     getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,
                WindowManager.LayoutParams.FLAG_FULLSCREEN);

        super.onCreate(savedInstanceState);

        setContentView(R.layout.main);
       
        list=(ListView)findViewById(R.id.list);
        adapter=new LazyAdapter(this, mStrings);
        list.setAdapter(adapter);
       
        Button b=(Button)findViewById(R.id.button1);
        b.setOnClickListener(listener);
    }
   
    @Override
    public void onDestroy()
    {
        adapter.imageLoader.stopThread();
        list.setAdapter(null);
        super.onDestroy();
    }
   
    public OnClickListener listener=new OnClickListener(){
        @Override
        public void onClick(View arg0) {
            adapter.imageLoader.clearCache();
            adapter.notifyDataSetChanged();
        }
    };
   
    private String[] mStrings={
            "http://a3.twimg.com/profile_images/670625317/aam-logo-v3-twitter.png",
            "http://a3.twimg.com/profile_images/740897825/AndroidCast-350_normal.png",
            "http://a3.twimg.com/profile_images/121630227/Droid_normal.jpg",
            "http://a1.twimg.com/profile_images/957149154/twitterhalf_normal.jpg",
            "http://a1.twimg.com/profile_images/97470808/icon_normal.png",
            "http://a3.twimg.com/profile_images/511790713/AG.png",
            "http://a3.twimg.com/profile_images/956404323/androinica-avatar_normal.png",
            "http://a1.twimg.com/profile_images/909231146/Android_Biz_Man_normal.png",
            "http://a3.twimg.com/profile_images/72774055/AndroidHomme-LOGO_normal.jpg",
            "http://a1.twimg.com/profile_images/349012784/android_logo_small_normal.jpg",
            "http://a1.twimg.com/profile_images/841338368/ea-twitter-icon.png",
            "http://a3.twimg.com/profile_images/64827025/android-wallpaper6_2560x160_normal.png",
            "http://a3.twimg.com/profile_images/77641093/AndroidPlanet_normal.png",
            "http://a1.twimg.com/profile_images/605536070/twitterProfilePhoto_normal.jpg",
            "http://a1.twimg.com/profile_images/850960042/elandroidelibre-logo_300x300_normal.jpg",
            "http://a1.twimg.com/profile_images/655119538/andbook.png",
            "http://a3.twimg.com/profile_images/768060227/ap4u_normal.jpg",
            "http://a1.twimg.com/profile_images/74724754/android_logo_normal.png",
            "http://a3.twimg.com/profile_images/681537837/SmallAvatarx150_normal.png",
            "http://a1.twimg.com/profile_images/63737974/2008-11-06_1637_normal.png",
            "http://a3.twimg.com/profile_images/548410609/icon_8_73.png",
            "http://a1.twimg.com/profile_images/612232882/nexusoneavatar_normal.jpg",
            "http://a1.twimg.com/profile_images/213722080/Bugdroid-phone_normal.png",
            "http://a1.twimg.com/profile_images/645523828/OT_icon_090918_android_normal.png",
            "http://a3.twimg.com/profile_images/64827025/android-wallpaper6_2560x160_normal.png",
            "http://a3.twimg.com/profile_images/77641093/AndroidPlanet.png",
            "http://a1.twimg.com/profile_images/605536070/twitterProfilePhoto_normal.jpg",
            "http://a1.twimg.com/profile_images/850960042/elandroidelibre-logo_300x300_normal.jpg",
            "http://a1.twimg.com/profile_images/655119538/andbook_normal.png",
            "http://a3.twimg.com/profile_images/511790713/AG_normal.png",
            "http://a3.twimg.com/profile_images/956404323/androinica-avatar.png",
            "http://a1.twimg.com/profile_images/909231146/Android_Biz_Man_normal.png",
            "http://a3.twimg.com/profile_images/72774055/AndroidHomme-LOGO_normal.jpg",
            "http://a1.twimg.com/profile_images/349012784/android_logo_small_normal.jpg",
            "http://a1.twimg.com/profile_images/841338368/ea-twitter-icon_normal.png",
            "http://a3.twimg.com/profile_images/64827025/android-wallpaper6_2560x160_normal.png",
            "http://a3.twimg.com/profile_images/77641093/AndroidPlanet.png",
            "http://a1.twimg.com/profile_images/605536070/twitterProfilePhoto_normal.jpg",
            "http://a3.twimg.com/profile_images/64827025/android-wallpaper6_2560x160_normal.png",
            "http://a3.twimg.com/profile_images/77641093/AndroidPlanet_normal.png",
            "http://a1.twimg.com/profile_images/605536070/twitterProfilePhoto_normal.jpg",
            "http://a1.twimg.com/profile_images/850960042/elandroidelibre-logo_300x300.jpg",
            "http://a1.twimg.com/profile_images/655119538/andbook_normal.png",
            "http://a3.twimg.com/profile_images/511790713/AG_normal.png",
            "http://a3.twimg.com/profile_images/956404323/androinica-avatar_normal.png",
            "http://a1.twimg.com/profile_images/909231146/Android_Biz_Man_normal.png",
            "http://a3.twimg.com/profile_images/121630227/Droid.jpg",
            "http://a1.twimg.com/profile_images/957149154/twitterhalf_normal.jpg",
            "http://a1.twimg.com/profile_images/97470808/icon_normal.png",
            "http://a3.twimg.com/profile_images/511790713/AG_normal.png",
            "http://a3.twimg.com/profile_images/956404323/androinica-avatar_normal.png",
            "http://a1.twimg.com/profile_images/909231146/Android_Biz_Man.png",
            "http://a3.twimg.com/profile_images/72774055/AndroidHomme-LOGO_normal.jpg",
            "http://a1.twimg.com/profile_images/349012784/android_logo_small_normal.jpg",
            "http://a1.twimg.com/profile_images/841338368/ea-twitter-icon_normal.png",
            "http://a3.twimg.com/profile_images/64827025/android-wallpaper6_2560x160_normal.png",
            "http://a3.twimg.com/profile_images/77641093/AndroidPlanet.png",
            "http://a3.twimg.com/profile_images/670625317/aam-logo-v3-twitter_normal.png",
            "http://a3.twimg.com/profile_images/740897825/AndroidCast-350_normal.png",
            "http://a3.twimg.com/profile_images/121630227/Droid_normal.jpg",
            "http://a1.twimg.com/profile_images/957149154/twitterhalf_normal.jpg",
            "http://a1.twimg.com/profile_images/97470808/icon.png",
            "http://a3.twimg.com/profile_images/511790713/AG_normal.png",
            "http://a3.twimg.com/profile_images/956404323/androinica-avatar_normal.png",
            "http://a1.twimg.com/profile_images/909231146/Android_Biz_Man_normal.png",
            "http://a3.twimg.com/profile_images/72774055/AndroidHomme-LOGO_normal.jpg",
            "http://a1.twimg.com/profile_images/349012784/android_logo_small_normal.jpg",
            "http://a1.twimg.com/profile_images/841338368/ea-twitter-icon.png",
            "http://a3.twimg.com/profile_images/64827025/android-wallpaper6_2560x160_normal.png",
            "http://a3.twimg.com/profile_images/77641093/AndroidPlanet_normal.png",
            "http://a1.twimg.com/profile_images/605536070/twitterProfilePhoto_normal.jpg",
            "http://a1.twimg.com/profile_images/850960042/elandroidelibre-logo_300x300_normal.jpg",
            "http://a1.twimg.com/profile_images/655119538/andbook_normal.png",
            "http://a3.twimg.com/profile_images/768060227/ap4u_normal.jpg",
            "http://a1.twimg.com/profile_images/74724754/android_logo.png",
            "http://a3.twimg.com/profile_images/681537837/SmallAvatarx150_normal.png",
            "http://a1.twimg.com/profile_images/63737974/2008-11-06_1637_normal.png",
            "http://a3.twimg.com/profile_images/548410609/icon_8_73_normal.png",
            "http://a1.twimg.com/profile_images/612232882/nexusoneavatar_normal.jpg",
            "http://a1.twimg.com/profile_images/213722080/Bugdroid-phone_normal.png",
            "http://a1.twimg.com/profile_images/645523828/OT_icon_090918_android.png",
            "http://a3.twimg.com/profile_images/64827025/android-wallpaper6_2560x160_normal.png",
            "http://a3.twimg.com/profile_images/77641093/AndroidPlanet_normal.png",
            "http://a1.twimg.com/profile_images/605536070/twitterProfilePhoto_normal.jpg",
            "http://a1.twimg.com/profile_images/850960042/elandroidelibre-logo_300x300_normal.jpg",
            "http://a1.twimg.com/profile_images/655119538/andbook.png",
            "http://a3.twimg.com/profile_images/511790713/AG_normal.png",
            "http://a3.twimg.com/profile_images/956404323/androinica-avatar_normal.png",
            "http://a1.twimg.com/profile_images/909231146/Android_Biz_Man_normal.png",
            "http://a3.twimg.com/profile_images/72774055/AndroidHomme-LOGO_normal.jpg",
            "http://a1.twimg.com/profile_images/349012784/android_logo_small_normal.jpg",
            "http://a1.twimg.com/profile_images/841338368/ea-twitter-icon.png",
            "http://a3.twimg.com/profile_images/64827025/android-wallpaper6_2560x160_normal.png",
            "http://a3.twimg.com/profile_images/77641093/AndroidPlanet_normal.png",
            "http://a1.twimg.com/profile_images/605536070/twitterProfilePhoto_normal.jpg",
            "http://a3.twimg.com/profile_images/64827025/android-wallpaper6_2560x160_normal.png",
            "http://a3.twimg.com/profile_images/77641093/AndroidPlanet_normal.png",
            "http://a1.twimg.com/profile_images/605536070/twitterProfilePhoto.jpg",
            "http://a1.twimg.com/profile_images/850960042/elandroidelibre-logo_300x300_normal.jpg",
            "http://a1.twimg.com/profile_images/655119538/andbook_normal.png",
            "http://a3.twimg.com/profile_images/511790713/AG_normal.png",
            "http://a3.twimg.com/profile_images/956404323/androinica-avatar_normal.png",
            "http://a1.twimg.com/profile_images/909231146/Android_Biz_Man_normal.png",
            "http://a3.twimg.com/profile_images/121630227/Droid_normal.jpg",
            "http://a1.twimg.com/profile_images/957149154/twitterhalf.jpg",
            "http://a1.twimg.com/profile_images/97470808/icon_normal.png",
            "http://a3.twimg.com/profile_images/511790713/AG_normal.png",
            "http://a3.twimg.com/profile_images/956404323/androinica-avatar_normal.png",
            "http://a1.twimg.com/profile_images/909231146/Android_Biz_Man_normal.png",
            "http://a3.twimg.com/profile_images/72774055/AndroidHomme-LOGO_normal.jpg",
            "http://a1.twimg.com/profile_images/349012784/android_logo_small.jpg",
            "http://a1.twimg.com/profile_images/841338368/ea-twitter-icon_normal.png",
            "http://a3.twimg.com/profile_images/64827025/android-wallpaper6_2560x160_normal.png",
            "http://a3.twimg.com/profile_images/77641093/AndroidPlanet_normal.png"
    };
}

item.xml:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
  xmlns:android="http://schemas.android.com/apk/res/android"
  android:layout_width="fill_parent"
  android:layout_height="wrap_content">
  <ImageView
        android:id="@+id/image"
      android:layout_width="50dip"
      android:layout_height="50dip" android:src="@drawable/icon" android:scaleType="centerCrop"/>
  <TextView
        android:id="@+id/text"
        android:layout_width="fill_parent"
      android:layout_height="wrap_content"
      android:layout_weight="1" android:layout_gravity="left|center_vertical" android:textSize="20dip" android:layout_marginLeft="10dip"/>
</LinearLayout>

main.xml:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:orientation="vertical"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent">
    <ListView
        android:id="@+id/list"
        android:layout_width="fill_parent"
        android:layout_height="fill_parent"
        android:layout_weight="1"/>
    <Button
        android:id="@+id/button1"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:text="Clear Cache"/>
</LinearLayout>




























Simple Steps Of DOM parsing

lets take a simple xml file ,, suppose we are getting any xml from server side (mean through url)... in the bellow given format
<root>
<item>
<name>sweet</name>
<type category="chocolate">Truffels...</type >
</item>
<item>
<name>dessert</name>
<type category="icecream">crunchy choco</type >
</item>
</root>

A simple xml file. 


Friday 23 September 2011

Customizing Toast

Many times we want to display our toast in custom manner, We can modify a Toast by setting its display position and assigning it alternative views or layouts.

Thursday 22 September 2011

Smooth List View

Listview is very common in android, and easy to make. But main issue is how can we make it smooth and maintain it's performance. when data may be collection of images and text. Now here is a quite good technique to represent our data in list view.

for example we have to display :



Here we need to display images and text . And data should be downloaded from internet. Now we will create a getter and setter class for image and text. The name should be: DataValues



public  class DataValues{

private String imgURL, text;

public void setData(String imgURL, String text){
this.imgURL = imgURL;
this.text = text;
}

public String getImgURL()
{
return imgURL;
}
public String getText()
{
return text;
}
}


Now, let's create xml layout. row_data_image.xml

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="horizontal"
android:layout_width="fill_parent"
android:layout_height="wrap_content">
<ImageView android:id="@+id/image"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:src="@drawable/icon"/>
<TextView android:id="@+id/text"
android:layout_width="wrap_content"
android:layout_height="wrap_content"/>



Now we will create AsyncImageLoader; This functionality can be done "AsyncTask" but here we are going to use thread and handler.

Note: in the given code we are using "SoftReference" for caching images.

public class AsyncImageLoader {
private HashMap<String, SoftReference<Drawable>> imgCache;
public AsyncImageLoader() {
imgCache = new HashMap<String, SoftReference<Drawable>>();
}
public Drawable loadDrawable(final String imgURL, final ImageCallback imageCallback) {
if (drawableMap.containsKey(imgURL)) {
SoftReference<Drawable> softReference = imgCache.get(imgURL);
Drawable drawable = softReference.get();
if (drawable != null) {
return drawable;
}
}
final Handler handler = new Handler() {
@Override
public void handleMessage(Message message) {
imageCallback.imageLoaded((Drawable) message.obj, imgURL);
}
};
new Thread() {
@Override
public void run() {
Drawable drawableImg = loadImageFromUrl(imgURL);
imgCache.put(imgURL, new SoftReference<Drawable>(drawableImg ));
Message message = handler.obtainMessage(0, drawableImg );
handler.sendMessage(message);
}
}.start();
return null;
}

// Download image from internet
public static Drawable loadImageFromUrl(String url) {
InputStream inputStream;
try {
inputStream = new URL(url).openStream();
} catch (IOException e) {
throw new RuntimeException(e);
}
return Drawable.createFromStream(inputStream, "src");
}

public interface ImageCallback {
public void imageLoaded(Drawable imageDrawable, String imgURL);
}



Create ViewWrap class for get ids of views:

public class ViewWrap{
private View mainView;
private TextView textView;
private ImageView imgView;
public ViewCache(View mainView) {
this.mainView = mainView;
}
public TextView getTextView() {
if (textView == null) {
textView = (TextView) mainView.findViewById(R.id.text);
}
return titleView;
}
public ImageView getImageView() {
if (imgView == null) {
imgView = (ImageView) mainView.findViewById(R.id.image);
}
return imgView;
}


Wednesday 21 September 2011

Android Device Information

Android provides some classes and methods by which we can get the information of android devices. some examaples are given bellow.

Get sim serial number:

TelephonyManager tm = (TelephonyManager) getSystemService(Context.TELEPHONY_SERVICE);
String getSimSerialNumber=tm.getSimSerialNumber();

Get Device ID :

TelephonyManager tManager = (TelephonyManager)myActivity.getSystemService(Context.TELEPHONY_SERVICE);
String uid = tManager.getDeviceId();

Get Ram size :

MemoryInfo mi = new MemoryInfo();
ActivityManager activityManager = (ActivityManager) getSystemService(ACTIVITY_SERVICE);
activityManager.getMemoryInfo(mi);
long availableMegs = mi.availMem / 1048576L;

Get Manufacture info:


String m = Build.MANUFACTURER;
 

Get Networkoperator & SIM operator name:
String m = Build.MANUFACTURER;

TelephonyManager telephonyManager =((TelephonyManager) Context.getSystemService(Context.TELEPHONY_SERVICE));

//<------------ Network Operator-----------------

String operatorName = telephonyManager.getNetworkOperatorName();

//<------------SIM Operator------------
String operatorName = telephonyManager.getSimOperatorName();


Sim number:


mPhoneNumber = telephonyManager.getLine1Number();


Get Network Type :

if(telephonyManager.getNetworkType() == TelephonyManager.NETWORK_TYPE_UMTS)
Log.v(TAG, "3G");

if(telephonyManager.getNetworkType() == TelephonyManager.NETWORK_TYPE_EDGE )
Log.v(TAG, "GSM");

if(telephonyManager.getNetworkType() == TelephonyManager.TelephonyManager.NETWORK_TYPE_CDMA)
 Log.v(TAG, "CDMA");


 

Tuesday 20 September 2011

Android database Basic

In android we create our database through SQLiteOpenHelper  class. this class takes care of opening the database if it exists, creating it if it does not, and upgrading it as necessary. Transactions are used to make sure the database is always in a sensible state, with the help of it's methods, we can easly tackcare of our database.

Best practice is that we have to create our application modulewise. So we will create our database class in 
separate manner. The name of our class is "DatabaseHelper".
Lets start:

package com.android.appdemo.database;

import android.content.ContentValues;
import android.content.Context;
import android.database.Cursor;
import android.database.SQLException;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteOpenHelper;
import android.util.Log;
public class DBAdapter
{
    
    private static final String DATABASE_NAME = "my_database";
    private static final String DATABASE_TABLE = "records";
    private static final int DATABASE_VERSION = 1;

    private static final String DATABASE_CREATE =
        "create table titles (_id integer primary key autoincrement, "
        + "name text not null, address text not null, "
        + "city text not null);";
       
    private final Context context;
   
    private DatabaseHelper DBHelper;
    private SQLiteDatabase db;

    public DBAdapter(Context ctx)
    {
        this.context = ctx;
        DBHelper = new DatabaseHelper(context);
    }
       
public class DatabaseHelper extends SQLiteOpenHelper  {

DatabaseHelper(Context context)
        {
            super(context, DATABASE_NAME, null, DATABASE_VERSION);
        }

        @Override
        public void onCreate(SQLiteDatabase db)
        {
            db.execSQL(DATABASE_CREATE);
        }

        @Override
        public void onUpgrade(SQLiteDatabase db, int oldVersion,
        int newVersion)
        {
            Log.w(TAG, "Upgrading database from version " + oldVersion
                    + " to "
                    + newVersion + ", which will destroy all old data");
            db.execSQL("DROP TABLE IF EXISTS titles");
            onCreate(db);
        }
    }   
   
    //---opens the database---
    public DBAdapter open() throws SQLException
    {
        db = DBHelper.getWritableDatabase();
        return this;
    }

    //---closes the database---   
    public void close()
    {
        DBHelper.close();
    }
   

//---insert a values into the database---
    public long insertTitle(String name, String add, String city)
    {
        ContentValues initialValues = new ContentValues();
        initialValues.put("name", name);
        initialValues.put("address", add);
        initialValues.put("city", city);
        return db.insert(DATABASE_TABLE, null, initialValues);
    }

//--- update the record------

public boolean updateName(int id, String name)
{
 ContentValues args = new ContentValues();
        args.put("name", name);
               return db.update(DATABASE_TABLE, args,
                         "_id"+ "=" + id, null) > 0;

}

 //---deletes a particular title---
    public boolean deleteName(long rowId)
    {
        return db.delete(DATABASE_TABLE, "_id"+
        "=" + rowId, null) > 0;
    }

}
You can also copy your database from sdcard and asset folder through code

Code copy database from SD

public void sdCardDatabase() {
private String databasePath = Environment.getExternalStorageDirectory().getAbsoluteFile()+ "/database.db";

  try {
   File f1 = new File("path of your database");
   if (f1.exists()) {
    File f2 = new File(databasePath);
    f2.createNewFile();
    InputStream in = new FileInputStream(f1);
    OutputStream out = new FileOutputStream(f2);
    byte[] bufer = new byte[1024];
    int len;
    while ((len = in.read(bufer)) > 0) {
     out.write(bufer, 0, len);
    }
    in.close();
    out.close();
   }
  } catch (FileNotFoundException e) {
   Log.e(TAG, e.getMessage());
 
  } catch (IOException e) {
 
  }

 }


Monday 19 September 2011

Layout design for different - 2 screen resolution

In Android this is the main thing to maintain the layout according to screen resolution. But thid can be done now easly. Android 3.2 has introduced new APIs that allow you to more precisely control the layout resources your application uses for different screen sizes.

  • Android groups all actual screen sizes into four generalized sizes: small, normal, large, and extra large.
  • Android groups all actual screen densities into four generalized densities: low, medium, high, and extra high.
  • A virtual pixel unit that you should use when defining UI layout, to express layout dimensions or position in a density-independent way.
Now You can create different - 2 layout resolution wise and place them in your application.

example:

res/layout/my_layout.xml             // layout for normal screen size ("default")
res
/layout-small/my_layout.xml       // layout for small screen size
res
/layout-large/my_layout.xml       // layout for large screen size
res
/layout-xlarge/my_layout.xml      // layout for extra large screen size
res
/layout-xlarge-land/my_layout.xml // layout for extra large in landscape orientation

Same thing will be happend with your images :

res/drawable-mdpi/my_icon.png        // bitmap for medium density
res
/drawable-hdpi/my_icon.png        // bitmap for high density
res
/drawable-xhdpi/my_icon.png       // bitmap for extra high density


Here is a quick checklist about how you can ensure that your application displays properly on different screens:
  1. Use wrap_content, fill_parent, or dp units when specifying dimensions in an XML layout file
  2. Do not use hard coded pixel values in your application code
  3. Do not use AbsoluteLayout (it's deprecated)
  4. Supply alternative bitmap drawables for different screen densities
For more you may reffer Android Developer site

Sending Email

We can send email in android with the help of Android Intent with user interface and also without promt to user.

First we will see how can we send email with mail interface:

final Intent emailIntent = new Intent(android.content.Intent.ACTION_SEND);
emailIntent .setType("plain/text");
emailIntent .putExtra(android.content.Intent.EXTRA_EMAIL, new String[]{"abc@pqr.com"});
emailIntent .putExtra(android.content.Intent.EXTRA_SUBJECT, mySubject);
emailIntent .putExtra(android.content.Intent.EXTRA_TEXT, myBodyText);
emailIntent.putExtra(Intent.EXTRA_STREAM, Uri.parse("file:/"+ FileName));  // Attachment

context.startActivity(Intent.createChooser(emailIntent, "Send mail...));




Second way:

We can also send mail to user without providing the mail interface;
This can be done by JavaMail API implemented for Andorid . We can also send html content, attachment.

Hope the given demo code will help you :)

Mail sendMail = new Mail("My_User_ID", "PASSWORD"); // Replace user id and password
//according  to your credential
String[] toArray = {"1st mail id", "2nd mail id"};
sendMail.setTo(toArray);
sendMail.setFrom("USER EMAIL");
sendMail.setSubject("This is an email sent using Mail JavaMail wrapper from an Android device.");
sendMail.setBody("Email body contents");
try {
sendMail.addAttachment("/sdcard/imagefolder/myImage.png"); // Image path for attachment
if(sendMail.send()) {
Toast.makeText(this, "Email was sent successfully.", Toast.LENGTH_SHORT).show();
} else {
Toast.makeText(this, "Email was not sent.", Toast.LENGTH_SHORT).show();
}
} catch(Exception e) {
Log.e(TAG, "Could not send email", e);
}