从asyncTask传递数据到自定义适配器

时间:2016-05-01 13:31:40

标签: android android-asynctask

我正在上一门在线课程并为自学而制作一个Android应用程序。在这个应用程序中,我想在gridView中显示电影海报的缩略图。现在我的问题是如何将movies arrayList传递给asyncTask的自定义适配器。我可以用onPostExecute方法实现一些目标。我的意思是如何在asyncTask的onPostExecute方法中异步设置适配器的数据源? 这是我的代码。

    public class MainActivity extends AppCompatActivity {
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        FetchMovies mMovies = new FetchMovies(this);
        mMovies.execute("popularity.desc");
        GridView gridView= (GridView) findViewById(R.id.gridview);
        gridView.setAdapter(new CustomAdapter(this,new ArrayList<MovieContract>()));
        gridView.setOnItemClickListener(new AdapterView.OnItemClickListener() {
            public void onItemClick(AdapterView<?> parent, View v,
                                    int position, long id) {
                Toast.makeText(MainActivity.this, "" + position,
                        Toast.LENGTH_SHORT).show();
            }
        });
    }}


    public class CustomAdapter extends BaseAdapter {
    private Context mContext;
    private ArrayList<MovieContract> movie_list;
    public CustomAdapter(Context context, ArrayList<MovieContract> movie_list) {
        mContext = context;
        this.movie_list= movie_list;
    }
    @Override
    public int getCount() {
        return movie_list.size();
    }
    @Override
    public MovieContract getItem(int position) {

        return movie_list.get(position);
    }
    @Override
    public long getItemId(int position) {
        return 0;
    }
    @Override
    public View getView(int position, View convertView, ViewGroup parent) {
        ImageView imageView;
        if (convertView == null) {
            imageView = new ImageView(mContext);
            imageView.setLayoutParams(new GridView.LayoutParams(85, 85));
            imageView.setScaleType(ImageView.ScaleType.FIT_XY);
            imageView.setPadding(8, 8, 8, 8);
           Picasso.with(mContext).load("http://image.tmdb.org/t/p/w500/" + movie_list.get(position).getMovie_poster()).into(imageView);
        } else {
            imageView = (ImageView) convertView;
        }
     //      imageView.setImageResource(mThumbIds[position]);
        return imageView;
    }}


