I have a Fragment Home.java in the MainActivity which has view pager images. I've used a timer to schedule the automatic sliding of the images inside this viewpager. Whenever I click on the back button on the device to exit the application, I get a NULL POINTER EXCEPTION. Here's my code
public class Home extends Fragment {
Timer timer ; //Timer variable
int page = -1; //Page starts at zero.
int page1 = 8; //Number of images there are
int flag = 0;
int y =0;
ImageLoader imageLoader;
DisplayImageOptions options;
//Images to be displayed on top
String[] imageUrls = new String [] {
"https://lh3.googleusercontent.com/-JB9v6rtgHhk/URqup21F-zI/AAAAAAAAAbs/64Fb8qMZWXk/s1024/Golden%252520Grass.jpg",
"https://lh4.googleusercontent.com/-EIBGfnuLtII/URquqVHwaRI/AAAAAAAAAbs/FA4McV2u8VE/s1024/Grand%252520Teton.jpg",
"https://lh4.googleusercontent.com/-WoMxZvmN9nY/URquq1v2AoI/AAAAAAAAAbs/grj5uMhL6NA/s1024/Grass%252520Closeup.jpg",
"https://lh4.googleusercontent.com/-zAvf__52ONk/URqutT_IuxI/AAAAAAAAAbs/D_bcuc0thoU/s1024/Highway%2525201.jpg",
"https://lh4.googleusercontent.com/-vPeekyDjOE0/URquwzJ28qI/AAAAAAAAAbs/qxcyXULsZrg/s1024/Lake%252520Tahoe%252520Colors.jpg",
"https://lh3.googleusercontent.com/-897VXrJB6RE/URquxxxd-5I/AAAAAAAAAbs/j-Cz4T4YvIw/s1024/Leica%25252050mm%252520Summilux.jpg",
"https://lh3.googleusercontent.com/-D_5lNxnDN6g/URqu2Tk7HVI/AAAAAAAAAbs/p0ddca9W__Y/s1024/Lost%252520in%252520a%252520Field.jpg",
"https://lh4.googleusercontent.com/-Z4zGiC5nWdc/URqvBdEwivI/AAAAAAAAAbs/ZRZR1VJ84QA/s1024/Sin%252520Lights.jpg"
};
ViewPager pager;
CirclePageIndicator circleindicator;
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View rootView = inflater.inflate(R.layout.home, container, false);
imageLoader = ImageLoader.getInstance();
imageLoader.init(ImageLoaderConfiguration.createDefault(getActivity()));
options = new DisplayImageOptions.Builder()
.showImageForEmptyUri(R.drawable.ic_launcher)
.showImageOnFail(R.drawable.add_marker)
.resetViewBeforeLoading(true)
.cacheOnDisc(true)
.imageScaleType(ImageScaleType.EXACTLY)
.bitmapConfig(Bitmap.Config.RGB_565)
.considerExifParams(true)
.displayer(new FadeInBitmapDisplayer(300))
.build();
pager = (ViewPager) rootView.findViewById(R.id.view_pagerhome);
pager.setAdapter(new ImagePagerAdapter(imageUrls));
circleindicator = (CirclePageIndicator) rootView.findViewById(R.id.indicatorhome);
circleindicator.setViewPager(pager);
pageSwitcher(); //This method will change the images automatically after a certain period of time
return rootView;
}
public static Timer getTimerValue()
{
return timer;
}
private void pageSwitcher() {
timer = new Timer(); // At this line a new Thread will be created
timer.scheduleAtFixedRate(new RemindTask(), 0, 3 * 1000);
// Delay in milliseconds
}
// this is an inner class...
class RemindTask extends TimerTask {
//Still to be executed, on manual change page
// Thought!! on pagechangelistener() set the pager.setCurrentItem to current position
//Find a way to determine the current position
//and when you find the current position update page and page1 items accordingly.
public void run() {
// As the TimerTask run on a seprate thread from UI thread we have
// to call runOnUiThread to do work on UI thread.
getActivity().runOnUiThread(new Runnable() {
public void run() {
if(page>8)
{
//This code will execute right to left
//Here page1 is decrement with the starting value of 8 equal to the number of pages
//On Reaching zero it should take the control to the else statement and execute
//left to right
//Managing manual view pager changes
y = pager.getCurrentItem();
y--;
page1 = y;
//managed
pager.setCurrentItem(page1--);
if(page1==-1)
{
page=-1;
flag=0;
}
}
else
{
//This code will execute from left to right.
//where page is the page number (total images - here 8)
//On reaching the end where page = 8, page 1 will set to 8 and then move
//right to left
//Managing manual view pager changes
if(flag==0)
{
int x = pager.getCurrentItem();
page = x;
flag = 1;
}
else
{
int x = pager.getCurrentItem();
x++;
page = x;
}
//managed
pager.setCurrentItem(page++);
if(page==8)
{
page1=8;
}
}
}
});
}
}
//This adapter is for the images on the top of home screen, the sliding images
private class ImagePagerAdapter extends PagerAdapter {
private String[] images;
ImagePagerAdapter(String[] images) {
this.images = images;
}
@Override
public void destroyItem(ViewGroup container, int position, Object object) {
container.removeView((View) object);
}
@Override
public int getCount() {
return images.length;
}
@Override
public Object instantiateItem(ViewGroup view, int position) {
View imageLayout = getLayoutInflater(getArguments()).inflate(R.layout.item_pager_image, view, false);
assert imageLayout != null;
ImageView imageView = (ImageView) imageLayout.findViewById(R.id.image);
final ProgressBar spinner = (ProgressBar) imageLayout.findViewById(R.id.loading);
imageLoader.displayImage(images[position], imageView, options, new SimpleImageLoadingListener() {
@Override
public void onLoadingStarted(String imageUri, View view) {
spinner.setVisibility(View.VISIBLE);
}
@Override
public void onLoadingComplete(String imageUri, View view, Bitmap loadedImage) {
spinner.setVisibility(View.GONE);
}
});
view.addView(imageLayout, 0);
return imageLayout;
}
@Override
public boolean isViewFromObject(View view, Object object) {
return view.equals(object);
}
@Override
public void restoreState(Parcelable state, ClassLoader loader) {
}
@Override
public Parcelable saveState() {
return null;
}
}
//End of adapter
}
Here's my logcat
How to solve this? What I did was in MainActivity called the timer variable and cancel it before the activity finishes. This is how I did it.
@Override
public void onBackPressed() {
if (doubleBackToExitPressedOnce) {
Timer timer = Home.getTimerValue();
timer.cancel();
super.onBackPressed();
return;
}
this.doubleBackToExitPressedOnce = true;
Toast.makeText(this, "Press Again to Exit", Toast.LENGTH_SHORT).show();
}
If I'm on the MainActivity and I press back twice I don't get a NPE. But if I navigate to another activity and come back to the MainActivity I get this exception again.