1 /* 2 * Copyright 2018 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 17 package com.android.pump.activity; 18 19 import android.Manifest; 20 import android.content.pm.PackageManager; 21 import android.os.Bundle; 22 import android.view.Menu; 23 import android.view.MenuItem; 24 import android.view.View; 25 26 import androidx.annotation.IdRes; 27 import androidx.annotation.NonNull; 28 import androidx.annotation.Nullable; 29 import androidx.annotation.UiThread; 30 import androidx.appcompat.app.ActionBar; 31 import androidx.appcompat.app.AppCompatActivity; 32 import androidx.core.content.ContextCompat; 33 import androidx.core.view.GravityCompat; 34 import androidx.drawerlayout.widget.DrawerLayout; 35 import androidx.fragment.app.Fragment; 36 import androidx.fragment.app.FragmentManager; 37 import androidx.fragment.app.FragmentPagerAdapter; 38 import androidx.viewpager.widget.ViewPager; 39 40 import com.android.pump.R; 41 import com.android.pump.fragment.AlbumFragment; 42 import com.android.pump.fragment.ArtistFragment; 43 import com.android.pump.fragment.AudioFragment; 44 import com.android.pump.fragment.GenreFragment; 45 import com.android.pump.fragment.HomeFragment; 46 import com.android.pump.fragment.MovieFragment; 47 import com.android.pump.fragment.OtherFragment; 48 import com.android.pump.fragment.PermissionFragment; 49 import com.android.pump.fragment.PlaylistFragment; 50 import com.android.pump.fragment.SeriesFragment; 51 import com.android.pump.util.Globals; 52 import com.google.android.material.bottomnavigation.BottomNavigationView; 53 import com.google.android.material.bottomnavigation.BottomNavigationView.OnNavigationItemSelectedListener; 54 import com.google.android.material.tabs.TabLayout; 55 56 @UiThread 57 public class PumpActivity extends AppCompatActivity implements OnNavigationItemSelectedListener { 58 // TODO The following should be a non-static member 59 private static boolean sIsMissingPermissions = true; 60 61 private static final Pages[] PAGES_LIST = { 62 new Pages(R.id.menu_home, new Page[] { 63 new Page(HomeFragment::newInstance, "Home") 64 }), 65 new Pages(R.id.menu_video, new Page[] { 66 new Page(MovieFragment::newInstance, "Movies"), 67 new Page(SeriesFragment::newInstance, "TV Shows"), 68 new Page(OtherFragment::newInstance, "Personal"), 69 new Page(HomeFragment::newInstance, "All videos") 70 }), 71 new Pages(R.id.menu_audio, new Page[] { 72 new Page(AudioFragment::newInstance, "All audios"), 73 new Page(PlaylistFragment::newInstance, "Playlists"), 74 new Page(AlbumFragment::newInstance, "Albums"), 75 new Page(GenreFragment::newInstance, "Genres"), 76 new Page(ArtistFragment::newInstance, "Artists") 77 }), 78 new Pages(R.id.menu_favorite, new Page[] { 79 new Page(HomeFragment::newInstance, "Videos"), 80 new Page(HomeFragment::newInstance, "Audios") 81 }) 82 }; 83 84 private boolean mInitialized = false; 85 86 private ActivityPagerAdapter mActivityPagerAdapter; 87 88 private DrawerLayout mDrawerLayout; 89 private ViewPager mViewPager; 90 private TabLayout mTabLayout; 91 private BottomNavigationView mBottomNavigationView; 92 93 @Override onCreate(@ullable Bundle savedInstanceState)94 protected void onCreate(@Nullable Bundle savedInstanceState) { 95 super.onCreate(savedInstanceState); 96 // NOTE: If you are facing StrictMode violation by setContentView please disable instant run 97 setContentView(R.layout.activity_pump); 98 99 setSupportActionBar(findViewById(R.id.activity_pump_toolbar)); 100 101 mActivityPagerAdapter = new ActivityPagerAdapter(getSupportFragmentManager()); 102 103 mDrawerLayout = findViewById(R.id.activity_pump_drawer_layout); 104 mViewPager = findViewById(R.id.activity_pump_view_pager); 105 mTabLayout = findViewById(R.id.activity_pump_tab_layout); 106 mBottomNavigationView = findViewById(R.id.activity_pump_bottom_navigation_view); 107 108 mBottomNavigationView.setOnNavigationItemSelectedListener(this); 109 mBottomNavigationView.setSelectedItemId(R.id.menu_home); 110 mViewPager.setAdapter(mActivityPagerAdapter); 111 mTabLayout.setupWithViewPager(mViewPager); 112 } 113 114 @Override onResume()115 public void onResume() { 116 super.onResume(); 117 118 initialize(); 119 } 120 121 @Override onCreateOptionsMenu(@onNull Menu menu)122 public boolean onCreateOptionsMenu(@NonNull Menu menu) { 123 getMenuInflater().inflate(R.menu.activity_pump, menu); 124 return true; 125 } 126 127 @Override onOptionsItemSelected(@onNull MenuItem item)128 public boolean onOptionsItemSelected(@NonNull MenuItem item) { 129 if (item.getItemId() == android.R.id.home) { 130 mDrawerLayout.openDrawer(GravityCompat.START); 131 return true; 132 } 133 return super.onOptionsItemSelected(item); 134 } 135 136 @Override onNavigationItemSelected(@onNull MenuItem item)137 public boolean onNavigationItemSelected(@NonNull MenuItem item) { 138 for (Pages pages : PAGES_LIST) { 139 if (pages.getId() == item.getItemId()) { 140 selectPages(item.getTitle(), pages); 141 return true; 142 } 143 } 144 return false; 145 } 146 147 // TODO This should not be public initialize()148 public void initialize() { 149 if (ContextCompat.checkSelfPermission(this, Manifest.permission.READ_EXTERNAL_STORAGE) 150 == PackageManager.PERMISSION_GRANTED) { 151 if (!mInitialized) { 152 mInitialized = true; 153 154 sIsMissingPermissions = false; 155 mActivityPagerAdapter.notifyDataSetChanged(); 156 157 Globals.getMediaDb(this).load(); 158 } 159 } 160 } 161 selectPages(@onNull CharSequence title, @NonNull Pages pages)162 private void selectPages(@NonNull CharSequence title, @NonNull Pages pages) { 163 ActionBar actionBar = getSupportActionBar(); 164 if (actionBar != null) { 165 actionBar.setTitle(title); 166 } 167 168 Pages current = mActivityPagerAdapter.getPages(); 169 if (current != null) { 170 current.setCurrent(mViewPager.getCurrentItem()); 171 } 172 173 mActivityPagerAdapter.setPages(pages); 174 int count = mActivityPagerAdapter.getCount(); 175 mTabLayout.setVisibility(count <= 1 ? View.GONE : View.VISIBLE); 176 mTabLayout.setTabMode(count <= 4 ? TabLayout.MODE_FIXED : TabLayout.MODE_SCROLLABLE); 177 mViewPager.setCurrentItem(pages.getCurrent()); 178 } 179 180 private static class ActivityPagerAdapter extends FragmentPagerAdapter { 181 private Pages mPages; 182 ActivityPagerAdapter(@onNull FragmentManager fm)183 ActivityPagerAdapter(@NonNull FragmentManager fm) { 184 super(fm); 185 } 186 setPages(@onNull Pages pages)187 void setPages(@NonNull Pages pages) { 188 mPages = pages; 189 notifyDataSetChanged(); 190 } 191 getPages()192 @Nullable Pages getPages() { 193 return mPages; 194 } 195 196 @Override getCount()197 public int getCount() { 198 return mPages.getPages().length; 199 } 200 201 @Override getItem(int position)202 public @NonNull Fragment getItem(int position) { 203 return mPages.getPages()[position].createFragment(); 204 } 205 206 @Override getItemId(int position)207 public long getItemId(int position) { 208 return mPages.getPages()[position].getId(); 209 } 210 211 @Override getItemPosition(@onNull Object object)212 public int getItemPosition(@NonNull Object object) { 213 return POSITION_NONE; 214 } 215 216 @Override getPageTitle(int position)217 public @NonNull CharSequence getPageTitle(int position) { 218 return mPages.getPages()[position].getTitle(); 219 } 220 } 221 222 private static class Page { 223 private static int sId = 0; 224 225 private final int mId; 226 private final PageCreator mPageCreator; 227 private final String mTitle; 228 Page(@onNull PageCreator pageCreator, @NonNull String title)229 Page(@NonNull PageCreator pageCreator, @NonNull String title) { 230 mId = sId++; 231 mPageCreator = pageCreator; 232 mTitle = title; 233 } 234 getId()235 int getId() { 236 if (isMissingPermissions()) { 237 return ~mId; 238 } 239 return mId; 240 } 241 createFragment()242 @NonNull Fragment createFragment() { 243 if (isMissingPermissions()) { 244 return PermissionFragment.newInstance(); 245 } 246 return mPageCreator.newInstance(); 247 } 248 getTitle()249 @NonNull String getTitle() { 250 return mTitle; 251 } 252 isMissingPermissions()253 private boolean isMissingPermissions() { 254 return sIsMissingPermissions; 255 } 256 } 257 258 private static class Pages { 259 private final int mId; 260 private final Page[] mPages; 261 262 private int mCurrent; 263 Pages(@dRes int id, @NonNull Page[] pages)264 Pages(@IdRes int id, @NonNull Page[] pages) { 265 mId = id; 266 mPages = pages; 267 } 268 getId()269 int getId() { 270 return mId; 271 } 272 getPages()273 @NonNull Page[] getPages() { 274 return mPages; 275 } 276 setCurrent(int current)277 void setCurrent(int current) { 278 mCurrent = current; 279 } 280 getCurrent()281 int getCurrent() { 282 return mCurrent; 283 } 284 } 285 286 @FunctionalInterface 287 private interface PageCreator { newInstance()288 @NonNull Fragment newInstance(); 289 } 290 } 291