dat255.grupp06.bibbla.fragments.SearchFragment.java Source code

Java tutorial

Introduction

Here is the source code for dat255.grupp06.bibbla.fragments.SearchFragment.java

Source

/**
    Copyright 2012 Fahad Al-Khameesi, Madeleine Appert, Niklas Logren, Arild Matsson and Jonathan Orr.
    
    This file is part of Bibbla.

    Bibbla is free software: you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation, either version 3 of the License, or
    (at your option) any later version.

    Bibbla is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    GNU General Public License for more details.

    You should have received a copy of the GNU General Public License
    along with Bibbla.  If not, see <http://www.gnu.org/licenses/>.    
 **/

package dat255.grupp06.bibbla.fragments;

import java.io.UnsupportedEncodingException;
import java.net.URLEncoder;
import java.util.ArrayList;

import android.os.Bundle;
import android.support.v4.app.FragmentManager;
import android.support.v4.app.FragmentTransaction;
import android.util.Log;
import android.view.KeyEvent;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.view.inputmethod.EditorInfo;
import android.widget.Button;
import android.widget.EditText;
import android.widget.ProgressBar;
import android.widget.TextView;
import android.widget.TextView.OnEditorActionListener;
import android.widget.Toast;

import com.actionbarsherlock.app.SherlockFragment;

import dat255.grupp06.bibbla.R;
import dat255.grupp06.bibbla.backend.Backend;
import dat255.grupp06.bibbla.backend.BackendFactory;
import dat255.grupp06.bibbla.model.Book;
import dat255.grupp06.bibbla.utils.Callback;
import dat255.grupp06.bibbla.utils.Message;

/**
 * A fragment that holds the search bar, button 
 * and a ListFragment that displays search results
 * 
 * @author Jonathan Orr
 */
public class SearchFragment extends SherlockFragment {

   SearchListFragment listFragment;
   EditText searchEdit;
   Button searchButton;
   ProgressBar searchProgress;
   
   @Override
   public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
      
      FragmentManager fragmentManager = getFragmentManager();
        FragmentTransaction fragmentTransaction = fragmentManager.beginTransaction();
      
      if(listFragment == null) {
           listFragment = new SearchListFragment();
           fragmentTransaction.add(R.id.list_container, listFragment);
      } else {
         fragmentTransaction.attach(listFragment);
      }

