windowIsTranslucentとwindowBackground愛恨み
2362 ワード
関連知識点:Activity、Window、Dialog、View関連
前言:今日は質問があります(以下).私を楽しませる原則を分かち合って、問題を解決した後、この編を書きます.
質問:
WindowBackgroundが透明な場合、windowIsTranslucentはfalse、Activity背景はなぜ黒なのか、なぜ透明ではないのか.WindowBackgroundが赤の場合、windowIsTranslucentはtrue、Activityバックグラウンドは赤ですが、なぜ透明ではありませんか?
解決:
1、単刀直入コアテーマ:windowBackground、windowIsTranslucentはその名の通りWindow属性ですが、具体的な実現はどこですか?RootViewで------つまりDecorViewクラスの1、私たちはDecorViewクラスに入ります:2、setWindowBackgroundメソッドを見つけますpublic void setWindowBackground(Drawable drawable) {
if (getBackground() != drawable) {
setBackgroundDrawable(drawable);
if (drawable != null) {
mResizingBackgroundDrawable = enforceNonTranslucentBackground(drawable,
mWindow.isTranslucent() || mWindow.isShowingWallpaper());
} else {
mResizingBackgroundDrawable = getResizingBackgroundDrawable(
getContext(), 0, mWindow.mBackgroundFallbackResource,
mWindow.isTranslucent() || mWindow.isShowingWallpaper());
}
if (mResizingBackgroundDrawable != null) {
mResizingBackgroundDrawable.getPadding(mBackgroundPadding);
} else {
mBackgroundPadding.setEmpty();
}
drawableChanged();
}
}
Windowに使用されていることがわかりますisTranslucent()では、さらに下を探します
3、enforceNonTranslucentBackgroundを見つける/**
* Enforces a drawable to be non-translucent to act as a background if needed, i.e. if the
* window is not translucent.
*/
private static Drawable enforceNonTranslucentBackground(Drawable drawable,
boolean windowTranslucent) {
if (!windowTranslucent && drawable instanceof ColorDrawable) {
ColorDrawable colorDrawable = (ColorDrawable) drawable;
int color = colorDrawable.getColor();
if (Color.alpha(color) != 255) {
ColorDrawable copy = (ColorDrawable) colorDrawable.getConstantState().newDrawable()
.mutate();
copy.setColor(
Color.argb(255, Color.red(color), Color.green(color), Color.blue(color)));
return copy;
}
}
return drawable;
}
EnforceNonTranslucentBackgroundの大まかな論理:windowTranslucent==falseの場合、enforceNonTranslucentBackgroundはバックグラウンドを不透明なバックグラウンドに強制的に変更します(PS:windowBackgroundが透明であっても)
public void setWindowBackground(Drawable drawable) {
if (getBackground() != drawable) {
setBackgroundDrawable(drawable);
if (drawable != null) {
mResizingBackgroundDrawable = enforceNonTranslucentBackground(drawable,
mWindow.isTranslucent() || mWindow.isShowingWallpaper());
} else {
mResizingBackgroundDrawable = getResizingBackgroundDrawable(
getContext(), 0, mWindow.mBackgroundFallbackResource,
mWindow.isTranslucent() || mWindow.isShowingWallpaper());
}
if (mResizingBackgroundDrawable != null) {
mResizingBackgroundDrawable.getPadding(mBackgroundPadding);
} else {
mBackgroundPadding.setEmpty();
}
drawableChanged();
}
}
/**
* Enforces a drawable to be non-translucent to act as a background if needed, i.e. if the
* window is not translucent.
*/
private static Drawable enforceNonTranslucentBackground(Drawable drawable,
boolean windowTranslucent) {
if (!windowTranslucent && drawable instanceof ColorDrawable) {
ColorDrawable colorDrawable = (ColorDrawable) drawable;
int color = colorDrawable.getColor();
if (Color.alpha(color) != 255) {
ColorDrawable copy = (ColorDrawable) colorDrawable.getConstantState().newDrawable()
.mutate();
copy.setColor(
Color.argb(255, Color.red(color), Color.green(color), Color.blue(color)));
return copy;
}
}
return drawable;
}