2012-08-30 113 views
4

因此,智能手機上的一切工作都很棒。但是,在平板電腦上,我的ListView旨在顯示爲左側導航元素,當前激活的項目在細節片段中展開。這也很好。但是,ListFragment的激活項目不會顯示爲選定狀態。我已將android:choiceMode設置爲singleChoice。我有正確的選擇器激活,並且當按下一個項目時出現背景可繪製。選擇器的右側項目爲android:state_activated="true"。我在我的styles.xml文件中指定android:activatedBackgroundIndicator。當我在onListItemClick中記錄listView.getCheckedItemCount()的輸出時,它會讓我回到1,正如我所期望的那樣。ListView項目不顯示爲激活

幾個星期前,甚至在我開始使用真實數據源和開始使用自定義列表視圖項目佈局之前,我甚至完全按照預期與ArrayAdapter一起工作。然後在某個地方我做了一些讓激活的項目顯示不正確的東西,但我不確定它是什麼。

selectable_background.xml

<selector xmlns:android="http://schemas.android.com/apk/res/android" 
     android:exitFadeDuration="@android:integer/config_mediumAnimTime" > 
    <item android:state_pressed="false" android:state_focused="true" android:drawable="@drawable/list_focused" /> 
    <item android:state_pressed="true" android:drawable="@drawable/pressed_background" /> 

    <!-- selected --> 
    <item android:state_activated="true" android:drawable="@drawable/pressed_background" /> 
    <item android:state_checked="true" android:drawable="@drawable/pressed_background" /> <!-- paranoia --> 
    <item android:state_selected="true" android:drawable="@drawable/pressed_background" /> <!-- paranoia --> 

    <!-- default --> 
    <item android:drawable="@android:color/transparent" /> 
</selector> 

fragment_list.xml

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

    <ListView xmlns:android="http://schemas.android.com/apk/res/android" 
     android:id="@id/android:list" 
     android:layout_width="match_parent" 
     android:layout_height="0dip" 
     android:layout_weight="1" 
     android:choiceMode="singleChoice" 
     android:listSelector="@drawable/selectable_background" > 
    </ListView> 
    <TextView android:id="@id/android:empty" 
     android:layout_width="match_parent" 
     android:layout_height="match_parent" 
     android:paddingTop="16dp" 
     android:paddingBottom="16dp" 
     android:paddingLeft="12dp" 
     android:paddingRight="12dp" 
     android:text="@string/empty_list" /> 
</LinearLayout> 

list_item.xml

<?xml version="1.0" encoding="utf-8"?> 
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" 
    android:orientation="horizontal" 
    android:layout_width="match_parent" 
    android:layout_height="wrap_content" > 

    <ImageView android:id="@+id/item_image" 
     android:layout_width="63dp" 
     android:layout_height="63dp" 
     android:contentDescription="@string/list_image" 
     android:src="@drawable/ic_thumbnail_placeholder" 
     android:background="#f0f0f0" /> 

    <TextView xmlns:android="http://schemas.android.com/apk/res/android" 
     android:id="@+id/item_name" 
     android:layout_width="match_parent" 
     android:layout_height="wrap_content" 
     android:textAppearance="?android:attr/textAppearanceListItemSmall" 
     android:gravity="center_vertical" 
     android:paddingLeft="?android:attr/listPreferredItemPaddingLeft" 
     android:paddingRight="?android:attr/listPreferredItemPaddingRight" 
     android:minHeight="?android:attr/listPreferredItemHeightSmall" /> 
</LinearLayout> 

MyListFragment.java

@Override 
public void onCreate(Bundle savedInstanceState) { 
    super.onCreate(savedInstanceState); 
    this.getActivity().getLoaderManager().initLoader(ALL_ITEMS_LOADER, null, this); 
    listAdapter = new SimpleCursorAdapter(
      this.getActivity(), 
      R.layout.list_item, 
      null, 
      new String[] { Item.NAME }, 
      new int[] { R.id.item_name }, 
      CursorAdapter.FLAG_REGISTER_CONTENT_OBSERVER 
    ); 
    this.setListAdapter(listAdapter); 
} 

@Override 
public Loader<Cursor> onCreateLoader(int i, Bundle bundle) { 
    Uri queryUri; 
    switch (i) { 
     case ALL_ITEMS_LOADER: 
      queryUri = Item.CONTENT_URI; 
      return new CursorLoader(this.getActivity(), queryUri, null, null, null, null); 
     default: 
      throw new IllegalArgumentException("Unknown loader ID: " + i); 
    } 
} 

@Override 
public void onLoadFinished(Loader<Cursor> cursorLoader, Cursor cursor) { 
    if (listAdapter == null) { 
     throw new IllegalStateException("List adapter is missing!"); 
    } else { 
     Log.d(TAG, "Load finished. Cursor swapped."); 
     listAdapter.swapCursor(cursor); 
    } 
} 

更新:

我也試着與我以前工作ArrayAdapter更換SimpleCursorAdapter,但沒有骰子:

listAdapter = new ArrayAdapter<String>(
     this.getActivity(), 
     R.layout.list_item, 
     R.id.item_name, 
     new String[] {"1", "2", "3"} 
); 

更新2:

啊哈!線索!

listAdapter = new ArrayAdapter<String>(
     this.getActivity(), 
     android.R.layout.simple_list_item_activated_1, 
     android.R.id.text1, 
     new String[] {"1", "2", "3"} 
); 

This works。但因爲我實際上需要使用自己的佈局,所以它不能解決我自己的問題。 R.layout.list_itemandroid.R.layout.simple_list_item_activated_1有什麼不同?

+0

你可以分享你的'ListAdapter'嗎? – DroidBender

+0

@MartijnVanMierloo這是一個'SimpleCursorAdapter'。 –

回答

4

幾星期前,我甚至已經完全按照預期工作......在開始使用自定義列表視圖項目佈局之前。

我的猜測是你之前使用的其中一個simple_list_item_activated_x佈局,它們在其背景可繪製的定義中定義了激活的drawable。框架所做的一件事就是將激活的邏輯與被按下的邏輯分開(前者是列表選擇器的一部分,而後者是列表項),但不需要這樣做,你可以將它們全部放置在列表項背景中,並完全禁用選擇器。

我建議將您的自定義drawable作爲每個列表項的背景,而不是列表選擇器;激活是應用於每個單獨項目視圖的狀態。然後,您可以設置android:listSelector="@null",因爲您在某些狀態下具有透明背景,並且不希望默認選擇器顯示。

+0

這似乎不太可能,因爲這是不久前的工作,我絕對沒有這樣做,並且按下也是一個適用於每個單獨的項目視圖的狀態,並且工作得很好。 –

+0

這是因爲選擇器的狀態是從ListView的全局狀態設置的,恰好被按下,因此它在該實例中顯示了正確的drawable,但不是因爲實際項目被設置爲按下。在切換到自定義佈局之前,您正在使用哪種佈局?它是android.R.layout.simple_list_item_activated選項之一嗎? – Devunwired

+0

很可能。我知道我在某個時刻。我有一個git commit,它的日誌消息**聲明**剛剛得到它與自定義佈局的工作,但我不相信自己給出了最新的發現。 –