簡體   English   中英

切換選項卡時無效上下文操作欄

[英]Invalidate Contextual Action Bar on When Switching Tabs

我正在尋找一種方法,以便當用戶切換標簽時,我所擁有的上下文操作欄變得無效。

我已將其設置為使選項卡鏈接到Fragments,並且每個選項卡都有不同的上下文操作欄。 我想在onTabUnselected()方法中可能有一種方法可以做到這一點,但我不知道如何去做。

任何幫助將非常感激。

package com.androidDev.taskmanager;

import java.util.ArrayList;
import java.util.Locale;

import android.app.ActionBar;
import android.app.FragmentTransaction;
import android.content.Context;
import android.content.Intent;
import android.os.Build;
import android.os.Bundle;
import android.support.v4.app.Fragment;
import android.support.v4.app.FragmentActivity;
import android.support.v4.app.FragmentManager;
import android.support.v4.app.FragmentPagerAdapter;
import android.support.v4.app.ListFragment;
import android.support.v4.view.ViewPager;
import android.util.SparseBooleanArray;
import android.view.ActionMode;
import android.view.LayoutInflater;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
import android.view.View;
import android.view.ViewGroup;
import android.widget.AdapterView;
import android.widget.AdapterView.OnItemLongClickListener;
import android.widget.ListView;
import android.widget.SimpleCursorAdapter;
import android.widget.Toast;

