如何自定义ActionBar?

[Brief]

由于Uses-SDK指定的版本不同, 从而会导致同样的代码有可能在运行时报错, 因此需要特别注意. 详见 [Troubles].

[Quick Start]

1. 编写Java代码和XML布局文件
public class ActivityEx extends Activity {
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        requestWindowFeature(Window.FEATURE_CUSTOM_TITLE);
        setContentView(R.layout.activity_test);
        getWindow().setFeatureInt(Window.FEATURE_CUSTOM_TITLE, R.layout.custom_actionbar);
	}
}
XML布局文件, 略.

 2. 编写styles.xml 自定义 Activity样式
<style name="ActionBar.Style.WindowTitle">
	<item name="android:textColor">#fff</item>
	<item name="android:textSize">14sp</item>
	<item name="android:textStyle">bold</item>
</style>

<style name="ActionBar.Style">
	<item name="android:singleLine">true</item>
	<item name="android:textAppearance">@style/ActionBar.Style.WindowTitle</item>
	<item name="android:shadowColor">#BB000000</item>
	<item name="android:shadowRadius">2.75</item>
</style>

<style name="ActionBar.Background">
	<item name="android:background">@null</item>
</style>

<style name="ActionBar" parent="android:Theme">
	<item name="android:windowTitleStyle">@style/ActionBar.Style</item>
	<item name="android:windowTitleSize">56dp</item>
	<item name="android:windowTitleBackgroundStyle">@style/ActionBar.Background</item>
</style>

P.S. 可参考 \android-sdk\platforms\android-[$level]\data\res\values\themes.xml

3. 编辑AndroidManifest.xml, 启用自定义样式

<activity android:name="net.oschina.my.ActionBarTest"
	android:theme="@style/ActionBar"
	android:label="@string/app_name" >
	<intent-filter>
		<action android:name="android.intent.action.MAIN" />
		<category android:name="android.intent.category.LAUNCHER" />
	</intent-filter>
</activity>


[Troubles]

笔者当前的工程配置如下:
<uses-sdk android:minSdkVersion="8" android:targetSdkVersion="17" />

如果按照默认的工程设置, 并只编写Java代码, 那么App运行时就会报错. 
因此, 为了保险起见, 强制设置Activity的theme, 并且该theme是继承于android:Theme, 否则也将会报错. 错误日志如下:

You cannot combine custom titles with other title features
根据报错日志, 我们可以看到抛异常的类是: android-[$level]\com\android\internal\policy\impl\PhoneWindow.java , 从中可以找到 requestFeature 函数, 如下:
@Override
public boolean requestFeature(int featureId) {
	if (mContentParent != null) {
		throw new AndroidRuntimeException("requestFeature() must be called before adding content");
	}
	final int features = getFeatures();
	if ((features != DEFAULT_FEATURES) && (featureId == FEATURE_CUSTOM_TITLE)) {

		/* Another feature is enabled and the user is trying to enable the custom title feature */
		throw new AndroidRuntimeException("You cannot combine custom titles with other title features");
	}
	if (((features & (1 << FEATURE_CUSTOM_TITLE)) != 0) &&
			(featureId != FEATURE_CUSTOM_TITLE) && (featureId != FEATURE_ACTION_MODE_OVERLAY)) {

		/* Custom title feature is enabled and the user is trying to enable another feature */
		throw new AndroidRuntimeException("You cannot combine custom titles with other title features");
	}
	if ((features & (1 << FEATURE_NO_TITLE)) != 0 && featureId == FEATURE_ACTION_BAR) {
		return false; // Ignore. No title dominates.
	}
	if ((features & (1 << FEATURE_ACTION_BAR)) != 0 && featureId == FEATURE_NO_TITLE) {
		// Remove the action bar feature if we have no title. No title dominates.
		removeFeature(FEATURE_ACTION_BAR);
	}
	return super.requestFeature(featureId);
}

从上面的代码基本可以知道, 为什么需要强制设置theme, 并且该theme还是继承于android:Theme.

[USAGE]

自定义标题的使用方法和View是相同的, 也是通过 findViewById(... ) 来获取对象, 然后绑定消息事件.

[SeeAlso]

http://blog.csdn.net/pathuang68/article/details/6646792

你可能感兴趣的:(android,自定义,action,标题栏,Bar)