2013-08-17 166 views
-3

我有一些关于Android编程的问题。更具体地说,我有一个ListView,其中每一行都包含五个小部件和每个触发事件。我为getView方法中的每个小部件创建了自定义适配器和定义的事件处理程序。一切工作正常,但由于所有这些事件处理程序里面的代码看起来很长,不可读和讨厌。有没有更好的设计?也许在getView方法之外创建事件处理程序? 问候Android,ListView适配器

根据建议,我张贴了部分源代码。正如你所看到的,我已经在getView方法之外创建了几个事件处理程序,并在里面创建了两个。我真的不知道哪种设计更好。

public class ListViewAdapter extends ArrayAdapter<HourReport> { 

private static Activity context; 
private int resourcecId; 
private TextView fromTime; 
private TextView toTime; 
private TextView total; 
private HourReport rowModelBean; 
private HourReport rowBean; 
private CheckBox billable; 
private ArrayList<HourReport> list; 
private HourReportCatalog catalog; 
private Map<Integer, Integer>selectedItems; 
private Map<Integer, Integer>selectedRoles; 




public ListViewAdapter(Activity context, int resourcecId, 
     ArrayList<HourReport> list, HourReportCatalog catalog) { 
    super(context, resourcecId, list); 
    this.catalog = catalog; 
    ListViewAdapter.context = context; 
    this.resourcecId = resourcecId; 
    this.list = list; 
    selectedItems = new HashMap<Integer, Integer>(); 
    selectedRoles = new HashMap<Integer, Integer>(); 

} 


// event handler for delete button "-" 

private OnClickListener delete = new OnClickListener() { 

    @Override 
    public void onClick(View deletBtnF) { 

     int myPosition = (Integer) deletBtnF.getTag(); 
     HourReport r = list.remove(myPosition); 
     selectedItems.put(myPosition, 0); 
     selectedRoles.put(myPosition, 0); 
     r.setTimeFinished(null); 
     r.setTimeStarted(null); 
     r.setTaks(null); 
     r.setTotal(0.0); 
     r.setBillable(false); 
     r.setEngagementContractID(0);  
     list.add(myPosition, r); 
     notifyDataSetChanged(); 
     if (r.getDateCreated() != null) { 
      Log.e("Listview adapter", "inside the if statement"); 
      Long id = r.getHourReportID(); 
      Log.e("", "date created" + r.getDateCreated()); 
      catalog.deleteHourReport(r); 
      r.setDateCreated(null); 
     } 
    } 

}; 

// event handler for textView which is responsible for defining dateFrom 
Calendar c = Calendar.getInstance(); 
OnClickListener onClickLisOnDateFrom = new OnClickListener() { 

    @Override 
    public void onClick(View editField) { 

     Integer position1 = (Integer) editField.getTag(); 
     TableRow parent = (TableRow) editField.getParent(); 
     fromTime = (TextView) parent.findViewById(R.id.viewTextFrom); 
     total = (TextView) parent.findViewById(R.id.textViewShowsTotal); 
     rowBean = getModel(position1); 

     TimePickerDialog.OnTimeSetListener timeListener1 = new TimePickerDialog.OnTimeSetListener() { 

      @Override 
      public void onTimeSet(TimePicker view, int hourOfDay, int minute) { 
       c.set(Calendar.HOUR_OF_DAY, hourOfDay); 
       c.set(Calendar.MINUTE, minute); 
       int hour = c.get(Calendar.HOUR_OF_DAY); 
       int minutes = c.get(Calendar.MINUTE); 
       String time = hour + ":" + minutes; 
       fromTime.setText(time); 
       setTimeFieldFrom(time); 
       String totalTime = totalHourCalculator(); 
       total.setText(totalTime); 

      } 
     }; 
     new TimePickerDialog(context, timeListener1, 
       c.get(Calendar.HOUR_OF_DAY), c.get(Calendar.MINUTE), true) 
       .show(); 

    } 
}; 
// event handler for textView which is responsible for defining dateTo 
private OnClickListener onClickLisOnDateTo = new OnClickListener() { 

    @Override 
    public void onClick(View editField) { 
     Integer position1 = (Integer) editField.getTag(); 
     Log.e("ListView - Timer ", "position: " + position1); 
     TableRow parent = (TableRow) editField.getParent(); 
     toTime = (TextView) parent.findViewById(R.id.viewTextFrom); 
     total = (TextView) parent.findViewById(R.id.textViewShowsTotal); 
     rowBean = getModel(position1); 

     TimePickerDialog.OnTimeSetListener timeListener2 = new TimePickerDialog.OnTimeSetListener() { 

      @Override 
      public void onTimeSet(TimePicker view, int hourOfDay, int minute) { 
       c.set(Calendar.HOUR_OF_DAY, hourOfDay); 
       c.set(Calendar.MINUTE, minute); 
       int hour = c.get(Calendar.HOUR_OF_DAY); 
       int minutes = c.get(Calendar.MINUTE); 
       String time = hour + ":" + minutes; 
       toTime.setText(time); 
       setTimeFieldTo(time); 
       String totalTime = totalHourCalculator(); 
       total.setText(totalTime); 
      } 
     }; 
     new TimePickerDialog(context, timeListener2, 
       c.get(Calendar.HOUR_OF_DAY), c.get(Calendar.MINUTE), true) 
       .show(); 
    } 
}; 

