2016-01-14 5 views
2

Я могу заполнить список своими значениями базы данных. Моя проблема заключается в том, что макет ListView выглядит так (например) -> (текст, кнопка удаления)ListView с использованием SimpleCursorAdapter OnItemClickListener не работает

Активность 1 || Delete_Button

Активность 2 || Delete_Button

и что я хочу, так это то, что когда я нажму «Активность 1», он перейдет к заданию 1-го действия. или когда я нажал «Действие 2», он перейдет к задаче 2-го действия. то же, что и кнопка удаления, если я нажал кнопку удаления строки 1, она удалит строку 1 и т. д.

Как это сделать? Я новичок в Android.

Это мой код:

ListView listView ; 
    ArrayList<String> list; 

    public int goal_id; 
    int i = 0; 

    //database variables 
    MyDBAdapter dbhandler; 


    protected void onCreate(Bundle savedInstanceState) { 
      super.onCreate(savedInstanceState); 
      setContentView(R.layout.activity_set_act); 
      TypefaceProvider.registerDefaultIconSets(); 

      Bundle extras = getIntent().getExtras(); 

      if (extras == null) { 
       return; 
      } 

      goal_id = Integer.parseInt(extras.getString("goalid")); 

      Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar); 
      setSupportActionBar(toolbar); 
      toolbar.setSubtitle("Activities List"); 
      ActionBar actionBar = getSupportActionBar(); 
      actionBar.setHomeAsUpIndicator(R.drawable.ic_back); 
      actionBar.setDisplayHomeAsUpEnabled(true); 

      FloatingActionButton fab = (FloatingActionButton) findViewById(R.id.fab); 
      fab.setOnClickListener(new View.OnClickListener() { 
       @Override 
       public void onClick(View view) { 
        Snackbar.make(view, "Added new activity", Snackbar.LENGTH_LONG) 
          .setAction("Added new activity", null).show(); 

        onCLick_addAct(); 
       } 
      }); 

      dbhandler = new MyDBAdapter(this); 
      populateListView(); 
      listView.setOnItemClickListener(new AdapterView.OnItemClickListener() { 

       @Override 
       public void onItemClick(AdapterView<?> parent, View view, int position, long id) { 

        Long temp = listView.getItemIdAtPosition(position); 
        MessageTo.message(SetActActivity.this, Long.toString(temp)); 
       } 
      }); 

     } 

     public void populateListView(){ 
      Cursor cursor = dbhandler.getAllActivitiesByGoalCursor(goal_id); 
      String[] actlist = new String[] {dbhandler.dbhandler.COLUMN_ACTIVITY_NAME}; 
      int[] actNames = new int[] {R.id.list_item_string}; 

      SimpleCursorAdapter myAdapter = new SimpleCursorAdapter(SetActActivity.this,R.layout.act_list,cursor,actlist,actNames,0){ 
      @Override 
      public View getView(int position, View convertView, ViewGroup parent) { 
       View v = convertView; 
       ViewHolder holder; 
       if (v == null) { 
        holder = new ViewHolder(); 
        LayoutInflater vi = (LayoutInflater) getSystemService(Context.LAYOUT_INFLATER_SERVICE); 
        v = vi.inflate(R.layout.act_list, null); 
        holder.textView = (TextView) v.findViewById(R.id.list_item_string); 
        holder.button = (Button) v.findViewById(R.id.delete_btn); 
        v.setTag(holder); 
        holder.button.setOnClickListener(new View.OnClickListener() { 
         @Override 
         public void onClick(View v) { 
          int pos = (int) v.getTag(); 
          list.remove(pos); 
          notifyDataSetChanged(); 
         } 
        }); 
       } else { 
        holder = (ViewHolder) v.getTag(); 
       } 
// holder.textView.setText(list.get(position).get("title")); //the get("title") is error. undefined 

       holder.button.setTag(position); 
       return v; 

      } 

      class ViewHolder { 
       TextView textView; 
       Button button; 
      } 
     }; 
     //handle listview and assign adapter 
     listView = (ListView)findViewById(R.id.list); 
     // Attach cursor adapter to the ListView 
     listView.setAdapter(myAdapter); 

    } 

