1/*
2 * Copyright (C) 2015 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 *      http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17package com.android.settings;
18
19import android.app.Activity;
20import android.app.ProgressDialog;
21import android.content.BroadcastReceiver;
22import android.content.Context;
23import android.content.Intent;
24import android.content.IntentFilter;
25import android.content.pm.PackageManager;
26import android.content.pm.ResolveInfo;
27import android.os.Bundle;
28import android.os.Handler;
29import android.os.Message;
30import android.os.UserHandle;
31import android.os.PowerManager;
32import android.os.SystemClock;
33import android.os.UserManager;
34import android.provider.Settings;
35import android.util.Log;
36import android.view.View;
37import android.view.WindowManager;
38import android.view.WindowManager.LayoutParams;
39import android.view.animation.AnimationUtils;
40
41import java.util.Objects;
42
43public class FallbackHome extends Activity {
44    private static final String TAG = "FallbackHome";
45    private static final int PROGRESS_TIMEOUT = 2000;
46
47    private boolean mProvisioned;
48
49    private final Runnable mProgressTimeoutRunnable = () -> {
50        View v = getLayoutInflater().inflate(
51                R.layout.fallback_home_finishing_boot, null /* root */);
52        setContentView(v);
53        v.setAlpha(0f);
54        v.animate()
55                .alpha(1f)
56                .setDuration(500)
57                .setInterpolator(AnimationUtils.loadInterpolator(
58                        this, android.R.interpolator.fast_out_slow_in))
59                .start();
60        getWindow().addFlags(LayoutParams.FLAG_KEEP_SCREEN_ON);
61    };
62
63    @Override
64    protected void onCreate(Bundle savedInstanceState) {
65        super.onCreate(savedInstanceState);
66
67        // Set ourselves totally black before the device is provisioned so that
68        // we don't flash the wallpaper before SUW
69        mProvisioned = Settings.Global.getInt(getContentResolver(),
70                Settings.Global.DEVICE_PROVISIONED, 0) != 0;
71        if (!mProvisioned) {
72            setTheme(R.style.FallbackHome_SetupWizard);
73            getWindow().getDecorView().setSystemUiVisibility(View.SYSTEM_UI_FLAG_FULLSCREEN
74                    | View.SYSTEM_UI_FLAG_HIDE_NAVIGATION | View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY);
75        } else {
76            getWindow().getDecorView().setSystemUiVisibility(View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN
77                    | View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION);
78        }
79
80        registerReceiver(mReceiver, new IntentFilter(Intent.ACTION_USER_UNLOCKED));
81        maybeFinish();
82    }
83
84    @Override
85    protected void onResume() {
86        super.onResume();
87        if (mProvisioned) {
88            mHandler.postDelayed(mProgressTimeoutRunnable, PROGRESS_TIMEOUT);
89        }
90    }
91
92    @Override
93    protected void onPause() {
94        super.onPause();
95        mHandler.removeCallbacks(mProgressTimeoutRunnable);
96    }
97
98    protected void onDestroy() {
99        super.onDestroy();
100        unregisterReceiver(mReceiver);
101    }
102
103    private BroadcastReceiver mReceiver = new BroadcastReceiver() {
104        @Override
105        public void onReceive(Context context, Intent intent) {
106            maybeFinish();
107        }
108    };
109
110    private void maybeFinish() {
111        if (getSystemService(UserManager.class).isUserUnlocked()) {
112            final Intent homeIntent = new Intent(Intent.ACTION_MAIN)
113                    .addCategory(Intent.CATEGORY_HOME);
114            final ResolveInfo homeInfo = getPackageManager().resolveActivity(homeIntent, 0);
115            if (Objects.equals(getPackageName(), homeInfo.activityInfo.packageName)) {
116                if (UserManager.isSplitSystemUser()
117                        && UserHandle.myUserId() == UserHandle.USER_SYSTEM) {
118                    // This avoids the situation where the system user has no home activity after
119                    // SUW and this activity continues to throw out warnings. See b/28870689.
120                    return;
121                }
122                Log.d(TAG, "User unlocked but no home; let's hope someone enables one soon?");
123                mHandler.sendEmptyMessageDelayed(0, 500);
124            } else {
125                Log.d(TAG, "User unlocked and real home found; let's go!");
126                getSystemService(PowerManager.class).userActivity(
127                        SystemClock.uptimeMillis(), false);
128                finish();
129            }
130        }
131    }
132
133    private Handler mHandler = new Handler() {
134        @Override
135        public void handleMessage(Message msg) {
136            maybeFinish();
137        }
138    };
139}
140