2012-08-02 24 views
21

Tôi gặp sự cố khi tạo lịch dựa trên GridView. Đây là Lưới:OnClickListener không hoạt động đối với mục đầu tiên trong GridView

GridView Calendar

Đây được coi là một cuốn lịch dân cư với các sự kiện, vì vậy tôi có bộ chuyển đổi của tôi thực hiện OnClickListener và tôi đặt người nghe rằng đối với mỗi nút trong lịch. Nó hoạt động hoàn hảo cho mỗi nút đơn EXCEPT cái đầu tiên (trong trường hợp này là số 30). Khi tôi nhấp vào nó chỉ không hoạt động, nhưng khi tôi nhấp vào nút khác sau khi tôi đã cố gắng nhấp vào nút đầu tiên, nó thực hiện nhấp chuột cho lần đầu tiên trước khi thực hiện nhấp chuột cho nút khác.

Tôi đã quét khoảng 10 trang câu hỏi có liên quan và không tìm thấy ai đó gặp sự cố này. Xin vui lòng giúp đỡ!

Như hỏi, đây là chức năng getView mã của tôi:

public View getView(int position, View convertView, ViewGroup parent) 
    { 
     View row = convertView; 
     ViewHolder holder; 
     if (row == null) 
     { 
      holder = new ViewHolder(); 
      LayoutInflater inflater = (LayoutInflater) _context.getSystemService(Context.LAYOUT_INFLATER_SERVICE); 
      row = inflater.inflate(R.layout.calendar_day_gridcell, parent, false); 
      holder.gridCell = (Button) row.findViewById(R.id.calendar_day_gridcell); 
      holder.multiDayEvent = (EventLengthView)row.findViewById(R.id.eventLengthView); 
     } 
     else{ 
      holder = (ViewHolder)row.getTag(); 
     } 

     int calendarGridHeight = (calendarView.getHeight()-5)/(getCount()/7); 
     AbsListView.LayoutParams params = new AbsListView.LayoutParams(
       android.view.ViewGroup.LayoutParams.FILL_PARENT, 
       calendarGridHeight); 
     row.setLayoutParams(params); 

     //Change the background drawable depending on the position in the calendar 
     if ((position+1) % 7 == 0){ 
      holder.gridCell.setBackgroundDrawable(getResources().getDrawable(R.drawable.calendar_button_selector_end_row)); 
     } 
     if (getCount() - position < 8){ 
      holder.gridCell.setBackgroundDrawable(getResources().getDrawable(R.drawable.calendar_button_selector_end_column)); 
     } 
     if (position == getCount()-1){ 
      holder.gridCell.setBackgroundDrawable(getResources().getDrawable(R.drawable.calendar_button_selector_end)); 
     } 
     holder.gridCell.setOnClickListener(this); 

     holder.gridCell.setTag(null);//clear tags 

     // ACCOUNT FOR SPACING 
     String[] day_color = list.get(position).split("-"); 
     int theday = Integer.parseInt(day_color[0]); 
     int themonth = Integer.parseInt(day_color[2]); 
     int theyear = Integer.parseInt(day_color[3]); 
     String date = DateFormat.format("dd/M/yy", new Date(theyear,themonth,theday)).toString(); 
     if ((!eventsMap.isEmpty()) && (eventsMap != null)) 
     { 
      if (eventsMap.containsKey(date)) 
      { 
       holder.multiDayEvent.SetMeasure(calendarView.getWidth()/7, calendarGridHeight); 

       holder.multiDayEvent.setVisibility(View.VISIBLE); 
       //holder.singleDayEvent.setVisibility(View.VISIBLE); 
       Event event = (Event) eventsMap.get(date); 
       holder.multiDayEvent.AddEvent(event); 
       holder.gridCell.setTag(event); 
      } 
      else{ 
       //holder.singleDayEvent.setVisibility(View.GONE); 
       holder.multiDayEvent.setVisibility(View.GONE); 
      } 
     } 

     // Set the Day GridCell 
     holder.gridCell.setText(Integer.toString(theday)); 

     if (day_color[1].equals("GREY")) 
     { 
      holder.gridCell.setTextColor(Color.GRAY); 
     } 
     if (day_color[1].equals("WHITE")) 
     { 
      holder.gridCell.setTextColor(Color.WHITE); 
     } 
     if (day_color[1].equals("BLUE")) 
     { 
      holder.gridCell.setTextColor(Color.BLUE); 
     } 

     row.setTag(holder); 
     return row; 
    } 

    public class ViewHolder{ 
     Button gridCell; 
     ImageView singleDayEvent; 
     EventLengthView multiDayEvent; 
    } 

    public void onClick(View view) 
    { 
     if (view.getTag() != null){ 
      Event event = (Event)view.getTag(); 

      eventListView.setAdapter(new EventListAdapter(CalendarScreen.this, event)); 
      eventListViewLayout.setVisibility(View.VISIBLE); 
      eventListViewLayout.startAnimation(fadeIn); 
     } 
     else if (eventListViewLayout.getVisibility() == View.VISIBLE){ 
      onBackPressed(); 
     } 
    } 

Các onClick được gọi cho mỗi gridcell TRỪ người đầu tiên ở góc trên cùng bên trái

+0

Vui lòng đặt mã bạn đã sử dụng .. –

+0

