2017-08-25 35 views
0

我通過使用回收站視圖來顯示天氣的列表每天一個星期的教程要設置的onClick用於查看持有人回收視圖。 有兩類對此我在困惑:我們爲什麼使用接口在MainActivity

ForecastAdapter和MainActivity

下面是上述兩個類代碼:

ForecastAdapter.java

public class ForecastAdapter extends RecyclerView.Adapter<ForecastAdapter.ForecastAdapterViewHolder> { 

    private String[] mWeatherData; 
    final private ForecastAdapterOnClickListener mClickHandler; 

    //Why do we need to create an interface here. 
    public interface ForecastAdapterOnClickListener { 
     void onClick(String weatherForDay); 
    } 

    public ForecastAdapter(ForecastAdapterOnClickListener forecastAdapterOnClickListener) { 
     mClickHandler = forecastAdapterOnClickListener; 
    } 


    public class ForecastAdapterViewHolder extends RecyclerView.ViewHolder implements View.OnClickListener{ 
     public final TextView mWeatherTextView; 

     public ForecastAdapterViewHolder(View view) { 
      super(view); 
      mWeatherTextView = (TextView) view.findViewById(R.id.tv_weather_data); 
      view.setOnClickListener(this); 
     } 

     @Override 
     public void onClick(View v) { 
      int adapterPosition = getAdapterPosition(); 
      String weatherForDay = mWeatherData[adapterPosition]; 

      //Why are we calling onClick from mClickHandler here. Why can't we just display Toast here. 
      mClickHandler.onClick(weatherForDay); 

      /*Why can't we just display the Toast from here like this: 
       Toast.makeText(v.getContext(), weatherForDay, Toast.LENGTH_SHORT).show() 
      */ 
     } 

    } 


    @Override 
    public ForecastAdapterViewHolder onCreateViewHolder(ViewGroup viewGroup, int viewType) { 
     Context context = viewGroup.getContext(); 
     int layoutIdForListItem = R.layout.forecast_list_item; 
     LayoutInflater inflater = LayoutInflater.from(context); 
     boolean shouldAttachToParentImmediately = false; 

     View view = inflater.inflate(layoutIdForListItem, viewGroup, shouldAttachToParentImmediately); 
     return new ForecastAdapterViewHolder(view); 
    } 


    @Override 
    public void onBindViewHolder(ForecastAdapterViewHolder forecastAdapterViewHolder, int position) { 
     String weatherForThisDay = mWeatherData[position]; 
    forecastAdapterViewHolder.mWeatherTextView.setText(weatherForThisDay); 
    } 


    @Override 
    public int getItemCount() { 
     if (null == mWeatherData) return 0; 
     return mWeatherData.length; 
    } 


    public void setWeatherData(String[] weatherData) { 
     mWeatherData = weatherData; 
     notifyDataSetChanged(); 
    } 
} 




MainActivity.java

//Why are implementing ForecastAdapterOnClickListener here? 
public class MainActivity extends AppCompatActivity implements ForecastAdapter.ForecastAdapterOnClickListener{ 

private RecyclerView mRecyclerView; 
private ForecastAdapter mForecastAdapter; 

private TextView mErrorMessageDisplay; 

private ProgressBar mLoadingIndicator; 

@Override 
protected void onCreate(Bundle savedInstanceState) { 
    super.onCreate(savedInstanceState); 
    setContentView(R.layout.activity_forecast); 

    mRecyclerView = (RecyclerView) findViewById(R.id.recyclerview_forecast); 
    mErrorMessageDisplay = (TextView) findViewById(R.id.tv_error_message_display); 

    LinearLayoutManager layoutManager 
      = new LinearLayoutManager(this, LinearLayoutManager.VERTICAL, false); 

    mRecyclerView.setLayoutManager(layoutManager); 


    mRecyclerView.setHasFixedSize(true); 


    mForecastAdapter = new ForecastAdapter(this); 
    mRecyclerView.setAdapter(mForecastAdapter); 


    mLoadingIndicator = (ProgressBar) findViewById(R.id.pb_loading_indicator); 

    loadWeatherData(); 
} 


private void loadWeatherData() { 
    showWeatherDataView(); 

    String location = SunshinePreferences.getPreferredWeatherLocation(this); 
    new FetchWeatherTask().execute(location); 
} 


@Override 
public void onClick(String weatherForDay) { 
    Context context = this; 
    Toast.makeText(context, weatherForDay, Toast.LENGTH_SHORT) 
      .show(); 
} 


private void showWeatherDataView() { 
    mErrorMessageDisplay.setVisibility(View.INVISIBLE); 
    mRecyclerView.setVisibility(View.VISIBLE); 
} 


private void showErrorMessage() { 
    mRecyclerView.setVisibility(View.INVISIBLE); 
    mErrorMessageDisplay.setVisibility(View.VISIBLE); 
} 

public class FetchWeatherTask extends AsyncTask<String, Void, String[]> { 

    @Override 
    protected void onPreExecute() { 
     super.onPreExecute(); 
     mLoadingIndicator.setVisibility(View.VISIBLE); 
    } 

    @Override 
    protected String[] doInBackground(String... params) { 
     if (params.length == 0) { 
      return null; 
     } 

     String location = params[0]; 
     URL weatherRequestUrl = NetworkUtils.buildUrl(location); 

     try { 
      String jsonWeatherResponse = NetworkUtils 
        .getResponseFromHttpUrl(weatherRequestUrl); 

      String[] simpleJsonWeatherData = OpenWeatherJsonUtils 
        .getSimpleWeatherStringsFromJson(MainActivity.this, jsonWeatherResponse); 

      return simpleJsonWeatherData; 

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

    @Override 
    protected void onPostExecute(String[] weatherData) { 
     mLoadingIndicator.setVisibility(View.INVISIBLE); 
     if (weatherData != null) { 
      showWeatherDataView(); 
      mForecastAdapter.setWeatherData(weatherData); 
     } else { 
      showErrorMessage(); 
     } 
    } 
} 

@Override 
public boolean onCreateOptionsMenu(Menu menu) { 
    MenuInflater inflater = getMenuInflater(); 
    inflater.inflate(R.menu.forecast, menu); 
    return true; 
} 

@Override 
public boolean onOptionsItemSelected(MenuItem item) { 
    int id = item.getItemId(); 

    if (id == R.id.action_refresh) { 
     mForecastAdapter.setWeatherData(null); 
     loadWeatherData(); 
     return true; 
    } 

    return super.onOptionsItemSelected(item); 
} 

}

的適配器,視圖保持器和再循環器視圖按預期方式工作。我們現在應該在回收站視圖的行上實施點擊處理。無論何時點擊某一行,我們都應該顯示一個敬酒。

如您所見,我們在ForecastAdapterViewHolder中實現了OnClickListener,在onClick函數中我們調用了界面「ForecastAdapterOnClickListener」的onClick。 在MainActivity.java,我們正在實施這種「ForecastAdapterOnClickListener」,然後顯示敬酒。

爲什麼我們不能只顯示在onclick敬酒是針對「ForecastAdapterViewHolder」類中定義。我已經嘗試過,它的工作原理。代碼中正在做什麼的要點是什麼? 這樣設置點擊監聽器有一些優勢嗎?

+0

我能做到這一點。我的問題是,在執行代碼中有什麼優勢? –

回答

0

因爲你必須事後顯示信息,而不是ViewHolder既不適配器的作用。活動/片段必須這樣做。 這是保持你的代碼組織。

相關問題