1 /* 2 * Copyright (C) 2016 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 package com.android.emergency.view; 17 18 import androidx.fragment.app.Fragment; 19 import androidx.fragment.app.FragmentActivity; 20 import androidx.fragment.app.FragmentManager; 21 import android.content.Context; 22 import android.content.Intent; 23 import android.content.SharedPreferences; 24 import android.graphics.Bitmap; 25 import android.graphics.drawable.Drawable; 26 import android.os.Bundle; 27 import androidx.annotation.LayoutRes; 28 import android.os.UserHandle; 29 import android.os.UserManager; 30 import com.google.android.material.tabs.TabLayout; 31 import com.google.android.material.tabs.TabLayout.TabLayoutOnPageChangeListener; 32 import com.google.android.material.tabs.TabLayout.ViewPagerOnTabSelectedListener; 33 import androidx.fragment.app.FragmentStatePagerAdapter; 34 import androidx.viewpager.widget.ViewPager; 35 import androidx.preference.PreferenceManager; 36 37 import android.provider.Settings; 38 import android.text.TextUtils; 39 import android.util.Log; 40 import android.util.Pair; 41 import android.view.Menu; 42 import android.view.MenuInflater; 43 import android.view.MenuItem; 44 import android.view.View; 45 import android.widget.ImageView; 46 import android.widget.LinearLayout; 47 import android.widget.TextView; 48 import android.widget.Toolbar; 49 import android.widget.ViewFlipper; 50 51 import com.android.emergency.CircleFramedDrawable; 52 import com.android.emergency.R; 53 import com.android.emergency.edit.EditInfoActivity; 54 import com.android.emergency.util.PreferenceUtils; 55 import com.android.internal.annotations.VisibleForTesting; 56 import com.android.internal.logging.MetricsLogger; 57 import com.android.internal.logging.nano.MetricsProto.MetricsEvent; 58 import com.android.internal.util.UserIcons; 59 60 import java.util.ArrayList; 61 62 /** 63 * Activity for viewing emergency information. 64 */ 65 public class ViewInfoActivity extends FragmentActivity { 66 67 private static final String TAG = "ViewInfoActivity"; 68 69 private ImageView mPersonalCardLargeIcon; 70 private TextView mPersonalCardLargeItem; 71 private SharedPreferences mSharedPreferences; 72 private LinearLayout mPersonalCard; 73 private ViewFlipper mViewFlipper; 74 private ViewPagerAdapter mTabsAdapter; 75 private TabLayout mTabLayout; 76 private ArrayList<Pair<String, Fragment>> mFragments; 77 private Menu mMenu; 78 79 @Override setContentView(@ayoutRes int layoutResID)80 public void setContentView(@LayoutRes int layoutResID) { 81 super.setContentView(layoutResID); 82 setupTabs(); 83 Toolbar toolbar = (Toolbar) findViewById(R.id.action_bar); 84 setActionBar(toolbar); 85 getActionBar().setDisplayHomeAsUpEnabled(true); 86 } 87 88 @Override onCreate(Bundle savedInstanceState)89 protected void onCreate(Bundle savedInstanceState) { 90 super.onCreate(savedInstanceState); 91 setContentView(R.layout.view_activity_layout); 92 mSharedPreferences = PreferenceManager.getDefaultSharedPreferences(this); 93 mPersonalCard = (LinearLayout) findViewById(R.id.name_and_dob_linear_layout); 94 mPersonalCardLargeIcon = (ImageView) findViewById(R.id.personal_card_icon); 95 mPersonalCardLargeItem = (TextView) findViewById(R.id.personal_card_large); 96 mViewFlipper = (ViewFlipper) findViewById(R.id.view_flipper); 97 98 MetricsLogger.visible(this, MetricsEvent.ACTION_VIEW_EMERGENCY_INFO); 99 } 100 101 @Override onResume()102 public void onResume() { 103 super.onResume(); 104 loadUserInfo(); 105 // Update the tabs: new info might have been added/deleted from the edit screen that 106 // could lead to adding/removing a fragment 107 setupTabs(); 108 maybeHideTabs(); 109 } 110 loadUserInfo()111 private void loadUserInfo() { 112 UserManager userManager = getSystemService(UserManager.class); 113 if (TextUtils.isEmpty(userManager.getUserName())) { 114 mPersonalCard.setVisibility(View.GONE); 115 } else { 116 mPersonalCard.setVisibility(View.VISIBLE); 117 mPersonalCardLargeItem.setText(userManager.getUserName()); 118 119 Bitmap bitmapUserIcon = userManager.getUserIcon(UserHandle.myUserId()); 120 121 if (bitmapUserIcon == null) { 122 // Get default user icon. 123 Drawable defaultUserIcon = UserIcons.getDefaultUserIcon( 124 getApplicationContext().getResources(), UserHandle.myUserId(), 125 false /* light icon */); 126 bitmapUserIcon = UserIcons.convertToBitmap(defaultUserIcon); 127 } 128 129 Drawable drawableUserIcon = new CircleFramedDrawable(bitmapUserIcon, 130 (int) getResources().getDimension(R.dimen.action_bar_size)); 131 132 mPersonalCardLargeIcon.setImageDrawable(drawableUserIcon); 133 } 134 } 135 maybeHideTabs()136 private void maybeHideTabs() { 137 // Show a TextView with "No information provided" if there are no fragments. 138 if (mFragments.size() == 0) { 139 mViewFlipper.setDisplayedChild( 140 mViewFlipper.indexOfChild(findViewById(R.id.no_info))); 141 } else { 142 mViewFlipper.setDisplayedChild(mViewFlipper.indexOfChild(findViewById(R.id.tabs))); 143 } 144 145 TabLayout tabLayout = mTabLayout; 146 if (mFragments.size() <= 1) { 147 tabLayout.setVisibility(View.GONE); 148 } else { 149 tabLayout.setVisibility(View.VISIBLE); 150 } 151 } 152 153 @Override onCreateOptionsMenu(Menu menu)154 public boolean onCreateOptionsMenu(Menu menu) { 155 if (Settings.Secure.getInt(getContentResolver(), 156 Settings.Secure.USER_SETUP_COMPLETE, 0) == 0) { 157 Log.d(TAG, "Device setup not complete, not showing edit button."); 158 return super.onCreateOptionsMenu(menu); 159 } 160 161 MenuInflater inflater = getMenuInflater(); 162 inflater.inflate(R.menu.view_info_menu, menu); 163 mMenu = menu; 164 return super.onCreateOptionsMenu(menu); 165 } 166 167 @Override onOptionsItemSelected(MenuItem item)168 public boolean onOptionsItemSelected(MenuItem item) { 169 int itemId = item.getItemId(); 170 if (itemId == android.R.id.home) { 171 onBackPressed(); 172 return true; 173 } else if (itemId == R.id.action_edit) { 174 Intent intent = new Intent(this, EditInfoActivity.class); 175 intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP); 176 startActivity(intent); 177 return true; 178 } 179 return super.onOptionsItemSelected(item); 180 } 181 182 /** Return the tab layout. */ 183 @VisibleForTesting getTabLayout()184 public TabLayout getTabLayout() { 185 return mTabLayout; 186 } 187 188 @VisibleForTesting getMenu()189 public Menu getMenu() { 190 return mMenu; 191 } 192 193 /** Return the fragments. */ 194 @VisibleForTesting getFragments()195 public ArrayList<Pair<String, Fragment>> getFragments() { 196 return mFragments; 197 } 198 setUpFragments()199 private ArrayList<Pair<String, Fragment>> setUpFragments() { 200 // Return only the fragments that have at least one piece of information set: 201 ArrayList<Pair<String, Fragment>> fragments = new ArrayList<>(2); 202 203 if (PreferenceUtils.hasAtLeastOnePreferenceSet(this)) { 204 fragments.add(Pair.create(getResources().getString(R.string.tab_title_info), 205 ViewEmergencyInfoFragment.newInstance())); 206 } 207 if (PreferenceUtils.hasAtLeastOneEmergencyContact(this)) { 208 fragments.add(Pair.create(getResources().getString(R.string.tab_title_contacts), 209 ViewEmergencyContactsFragment.newInstance())); 210 } 211 return fragments; 212 } 213 setupTabs()214 private void setupTabs() { 215 mFragments = setUpFragments(); 216 mTabLayout = (TabLayout) findViewById(R.id.sliding_tabs); 217 if (mTabsAdapter == null) { 218 // The viewpager that will host the section contents. 219 ViewPager viewPager = (ViewPager) findViewById(R.id.view_pager); 220 mTabsAdapter = new ViewPagerAdapter(getSupportFragmentManager()); 221 viewPager.setAdapter(mTabsAdapter); 222 mTabLayout.setTabsFromPagerAdapter(mTabsAdapter); 223 224 // Set a listener via setOnTabSelectedListener(OnTabSelectedListener) to be notified 225 // when any tab's selection state has been changed. 226 mTabLayout.setOnTabSelectedListener( 227 new TabLayout.ViewPagerOnTabSelectedListener(viewPager)); 228 229 // Use a TabLayout.TabLayoutOnPageChangeListener to forward the scroll and selection 230 // changes to this layout 231 viewPager.addOnPageChangeListener(new TabLayoutOnPageChangeListener(mTabLayout)); 232 } else { 233 mTabsAdapter.notifyDataSetChanged(); 234 mTabLayout.setTabsFromPagerAdapter(mTabsAdapter); 235 } 236 } 237 238 /** The adapter used to handle the two fragments. */ 239 protected class ViewPagerAdapter extends FragmentStatePagerAdapter { ViewPagerAdapter(FragmentManager fm)240 public ViewPagerAdapter(FragmentManager fm) { 241 super(fm); 242 } 243 244 @Override getItem(int position)245 public Fragment getItem(int position) { 246 return mFragments.get(position).second; 247 } 248 249 @Override getCount()250 public int getCount() { 251 return mFragments.size(); 252 } 253 254 @Override getPageTitle(int position)255 public CharSequence getPageTitle(int position) { 256 return mFragments.get(position).first; 257 } 258 259 @Override getItemPosition(Object object)260 public int getItemPosition(Object object) { 261 // The default implementation assumes that items will never change position and always 262 // returns POSITION_UNCHANGED. This is how you can specify that the positions can change 263 return FragmentStatePagerAdapter.POSITION_NONE; 264 } 265 } 266 } 267