        fragmentTransaction.commit();
      return inflater.inflate(R.layout.fragment_search, container, false);
   }
   
   @Override
   public void onDestroyView() {
      FragmentManager fragmentManager = getFragmentManager();
        FragmentTransaction fragmentTransaction = fragmentManager.beginTransaction();
        fragmentTransaction.detach(listFragment);
        fragmentTransaction.commit();
        super.onDestroyView();
   }
   
   @Override
   public void onActivityCreated(Bundle savedInstanceState) {
      super.onActivityCreated(savedInstanceState);
      
      // Get our GUI elements.
      searchButton = (Button)getSherlockActivity().findViewById(R.id.button_search);
      searchEdit = (EditText)getSherlockActivity().findViewById(R.id.edit_search);
      
      searchEdit.setTextColor(0xfff0641e);

      searchProgress = (ProgressBar)getSherlockActivity().findViewById(R.id.progress_search);
      
      // Create a listener for keyboard "enter" button.
      OnEditorActionListener listener = new OnEditorActionListener() {
          public boolean onEditorAction(TextView v, int actionId, KeyEvent event) {
              if (actionId == EditorInfo.IME_ACTION_SEARCH) {
                 // Simulate click on the search button.
                  searchButton.performClick();
                  return true;
              }
              return false;
          }
      };
      // Add our newly created listener to the text field.
      searchEdit.setOnEditorActionListener(listener);
   }
   
   /**
    * Starts searching procedure in backend.
    */
   public void searchClicked() {
      
      // Convert search string to UTF-8.
      String searchString = searchEdit.getText().toString();
      try {
         searchString = URLEncoder.encode(searchString, "UTF-8");
      } catch (UnsupportedEncodingException e) {}

      // Display progress bar.
      setProgressBarVisibility(true);
      
      // No input? No need to search.
      if("".equals(searchString)) {
         listFragment.updateList(new ArrayList<Book>());
         return;
      }
      
      // Create a new callback object, which refers to our searchDone(). 
      Callback c = new Callback() {
         public void handleMessage(Message msg) {
            SearchFragment.this.searchDone(msg);
         }
      };
      
      // Call backend search.
      BackendFactory.getBackend().search(searchString, 0, c);
      listFragment.setLastSearchString(searchString);
   }
   
   /**
    * Is used to get more search results after the first page has already been
    * fetched.
    * @param page - What page do you want?
    * @param searchString - What are you searching for?
    */
   public void getMoreSearchResults(int page, String searchString) {
      
      setProgressBarVisibility(true);
      
      // Create a new callback object, which refers to our searchDone(). 
      Callback c = new Callback() {
         public void handleMessage(Message msg) {
            SearchFragment.this.moreSearchDone(msg);
         }
      };
      
      // Call backend search.
      Log.d("Jonis", "searching..... on page    "+page);
      BackendFactory.getBackend().search(searchString, page, c);
   }
   
   /**
    * Is called from a callback object when backend searching is done.
    * @param msg - Message object that contains all the books that searchJob
    *             finds. Also the occasional error message.
    */
   public void searchDone(Message msg) {
      // Hide progress bar.
      setProgressBarVisibility(false);
      
      // Did the job fail?
      if (msg.error != null) {
         // Log,
         Log.e("searching", "Searching failed: "+msg.error);
         // And toast user.
         Toast.makeText(getSherlockActivity().getApplicationContext(), "Searching failed: "+msg.error, Toast.LENGTH_LONG).show();
         return;
      }
      // Convert results to ArrayList<Book>.  
      @SuppressWarnings("unchecked")
      ArrayList<Book> books = (ArrayList<Book>) msg.obj;
            
      // Did we get no results? 
      if (books.size() == 0) {
         Toast.makeText(getSherlockActivity().getApplicationContext(), "No results found.", Toast.LENGTH_LONG).show();
      }
      
      // Update list with titles (empty or not).
      listFragment.updateList(books);
   }
   
   /**
    * Is called from a callback object when backend searching is done.
    * It is different from searchDone since we want to append the search
    * results to the current list instead of replacing it.
    * @param msg - Contains the books found by the search job and also
    *             an error message if there was an error.
    */
   public void moreSearchDone(Message msg) {
      // Hide progress bar.
      setProgressBarVisibility(false);
      
      // Did the job fail?
      if (msg.error != null) {
         // Log,
         Log.e("searching", "Searching failed: "+msg.error);
         // And toast user.
         Toast.makeText(getSherlockActivity().getApplicationContext(), "Searching failed: "+msg.error, Toast.LENGTH_LONG).show();
         return;
      }
      // Convert results to List<Book>.  
      @SuppressWarnings("unchecked")
      ArrayList<Book> books = (ArrayList<Book>) msg.obj;
            
      // Did we get no results? 
      if (books.size() == 0) {
         Toast.makeText(getSherlockActivity().getApplicationContext(), "No results found.", Toast.LENGTH_LONG).show();
      }
      
      // Update list with titles (empty or not).
      listFragment.appendList(books);
   }
   
   /**
    * Changes the visibility of the progress bar.
    * @param visible - should we show or hide the progress bar? 
    */
   private void setProgressBarVisibility(boolean visible) {
      // Do only this if searchProgress exists.
      if (searchProgress != null) {
         // setVisibility takes an int.
         int visibilityCode = (visible) ? View.VISIBLE : View.GONE;
         searchProgress.setVisibility(visibilityCode);
      }
   }
}