Это один код -> он не будет различать, если я нажал на TextView или кнопку удаления. Он по-прежнему будет реализовывать ту же функцию, что и не то, что я хочу. :(

listView.setOnItemClickListener(new AdapterView.OnItemClickListener() { 

        @Override 
        public void onItemClick(AdapterView<?> parent, View view, int position, long id) { 

         Long temp = listView.getItemIdAtPosition(position); 
         MessageTo.message(SetActActivity.this, Long.toString(temp)); 
        } 
       }); 
+0

вам нужно создать пользовательский класс SimpleCursorAdapter и переопределить GetView() метод и следовать @Ichigo Kurosakio пост. – Bharatesh

+0

как переопределить ?? :(@bharat – Ruby

+0

на кнопку «удалить»: вы действительно хотите удалить соответствующую строку в базе данных? – 0X0nosugar

ответ

1

Вы используете фокусируемый элемент (Button) в списке, который переопределяет событие OnItemClickListener. Решение состоит в использовании двух отдельных onClickListeners при создании представлений в адаптере.

Эта проблема довольно распространена. См. this для справки.

Теперь код для пользовательских SimpleCursorAdapter:

public class MyAdapter extends SimpleCursorAdapter 
{ 

    private Context mContext; 
    private Context appContext; 
    private int layout; 
    private Cursor cr; 
    private final LayoutInflater inflater; 

    public MyAdapter(Context context, int layout, Cursor c, String[] from, int[] to) 
    { 
     super(context, layout, c, from, to); 
     this.layout = layout; 
     this.mContext = context; 
     this.inflater = LayoutInflater.from(context); 
     this.cr = c; 
    } 

    @Override 
    public View newView(Context context, Cursor cursor, ViewGroup parent) 
    { 
     return inflater.inflate(layout, null); 
    } 

    @Override 
    public void bindView(View view, final Context context, Cursor cursor) 
    { 
     super.bindView(view, context, cursor); 
     RelativeLayout parentView = (RelativeLayout) view.findViewById(R.id.parentView); 
     TextView textview = (TextView) view.findViewById(R.id.itemLayoutText); 
     // Set the text using cursor with column index. 
     textview.setText(cursor.getString(1)); 
     Button button = (Button) view.findViewById(R.id.itemLayoutBtn); 
     button.setOnClickListener(new View.OnClickListener() 
     { 
      @Override 
      public void onClick(View view) 
      { 
       // Use interface to send a callback to the activity 
       Toast.makeText(context, "Button clicked", Toast.LENGTH_SHORT).show(); 
      } 
     }); 

     parentView.setOnClickListener(new View.OnClickListener() 
     { 
      @Override 
      public void onClick(View view) 
      { 
       // Use interface to send a callback to the activity 
       Toast.makeText(context, "List item clicked", Toast.LENGTH_SHORT).show(); 
      } 
     }); 

    } 
} 

Макет элемента списка:

<?xml version="1.0" encoding="utf-8"?> 
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" 
       android:orientation="vertical" 
       android:layout_width="match_parent" 
       android:layout_height="match_parent" 
       android:id="@+id/parentView"> 

    <TextView 
     android:layout_width="match_parent" 
     android:layout_height="match_parent" 
     android:layout_alignParentLeft="true" 
     android:textAppearance="?android:textAppearanceMedium" 
     android:id="@+id/itemLayoutText"/> 

    <Button 
     android:layout_width="wrap_content" 
     android:layout_height="wrap_content" 
     android:id="@+id/itemLayoutBtn" 
     android:text="Delete" 
     android:layout_alignParentRight="true" 
     /> 

</RelativeLayout> 
+0

Я попробую это. спасибо :) :) – Ruby

+0

Дайте мне знать, если это вам помогло. –

+0

textview.setText (cursor.getString (1)); <- можете ли вы объяснить мне cursor.getString (1)? он печатает тот же текст в текстовом виде во всех элементах списка. – Ruby

0

Вы можете просто добавить в методе вашего пользовательского адаптера GetView() в setOnClickListener() для кнопки, которую вы используете.

Любые данные, связанные с кнопкой должна быть добавлена ​​с MyButton. SetTag() в GetView() и могут быть доступны в onClickListener через view.getTag()

Проверка решения в этом link

+0

Но я использую SimpleCursorAdapter .. :( – Ruby

+0

как переопределить ????? – Ruby

2

Обновлено: Как вы не можете удалить ро w/item из курсора, а также повторный запрос курсора каждый раз, когда пользователь нажимает delete, не является хорошей идеей.

Вместо этого вы можете прочитать все значения из курсора и поместить его в List<Map<String,String> items и передать этот объект SimpleAdapter. попробуйте под кодом.

items = new ArrayList<Map<String,String>>(); 
    Map<String, String> item; 
    cursor.moveToFirst(); 
    while (!cursor.isAfterLast()) { 
     String name = cursor.getString(cursor.getColumnIndex("title"));//column name 
     String id = cursor.getString(cursor.getColumnIndex("_id"));//column name 
     item = new HashMap<>(); 
     item.put("title", name); 
     item.put("id", id); 
     items.add(item); 
     cursor.moveToNext(); 
    } 

    SimpleAdapter adapter = new SimpleAdapter(this, items, R.layout.adapter_text_button, new String[]{"title" 
    }, new int[]{R.id.title}) { 
     @Override 

     public View getView(int position, View convertView, ViewGroup parent) { 
      View v = convertView; 
      ViewHolder holder; 
      if (v == null) { 
       holder = new ViewHolder(); 
       LayoutInflater vi = (LayoutInflater) getSystemService(Context.LAYOUT_INFLATER_SERVICE); 
       v = vi.inflate(R.layout.adapter_text_button, null); 
       holder.textView = (TextView) v.findViewById(R.id.title); 
       holder.button = (Button) v.findViewById(R.id.action); 
       v.setTag(holder); 
       holder.button.setOnClickListener(new View.OnClickListener() { 
        @Override 
        public void onClick(View v) { 
         int pos = (int) v.getTag(); 
         Map<String, String> item = items.get(pos); 
         String id = item.get("id"); 
         //using this id delete the record from the database 
         items.remove(item); 
         notifyDataSetChanged(); 
         Log.i("TAG", "ID " + id); 
        } 
       }); 
      } else { 
       holder = (ViewHolder) v.getTag(); 
      } 
      Map<String, String> data = items.get(position); 
      holder.textView.setText(data.get("title")); 
      holder.button.setTag(position); 
      return v; 

     } 

     class ViewHolder { 
      TextView textView; 
      Button button; 
     } 
    }; 

    listView.setAdapter(adapter); 

Happy_Coding;

+0

это на другом Java-классе? Или внутри onCreate Method? – Ruby

+0

внутри onCreate только – Bharatesh

+0

мой плохой. Я попробую это. – Ruby

Смежные вопросы