這是一個困難的問題,所以我附上了一張圖片以幫助可視化一點。 如何更改家長片段和RecyclerView視圖的顏色,取決於來自recyclerview的OnClickListener位置
所以我有一個recyclerview包含調色板的顏色。它通過爲每種顏色創建一個新的ImageView來加載顏色,然後更改每個imageview的顏色和drawable,併爲「selected color」設置不同的顏色。所選顏色也用於從父DialogFragment中更改工具欄的顏色。
問題在於OnClicklistener在經過數小時的研究之後根本沒有工作。現在,我不能在沒有應用程序崩潰的情況下使用OnClickListener。
現在,讓我們來看看實際的代碼和問題。 我將聲明(給你)一些變量和類我使用:
ArrayList<String> colorsList = //arraylist which contains all the colors which can be displayed
NewNotebookFragment = //DialogFragment, contains a toolbar, miscellaneous views and a rvNewNotebook
RecyclerView rvNewNotebook = //the recyclerview containing imageviews representing each individual color retrieved from colorsList
NewNotebookAdapter = adapter which is bound to rvNewNotebook
現在,我所做的是使NewNotebookFragment的方法稱爲changeColor可以接收一個int,表示位置的顏色被選中。 changeColor()更改工具欄的顏色。 changeColor()從onclickListener的onClick方法中調用,在NewNotebookAdapter的Viewholder中定義。 現在來看實際的代碼。
newNotebookFragment:
public class NewNotebookFragment extends DialogFragment {
RecyclerView rvNewNotebook;
int activeColor;
ArrayList<String> colors=Helpers.getPossibleColors();
@Override
public View onCreateView ...}
@Override
public void onViewCreated(View v, Bundle savedInstanceState){
activeColor=new Random().nextInt(colors.size());
toolbar = (Toolbar) v.findViewById(R.id.newnotebooktoolbar);
toolbar.setOnMenuItemClickListener(new Toolbar.OnMenuItemClickListener() {
@Override
public boolean onMenuItemClick(MenuItem item) {
return false;
}
});
toolbar.inflateMenu(R.menu.newnotebook);
toolbar.setTitle("Create new Notebook");
if(Helpers.isColorDark(Color.parseColor(colors.get(activeColor)))){
toolbar.setTitleTextColor(getResources().getColor(R.color.md_dark_primary_text));
}else{
toolbar.setTitleTextColor(getResources().getColor(R.color.md_light_primary_text));
}
rvNewNotebook = (RecyclerView) v.findViewById(R.id.rvNewNotebook);
final GridLayoutManager rvNotebookManager = new GridLayoutManager(getContext(),6);
rvNewNotebook.setLayoutManager(rvNotebookManager);
NewNotebookAdapter adapter= new NewNotebookAdapter(getContext(), Helpers.getPossibleColors(), activeColor);
toolbar.setBackgroundColor(Color.parseColor(Helpers.getPossibleColors().get(activeColor)));
rvNewNotebook.setAdapter(adapter);
Log.d("onViewCreated", ""+rvNewNotebook.getWidth());
}
@Override public void onResume(){...}
public static NewNotebookFragment newInstance() {...}
public void changeColor(int position){
if(Helpers.isColorDark(Color.parseColor(colors.get(position)))){
toolbar.setTitleTextColor(getResources().getColor(R.color.md_dark_primary_text));
}else{
toolbar.setTitleTextColor(getResources().getColor(R.color.md_light_primary_text));
}
toolbar.setBackgroundColor(Color.parseColor(Helpers.getPossibleColors().get(position)));
}
NewNotebookAdapter:
public class NewNotebookAdapter extends RecyclerView.Adapter<NewNotebookAdapter.ViewHolder>{
Context context;
ArrayList<String> colors = new ArrayList<>();
int activeColor;
public NewNotebookAdapter(){
}
public static class ViewHolder extends RecyclerView.ViewHolder implements View.OnClickListener{
public ImageView ivSwatch;
public Toolbar toolbar;
public ViewHolder(View itemView) {
super(itemView);
ivSwatch = (ImageView) itemView.findViewById(R.id.ivSwatch);
toolbar = (Toolbar) itemView.findViewById(R.id.newnotebooktoolbar);
ivSwatch.setOnClickListener(this);
}
@Override
public void onClick(View view) {
NewNotebookFragment newNotebookFragment = new NewNotebookFragment();
final int adapterPosition = ViewHolder.this.getAdapterPosition();
Log.d("OnClick. Adapter", "getAdapterPosition: "+adapterPosition);
newNotebookFragment.changeColor(adapterPosition);
}
}
public NewNotebookAdapter(Context context, ArrayList<String> colors, int activeColor){
this.context=context;
this.colors=colors;
this.activeColor=activeColor;
}
@Override
public ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
View v = LayoutInflater.from(parent.getContext()).inflate(R.layout.colorcircle,parent,false);
return new ViewHolder(v);
}
@Override
public void onBindViewHolder(ViewHolder holder, int position) {
Drawable drawablefull = ContextCompat.getDrawable(context,R.drawable.colorcircle);
Drawable drawableHollow = ContextCompat.getDrawable(context,R.drawable.coloroutlinecircle);
if (position==activeColor){
holder.ivSwatch.setImageDrawable(drawablefull.mutate());
}else if (position!=activeColor){
holder.ivSwatch.setImageDrawable(drawableHollow.mutate());
}
holder.ivSwatch.setColorFilter(Color.parseColor(colors.get(position)));
目前的問題我有如下堆棧跟蹤:
FATAL EXCEPTION: main
Process: com.twotowerstudios.virtualnotebookdesign, PID: 32272
java.lang.IllegalStateException: Fragment NewNotebookFragment{b10003e} not attached to Activity
at android.support.v4.app.Fragment.getResources(Fragment.java:648)
at com.twotowerstudios.virtualnotebookdesign.NewNotebookDialog.NewNotebookFragment.changeColor(NewNotebookFragment.java:85)
at com.twotowerstudios.virtualnotebookdesign.NewNotebookDialog.NewNotebookAdapter$ViewHolder.onClick(NewNotebookAdapter.java:49)
at android.view.View.performClick(View.java)
at android.view.View$PerformClick.run(View.java)
at android.os.Handler.handleCallback(Handler.java)
at android.os.Handler.dispatchMessage(Handler.java)
at android.os.Looper.loop(Looper.java)
at android.app.ActivityThread.main(ActivityThread.java)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java)
at de.robv.android.xposed.XposedBridge.main(XposedBridge.java:132)
現在我幾乎可以肯定這是有關我的onClick方法,它創建一個NewNotebookFragment的新實例,導致fr我在onClick方法中使用的實際上與已經被使用和顯示的方法不一樣。但是,我正在做這個主題,因爲我沒有真正的想法來解決整個問題。我不知道我怎麼能夠從onClick方法得到實際的NewNotebookFragment,所以我可以修改它或從中調用方法。我不知道是否曾經修復過如果它甚至可以工作或者其他任何問題。我怎麼能得到這個工作?
編輯:我得到它完美的工作。基本上我所做的是在Imageviews上的onBindViewHolder中定義setonclickListener。 clickListener將調用一個名爲AdapterInterface的接口,並在其中使用名爲clickListener的方法,該方法允許將顏色的int傳遞給父片段。該片段將實現在適配器中定義的接口,並使用傳遞給它的顏色並從中調用changeColor方法來覆蓋clickListener。如果將來有人需要示例,請隨時與我聯繫。相關更改在這兩個文件中,上傳到Github:https://gist.github.com/coldblade2000/0c2cac8b1af4df5985fe6cebebc9cff2鏈接包含一定級別的解釋和有關這兩個類別的文檔
我不是在我的電腦,但我認爲你只是引導我正確的軌道上的接口。我不知道他們是什麼時候。一旦完成,我會發布我的固定代碼。雖然我不明白。我怎麼能改變回收站的孩子?我是否會用我的片段中的另一個activeColor銷燬並重新創建recyclerview? – coldblade2000
您可以從附加的ArrayList中刪除/更改子索引(在您的情況下爲顏色),並使用notifyItemRemoved()或notifyItemChanged()更新回收視圖。或者如果您的整個顏色數據數組列表發生了更改,請使用notifyDataSetChanged() –