From dbe4e751b70b1f1699eed4047c7a1a772c4bcc8f Mon Sep 17 00:00:00 2001 From: Dianne Hackborn Date: Fri, 11 Oct 2013 16:17:58 -0700 Subject: [PATCH] New system UI API demos. - Content browser that hides nav bar. - Translucent bars. - All the new flags on the direct system UI tweaker example. Change-Id: I16fc8da252174db1ed45b0f60c37d6cbb8d7f13c --- samples/ApiDemos/AndroidManifest.xml | 21 ++ .../res/layout/content_browser_nav.xml | 51 ++++ .../ApiDemos/res/layout/system_ui_modes.xml | 259 +++++++++-------- .../ApiDemos/res/layout/translucent_bars.xml | 27 ++ samples/ApiDemos/res/values-land/integers.xml | 21 ++ samples/ApiDemos/res/values-v19/bools.xml | 22 ++ samples/ApiDemos/res/values/bools.xml | 5 + samples/ApiDemos/res/values/integers.xml | 21 ++ .../apis/view/ContentBrowserNavActivity.java | 266 ++++++++++++++++++ .../android/apis/view/SystemUIModes.java | 51 +++- .../apis/view/TranslucentBarsActivity.java | 36 +++ 11 files changed, 663 insertions(+), 117 deletions(-) create mode 100644 samples/ApiDemos/res/layout/content_browser_nav.xml create mode 100644 samples/ApiDemos/res/layout/translucent_bars.xml create mode 100644 samples/ApiDemos/res/values-land/integers.xml create mode 100644 samples/ApiDemos/res/values-v19/bools.xml create mode 100644 samples/ApiDemos/res/values/integers.xml create mode 100644 samples/ApiDemos/src/com/example/android/apis/view/ContentBrowserNavActivity.java create mode 100644 samples/ApiDemos/src/com/example/android/apis/view/TranslucentBarsActivity.java diff --git a/samples/ApiDemos/AndroidManifest.xml b/samples/ApiDemos/AndroidManifest.xml index 898de2792..3d1d2c1c2 100644 --- a/samples/ApiDemos/AndroidManifest.xml +++ b/samples/ApiDemos/AndroidManifest.xml @@ -2401,6 +2401,17 @@ + + + + + + + + + + + + + + diff --git a/samples/ApiDemos/res/layout/content_browser_nav.xml b/samples/ApiDemos/res/layout/content_browser_nav.xml new file mode 100644 index 000000000..e006620fd --- /dev/null +++ b/samples/ApiDemos/res/layout/content_browser_nav.xml @@ -0,0 +1,51 @@ + + + + + + + + + + diff --git a/samples/ApiDemos/res/layout/system_ui_modes.xml b/samples/ApiDemos/res/layout/system_ui_modes.xml index aaf6c1a21..a4e63e329 100644 --- a/samples/ApiDemos/res/layout/system_ui_modes.xml +++ b/samples/ApiDemos/res/layout/system_ui_modes.xml @@ -28,126 +28,159 @@ android:layout_width="match_parent" android:layout_height="match_parent" android:fitsSystemWindows="true"> - + android:background="#60000000"> + - - - - + + + + + + - - - - + + + + - - - - - - - + + + + + + + + + + + diff --git a/samples/ApiDemos/res/layout/translucent_bars.xml b/samples/ApiDemos/res/layout/translucent_bars.xml new file mode 100644 index 000000000..c7cbe4056 --- /dev/null +++ b/samples/ApiDemos/res/layout/translucent_bars.xml @@ -0,0 +1,27 @@ + + + + + + diff --git a/samples/ApiDemos/res/values-land/integers.xml b/samples/ApiDemos/res/values-land/integers.xml new file mode 100644 index 000000000..d7e7c3795 --- /dev/null +++ b/samples/ApiDemos/res/values-land/integers.xml @@ -0,0 +1,21 @@ + + + + + + 3 + diff --git a/samples/ApiDemos/res/values-v19/bools.xml b/samples/ApiDemos/res/values-v19/bools.xml new file mode 100644 index 000000000..136d8fe17 --- /dev/null +++ b/samples/ApiDemos/res/values-v19/bools.xml @@ -0,0 +1,22 @@ + + + + + + true + diff --git a/samples/ApiDemos/res/values/bools.xml b/samples/ApiDemos/res/values/bools.xml index 366d7337a..fa3f25fb8 100644 --- a/samples/ApiDemos/res/values/bools.xml +++ b/samples/ApiDemos/res/values/bools.xml @@ -44,4 +44,9 @@ for JellyBean MR 2 is true. --> false + + false + diff --git a/samples/ApiDemos/res/values/integers.xml b/samples/ApiDemos/res/values/integers.xml new file mode 100644 index 000000000..70a6c69bc --- /dev/null +++ b/samples/ApiDemos/res/values/integers.xml @@ -0,0 +1,21 @@ + + + + + + 2 + diff --git a/samples/ApiDemos/src/com/example/android/apis/view/ContentBrowserNavActivity.java b/samples/ApiDemos/src/com/example/android/apis/view/ContentBrowserNavActivity.java new file mode 100644 index 000000000..2c5f7bf20 --- /dev/null +++ b/samples/ApiDemos/src/com/example/android/apis/view/ContentBrowserNavActivity.java @@ -0,0 +1,266 @@ +/* + * Copyright (C) 2013 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.example.android.apis.view; + +import android.app.ActionBar; +import android.app.ActionBar.Tab; +import android.app.Activity; +import android.app.FragmentTransaction; +import android.content.Context; +import android.content.Intent; +import android.net.Uri; +import android.os.Bundle; +import android.os.Handler; +import android.util.AttributeSet; +import android.util.TypedValue; +import android.view.Menu; +import android.view.MenuInflater; +import android.view.MenuItem; +import android.view.View; +import android.view.ViewGroup; +import android.view.Window; +import android.widget.Button; +import android.widget.ScrollView; +import android.widget.SearchView; +import android.widget.SeekBar; +import android.widget.ShareActionProvider; +import android.widget.TextView; +import android.widget.Toast; +import android.widget.SearchView.OnQueryTextListener; + +import com.example.android.apis.R; + +/** + * This activity demonstrates how to use system UI flags to implement + * a content browser style of UI (such as a book reader) that hides the + * nav bar as well as the status bar. + */ +public class ContentBrowserNavActivity extends Activity + implements OnQueryTextListener, ActionBar.TabListener { + + /** + * Implementation of a view for displaying immersive content, using system UI + * flags to transition in and out of modes where the user is focused on that + * content. + */ +//BEGIN_INCLUDE(content) + public static class Content extends ScrollView + implements View.OnSystemUiVisibilityChangeListener, View.OnClickListener { + TextView mText; + TextView mTitleView; + SeekBar mSeekView; + boolean mNavVisible; + int mBaseSystemUiVisibility = SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN + | SYSTEM_UI_FLAG_LAYOUT_STABLE | SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION; + int mLastSystemUiVis; + + Runnable mNavHider = new Runnable() { + @Override public void run() { + setNavVisibility(false); + } + }; + + public Content(Context context, AttributeSet attrs) { + super(context, attrs); + + mText = new TextView(context); + mText.setTextSize(TypedValue.COMPLEX_UNIT_DIP, 16); + mText.setText(context.getString(R.string.alert_dialog_two_buttons2ultra_msg)); + mText.setClickable(false); + mText.setOnClickListener(this); + mText.setTextIsSelectable(true); + addView(mText, new ViewGroup.LayoutParams( + ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.WRAP_CONTENT)); + + setOnSystemUiVisibilityChangeListener(this); + } + + public void init(TextView title, SeekBar seek) { + // This called by the containing activity to supply the surrounding + // state of the content browser that it will interact with. + mTitleView = title; + mSeekView = seek; + setNavVisibility(true); + } + + @Override public void onSystemUiVisibilityChange(int visibility) { + // Detect when we go out of low-profile mode, to also go out + // of full screen. We only do this when the low profile mode + // is changing from its last state, and turning off. + int diff = mLastSystemUiVis ^ visibility; + mLastSystemUiVis = visibility; + if ((diff&SYSTEM_UI_FLAG_LOW_PROFILE) != 0 + && (visibility&SYSTEM_UI_FLAG_LOW_PROFILE) == 0) { + setNavVisibility(true); + } + } + + @Override protected void onWindowVisibilityChanged(int visibility) { + super.onWindowVisibilityChanged(visibility); + + // When we become visible, we show our navigation elements briefly + // before hiding them. + setNavVisibility(true); + getHandler().postDelayed(mNavHider, 2000); + } + + @Override protected void onScrollChanged(int l, int t, int oldl, int oldt) { + super.onScrollChanged(l, t, oldl, oldt); + + // When the user scrolls, we hide navigation elements. + setNavVisibility(false); + } + + @Override public void onClick(View v) { + // When the user clicks, we toggle the visibility of navigation elements. + int curVis = getSystemUiVisibility(); + setNavVisibility((curVis&SYSTEM_UI_FLAG_LOW_PROFILE) != 0); + } + + void setBaseSystemUiVisibility(int visibility) { + mBaseSystemUiVisibility = visibility; + } + + void setNavVisibility(boolean visible) { + int newVis = mBaseSystemUiVisibility; + if (!visible) { + newVis |= SYSTEM_UI_FLAG_LOW_PROFILE | SYSTEM_UI_FLAG_FULLSCREEN + | SYSTEM_UI_FLAG_HIDE_NAVIGATION | SYSTEM_UI_FLAG_IMMERSIVE; + } + final boolean changed = newVis == getSystemUiVisibility(); + + // Unschedule any pending event to hide navigation if we are + // changing the visibility, or making the UI visible. + if (changed || visible) { + Handler h = getHandler(); + if (h != null) { + h.removeCallbacks(mNavHider); + } + } + + // Set the new desired visibility. + setSystemUiVisibility(newVis); + mTitleView.setVisibility(visible ? VISIBLE : INVISIBLE); + mSeekView.setVisibility(visible ? VISIBLE : INVISIBLE); + } + } +//END_INCLUDE(content) + + Content mContent; + + public ContentBrowserNavActivity() { + } + + @Override + public void onCreate(Bundle savedInstanceState) { + super.onCreate(savedInstanceState); + + getWindow().requestFeature(Window.FEATURE_ACTION_BAR_OVERLAY); + + setContentView(R.layout.content_browser_nav); + mContent = (Content)findViewById(R.id.content); + mContent.init((TextView)findViewById(R.id.title), + (SeekBar)findViewById(R.id.seekbar)); + + ActionBar bar = getActionBar(); + bar.addTab(bar.newTab().setText("Tab 1").setTabListener(this)); + bar.addTab(bar.newTab().setText("Tab 2").setTabListener(this)); + bar.addTab(bar.newTab().setText("Tab 3").setTabListener(this)); + } + + @Override + public boolean onCreateOptionsMenu(Menu menu) { + MenuInflater inflater = getMenuInflater(); + inflater.inflate(R.menu.content_actions, menu); + SearchView searchView = (SearchView) menu.findItem(R.id.action_search).getActionView(); + searchView.setOnQueryTextListener(this); + + // Set file with share history to the provider and set the share intent. + MenuItem actionItem = menu.findItem(R.id.menu_item_share_action_provider_action_bar); + ShareActionProvider actionProvider = (ShareActionProvider) actionItem.getActionProvider(); + actionProvider.setShareHistoryFileName(ShareActionProvider.DEFAULT_SHARE_HISTORY_FILE_NAME); + // Note that you can set/change the intent any time, + // say when the user has selected an image. + Intent shareIntent = new Intent(Intent.ACTION_SEND); + shareIntent.setType("image/*"); + Uri uri = Uri.fromFile(getFileStreamPath("shared.png")); + shareIntent.putExtra(Intent.EXTRA_STREAM, uri); + actionProvider.setShareIntent(shareIntent); + return true; + } + + @Override + public void onAttachedToWindow() { + super.onAttachedToWindow(); + } + + @Override + protected void onResume() { + super.onResume(); + } + + /** + * This method is declared in the menu. + */ + public void onSort(MenuItem item) { + } + + @Override + public boolean onOptionsItemSelected(MenuItem item) { + switch (item.getItemId()) { + case R.id.show_tabs: + getActionBar().setNavigationMode(ActionBar.NAVIGATION_MODE_TABS); + item.setChecked(true); + return true; + case R.id.hide_tabs: + getActionBar().setNavigationMode(ActionBar.NAVIGATION_MODE_STANDARD); + item.setChecked(true); + return true; + case R.id.stable_layout: + item.setChecked(!item.isChecked()); + mContent.setBaseSystemUiVisibility(item.isChecked() + ? View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN + | View.SYSTEM_UI_FLAG_LAYOUT_STABLE + : View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN); + return true; + } + return false; + } + + @Override + public boolean onQueryTextChange(String newText) { + return true; + } + + @Override + public boolean onQueryTextSubmit(String query) { + Toast.makeText(this, "Searching for: " + query + "...", Toast.LENGTH_SHORT).show(); + return true; + } + + @Override + public void onTabSelected(Tab tab, FragmentTransaction ft) { + } + + @Override + public void onTabUnselected(Tab tab, FragmentTransaction ft) { + } + + @Override + public void onTabReselected(Tab tab, FragmentTransaction ft) { + } +} diff --git a/samples/ApiDemos/src/com/example/android/apis/view/SystemUIModes.java b/samples/ApiDemos/src/com/example/android/apis/view/SystemUIModes.java index 730534a90..8197e05da 100644 --- a/samples/ApiDemos/src/com/example/android/apis/view/SystemUIModes.java +++ b/samples/ApiDemos/src/com/example/android/apis/view/SystemUIModes.java @@ -136,6 +136,30 @@ public class SystemUIModes extends Activity win.setAttributes(winParams); } + private void setTranslucentStatus(boolean on) { + Window win = getWindow(); + WindowManager.LayoutParams winParams = win.getAttributes(); + final int bits = WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS; + if (on) { + winParams.flags |= bits; + } else { + winParams.flags &= ~bits; + } + win.setAttributes(winParams); + } + + private void setTranslucentNavigation(boolean on) { + Window win = getWindow(); + WindowManager.LayoutParams winParams = win.getAttributes(); + final int bits = WindowManager.LayoutParams.FLAG_TRANSLUCENT_NAVIGATION; + if (on) { + winParams.flags |= bits; + } else { + winParams.flags &= ~bits; + } + win.setAttributes(winParams); + } + private String getDisplaySize() { DisplayMetrics dm = getResources().getDisplayMetrics(); return String.format("DisplayMetrics = (%d x %d)", dm.widthPixels, dm.heightPixels); @@ -151,9 +175,10 @@ public class SystemUIModes extends Activity static int TOAST_LENGTH = 500; IV mImage; - CheckBox[] mCheckControls = new CheckBox[6]; + CheckBox[] mCheckControls = new CheckBox[8]; int[] mCheckFlags = new int[] { View.SYSTEM_UI_FLAG_LOW_PROFILE, View.SYSTEM_UI_FLAG_FULLSCREEN, View.SYSTEM_UI_FLAG_HIDE_NAVIGATION, + View.SYSTEM_UI_FLAG_IMMERSIVE, View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY, View.SYSTEM_UI_FLAG_LAYOUT_STABLE, View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN, View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION }; @@ -179,9 +204,11 @@ public class SystemUIModes extends Activity mCheckControls[0] = (CheckBox) findViewById(R.id.modeLowProfile); mCheckControls[1] = (CheckBox) findViewById(R.id.modeFullscreen); mCheckControls[2] = (CheckBox) findViewById(R.id.modeHideNavigation); - mCheckControls[3] = (CheckBox) findViewById(R.id.layoutStable); - mCheckControls[4] = (CheckBox) findViewById(R.id.layoutFullscreen); - mCheckControls[5] = (CheckBox) findViewById(R.id.layoutHideNavigation); + mCheckControls[3] = (CheckBox) findViewById(R.id.modeImmersive); + mCheckControls[4] = (CheckBox) findViewById(R.id.modeImmersiveSticky); + mCheckControls[5] = (CheckBox) findViewById(R.id.layoutStable); + mCheckControls[6] = (CheckBox) findViewById(R.id.layoutFullscreen); + mCheckControls[7] = (CheckBox) findViewById(R.id.layoutHideNavigation); for (int i=0; i