public class Home extends FragmentActivity implements ActionBar.TabListener {
    private SectionsPagerAdapter mSectionsPagerAdapter;
    private ViewPager mViewPager;
    public static Menu mainMenu;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_home);

        // Set up the action bar.
        final ActionBar actionBar = getActionBar();
        actionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_TABS);

        // Create the adapter that will return a fragment for each of the three
        // primary sections of the app.
        mSectionsPagerAdapter = new SectionsPagerAdapter(getSupportFragmentManager());

        // Set up the ViewPager with the sections adapter.
        mViewPager = (ViewPager) findViewById(R.id.pager);
        mViewPager.setAdapter(mSectionsPagerAdapter);

        // When swiping between different sections, select the corresponding
        // tab. We can also use ActionBar.Tab#select() to do this if we have
        // a reference to the Tab.
        mViewPager.setOnPageChangeListener(new ViewPager.SimpleOnPageChangeListener() {
                    @Override
                    public void onPageSelected(int position) {
                        actionBar.setSelectedNavigationItem(position);
                    }
                });

        // For each of the sections in the app, add a tab to the action bar.
        for (int i = 0; i < mSectionsPagerAdapter.getCount(); i++) {
            // Create a tab with text corresponding to the page title defined by
            // the adapter. Also specify this Activity object, which implements
            // the TabListener interface, as the callback (listener) for when
            // this tab is selected.
            actionBar.addTab(actionBar.newTab().setText(mSectionsPagerAdapter.getPageTitle(i)).setTabListener(this));
        }
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        // Inflate the menu; this adds items to the action bar if it is present.
        getMenuInflater().inflate(R.menu.home, menu);
        mainMenu = menu;
        return true;
    }




    @Override
    public void onTabSelected(ActionBar.Tab tab,
            FragmentTransaction fragmentTransaction) {
        // When the given tab is selected, switch to the corresponding page in
        // the ViewPager.
        mViewPager.setCurrentItem(tab.getPosition());
    }

    @Override
    public void onTabUnselected(ActionBar.Tab tab,FragmentTransaction fragmentTransaction) {
    }

    @Override
    public void onTabReselected(ActionBar.Tab tab, FragmentTransaction fragmentTransaction) {
    }

    public class SectionsPagerAdapter extends FragmentPagerAdapter {

        public SectionsPagerAdapter(FragmentManager fm) {
            super(fm);
        }

        @Override
        public Fragment getItem(int position) {
            // getItem is called to instantiate the fragment for the given page.
            // Return a DummySectionFragment (defined as a static inner class
            // below) with the page number as its lone argument.
            if(position==0){
                Fragment fragment = new ViewTaskFragment();
                return fragment;
            }
            else {
                Fragment fragment = new ViewReminderFragment();
                return fragment;
            }
        }

        @Override
        public int getCount() {
            // Show 2 total pages.
            return 2;
        }

        @Override
        public CharSequence getPageTitle(int position) {
            Locale l = Locale.getDefault();
            switch (position) {
            case 0:
                return getString(R.string.title_tasks).toUpperCase(l);
            case 1:
                return getString(R.string.title_reminders).toUpperCase(l);
            }
            return null;
        }
    }

    public static class ViewTaskFragment extends ListFragment {
        private final boolean POST_HONEYCOMB = Build.VERSION.SDK_INT >= Build.VERSION_CODES.HONEYCOMB;
        private SimpleCursorAdapter sca;
        private ListView lv;
        private ActionMode.Callback mActionModeCallback = new ActionMode.Callback() {
            // Called when the action mode is created; startActionMode() was called
            @Override
            public boolean onCreateActionMode(ActionMode mode, Menu menu) {
                // Inflate a menu resource providing context menu items
                MenuInflater inflater = mode.getMenuInflater();
                inflater.inflate(R.menu.task_context_menu, menu);
                return true;
            }

            // Called each time the action mode is shown. Always called after onCreateActionMode, but
            // may be called multiple times if the mode is invalidated.
            @Override
            public boolean onPrepareActionMode(ActionMode mode, Menu menu) {
                return false; // Return false if nothing is done
            }

            // Called when the user selects a contextual menu item
            @Override
            public boolean onActionItemClicked(ActionMode mode, MenuItem item) {
                switch (item.getItemId()) {
                    case R.id.menu_delete:
                        MyDB db = new MyDB(getActivity());
                        SparseBooleanArray checked = lv.getCheckedItemPositions();
                        ArrayList<String> valueBuilder = new ArrayList<String>();
                        String[] values;
                        for (int i = 0; i < checked.size(); i++) {
                            if(checked.valueAt(i) == true) {
                                valueBuilder.add(String.valueOf(lv.getItemIdAtPosition(i)));
                            }
                        }
                        values = valueBuilder.toArray(new String[valueBuilder.size()]);
                        if(values!=null)
                            db.deleteTasks(values);
                        refreshListView();
                        mode.finish(); // Action picked, so close the CAB
                        return true;
                    default:
                        return false;
                }
            }
            // Called when the user exits the action mode
            @Override
            public void onDestroyActionMode(ActionMode mode) {
                lv.clearChoices();
                for (int i = 0; i < lv.getChildCount(); i++)
                    lv.setItemChecked(i, false);
                mode = null;
            }
        };
        public ViewTaskFragment() {}
        @Override
        public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstaceState) {
            final View rootView = inflater.inflate(R.layout.view_task, container, false);
            Context context = getActivity();
            hasOptionsMenu();
            String[] from = {"_id", "task_name", "completion_date"};
            int[] to={R.id.rpt_task_id, R.id.rpt_task_name, R.id.rpt_completion_date};
            MyDB db = new MyDB(context);
            sca = new SimpleCursorAdapter(context, R.layout.task_item, db.selectTasks(), from, to, 0);
            lv = (ListView) rootView.findViewById(android.R.id.list);
            lv.setAdapter(sca);
            lv.setLongClickable(true);
            lv.setOnItemLongClickListener(new OnItemLongClickListener() {
                    public boolean onItemLongClick(AdapterView<?> parent, View v, int position, long id) {
                        Toast.makeText(getActivity(), "Running onItemLongClick Orig Code", Toast.LENGTH_SHORT).show();
                        if(POST_HONEYCOMB) {
                             getActivity(). startActionMode(mActionModeCallback);
                        }
                        else {
                            //Needs at least honeycomb
                        }
                        return true;
                    }
                });
            return rootView;
        }

        @Override
        public void onResume() {
            super.onResume();
            refreshListView();
        }
        public void refreshListView() {
            MyDB db = new MyDB(getActivity());
            sca.changeCursor(db.selectTasks());
        }

    }
    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        // Handle item selection
        Intent intent = null;
        switch (item.getItemId()) {
        case R.id.mnu_action_settings:
            intent = new Intent(this, Settings.class);
            startActivity(intent);
            return true;
        case R.id.mnu_add_reminder:
            intent = new Intent(this, AddReminder.class);
            startActivity(intent);  
            return true;
        case R.id.mnu_add_task:
            intent = new Intent(this, AddTask.class);
            startActivity(intent);
            return true;
        default:
            return super.onOptionsItemSelected(item);
        }
    }
    /** New Fragment Section**/
    public static class ViewReminderFragment extends Fragment {
        private final boolean POST_HONEYCOMB = Build.VERSION.SDK_INT >= Build.VERSION_CODES.HONEYCOMB;
        private SimpleCursorAdapter sca;
        private ListView lv;
        private ActionMode.Callback mActionModeCallback = new ActionMode.Callback() {
            // Called when the action mode is created; startActionMode() was called
            @Override
            public boolean onCreateActionMode(ActionMode mode, Menu menu) {
                // Inflate a menu resource providing context menu items
                MenuInflater inflater = mode.getMenuInflater();
                inflater.inflate(R.menu.task_context_menu, menu);
                return true;
            }

            // Called each time the action mode is shown. Always called after onCreateActionMode, but
            // may be called multiple times if the mode is invalidated.
            @Override
            public boolean onPrepareActionMode(ActionMode mode, Menu menu) {
                return false; // Return false if nothing is done
            }

            // Called when the user selects a contextual menu item
            @Override
            public boolean onActionItemClicked(ActionMode mode, MenuItem item) {
                switch (item.getItemId()) {
                    case R.id.menu_delete:
                        refreshListView();
                        mode.finish(); // Action picked, so close the CAB
                        return true;
                    default:
                        return false;
                }
            }
            // Called when the user exits the action mode
            @Override
            public void onDestroyActionMode(ActionMode mode) {
                lv.clearChoices();
                for (int i = 0; i < lv.getChildCount(); i++)
                    lv.setItemChecked(i, false);
                mode = null;
            }
        };


        public ViewReminderFragment() {}
        @Override
        public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstaceState) {
            final View rootView = inflater.inflate(R.layout.view_reminder, container, false);
            Context context = getActivity();
            hasOptionsMenu();
            String[] from = {"_id", "task_name", "reminder_date"};
            int[] to={R.id.rpt_task_id, R.id.rpt_task_name, R.id.rpt_reminder_date};
            MyDB db = new MyDB(context);
            sca = new SimpleCursorAdapter(context, R.layout.reminder_item, db.selectReminder(), from, to, 0);
            lv = (ListView) rootView.findViewById(R.id.reminderList);
            lv.setAdapter(sca);
            lv.setLongClickable(true);
            lv.setOnItemLongClickListener(new OnItemLongClickListener() {
                    public boolean onItemLongClick(AdapterView<?> parent, View v, int position, long id) {
                        if(POST_HONEYCOMB) {
                             getActivity(). startActionMode(mActionModeCallback);
                        }
                        else {
                            //Needs at least honeycomb
                        }
                        return true;
                    }
                });
            return rootView;
        }

        @Override
        public void onResume() {
            super.onResume();
            refreshListView();
        }
        public void refreshListView() {
            MyDB db = new MyDB(getActivity());
            sca.changeCursor(db.selectReminder());
        }
    }

