Java 更新Android选项卡图标

Java 更新Android选项卡图标,java,android,android-tabhost,Java,Android,Android Tabhost,我有一个活动,它有一个TabHost,其中包含一组tabspec,每个tabspec都有一个列表视图,其中包含选项卡要显示的项目。创建每个选项卡规范后,我将在选项卡标题中显示一个图标 选项卡规格是在setupTabs()方法中以这种方式创建的,该方法循环创建适当数量的选项卡: TabSpec ts = mTabs.newTabSpec("tab"); ts.setIndicator("TabTitle", iconResource); ts.setCon

我有一个活动,它有一个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();

有没有办法在不删除和重新创建所有选项卡的情况下替换显示的图标?

简单的回答是,您没有遗漏任何内容。Android SDK没有提供在创建
TabHost
后更改其指示符的直接方法。
TabSpec
仅用于构建选项卡,因此在事实发生后更改
TabSpec
将无效

不过,我认为有一个解决办法。调用
mTabs.getTabWidget()
以获取
TabWidget
对象。这只是
ViewGroup
的一个子类,因此您可以调用
getChildCount()
getChildAt()
来访问
TabWidget
中的各个选项卡。这些选项卡中的每一个都是一个视图,对于带有图形指示器和文本标签的选项卡,几乎可以肯定它是另一个
ViewGroup
(可能是
LinearLayout
,但这并不重要)包含
ImageView
TextView
。因此,只要稍微摆弄一下调试器或
Log.i
,您就应该能够找到获取
ImageView
的方法,并直接对其进行更改


缺点是,如果你不小心,选项卡中控件的确切布局可能会改变,你的应用程序可能会崩溃。您最初的解决方案可能更稳健,但它可能会导致其他不必要的副作用,如闪烁或聚焦问题。

为了确认dominics的答案,以下是他的代码解决方案(实际有效):


当然,它一点也不完美,在getChildAt()中使用这些直接索引一点也不好…

请参阅我的文章,其中包含有关的代码示例

谢谢
Spct这就是我所做的,它对我有用。我在扩展自TabBarActivity的activity中创建了此函数

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);
试试这个:

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));
        }
    }
});

伟大的正是我想要的。谢谢次要改进-使用:TabWidget.getChildTabViewAt(…)而不是getChildAt(…),仅用于提供信息:如果使用材质选项卡布局,则将方法第一行更新为as ViewGroup identifView=(ViewGroup)tabLayout.getTabAt(0).getCustomView();快乐编码:)
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));
        }
    }
});