Android搜索小工具重新搜索?

时间:2014-04-22 23:36:11

标签: java android search

我有一个Activity来调用onSearchRequested()并打开YelpResultsActivity。一旦进入YelpResultsActivity,如果用户希望重新搜索而不回到之前的Activity,我希望能够打开搜索小部件并使用新查询重新搜索。我在清单中有singleTop并覆盖onSearchRequested()。即使使用测试“黄金”,它也会显示之前的搜索。它确实只在我YelpResultsActivity内部时调用,我通过日志消息测试它。我错过了什么?如何让用户在YelpResultsActivity内重新搜索?!

编辑:我注意到在第二次搜索后将视图更改为横向时,此功能正常。因此,如果我可以刷新视图而不会崩溃,我可以让它工作。

的AndroidManifest.xml

<activity
        android:label="@string/app_name"
        android:launchMode="singleTop"
        android:name=".YelpResultsActivity" >

        <!-- Setup the search configuration -->
        <meta-data
            android:name="android.app.searchable"
            android:resource="@xml/searchable" />

        <!-- Declare the intent for popup upon callback -->
        <intent-filter >
            <action android:name="android.intent.action.SEARCH" />
        </intent-filter>

        <intent-filter >
            <action android:name="android.intent.action.VIEW" />
        </intent-filter>
</activity>
<activity android:name="groupo.travellight.app.TripActivity"
        android:label="Trips"
        android:icon="@drawable/ic_action_trip">
        <!-- enable the search widget to send searches to YelpResultsActivity -->
        <meta-data android:name="android.app.default_searchable"
            android:value=".YelpResultsActivity" />
</activity>

TripActivity.java在菜单项

中调用搜索小部件
@Override
public boolean onOptionsItemSelected(MenuItem item) 
{        
    switch (item.getItemId()) 
    {
        case R.id.menu_yelpsearch:
            onSearchRequested(); //call search dialog
            return true;

        default:
            return super.onOptionsItemSelected(item);
    }
 }

YelpResultsActivity.java只使用自定义适配器获取结果并将其发布到自定义列表视图。

// Callback on creation of results activity
public void onCreate(Bundle savedInstanceState)
{
    super.onCreate(savedInstanceState);
    setTitle("Results"); //set the actionbar title
    handleIntent(getIntent());
}

// Callback detected from activity thread
public void onNewIntent(Intent intent)
{
    setIntent(intent);
    handleIntent(intent);
}

// Callback detected from the search dialog
// call the search logic
private void handleIntent(Intent intent)
{
    // If it was the action search intent search yelp
    if (Intent.ACTION_SEARCH.equals(intent.getAction()))
    {
        String query = intent.getStringExtra(SearchManager.QUERY);
        new SearchYelp().execute(query); //execute new thread and call the query
    }
}

@Override
public boolean onSearchRequested()
{
    new SearchYelp().execute("golf"); //execute new thread and call the query
    return true;
}

/**
 * Post the results of the SearchYelp thread
 */
private void postResults()
{
    ArrayList<HashMap<String, String>> sList = new ArrayList<HashMap<String, String>>();

    // For every item in the JSON bundle
    // add details from JSON string to a hashmap
    for (int i = 0; i < jsonResponse.getBundleSize(); i++)
    {
        HashMap<String, String> map = new HashMap<String, String>();

        // Yelp result strings, post parsed
        map.put(KEY_NAME, jsonResponse.getBusinessName(i));
        map.put(KEY_DESCRIPTION, jsonResponse.getSnippet(i));
        map.put(KEY_RATINGURL, jsonResponse.getRatingURL(i));
        map.put(KEY_THUMBURL, jsonResponse.getThumbURL(i));
        map.put(KEY_RATINGINT, jsonResponse.getRating(i));

        sList.add(map); //add the hashmap to the list
    }

    adapter = new CustomAdapter(this, sList); //send the details to the data adapter
    setListAdapter(adapter); //set the adapter for this activity as the custom adapter
}

/**
* Thread that accesses yelp API via JSON
 *
 * @author Brant Unger
 * @version 0.1
 */
class SearchYelp extends AsyncTask<String, Void, String>
{
    String stringJSON;

    /**
     * Functionality called in a seperate thread
     * @param query
     * @return String JSON formatted response
     */
    protected String doInBackground(String... query)
    {
        try
        {
            stringJSON = new Yelp().search(query[0], "Mesa, AZ");
            jsonResponse.setResponse(stringJSON);
            jsonResponse.parseBusiness(); //parse JSON data
        }
        catch (Exception e)
        {
            System.out.println(e.getMessage());
        }

        return stringJSON;
    }

    /**
     * Post the results of the query
     * @param query Search parameter called from above
     */
    protected void onPostExecute(String query)
    {
        postResults();
        }
    }
}

CustomAdapter.java

/**
 * Custom data adapter that places yelp data into the proper layout fields
 * @author Brant Unger
 * @version 0.2
 */