     // event handler for check box 
private OnClickListener checkBoxListener = new OnClickListener() { 

    @Override 
    public void onClick(View checkBox) { 

     Integer num = (Integer) checkBox.getTag(); 
     rowBean = getModel(num); 
     if (rowBean.isBillable()) { 
      rowBean.setBillable(false); 
     } else { 
      rowBean.setBillable(true); 
     } 
    } 
}; 

@Override 
public View getView(int position, View convertView, ViewGroup parent) { 
    getHourReportList(); 
    TextView deleteBtnV = null; 
    View row = convertView; 
    Spinner taskSpinner, roleSpinner; 
    TextView addReport; 
    final ViewHolder viewHolder; 
    if (row == null) { 
     LayoutInflater layoutInflater = context.getLayoutInflater(); 
     row = layoutInflater.inflate(resourcecId, parent, false); 
     viewHolder = new ViewHolder(row);   
     fromTime = viewHolder.getFromTime(); 
     deleteBtnV = viewHolder.getDeleteBtnVView(); 
     deleteBtnV.setOnClickListener(delete); 
     billable = viewHolder.getCheckBox(); 
     addReport = viewHolder.getAddButtonView(); 

     // event handler for the button "+" which adds extra row 
     addReport.setOnClickListener(new OnClickListener() { 

      @Override 
      public void onClick(View view) { 
       Integer myPosition = (Integer) view.getTag(); 
       HourReport report = list.get(myPosition); 
       HourReport nReport = new HourReport(); 
       nReport.setClaimDate(report.getClaimDate()); 
       nReport.setEmployeeID(report.getEmployeeID()); 
       nReport.setBillable(false); 
       nReport.setEngagementContractID(0); 
       list.add(myPosition + 1, nReport); 
       notifyDataSetChanged(); 

      } 
     }); 
     viewHolder.adapter = new SpinerAdapter(context);    
     taskSpinner = viewHolder.getSpinnerTask(); 
     roleSpinner = viewHolder.getSpinnerRole(); 

     //event handler for the spinner 
     taskSpinner.setOnItemSelectedListener(new OnItemSelectedListener() { 

      @Override 
      public void onItemSelected(AdapterView<?> arg0, View spin, 
        int selected, long arg3) { 
       Spinner spinner = (Spinner) spin.getParent(); 
       Integer myPosition = (Integer) spinner.getTag();      
       viewHolder.adapter.setSelected(selected);     
       String task = viewHolder.adapter.getSelectcetdTask(); 
       long engmId = viewHolder.adapter.getSelectedTaskID(); 
       rowBean = getModel(myPosition);     
       rowBean.setTaks(task); 
       rowBean.setEngagementContractID(engmId); 
       selectedItems.put(myPosition, selected);      
      } 

      @Override 
      public void onNothingSelected(AdapterView<?> arg0) { 
      } 
     }); 

     ////event handler for the spinner 
     roleSpinner.setOnItemSelectedListener(new OnItemSelectedListener() { 

      @Override 
      public void onItemSelected(AdapterView<?> arg0, View spin, 
        int selectedRole, long arg3) {     
       Spinner spinner = (Spinner) spin.getParent(); 
       Integer myPosition = (Integer) spinner.getTag(); 
       selectedRoles.put(myPosition, selectedRole);     
      } 

      @Override 
      public void onNothingSelected(AdapterView<?> arg0) { 
       // TODO Auto-generated method stub    
      } 
     }); 

     fromTime = viewHolder.getFromTime(); 
     toTime = viewHolder.getToTime(); 
     fromTime.setOnClickListener(onClickLisOnDateFrom); 
     toTime.setOnClickListener(onClickLisOnDateTo); 
     billable.setOnClickListener(checkBoxListener); 
     row.setTag(viewHolder); 

    } else { 
     viewHolder = (ViewHolder) row.getTag(); 
     fromTime = viewHolder.getFromTime(); 
     toTime = viewHolder.getToTime(); 
     taskSpinner = viewHolder.getSpinnerTask(); 
     roleSpinner = viewHolder.getSpinnerRole(); 
     total = viewHolder.getTotal(); 
     billable = viewHolder.getCheckBox(); 
     TextView date = viewHolder.getDate(); 
     deleteBtnV = viewHolder.getDeleteBtnVView(); 
     addReport = viewHolder.getAddButtonView(); 

    } 
    HourReport model = getModel(position); 
    Integer selection = 0; 
    if (selectedItems.get(position) != null) { 
     selection = selectedItems.get(position); 
    } 
    int selectionR = 0; 
    if (selectedRoles.get(position) != null) { 
     selectionR = selectedRoles.get(position); 
    } 

    viewHolder.getFromTime().setText(
      parseDateToString(model.getTimeStarted())); 
    viewHolder.getToTime().setText(
      parseDateToString(model.getTimeFinished())); 
    viewHolder.getTotal().setText(
      convertDoubleTotToStringTot(model.getTotal())); 
    viewHolder.getDate().setText(
      parseDateToStringDDate(model.getClaimDate())); 
    viewHolder.getCheckBox().setChecked(model.isBillable()); 

    Log.e("", "tag " + selection + " date " + model.getClaimDate()); 

    viewHolder.taskSpinner.setSelection(selection); 
    viewHolder.roleSpinner.setSelection(selectionR); 
    fromTime.setTag(Integer.valueOf(position)); 
    toTime.setTag(Integer.valueOf(position)); 
    taskSpinner.setTag(Integer.valueOf(position)); 
    roleSpinner.setTag(Integer.valueOf(position)); 
    billable.setTag(Integer.valueOf(position)); 
    deleteBtnV.setTag(Integer.valueOf(position)); 
    addReport.setTag(Integer.valueOf(position)); 

    return row; 
}![here you have screen shoot of single row][1] 
+0

我会推荐发布你的代码,以便人们可以更好地看看他们试图帮助你解决的问题。 –

回答

0
创建

OnClickListener单个实例(例如,作为一个内部类),并且该实例分配给每一个部件。如果您需要知道该窗口小部件属于哪个行,您可以在该窗口小部件上调用setTag("pos", position)。通过这样做,您可以通过调用view.getTag("pos")中的onClick(View view)方法来获取位置。希望这可以帮助。