[Tại sao bạn không thử ví dụ này] (http://w2davids.wordpress.com/android-simple-calendar/) – Praveenkumar

+0

mã của tôi dựa trên ví dụ đó – Valentin

Trả lời

8

Ok, tôi đã tìm thấy giải pháp. Vấn đề là những dòng này:

ViewHolder holder; 
if (convertView == null) 
{ 
    holder = new ViewHolder(); 
    LayoutInflater inflater = (LayoutInflater) _context.getSystemService(Context.LAYOUT_INFLATER_SERVICE); 
    convertView = inflater.inflate(R.layout.calendar_day_gridcell, parent, false); 
    holder.gridCell = (Button) convertView.findViewById(R.id.calendar_day_gridcell_button); 
    holder.multiDayEvent = (EventLengthView) convertView.findViewById(R.id.eventLengthView); 
    convertView.setTag(holder); 
} 
else { 
    holder = (ViewHolder) convertView.getTag(); 
} 

Khi đặt instatiating nút gridCell đó, bằng cách nào đó, nó pha trộn lên người nghe bấm vào vị trí đầu tiên trong các bộ chuyển đổi. Tôi cuối cùng đã sửa chữa nó bằng cách chỉ instatiating người giữ trong mỗi vượt qua, thay vì nhận được nó bằng thẻ (đó là tốt hơn cho hiệu suất, nhưng cũng oh). Cảm ơn tất cả mọi người đã giúp đỡ.

+0

bạn có thể đặt thêm một số mã –

+0

Thực sự không tái sử dụng convertView đã làm việc này đúng cách –

0

Đặt onItemClickListener trên đối tượng GridView thay thiết lập onClickListeners trên mỗi nút.

Và tôi đã tìm thấy một câu hỏi khác với sự cố của bạn here. Bounty có thể?

+0

không hoạt động. Tôi đã thử nó. – Valentin

+0

Tôi cũng đã thử thay thế các nút bằng ImageViews (như tôi biết các nút chặn onItemClickListeners của GridView) nhưng nó vẫn không hoạt động. – Valentin

+0

vui lòng thêm mã – png

0

Vui lòng tham khảo link này, nó đã đặt màu nền của khung nhìn thành TRANSPARENT. Nó có thể giúp bạn.

1

Đối với những gì nó có giá trị, tôi cũng đã có vấn đề này (ô đầu tiên trong GridView có trì hoãn onclick).

Trong trường hợp của tôi, tôi đã sử dụng lưới xem nhẹ (tùy chỉnh) với bộ số lần xem ảo động mà tôi có thể hiển thị/đi và vẽ lại lưới xem. Tất cả các lần xem trước được chuẩn bị trước và được lưu trữ trong bộ điều hợp.

Ban đầu, tôi đã sử dụng notifyDataSetChanged() trên bộ điều hợp nhưng điều này dẫn đến sự cố nhấp chuột bị trì hoãn cho ô đầu tiên bất cứ khi nào tập hợp được cập nhật. Tôi đã thay đổi để chỉ làm mất hiệu lực GridView và bây giờ mọi thứ là tốt. Ghi nhớ rằng tất cả các quan điểm của tôi đã được tạo ra và được lưu trữ trong bộ điều hợp, nó chỉ là phương thức getview để kiểm tra xem cái nào thực sự nhìn thấy được.

8

Sử dụng của bạn OnClickListener() trong hoạt động của bạn sau khi .setAdapter() phương pháp, không phải trong lớp adapter của bạn.

gridView.setAdapter(adapter); 
gridView.setOnItemClickListener(new OnItemClickListener() { 
public void onItemClick(AdapterView parent, View v, int position, long id) { 
    Toast.makeText(GridViewActivity.this, "" + position, 
      Toast.LENGTH_SHORT).show(); 
    } 
}); 
+1

cảm ơn. vấn đề của tôi đã được giải quyết bằng giải pháp của bạn. –

+1

Giải pháp này là tốt nhất – Miguel

+0

Hãy để tôi nói, bạn sẽ kết hôn với tôi? Làm việc như một nét duyên dáng ... –

1

Tôi gặp vấn đề tương tự. Sự kiện nhấp chuột vào mục đầu tiên đã bị trì hoãn đáng kể. Tôi đã sử dụng notifyDataSetInvalidated().Sử dụng onItemClickListener() đã giải quyết được sự cố, mặc dù tôi vẫn không hiểu tại sao trình nghe onClick trên các mục riêng lẻ lại có hành vi này.

13

Tôi đã gặp phải vấn đề tương tự.Kiểm tra setLayoutParams bên trong mệnh đề if (view == null) đã được thực hiện. Bạn không phải hy sinh chế độ xem lại theo cách đó.

thích:

if(row == null){ 
    // inflate row 
    row.setLayoutParams(params); 
    //remaining code 
}else{ 
    holder = (ViewHolder)row.getTag(); 
} 
// everything else 

Tôi không biết tại sao nó hoạt động nhưng nó làm việc cho tôi. Tôi cũng nhận thấy rằng tất cả các mã liên quan đến cùng một vấn đề trong stackoverflow cũng đã sử dụng setLayoutParams bên ngoài mệnh đề if. Đây là lần đầu tiên của tôi vì vậy tôi không biết nếu tôi có thể đăng bài này ở khắp mọi nơi. Hy vọng nó đã giúp.

Nguồn: Lô đường nhỏ và lỗi.

+2

Làm việc cho tôi và tiết kiệm rất nhiều thời gian – 365SplendidSuns

+0

Cảm ơn rất nhiều! Nó giúp. – Zikkoua

+0

cảm ơn bạn đã giúp tôi rất nhiều :) – Radwa

Các vấn đề liên quan