public class CustomAdapter extends BaseAdapter
{
     private ArrayList<HashMap<String, String>> data;
     private static LayoutInflater inflater;
     private Activity activity;

/**
 * Constructor for a custom data adapter to handle
 * posting yelp results to a custom user interface
 * @param activityCaller Activity The activity where the data is called from
 * @param dataCaller ArrayList The list containing a hashmap of yelp results
 */
public CustomAdapter(Activity activityCaller, ArrayList<HashMap<String, String>> dataCaller)
{
    activity = activityCaller;
    data = dataCaller;
    inflater = (LayoutInflater) activity.getSystemService(Context.LAYOUT_INFLATER_SERVICE);

}

/**
 * Inherited method from BaseAdapter that returns the size of
 * the data in the adapter
 * @return int The number of yelp results
 */
public int getCount()
{
    return data.size();
}

/**
 * Get the object
 * @param position The index of where the data is being held
 * @return The item's position
 */
public Object getItem(int position)
{
    return position;
}

/**
 * Get the item's numerical ID
 * @param position The index of where the data is being held
 * @return The item's position
 */
public long getItemId(int position)
{
    return position;
}

/**
 * Inherited method from BaseAdapter that returns an inflated
 * view generated via data held in the adapter
 * @param position The index of where the data is being held
 * @param convertView The view to grab and convert
 * @param parent The parent where the view can be found
 * @return View The view populated with data
 */
public View getView(int position, View convertView, ViewGroup parent)
{
    View viewInflater = convertView;
    if (convertView == null)
    {
        viewInflater = inflater.inflate(R.layout.custom_list_row, null);
    }

    // Define activity objects for use in posting the data into the UI
    TextView businessName = (TextView) viewInflater.findViewById(R.id.businessName);
    TextView description = (TextView) viewInflater.findViewById(R.id.description);
    TextView ratingInt = (TextView) viewInflater.findViewById(R.id.ratingInt);
    ImageView thumbImg = (ImageView) viewInflater.findViewById(R.id.list_image);
    ImageView ratingStars = (ImageView) viewInflater.findViewById(R.id.ratingImg);

    // Define a new result and set it at the current adapter index
    HashMap<String, String> result = new HashMap<String, String>();
    result = data.get(position);

    // Set all the UI details into the view
    businessName.setText(result.get(YelpResultsActivity.KEY_NAME));
    description.setText(result.get(YelpResultsActivity.KEY_DESCRIPTION));
    ratingInt.setText(result.get(YelpResultsActivity.KEY_RATINGINT));

    // Download and set the rating star and thumbnail images
    new DownloadImageTask(ratingStars)
            .execute(result.get(YelpResultsActivity.KEY_RATINGURL));
    new DownloadImageTask(thumbImg)
            .execute(result.get(YelpResultsActivity.KEY_THUMBURL));

    return viewInflater;
}

/**
 * Download thumbnail image and set it into the UI
 * via a separate thread
 */
private class DownloadImageTask extends AsyncTask<String, Void, Bitmap>
{
    ImageView bmImage;

    public DownloadImageTask(ImageView bmImage)
    {
        this.bmImage = bmImage;
    }

    /**
     * Download and set the image into the UI in the background.
     * @param urls String URL of the image location
     * @return Bitmap Returns the image to post
     */
    protected Bitmap doInBackground(String... urls)
    {
        String urldisplay = urls[0];
        Bitmap mIcon11 = null;
        try
        {
            InputStream in = new java.net.URL(urldisplay).openStream();
            mIcon11 = BitmapFactory.decodeStream(in);
        } catch (Exception e)
        {
            Log.e("Error", e.getMessage());
            e.printStackTrace();
        }
        return mIcon11;
    }

    /**
     * Call cleanup and set the image to the UI
     * @param result Image result
     */
    protected void onPostExecute(Bitmap result)
    {
        bmImage.setImageBitmap(result);
    }

}

}

1 个答案:

答案 0 :(得分:0)

改变这些做了我想做的事情:

//make this a class variable
ArrayList<HashMap<String, String>> sList = new ArrayList<HashMap<String, String>>(); 

// Callback detected from the search dialog
// call the search logic
private void handleIntent(Intent intent)
{
    // If the adapter is not null it means it has items in it
    // this means we are re-searching and need to reset the list
    // and adapter
    if (adapter != null)
    {
        sList.clear();
        finish();
        startActivity(intent);
    }

    // If it was the action search intent search yelp
    if (Intent.ACTION_SEARCH.equals(intent.getAction()))
    {
        String query = intent.getStringExtra(SearchManager.QUERY);
        new SearchYelp().execute(query); //execute new thread and call the query
    }
}

 /**
 * Post the results of the SearchYelp thread
 */
private void postResults()
{
    // For every item in the JSON bundle
    // add details from JSON string to a hashmap
    for (int i = 0; i < jsonResponse.getBundleSize(); i++)
    {
        HashMap<String, String> map = new HashMap<String, String>();

        // Yelp result strings, post parsed
        map.put(KEY_NAME, jsonResponse.getBusinessName(i));
        map.put(KEY_DESCRIPTION, jsonResponse.getSnippet(i));
        map.put(KEY_RATINGURL, jsonResponse.getRatingURL(i));
        map.put(KEY_THUMBURL, jsonResponse.getThumbURL(i));
        map.put(KEY_RATINGINT, jsonResponse.getRating(i));

        sList.add(map); //add the hashmap to the list
    }

    adapter = new CustomAdapter(this, sList); //send the details to the data adapter
    setListAdapter(adapter); //set the adapter for this activity as the custom adapter
}