我想我找到了一種不是“作弊”的有趣方式。

首先,我創建了一個FragmentTabListener接口,以便活動可以讓選項卡片段在被選中或未被選中時知道。

public interface FragmentTabListener {
    public void onTabSelected();

    public void onTabUnselected();
}

然后,在ActionBar.TabListener onTabUnselected()方法上,我可以讓每個選項卡知道它何時被選中或未被選中。

ActionBar.TabListener tabListener = new ActionBar.TabListener() {

    @Override
    public void onTabUnselected(Tab tab, FragmentTransaction ft) {
        ((FragmentTabListener) MyFragmentForTab).onTabUnselected();
    }

我創建了一個不同的監聽器,因為我真的不想將其他東西暴露給選項卡,只是選擇或取消選擇它。 此外,以上是稍微偽代碼以隱藏無關信息。

接下來,在用於特定選項卡的片段上,無論何時創建它都會保留actionMode(並在每次銷毀時將其刪除)

@Override
public boolean onCreateActionMode(ActionMode mode, Menu menu) {
    // Inflate the menu for the CAB
    ...
    MyFragmentForTab.this.mActionMode = mode;
    return true;
}

@Override
public void onDestroyActionMode(ActionMode mode) {
    MyFragmentForTab.this.mActionMode = null;
}

最后,當選項卡未被選中時,我只是打電話

if (this.mActionMode != null)
    this.mActionMode.finish();

所以這在做它的方式上有點作弊,但它確實有效。

我把它放在onTabUnselected()方法中。

        mViewPager.startActionMode(new ActionMode.Callback() {
        @Override
        public boolean onPrepareActionMode(ActionMode mode, Menu menu) {
            // TODO Auto-generated method stub
            return false;
        }   
        @Override
        public void onDestroyActionMode(ActionMode mode) {
            // TODO Auto-generated method stub

        }   
        @Override
        public boolean onCreateActionMode(ActionMode mode, Menu menu) {
            // TODO Auto-generated method stub
            return false;
        }   
        @Override
        public boolean onActionItemClicked(ActionMode mode, MenuItem item) {
            // TODO Auto-generated method stub
            return false;
        }
    });

隱藏它怎么樣?

 getActionBar().hide();

或作弊。 如果選項卡打開(布爾值x =真)。 如果為true,請使用Action Bar的功能。 如果x = false則什么也不做。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM