43

タブによって表示されるアイテムを含むリストビューを持つTabSpecのセットを含むTabHostを持つアクティビティがあります。各TabSpecを作成するときに、タブヘッダーに表示されるアイコンを設定します。

TabSpecはsetupTabs()、適切な数のタブを作成するためにループするメソッド内でこのように作成されます。

TabSpec ts = mTabs.newTabSpec("tab");
ts.setIndicator("TabTitle", iconResource);

ts.setContent(new TabHost.TabContentFactory(
{
    public View createTabContent(String tag)
    {
        ... 
    }            
});
mTabs.addTab(ts);

プログラムの実行中に各タブに表示されるアイコンを変更できるようにしたい場合がいくつかあります。現在、すべてのタブを削除し、上記のコードを再度呼び出して再作成しています。

mTabs.getTabWidget().removeAllViews();
mTabs.clearAllTabs(true);
setupTabs();

すべてのタブを削除して再作成せずに、表示されているアイコンを置き換える方法はありますか?

4

5 に答える 5

37

簡単に言えば、何も見逃していないということです。Android SDK には、作成後にインジケーターを変更するための直接的な方法はありませんTabHost。はTabSpecタブを作成するためにのみ使用されるため、TabSpec事後に を変更しても効果はありません。

とはいえ、回避策はあると思います。mTabs.getTabWidget()オブジェクトを取得するために呼び出しTabWidgetます。これは の単なるサブクラスでViewGroupあるため、 を呼び出しgetChildCount()getChildAt()内の個々のタブにアクセスできますTabWidget。これらの各タブはビューでもあり、グラフィック インジケーターとテキスト ラベルを含むタブの場合、ほぼ確実に と を含む別のタブViewGroup(の可能性がありますが、問題ではありLinearLayoutません) です。そのため、デバッガまたは を少しいじるだけで、を取得して直接変更するためのレシピを見つけることができるはずです。ImageViewTextViewLog.iImageView

欠点は、注意しないと、タブ内のコントロールの正確なレイアウトが変更され、アプリが壊れる可能性があることです。最初のソリューションはおそらくより堅牢ですが、ちらつきやフォーカスの問題など、他の望ましくない副作用につながる可能性があります。

于 2008-09-15T23:59:28.807 に答える
30

ドミニクスの答えを確認するために、コードでの彼のソリューションを次に示します(実際に機能します):

tabHost.setOnTabChangedListener(new OnTabChangeListener() {
    public void onTabChanged(String tabId) {
        if (TAB_MAP.equals(tabId)) {
            ImageView iv = (ImageView) tabHost.getTabWidget().getChildAt(0).findViewById(android.R.id.icon);
            iv.setImageDrawable(getResources().getDrawable(R.drawable.tab_map_black));
            iv = (ImageView) tabHost.getTabWidget().getChildAt(1).findViewById(android.R.id.icon);
            iv.setImageDrawable(getResources().getDrawable(R.drawable.tab_list_white));
        } else if (TAB_LIST.equals(tabId)) {
            ImageView iv = (ImageView) tabHost.getTabWidget().getChildAt(0).findViewById(android.R.id.icon);
            iv.setImageDrawable(getResources().getDrawable(R.drawable.tab_map_white));
            iv = (ImageView) tabHost.getTabWidget().getChildAt(1).findViewById(android.R.id.icon);
            iv.setImageDrawable(getResources().getDrawable(R.drawable.tab_list_black));
        }
    }
});

もちろん、それはまったく洗練されておらず、 getChildAt() でこれらの直接インデックスを使用するのはまったく良くありません...

于 2009-02-02T17:19:26.177 に答える
6

カスタマイズされたAndroidタブに関するコード例を含む私の投稿を参照してください。

ありがとうSpct

于 2009-02-04T05:41:23.260 に答える
5

これは私がやったことであり、私にとってはうまくいきます。TabBarActivity から拡張されたアクティビティでこの関数を作成しました

public void updateTab(int stringID) {
    ViewGroup identifyView = (ViewGroup)getTabWidget().getChildAt(0);
    TextView v =  (TextView)identifyView.getChildAt(identifyView.getChildCount() - 1);
    v.setText(stringID);
}

この関数を変更してテキストの代わりに画像を変更するか、両方を変更できます。また、これを変更して任意のタブの子を取得することもできます。実行時に最初のタブのテキストを変更することに特に興味がありました。

この呼び出しを使用して、関連するアクティビティからこの関数を呼び出しました

getParent().updateTab(R.string.tab_bar_analyze);
于 2011-07-08T17:13:58.257 に答える
4

これを試して:

tabHost.setOnTabChangedListener(new OnTabChangeListener() {
    public void onTabChanged(String tabId) {
        if (TAB_MAP.equals(tabId)) {
            ImageView iv = (ImageView) tabHost.getTabWidget().getChildAt(0).findViewById(android.R.id.icon);
            iv.setImageDrawable(getResources().getDrawable(R.drawable.tab_map_black));
            iv = (ImageView) tabHost.getTabWidget().getChildAt(1).findViewById(android.R.id.icon);
            iv.setImageDrawable(getResources().getDrawable(R.drawable.tab_list_white));
        } else if (TAB_LIST.equals(tabId)) {
            ImageView iv = (ImageView) tabHost.getTabWidget().getChildAt(0).findViewById(android.R.id.icon);
            iv.setImageDrawable(getResources().getDrawable(R.drawable.tab_map_white));
            iv = (ImageView) tabHost.getTabWidget().getChildAt(1).findViewById(android.R.id.icon);
            iv.setImageDrawable(getResources().getDrawable(R.drawable.tab_list_black));
        }
    }
});
于 2012-08-04T12:48:59.833 に答える