Home | History | Annotate | Download | only in app
      1 /*
      2  * Copyright (C) 2010 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.example.android.apis.app;
     18 
     19 import com.example.android.apis.R;
     20 import com.example.android.apis.Shakespeare;
     21 
     22 import android.app.Activity;
     23 import android.app.Fragment;
     24 import android.app.FragmentTransaction;
     25 import android.app.ListFragment;
     26 import android.content.Intent;
     27 import android.content.res.Configuration;
     28 import android.os.Bundle;
     29 import android.util.TypedValue;
     30 import android.view.LayoutInflater;
     31 import android.view.View;
     32 import android.view.ViewGroup;
     33 import android.widget.ArrayAdapter;
     34 import android.widget.ListView;
     35 import android.widget.ScrollView;
     36 import android.widget.TextView;
     37 
     38 /**
     39  * Demonstration of using fragments to implement different activity layouts.
     40  * This sample provides a different layout (and activity flow) when run in
     41  * landscape.
     42  */
     43 public class FragmentLayout extends Activity {
     44 
     45 //BEGIN_INCLUDE(main)
     46     @Override
     47     protected void onCreate(Bundle savedInstanceState) {
     48         super.onCreate(savedInstanceState);
     49 
     50         setContentView(R.layout.fragment_layout);
     51     }
     52 //END_INCLUDE(main)
     53 
     54     /**
     55      * This is a secondary activity, to show what the user has selected
     56      * when the screen is not large enough to show it all in one activity.
     57      */
     58 //BEGIN_INCLUDE(details_activity)
     59     public static class DetailsActivity extends Activity {
     60 
     61         @Override
     62         protected void onCreate(Bundle savedInstanceState) {
     63             super.onCreate(savedInstanceState);
     64 
     65             if (getResources().getConfiguration().orientation
     66                     == Configuration.ORIENTATION_LANDSCAPE) {
     67                 // If the screen is now in landscape mode, we can show the
     68                 // dialog in-line with the list so we don't need this activity.
     69                 finish();
     70                 return;
     71             }
     72 
     73             if (savedInstanceState == null) {
     74                 // During initial setup, plug in the details fragment.
     75                 DetailsFragment details = new DetailsFragment();
     76                 details.setArguments(getIntent().getExtras());
     77                 getFragmentManager().beginTransaction().add(android.R.id.content, details).commit();
     78             }
     79         }
     80     }
     81 //END_INCLUDE(details_activity)
     82 
     83     /**
     84      * This is the "top-level" fragment, showing a list of items that the
     85      * user can pick.  Upon picking an item, it takes care of displaying the
     86      * data to the user as appropriate based on the currrent UI layout.
     87      */
     88 //BEGIN_INCLUDE(titles)
     89     public static class TitlesFragment extends ListFragment {
     90         boolean mDualPane;
     91         int mCurCheckPosition = 0;
     92 
     93         @Override
     94         public void onActivityCreated(Bundle savedInstanceState) {
     95             super.onActivityCreated(savedInstanceState);
     96 
     97             // Populate list with our static array of titles.
     98             setListAdapter(new ArrayAdapter<String>(getActivity(),
     99                     android.R.layout.simple_list_item_activated_1, Shakespeare.TITLES));
    100 
    101             // Check to see if we have a frame in which to embed the details
    102             // fragment directly in the containing UI.
    103             View detailsFrame = getActivity().findViewById(R.id.details);
    104             mDualPane = detailsFrame != null && detailsFrame.getVisibility() == View.VISIBLE;
    105 
    106             if (savedInstanceState != null) {
    107                 // Restore last state for checked position.
    108                 mCurCheckPosition = savedInstanceState.getInt("curChoice", 0);
    109             }
    110 
    111             if (mDualPane) {
    112                 // In dual-pane mode, the list view highlights the selected item.
    113                 getListView().setChoiceMode(ListView.CHOICE_MODE_SINGLE);
    114                 // Make sure our UI is in the correct state.
    115                 showDetails(mCurCheckPosition);
    116             }
    117         }
    118 
    119         @Override
    120         public void onSaveInstanceState(Bundle outState) {
    121             super.onSaveInstanceState(outState);
    122             outState.putInt("curChoice", mCurCheckPosition);
    123         }
    124 
    125         @Override
    126         public void onListItemClick(ListView l, View v, int position, long id) {
    127             showDetails(position);
    128         }
    129 
    130         /**
    131          * Helper function to show the details of a selected item, either by
    132          * displaying a fragment in-place in the current UI, or starting a
    133          * whole new activity in which it is displayed.
    134          */
    135         void showDetails(int index) {
    136             mCurCheckPosition = index;
    137 
    138             if (mDualPane) {
    139                 // We can display everything in-place with fragments, so update
    140                 // the list to highlight the selected item and show the data.
    141                 getListView().setItemChecked(index, true);
    142 
    143                 // Check what fragment is currently shown, replace if needed.
    144                 DetailsFragment details = (DetailsFragment)
    145                         getFragmentManager().findFragmentById(R.id.details);
    146                 if (details == null || details.getShownIndex() != index) {
    147                     // Make new fragment to show this selection.
    148                     details = DetailsFragment.newInstance(index);
    149 
    150                     // Execute a transaction, replacing any existing fragment
    151                     // with this one inside the frame.
    152                     FragmentTransaction ft = getFragmentManager().beginTransaction();
    153                     if (index == 0) {
    154                         ft.replace(R.id.details, details);
    155                     } else {
    156                         ft.replace(R.id.a_item, details);
    157                     }
    158                     ft.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_FADE);
    159                     ft.commit();
    160                 }
    161 
    162             } else {
    163                 // Otherwise we need to launch a new activity to display
    164                 // the dialog fragment with selected text.
    165                 Intent intent = new Intent();
    166                 intent.setClass(getActivity(), DetailsActivity.class);
    167                 intent.putExtra("index", index);
    168                 startActivity(intent);
    169             }
    170         }
    171     }
    172 //END_INCLUDE(titles)
    173 
    174     /**
    175      * This is the secondary fragment, displaying the details of a particular
    176      * item.
    177      */
    178 //BEGIN_INCLUDE(details)
    179     public static class DetailsFragment extends Fragment {
    180         /**
    181          * Create a new instance of DetailsFragment, initialized to
    182          * show the text at 'index'.
    183          */
    184         public static DetailsFragment newInstance(int index) {
    185             DetailsFragment f = new DetailsFragment();
    186 
    187             // Supply index input as an argument.
    188             Bundle args = new Bundle();
    189             args.putInt("index", index);
    190             f.setArguments(args);
    191 
    192             return f;
    193         }
    194 
    195         public int getShownIndex() {
    196             return getArguments().getInt("index", 0);
    197         }
    198 
    199         @Override
    200         public View onCreateView(LayoutInflater inflater, ViewGroup container,
    201                 Bundle savedInstanceState) {
    202             if (container == null) {
    203                 // We have different layouts, and in one of them this
    204                 // fragment's containing frame doesn't exist.  The fragment
    205                 // may still be created from its saved state, but there is
    206                 // no reason to try to create its view hierarchy because it
    207                 // won't be displayed.  Note this is not needed -- we could
    208                 // just run the code below, where we would create and return
    209                 // the view hierarchy; it would just never be used.
    210                 return null;
    211             }
    212 
    213             ScrollView scroller = new ScrollView(getActivity());
    214             TextView text = new TextView(getActivity());
    215             int padding = (int)TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP,
    216                     4, getActivity().getResources().getDisplayMetrics());
    217             text.setPadding(padding, padding, padding, padding);
    218             scroller.addView(text);
    219             text.setText(Shakespeare.DIALOGUE[getShownIndex()]);
    220             return scroller;
    221         }
    222     }
    223 //END_INCLUDE(details)
    224 }
    225