I've successfully managed to extend a CursorAdapter and change the bindView- and newView-methods to be able to have clickable buttons inside my list. The button (which actually is a clickable ImageView) uses a selector as a backgroundresource, and everything works fine except that when I click the list-item-view, the selector of the button/imageview is activated and hence it appears as if I clicked the button/imageview even though I didn't. The method inside the onclicklistener that's bound to the button/imageview though, is not activated when clicking the list-item-view, so that works properly, it's only the selector. Here is my CustomCursorAdapter:
public class CustomCursorAdapter extends CursorAdapter {
Context context;
LayoutInflater inflater;
AlertDialog.Builder builder;
public CustomCursorAdapter(Context context, Cursor cursor, int flags) {
super(context, cursor, flags);
this.context = context;
inflater = LayoutInflater.from(context);
}
#Override
public void bindView(View view, Context c, Cursor cursor){
ViewHolder holder = (ViewHolder) view.getTag();
final Context context = c;
final String name = cursor.getString(cursor.getColumnIndex("name"));
final String number = cursor.getString(cursor.getColumnIndex("number"));
final String mail = cursor.getString(cursor.getColumnIndex("mail"));
holder.getTvName().setText(name);
holder.getTvNumber().setText(number);
holder.getTvMail().setText(mail);
int row_id = cursor.getInt(cursor.getColumnIndex("_id"));
holder.getCallButton().setTag(row_id);
holder.getCallButton().setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
builder = new AlertDialog.Builder(context);
builder.setMessage("Call " + name + "?")
.setPositiveButton("Call", new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog, int id) {
String uri = "tel:" + nummer.trim();
Intent intent = new Intent(Intent.ACTION_CALL);
intent.setData(Uri.parse(uri));
context.startActivity(intent);
}
})
.setNegativeButton("Cancel", new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog, int id) {
// User cancelled the dialog
}
});
builder.create().show();
}
});
}
#Override
public View newView(Context context, Cursor cursor, ViewGroup parent) {
View convertView = inflater.inflate(R.layout.contact_list_row, parent, false);
ViewHolder holder = new ViewHolder();
holder.setCallButton((ImageView) convertView.findViewById(R.id.bCall));
holder.setTvName((TextView) convertView.findViewById(R.id.tvName));
holder.setTvNumber((TextView) convertView.findViewById(R.id.tvNumber));
holder.setTvMail((TextView) convertView.findViewById(R.id.tvMail));
convertView.setTag(holder);
return convertView;
}
public static class ViewHolder {
private TextView tvName, tvNumber, tvMail;
private ImageView bCall;
public ImageView getCallButton() {
return bCall;
}
public void setCallButton(ImageView bCall) {
this.bCall = bCall;
}
public TextView getTvName() {
return tvName;
}
public void setTvName(TextView tvName) {
this.tvName = tvName;
}
public TextView getTvNumber() {
return tvNumber;
}
public void setTvNumber(TextView tvNumber) {
this.tvNumber = tvNumber;
}
public TextView getTvMail() {
return tvMail;
}
public void setTvMail(TextView tvMail) {
this.tvMail = tvMail;
}
}
}
This is the listView-XML:
<ListView
android:id="#+id/listView"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:cacheColorHint="#android:color/transparent"
android:listSelector="#android:color/transparent" />
And the contact_list_row.XML:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="#drawable/list_background"
android:orientation="horizontal" >
<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="vertical" >
<TextView
android:id="#+id/tvName"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
<TextView
android:id="#+id/tvNumber"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
<TextView
android:id="#+id/tvMail"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
</LinearLayout>
<ImageView
android:id="#+id/bCall"
android:background="#drawable/button"
android:clickable="true"
android:src="#drawable/ic_clean_phone" />
Selector:
<selector xmlns:android="http://schemas.android.com/apk/res/android" >
<item android:state_pressed="true" android:drawable="#drawable/h_main_button_background_pressed"></item>
<item android:drawable="#drawable/h_main_button_background"></item>
</selector>
If you find any other errors or unnecessary code, I'm very thankful for that too!
Related
I'm creating a shopping list similar to listonic app, but I'm stuck in listView, the button inside my listView does not read clicks but OnItemClickListener is working well. the objective is the user can save multiple shopping list for example grocery list, self-care list, etc. I have searched everywhere but did not find something that works.
here is the activity for the shopping list
private ArrayList<String> data = new ArrayList<String>();
private FloatingActionButton addList;
private ListView listView;
private TextView nList_name;
private DatabaseHelper dbHelper;
ArrayAdapter<String> mAdapter;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_my_lists);
dbHelper = new DatabaseHelper(this);
listView = findViewById(R.id.list_view);
addList = findViewById(R.id.add_list);
loadTaskList();
addList.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
add_item();
}
});
listView.setOnItemClickListener(new AdapterView.OnItemClickListener() {
#Override
public void onItemClick(AdapterView<?> adapterView, View view, int position, long l) {
Toast.makeText(MyListsActivity.this, "list num "+position, Toast.LENGTH_SHORT).show();
}
});
}
private class MyListAdapter extends ArrayAdapter<String>
{
private final int layout;
public MyListAdapter(#NonNull Context context, int resource, #NonNull List<String> objects) {
super(context, resource, objects);
layout = resource;
}
#NonNull
#Override
public View getView(int position, #Nullable View convertView, #NonNull ViewGroup parent) {
ViewHolder viewHolder;
final int pos = position;
if (convertView == null)
{
LayoutInflater inflater = LayoutInflater.from(getContext());
convertView = inflater.inflate(layout, parent, false);
viewHolder = new ViewHolder();
viewHolder.thumbnail = convertView.findViewById(R.id.list_item_thumbnail);
viewHolder.title = convertView.findViewById(R.id.list_item_text);
viewHolder.button = convertView.findViewById(R.id.list_item_btn);
}
else
{
viewHolder = (ViewHolder) convertView.getTag();
}
viewHolder.title.setText(getItem(position));
viewHolder.button.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
Toast.makeText(MyListsActivity.this, "btn at row "+position, Toast.LENGTH_SHORT).show();
}
});
convertView.setTag(viewHolder);
return convertView;
}
}
public static class ViewHolder
{
ImageView thumbnail;
TextView title;
Button button;
}
private void add_item()
{
AlertDialog.Builder builder = new AlertDialog.Builder(MyListsActivity.this);
builder.setTitle("Add new list");
View v = LayoutInflater.from(MyListsActivity.this).inflate(R.layout.shop_list_dialog_item, null, false);
builder.setView(v);
TextInputEditText nList_name_edit_txt = v.findViewById(R.id.list_name_edit_txt);
TextInputLayout nList_name_layout = v.findViewById(R.id.list_name_layout);
builder.setPositiveButton("CREATE", new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialogInterface, int i){}
}).setNegativeButton("CANCEL", new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialogInterface, int i) {dialogInterface.cancel();}
});
AlertDialog dialog = builder.create();
dialog.show();
dialog.getButton(AlertDialog.BUTTON_POSITIVE).setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view)
{
String task = String.valueOf(nList_name_edit_txt.getText()).trim();
if (!TextUtils.isEmpty(nList_name_edit_txt.getText()))
{
dbHelper.insertNewTask(task);
loadTaskList();
dialog.cancel();
}
else{nList_name_layout.setError("Name your list");}
}
});
}
private void loadTaskList() {
ArrayList<String> taskList = dbHelper.getTaskList();
if(mAdapter==null){
mAdapter = new ArrayAdapter<String>(this, R.layout.list_wrapper_item, R.id.list_item_text, taskList);
listView.setAdapter(mAdapter);
}
else{
mAdapter.clear();
mAdapter.addAll(taskList);
mAdapter.notifyDataSetChanged();
}
}
}
this is the xml for the shopping list activity
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".MyListsActivity">
<com.google.android.material.floatingactionbutton.FloatingActionButton
android:id="#+id/add_list"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginEnd="30dp"
android:layout_marginBottom="30dp"
android:clickable="true"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:srcCompat="#drawable/ic_baseline_add_24" />
<ListView
android:id="#+id/list_view"
android:layout_width="match_parent"
android:layout_height="match_parent"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" >
</ListView>
</androidx.constraintlayout.widget.ConstraintLayout>
and this is the layout for the adapter
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:descendantFocusability="blocksDescendants">
<ImageView
android:id="#+id/list_item_thumbnail"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginStart="30dp"
android:layout_marginTop="30dp"
android:layout_marginBottom="30dp"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:srcCompat="#drawable/ic_baseline_image_24" />
<TextView
android:id="#+id/list_item_text"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginStart="30dp"
android:layout_marginTop="30dp"
android:layout_marginBottom="30dp"
android:textColor="#color/youtube"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintStart_toEndOf="#+id/list_item_thumbnail"
app:layout_constraintTop_toTopOf="parent" />
<Button
android:id="#+id/list_item_btn"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="30dp"
android:layout_marginEnd="30dp"
android:layout_marginBottom="30dp"
android:focusable="false"
android:focusableInTouchMode="false"
android:text="Button"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintTop_toTopOf="parent" />
</androidx.constraintlayout.widget.ConstraintLayout>
Your MyListAdapter works as it should except int position should be final int position because button calls it from inner class.
The problem is that you are not using MyListAdapter. So change
mAdapter = new ArrayAdapter<String>(this, R.layout.list_wrapper_item, R.id.list_item_text, taskList);
To
mAdapter = new MyListAdapter(this, R.layout.list_wrapper_item, taskList);
This question already has answers here:
What is a NullPointerException, and how do I fix it?
(12 answers)
Closed 4 years ago.
I am facing issue when i try to access the textview id from layout and set that id in my adapter class. It gives null pointer exception .How do I access the textview in adapter class.
Following is the code
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/gridCatalogProductContainer"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_gravity="center"
android:descendantFocusability="blocksDescendants"
android:orientation="vertical"
android:padding="2dp">
<com.android.ordering.newui.CustomSquareLayout
android:id="#+id/frame"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
>
<ImageView
android:id="#+id/gridViewImage"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:adjustViewBounds="true"
android:scaleType="fitXY"
android:src="#drawable/catalog_image_selector" />
<TextView
android:id="#+id/gridCatalogProducttNametextView"
android:layout_width="#dimen/image_width"
android:layout_height="#dimen/image_height"
android:layout_gravity="center"
android:background="#color/header_background"
android:fontFamily="serif"
android:gravity="center"
android:padding="5dp"
android:text="New Text"
android:textColor="#color/white"
android:textSize="18sp" />
<TextView
android:id="#+id/gridViewImageTitle"
android:layout_width="#dimen/catalog_image_size"
android:layout_height="wrap_content"
android:layout_gravity="bottom"
android:layout_marginBottom="10dp"
android:gravity="center"
android:maxLines="1"
android:visibility="gone"
android:singleLine="false"
android:text=""
android:textAppearance="#style/white_text_appearance"
android:textSize="#dimen/grid_item_text_view_size" />
</com.android.emobilepos.ordering.newui.CustomSquareLayout>
</FrameLayout>
Below is my complete adapter class code where i got the crash when trying to set data in textview.
public class ProductCatalogAdapter extends CursorAdapter {
private final String attrToDisplay;
private final DisplayImageOptions options;
private OrderingMainCallback callback;
private LayoutInflater inflater;
MyPreferences preferences;
private ImageLoader imageLoader;
public ProductCatalogAdapter(OrderingMainCallback callback, Context context, Cursor c, boolean autoRequery) {
super(context, c, autoRequery);
this.callback = callback;
inflater = LayoutInflater.from(context);
preferences = new MyPreferences(context);
this.imageLoader = ImageLoader.getInstance();
File cacheDir = new File(preferences.getCacheDir());
if (!cacheDir.exists())
cacheDir.mkdirs();
ImageLoaderConfiguration config = new ImageLoaderConfiguration.Builder(context).memoryCacheExtraOptions(100, 100)
.discCacheExtraOptions(1000, 1000, Bitmap.CompressFormat.JPEG, 100, null).discCache(new UnlimitedDiscCache(cacheDir)).build();
imageLoader.init(config);
imageLoader.handleSlowNetwork(true);
attrToDisplay = preferences.getPreferencesValue(MyPreferences.pref_attribute_to_display);
options = new DisplayImageOptions.Builder().resetViewBeforeLoading(true).displayer(new SimpleBitmapDisplayer()).cacheOnDisc(true)
.imageScaleType(ImageScaleType.IN_SAMPLE_INT)
.showImageOnLoading(R.drawable.loading_image)
// .showImageForEmptyUri(R.drawable.no_image)
.build();
}
#Override
public View newView(Context context, Cursor cursor, ViewGroup parent) {
View retView;
ViewHolder holder = new ViewHolder();
retView = inflater.inflate(R.layout.catalog_listview_adapter, parent, false);
holder.title = retView.findViewById(R.id.gridViewImageTitle);
holder.itemImage = retView.findViewById(R.id.gridViewImage);
holder.productNameTxt = retView.findViewById(R.id.gridCatalogProducttNametextView);
holder.prodNameIdx = cursor.getColumnIndex(attrToDisplay);
holder.prodIdIdx = cursor.getColumnIndex("_id");
holder.prodImgNameIdx = cursor.getColumnIndex("prod_img_name");
retView.setTag(holder);
return retView;
}
#Override
public void bindView(View view, Context context, final Cursor cursor) {
final ViewHolder holder = (ViewHolder) view.getTag();
holder.productNameTxt.setText(cursor.getString(holder.prodNameIdx));
holder.productNameTxt.setVisibility(View.INVISIBLE);
holder.title.setText(cursor.getString(holder.prodNameIdx));
String urlLink = cursor.getString(holder.prodImgNameIdx);
// holder.itemImage.setOnClickListener(new View.OnClickListener() {
// #Override
// public void onClick(View v) {
// if (preferences.isFastScanningMode()) {
// callback.addProduct(cursor.getString(holder.prodIdIdx));
// }
// }
// });
imageLoader.displayImage(urlLink, holder.itemImage, options, new ImageLoadingListener() {
#Override
public void onLoadingStarted(String s, View view) {
if (TextUtils.isEmpty(s)) {
holder.productNameTxt.setVisibility(View.VISIBLE);
holder.itemImage.setVisibility(View.GONE);
}else {
holder.productNameTxt.setVisibility(View.INVISIBLE);
holder.itemImage.setVisibility(View.VISIBLE);
}
}
#Override
public void onLoadingFailed(String s, View view, FailReason failReason) {
holder.productNameTxt.setVisibility(View.VISIBLE);
holder.itemImage.setVisibility(View.GONE);
}
#Override
public void onLoadingComplete(String s, View view, Bitmap bitmap) {
if (TextUtils.isEmpty(s)) {
holder.productNameTxt.setVisibility(View.VISIBLE);
holder.itemImage.setVisibility(View.GONE);
}else {
holder.productNameTxt.setVisibility(View.INVISIBLE);
holder.itemImage.setVisibility(View.VISIBLE);
}
}
#Override
public void onLoadingCancelled(String s, View view) {
}
});
if(TextUtils.isEmpty(urlLink)){
}
}
public class ViewHolder {
CustomSquareLayout customSquareLayout;
TextView title, productNameTxt;
ImageView itemImage;
int prodNameIdx;
public int prodIdIdx;
int prodImgNameIdx;
}
}
<com.android.ordering.newui.CustomSquareLayout
android:id="#+id/frame"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
>
</com.android.emobilepos.ordering.newui.CustomSquareLayout>
Your CustomSquareLayout start and end is not same i.e the package path is different and should be same.
I tried all the solution that i found here in the stackoverflow but it seems like none of them work.
Here is my main activity:
public class MerchantLocatorActivity extends AppCompatActivity implements OnMapReadyCallback {
public void init(){
merchantLocatorResponseObject = new MerchantLocatorResponse();
merchantLocatorResponseObject.setTitle("Spherical");
merchantLocatorResponseObject.setAddress("8007 Pioneer St, Kapitolyo, Mandaluyong, 1550 Metro Manila");
merchantLocatorResponseObject.setLatitude( 14.573249);
merchantLocatorResponseObject.setLongitude(121.057022);
merchantLocatorObjectArray.add(merchantLocatorResponseObject);
merchantLocatorResponseObject = new MerchantLocatorResponse();
merchantLocatorResponseObject.setTitle("Globe");
merchantLocatorResponseObject.setAddress("SCT, 584 Shaw Blvd, Mandaluyong, 1552 Metro Manila");
merchantLocatorResponseObject.setLatitude(14.585095);
merchantLocatorResponseObject.setLongitude(121.048893);
merchantLocatorObjectArray.add(merchantLocatorResponseObject);
merchantLocatorResponseObject = new MerchantLocatorResponse();
merchantLocatorResponseObject.setTitle("Sparndium");
merchantLocatorResponseObject.setAddress("Xavier, San Juan, 1502 Metro Manila");
merchantLocatorResponseObject.setLatitude(14.601918);
merchantLocatorResponseObject.setLongitude(121.042169);
merchantLocatorObjectArray.add(merchantLocatorResponseObject);
addMarker();
}
#OnClick(R.id.fab)
public void showAccToDialog() {
AlertDialog.Builder alertDialogBuilder = new AlertDialog.Builder(this);
View alertView = LayoutInflater.from(this).inflate(R.layout.dialog_biller, null);
alertDialogBuilder.setView(alertView);
final AlertDialog dialog = alertDialogBuilder.create();
dialog.show();
final ListView listViewBillers = (ListView) dialog.findViewById(R.id.biller_institutions_listview);
if (listViewBillers != null) {
MerchantLocatorAdapter adapter = new MerchantLocatorAdapter(
this, R.layout.merchant_locator_adapter, merchantLocatorObjectArray);
listViewBillers.setAdapter(adapter);
listViewBillers.setOnItemClickListener(new AdapterView.OnItemClickListener() {
#Override
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
geoLocate(merchantLocatorObjectArray,position);
DebugUtils.log("TESTTESTACTIVITYZXC");
DebugUtils.showToast(MerchantLocatorActivity.this,"HAHAHAH");
dialog.dismiss();
}
});
final EditText mSearchedittext = (EditText) dialog.findViewById(R.id.search_edittext);
mSearchedittext.addTextChangedListener(new TextWatcher() {
#Override
public void beforeTextChanged(CharSequence charSequence, int i, int i1, int i2) {
}
#Override
public void onTextChanged(CharSequence charSequence, int i, int i1, int i2) {
final ArrayList<MerchantLocatorResponse> searchResultObject = new ArrayList<>();
searchResultObject.clear();
for (int hay = 0; hay <= merchantLocatorObjectArray.size() - 1; hay++) {
if ( merchantLocatorObjectArray.get(hay).getTitle().toLowerCase().contains(charSequence)) {
searchResultObject.add( merchantLocatorObjectArray.get(hay));
}
}
MerchantLocatorAdapter adapter = new MerchantLocatorAdapter(
MerchantLocatorActivity.this, R.layout.merchant_locator_adapter, searchResultObject);
listViewBillers.setAdapter(adapter);
listViewBillers.setOnItemClickListener(new AdapterView.OnItemClickListener() {
#Override
public void onItemClick(AdapterView<?> adapter, View view, int position, long arg) {
geoLocate(searchResultObject,position);
dialog.dismiss();
}
});
}
#Override
public void afterTextChanged(Editable editable) {
}
});
}
}
}
i remove some part of the code because i think it's un necessary to include but let me know if there's some part that i need some clarification.
currently in my main activity, i'm calling a dialog that contains a listview and in my listview i have items.
My problem is i can't select any of my items even thought i have my setOnitemclick listener.
here is my adapter:
public class MerchantLocatorAdapter extends BaseAdapter {
private int resourceLayout;
private Context mContext;
ArrayList<MerchantLocatorResponse> merchantLocatorarray = new ArrayList<>();
public MerchantLocatorAdapter(Context context, int resource, ArrayList<MerchantLocatorResponse> merchantLocatorResponsesobjectArray) {
this.resourceLayout = resource;
this.mContext = context;
this.merchantLocatorarray = merchantLocatorResponsesobjectArray;
}
#Override
public int getCount() {
return merchantLocatorarray.size();
}
#Override
public Object getItem(int position) {
return null;
}
#Override
public long getItemId(int position) {
return 0;
}
#Override
public View getView(final int position, View convertView, ViewGroup parent) {
if (convertView == null) {
LayoutInflater inflater = (LayoutInflater) mContext
.getSystemService(mContext.LAYOUT_INFLATER_SERVICE);
convertView = inflater.inflate(resourceLayout, parent, false);
}
TextView tt1 = (TextView) convertView.findViewById(R.id.field_name_textview);
TextView tt2 = (TextView) convertView.findViewById(R.id.field_value_textview);
ImageButton direction = (ImageButton) convertView.findViewById(R.id.direction);
tt1.setText(merchantLocatorarray.get(position).getTitle());
tt2.setText(merchantLocatorarray.get(position).getAddress());
return convertView;
}
}
here is my layout for my adapter:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:card_view="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="wrap_content">
<android.support.v7.widget.CardView
android:id="#+id/card_view"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_gravity="center"
android:layout_margin="8dp"
android:elevation="3dp">
<LinearLayout
android:id="#+id/card_overflow"
android:focusable="true"
android:clickable="true"
android:background="#fff"
android:paddingLeft="16dp"
android:paddingRight="0dp"
android:paddingTop="10dp"
android:paddingBottom="10dp"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical">
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:weightSum="1">
<TextView
android:id="#+id/field_name_textview"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginBottom="5dp"
android:layout_toLeftOf="#+id/branch_btns"
android:layout_alignParentLeft="true"
android:textSize="17sp"
android:textStyle="bold"
android:textColor="#color/edittext_text"
android:text="test"/>
<LinearLayout
android:id="#+id/branch_btns"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentRight="true"
android:orientation="horizontal"
>
<ImageButton
android:id="#+id/direction"
android:layout_width="50sp"
android:layout_height="wrap_content"
android:src="#drawable/ic_direction"
android:scaleType="fitCenter"
android:background="#color/translucent_clear_bg"
/>
<ImageButton
android:id="#+id/btn_branch_phone"
android:layout_width="50sp"
android:layout_height="wrap_content"
android:src="#drawable/ic_call_phone"
android:scaleType="fitCenter"
android:background="#color/translucent_clear_bg"
/>
</LinearLayout>
</RelativeLayout>
<View
android:id="#+id/seperator"
android:layout_width="match_parent"
android:layout_height="2dp"
android:layout_marginBottom="5dp"
android:background="#android:color/darker_gray"
android:visibility="gone"
android:layout_marginTop="2dp"/>
<TextView
android:id="#+id/field_value_textview"
android:textSize="14sp"
android:textColor="#color/edittext_tint"
android:layout_marginTop="5dp"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="test"/>
</LinearLayout>
</android.support.v7.widget.CardView>
</LinearLayout>
i tried every solution that i found here in stackoverflow, and yet i can't still click my item. so please don't mark this as a duplicate.
if there's any part of the code that need clarification, please leave a comment and i'll answer as soon as possible. thanks.
Try to use Observable in you custom adapter:
// Define
private final PublishSubject<MerchantLocatorResponse> onItemClick = PublishSubject.create();
// Create the observable method
public Observable<ConversationMessage> getObservable(){
return onItemClick;
}
// Set the onClickListener into getView()
convertView.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
onItemClick.onNext(merchantLocatorarray.get(position));
}
});
Then, in your main activity listen to it and handle the click:
#OnClick(R.id.fab)
public void showAccToDialog() {
// bla bla bla
listViewBillers.setAdapter(adapter);
listViewBillers.getObservable().subscribe(geoLocate);
// bla bla bla
}
Consumer<MerchantLocatorResponse> geoLocate = new Consumer<MerchantLocatorResponse>() {
#Override
public void accept(MerchantLocatorResponse mlr) {
// Code after click event
}
};
Add those library in your gradle:
implementation "io.reactivex.rxjava2:rxjava:2.1.5"
implementation "io.reactivex.rxjava2:rxandroid:2.0.1"
Add convertView.setOnclickListener() in your code. Try below code in your adapter
#Override
public View getView(final int position, View convertView, ViewGroup parent) {
if (convertView == null) {
LayoutInflater inflater = (LayoutInflater) mContext
.getSystemService(mContext.LAYOUT_INFLATER_SERVICE);
convertView = inflater.inflate(resourceLayout, parent, false);
}
TextView tt1 = (TextView) convertView.findViewById(R.id.field_name_textview);
TextView tt2 = (TextView) convertView.findViewById(R.id.field_value_textview);
ImageButton direction = (ImageButton) convertView.findViewById(R.id.direction);
tt1.setText(merchantLocatorarray.get(position).getTitle());
tt2.setText(merchantLocatorarray.get(position).getAddress());
convertView.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
Toast.makeText(context, String.valueOf(position), Toast.LENGTH_SHORT).show();
}
});
return convertView;
} }
I try to display some items in a Gridview and set button click listener. When the item was clicked, it shows a dialog box, if clicking yes, it will change the Imageview.
java coding
public class table extends AppCompatActivity implements AdapterView.OnItemClickListener{
GridView gridView;
my_adapter my_adapter;
String table_names[]={"1a","1b","1c","1d","2a","2b","2c","2d","3a","3b","3c","3d"};
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_table);
gridView=(GridView)findViewById(R.id.gridview);
my_adapter=new my_adapter(this,table_names);
gridView.setAdapter(my_adapter);
gridView.setOnItemClickListener(this);
}
#Override
public void onItemClick(final AdapterView<?> adapterView, final View view, final int i, long l) {
new AlertDialog.Builder(this)
.setTitle("Table number: "+adapterView.getItemAtPosition(i).toString())
.setMessage("Open Table?")
.setPositiveButton("Yes", new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialog, int which) {
my_adapter.change_img(); // change to new image
}
})
.setNegativeButton("No", new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialog, int which) {
my_adapter.change_img2(); // change back to original image
}
})
.show();
}
}
class my_adapter extends BaseAdapter{
ImageView imageView;
LayoutInflater inflater=null;
Context ctx;
String table_names[];
ArrayList store_table_no;
my_adapter(Context ctx, String table_names[]){
this.ctx=ctx;
this.table_names=table_names;
store_table_no=new ArrayList<Integer>();
for (int i=0;i<table_names.length;i++){
store_table_no.add(table_names[i]);
}
}
#Override
public int getCount() {
return store_table_no.size();
}
#Override
public Object getItem(int i) {
return store_table_no.get(i);
}
#Override
public long getItemId(int i) {
return i;
}
#Override
public View getView(int i, View view, ViewGroup viewGroup) {
View row=view;
if(row==null){
inflater=(LayoutInflater)ctx.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
row=inflater.inflate(R.layout.single,null);
}
TextView tv_table_no=(TextView)row.findViewById(R.id.table_no);
imageView=(ImageView)row.findViewById(R.id.imageView);
tv_table_no.setText(""+store_table_no.get(i));
return row;
}
public void change_img(){
imageView.setImageResource(R.drawable.table_full);
}
public void change_img2(){
imageView.setImageResource(R.drawable.table3d2);
}
}
single.xml
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:orientation="vertical" android:layout_width="match_parent"
android:layout_height="match_parent">
<TextView
android:text="101"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="#+id/table_no"
android:layout_centerHorizontal="true"
android:layout_centerVertical="true"
android:textSize="22sp" />
<ImageView
app:srcCompat="#drawable/table"
android:id="#+id/imageView"
android:layout_centerHorizontal="true"
android:layout_centerVertical="true"
android:layout_width="130dp"
android:layout_height="100dp" />
</RelativeLayout>
Here is a screenshot, please have a look
It simply doesn't change the imageview. Looks like something is wrong with my coding. anyone knows what's happening ?
You are implementing GridView's OnItemClickListener to show a dialog and getting decision from user for each item. When you are showing up a dialog it needs to update current clicked item of grid. But in your case you have change_img() in adapter. No position specification is given to the adapter.
To make it work, move your logic from activity to adapter. Handle the click events with the positions.
In your activity,
public class table extends AppCompatActivity{
GridView gridView;
my_adapter my_adapter;
String table_names[] = {"1a", "1b", "1c", "1d", "2a", "2b", "2c", "2d", "3a", "3b", "3c", "3d"};
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_grid);
gridView = (GridView) findViewById(R.id.grid);
my_adapter = new my_adapter(this, table_names);
gridView.setAdapter(my_adapter);
}
class my_adapter extends BaseAdapter {
LayoutInflater inflater = null;
Context ctx;
String table_names[];
ArrayList<String> store_table_no;
my_adapter(Context ctx, String table_names[]) {
this.ctx = ctx;
this.table_names = table_names;
store_table_no = new ArrayList<>();
store_table_no.addAll(Arrays.asList(table_names));
}
#Override
public int getCount() {
return store_table_no.size();
}
#Override
public Object getItem(int i) {
return store_table_no.get(i);
}
#Override
public long getItemId(int i) {
return i;
}
#Override
public View getView(final int i, View view, ViewGroup viewGroup) {
View row = view;
if (row == null) {
inflater = (LayoutInflater) ctx.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
row = inflater.inflate(R.layout.single, null);
}
RelativeLayout layout = (RelativeLayout) row.findViewById(R.id.relative_layout);
TextView tv_table_no = (TextView) row.findViewById(R.id.table_no);
final ImageView imageView = (ImageView) row.findViewById(R.id.imageView);
tv_table_no.setText(store_table_no.get(i));
layout.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
new AlertDialog.Builder(GridActivity.this)
.setTitle("Table number: " + store_table_no.get(i))
.setMessage("Open Table?")
.setPositiveButton("Yes", new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialog, int which) {
imageView.setImageResource(R.mipmap.ic_launcher);
}
})
.setNegativeButton("No", new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialog, int which) {
imageView.setImageResource(R.drawable.icon);
}
})
.show();
}
});
return row;
}
}
}
In your xml file add id to Parent RElative Layout as follows,
single.xml
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:orientation="vertical" android:layout_width="match_parent"
android:id="#+id/relative_layout"
android:clickable="true"
android:layout_height="match_parent">
<TextView
android:text="101"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="#+id/table_no"
android:layout_centerHorizontal="true"
android:layout_centerVertical="true"
android:textSize="22sp" />
<ImageView
app:srcCompat="#drawable/table"
android:id="#+id/imageView"
android:layout_centerHorizontal="true"
android:layout_centerVertical="true"
android:layout_width="130dp"
android:layout_height="100dp" />
</RelativeLayout>
I hope it will help you.
I created a custom view with a edit text field and a button. I want to delete an item from listview by clicking on a button.
The code for the custom view:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent" android:layout_height="match_parent">
<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Delete"
android:id="#+id/delete_btn"
android:layout_alignParentTop="true"
android:layout_alignParentRight="true"
android:layout_alignParentEnd="true" />
<EditText
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="#+id/player_name_txt"
android:textColor="#ffffff"
android:editable="false"
android:background="#5eb8ed"
android:layout_alignParentTop="true"
android:layout_alignParentLeft="true"
android:layout_alignParentStart="true"
android:layout_alignBottom="#+id/delete_btn"
android:layout_toLeftOf="#+id/delete_btn"
android:layout_toStartOf="#+id/delete_btn" />
</RelativeLayout>
The code for the adapter and list view:
inflater = (LayoutInflater)this.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
playerListView = (ListView)this.findViewById(android.R.id.content).getRootView().findViewById(R.id.player_list);
playerListAdapter = new ArrayAdapter(this,R.layout.player_item,R.id.player_name_txt, new ArrayList<String>(){});
playerListView.setAdapter(playerListAdapter);
The Code I tried:
public void removePlayer(View v)
{
EditText pairedEdit = (EditText)findViewById(R.id.player_name_txt);
String name = pairedEdit.getText().toString();
playerListAdapter.remove(name);
playerListAdapter.notifyDataSetChanged();
}
Right now it removes the first item in the list view.
AlertDialog.Builder addPlayerBuilder = new AlertDialog.Builder(this);
final View customView = inflater.inflate(R.layout.add_player,null);
final EditText usernameEdit = (EditText)customView.findViewById(R.id.username_edit);
addPlayerBuilder.setView(customView);
addPlayerBuilder.setPositiveButton("Ok", new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialog, int id) {
String name = usernameEdit.getText().toString();
playerListAdapter.add(name);
playerListAdapter.notifyDataSetChanged();
dialog.dismiss();
}
});
addPlayerBuilder.setNegativeButton("Cancel", new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialog, int id) {
dialog.cancel();
}
});
AlertDialog dialog = addPlayerBuilder.create();
dialog.show();
In your button of custom layout place a onclicklistener which would remove the element from the arraylist by remove() function on the basis of its position and then call notifyDataSetInvalidated()
Use this:
Button b2 = (Button) row.findViewById(R.id.button1);
b2.setTag(arg0);
b2.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View arg0) {
int pos = (int)arg0.getTag();
lista.remove(pos);
SunetePreferateAdaptor.this.notifyDataSetChanged(); }
});
In adapter class on delete_btn click you have to call remove method :
public class yourAdapter extends BaseAdapter {
private static LayoutInflater inflater = null;
private Activity context;
private ArrayList<yourBean> arrList;
public yourAdapter(Activity context,
ArrayList<yourBean> arrList) {
this.context = context;
this.arrList = arrList;
inflater = (LayoutInflater) context
.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
}
public int getCount() {
return arrList.size();
}
public Object getItem(int position) {
return position;
}
public long getItemId(int position) {
return position;
}
#Override
public View getView(final int position, View convertView, ViewGroup parent) {
if (convertView == null) {
convertView = inflater.inflate(R.layout.list_row,
null);
viewHolder.delete_btn= (Button) convertView
.findViewById(R.id.delete_btn);
convertView.setTag(viewHolder);
} else {
viewHolder = (ViewHolder) convertView.getTag();
}
viewHolder.delete_btn.setTag(position);
viewHolder.delete_btn.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
arrayList.remove(position);
notifyDataSetChanged();
}
});
return convertView;
}
static class ViewHolder {
Button delete_btn;
}
}