public class FetchMovies extends AsyncTask<String,Void,ArrayList<MovieContract>> {


private  CustomAdapter customAdapter;

private Context context;

private ArrayList<MovieContract> mMovie_list = new ArrayList<>();

private MovieContract mMovieContract;

private  String poster_path;



public final String LOG_Tag=FetchMovies.class.getSimpleName();

public FetchMovies(Context context) {
    this.context = context;
}

@Override
protected ArrayList doInBackground(String[] params) {
    HttpURLConnection urlConnection = null;
    BufferedReader reader = null;
    String MoviesJsonStr = null;

    String  Api_key= "xxxxxxxxxxxxxxxxxxxxxx";
    try {

        final String Movies_base="http://api.themoviedb.org/3/discover/movie?";
        final String Sort_param="sort_by";
        final String ApiKey_param="api_key";
        final String Image_Size="w500";

        Uri MovieUriBuilder=Uri.parse(Movies_base).buildUpon()
                                .appendQueryParameter(Sort_param,params[0])
                                .appendQueryParameter(ApiKey_param, Api_key)
                                .build();

        Log.v(LOG_Tag, "URI Builder" + MovieUriBuilder.toString());

        URL url=  new URL(MovieUriBuilder.toString());
        urlConnection=(HttpURLConnection)url.openConnection();
        urlConnection.setRequestMethod("GET");
        urlConnection.connect();

        InputStream inputStream= urlConnection.getInputStream();
        StringBuffer buffer= new StringBuffer();
        if(inputStream==null){
            MoviesJsonStr=null;
        }

       reader= new BufferedReader(new InputStreamReader(inputStream));
        String Result;
        while ((Result=reader.readLine())!=null){
            buffer.append(Result + '\n');

        }

        if (buffer.length() == 0) {

            MoviesJsonStr = null;
        }
        MoviesJsonStr = buffer.toString();
        Log.v(LOG_Tag,"Forecast Jason String " + MoviesJsonStr);

    }


    catch (IOException e){

        Log.e("FetchMovies", "Error ", e);
        MoviesJsonStr=null;


    }


    finally {
        if (urlConnection != null) {
            urlConnection.disconnect();
        }
        if (reader != null) {
            try {
                reader.close();
            } catch (final IOException e) {
                Log.e("PlaceholderFragment", "Error closing stream", e);
            }
        }
    }


    try {

        return ParseMoviesJsonString(MoviesJsonStr);
    } catch (JSONException e) {
        e.printStackTrace();
    }

    return null;
}


private ArrayList<MovieContract> ParseMoviesJsonString(String movieJsonStr ) throws JSONException{

    final String json_result="results";
    final String json_poster_path="poster_path";
    final String json_original_title="original_title";
    final String json_title="title";
    final String json_releaseDate="release_date";
    final String json_overview="overview";
    final String json_vote_average="vote_average";

    ArrayList<MovieContract> movie_list= new ArrayList<>();

    JSONObject MovieJson = new JSONObject(movieJsonStr);
    JSONArray MovieArray = MovieJson.getJSONArray(json_result);

    String[] resultStrs = new String[MovieArray.length()];

    for(int i = 0; i < MovieArray.length(); i++) {



        //JSONObject Movieobject = MovieArray.getJSONObject(i);
        JSONObject result_movie=MovieArray.getJSONObject(i);
        MovieContract movie = new MovieContract();
        movie.setTitle(result_movie.getString(json_original_title));
        movie.setMovie_poster(result_movie.getString(json_poster_path));
        movie.setPlot_synopsis(result_movie.getString(json_overview));
        movie.setRelease_date(result_movie.getString(json_releaseDate));
        movie.setVote_average(result_movie.getString(json_vote_average));

        movie_list.add(movie);





    }
    for (MovieContract result : movie_list){

        Log.v(LOG_Tag," preparing data " + result.getMovie_poster() +  "  " +result.getPlot_synopsis() );
    }



    return movie_list;

}


@Override
protected void onPostExecute(ArrayList<MovieContract> Movie_list) {


}}

2 个答案:

答案 0 :(得分:4)

将ActivityAdapter声明为活动中的实例变量:

private CustomAdapter customAdapter;

创建适配器并以这种方式设置RecyclerView适配器:

customAdapter = new CustomAdapter(this,new ArrayList<MovieContract>());
gridView.setAdapter(customAdapter);

为CustomAdapter创建更新数据方法:

public void updateMovies(ArrayList<MovieContract> movie_list) {
    this.movie_list= movie_list;
}

然后在onPostExecute:

customAdapter.updateMovies(movie_list);
customAdapter.notifyDataSetChanged();

答案 1 :(得分:1)

我总是这样做,以使异步任务更有用

在异步任务类中创建一个Object

OnResult onresult;

在您的异步任务中

创建一个接口

public interface OnResult{

public void onfinishprogress(ArrayList<> resultlist);

}


//create a method in async task

public void setOnResult(OnResult onresult)
{

this.onresult=onresult;

}

在你的onPostExecute(..)中设置结果

onPostExecute(ArrayList<MovieContract> Movie_list){

if(this.onresult!=null)
   this.onresult.onfinishprogress(Movie_list);

}

现在来了如何在MainActivity中获得结果

FetchMovies fmv=FetchMovies();
fmv.execute(url);
//now get the result from the interface created above

fmv.setOnResult(new OnResult(){

onfinishprogress(ArrayList<> resultlist)
{
    //here you get the resultlist which you passed up there.    
   gridView.setAdapter(customAdapter);
}

});