2011-05-12 90 views
14

我有一個對話框與複選框,我試圖做不同的事情時,選擇選項和按下好的時候。我認爲在閱讀完一些教程後我知道自己在做什麼,但是當我按下OK時,即使沒有選中它,它也會提醒「一切」。所以看來我的if語句不能正常工作,但我不知道爲什麼。Android複選框對話框(簡單)

任何建議我做錯了什麼,以及如何解決它將不勝感激!

final CharSequence[] items = {"Item 1", "Item 2", "Item 3"}; 
    final boolean[] states = {false, false, false}; 
    AlertDialog.Builder builder = new AlertDialog.Builder(this); 
    builder.setTitle("What would you like to do?"); 
    builder.setMultiChoiceItems(items, states, new DialogInterface.OnMultiChoiceClickListener(){ 
     public void onClick(DialogInterface dialogInterface, int item, boolean state) { 
     } 
    }); 
    builder.setPositiveButton("Okay", new DialogInterface.OnClickListener() { 
     public void onClick(DialogInterface dialog, int id) { 
      SparseBooleanArray CheCked = ((AlertDialog)dialog).getListView().getCheckedItemPositions(); 
      if(CheCked.get(CheCked.keyAt(0)) == true){ 
       Toast.makeText(Backup.this, "Item 1", Toast.LENGTH_SHORT).show(); 
      } 
      if(CheCked.get(CheCked.keyAt(1)) == true){ 
       Toast.makeText(Backup.this, "Item 2", Toast.LENGTH_SHORT).show(); 
      } 
      if(CheCked.get(CheCked.keyAt(2)) == true){ 
       Toast.makeText(Backup.this, "Item 3", Toast.LENGTH_SHORT).show(); 
      } 
     } 
    }); 
    builder.setNegativeButton("Cancel", new DialogInterface.OnClickListener() { 
     public void onClick(DialogInterface dialog, int id) { 
      dialog.cancel(); 
     } 
    }); 
    builder.create().show(); 
} 

回答

7

的問題是,你使用keyAt,其中,根據API文檔

返回從index個 關鍵這個 SparseBooleanArray存儲的鍵值映射。

和這個SparseBooleanArray只包含您的清單中檢查的項目(getCheckedItemPositions)!

因此,如果您選中三項中的兩項,那麼CheCked成員將包含2個項目,當您撥打keyAt(2)時,它將返回0(不是IndexOutOfBoundsException,儘管該位置地圖不具有值)。

你應該使用簡單說就是SparseBooleanArrayget方法,從您ListView項目位置作爲參數:

builder.setPositiveButton("Okay", new DialogInterface.OnClickListener() 
{ 
    public void onClick(DialogInterface dialog, int id) 
    { 
     SparseBooleanArray CheCked = ((AlertDialog) dialog).getListView().getCheckedItemPositions(); 
     if (CheCked.get(0)) 
     { 
      Toast.makeText(TmpActivity2.this, "Item 1", Toast.LENGTH_SHORT).show(); 
     } 
     if (CheCked.get(1)) 
     { 
      Toast.makeText(TmpActivity2.this, "Item 2", Toast.LENGTH_SHORT).show(); 
     } 
     if (CheCked.get(2)) 
     { 
      Toast.makeText(TmpActivity2.this, "Item 3", Toast.LENGTH_SHORT).show(); 
     } 
    } 
}); 

您也可以鬆動,如果從句的== true一部分,但是這只是語義。

如果你看一看的getCheckedItemPositions方法的API文檔,你會發現這個解決方案:

返回
一個SparseBooleanArray將在每次調用返回true以get(int position)其中position是列表中的一個位置,或者如果選擇模式設置爲CHOICE_MODE_NONE,則爲null

+0

完美的謝謝你們兩個都很好的工作 – GFlam 2011-05-12 20:40:14

+0

@rekaszenu我認爲這個解決方案也更好。特別是對於大型列表。循環需要更多的資源。 – evilone 2011-05-13 10:39:55

+0

使用api的方式(幾乎)總是比使用方法的更好,但在大多數情況下,閱讀文檔只是無聊; :)這導致將'CheCked'成員作爲ListView'項目的完整'Map'和它們的檢查狀態來處理。 – rekaszeru 2011-05-13 11:03:28

10

我會做這樣的例子:

public class Main extends Activity { 

    CharSequence[] items = {"Google", "Apple", "Microsoft"}; 
    boolean[] itemsChecked = new boolean[items.length]; 

    /** Called when the activity is first created. */ 
    @Override 
    public void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     setContentView(R.layout.main); 

     Button btn = (Button) findViewById(R.id.btnDialog); 
     btn.setOnClickListener(new OnClickListener() { 

      @Override 
      public void onClick(View v) { 
       showDialog(0); 
      } 
     }); 
    } 

    @Override 
    protected Dialog onCreateDialog(int id) { 
     switch (id) { 
     case 0: 
      return new AlertDialog.Builder(this) 
      .setIcon(R.drawable.icon) 
      .setTitle("Dialog with simple text") 
      .setPositiveButton("OK", new DialogInterface.OnClickListener() { 

       @Override 
       public void onClick(DialogInterface dialog, int which) { 
        for (int i = 0; i < items.length; i++) { 
        if (itemsChecked[i]) { 
         Toast.makeText(getBaseContext(), items[i] + " checked!", Toast.LENGTH_LONG).show(); 
        } 
       } 
       } 
      }) 
      .setNegativeButton("Cancel", new DialogInterface.OnClickListener() { 

       @Override 
       public void onClick(DialogInterface dialog, int which) { 
        Toast.makeText(getBaseContext(), "Cancel clicked!", Toast.LENGTH_LONG).show(); 
       } 
      }) 
      .setMultiChoiceItems(items, itemsChecked, new DialogInterface.OnMultiChoiceClickListener() { 

       @Override 
       public void onClick(DialogInterface dialog, int which, boolean isChecked) { 
        Toast.makeText(getBaseContext(), items[which] + (isChecked ? "checked!" : "unchecked!"), Toast.LENGTH_SHORT).show(); 
       } 
      }) 
      .create(); 
     } 

     return null; 
    } 


} 
+0

我不希望東西在onClick上運行雖然我希望任何檢查運行時好的按下,只有當好的時候按下我不能運行onClick – GFlam 2011-05-12 19:32:29

+1

編輯我的代碼,但我希望你覺得有點難。將on循環添加到onClick方法並檢查哪個數組項的值爲true可不是那麼困難:) – evilone 2011-05-12 20:03:38

+0

對不起,我很新,這是在過去一個月的空閒時間學習java,但無論如何已經厭倦了作爲地獄以及大聲笑一直在這個應用程序的過去幾個小時的休息時間:)但你的方法工作得很好,就像另一個我只給他們支票,因爲它更簡單,因爲我已經有了,作爲我的代碼,並解釋我是什麼做錯了希望我可以給你們兩個支票,但我也給你一個投票,以及 – GFlam 2011-05-12 20:39:48

2

這應該有助於

.setMultiChoiceItems(items, itemsChecked, 
         new DialogInterface.OnMultiChoiceClickListener() { 
          @Override 
          public void onClick(DialogInterface dialog, 
            int which, boolean isChecked) { 




           Toast.makeText(
             getBaseContext(), 
             items[which] 
               + (isChecked ? " checked!" 
                 : " unchecked!"), 
             Toast.LENGTH_SHORT).show(); 
          } 
         }) 

但隨後你如何在其他類中使用檢查的項目?