<commit_before>/*
 * 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 android.support.v7.app;

import android.app.Activity;
import android.app.Dialog;
import android.content.Context;
import android.content.res.TypedArray;
import android.graphics.drawable.Drawable;
import android.os.Build;
import android.os.Bundle;
import android.support.v7.appcompat.R;
import android.support.v7.internal.view.SupportMenuInflater;
import android.support.v7.internal.view.WindowCallbackWrapper;
import android.support.v7.internal.view.menu.MenuBuilder;
import android.support.v7.internal.widget.TintTypedArray;
import android.support.v7.view.ActionMode;
import android.view.KeyEvent;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.View;
import android.view.Window;

abstract class AppCompatDelegateImplBase extends AppCompatDelegate {

    final Context mContext;
    final Window mWindow;
    final Window.Callback mOriginalWindowCallback;
    final AppCompatCallback mAppCompatCallback;

    private ActionBar mActionBar;
    private MenuInflater mMenuInflater;

    // true if this activity has an action bar.
    boolean mHasActionBar;
    // true if this activity's action bar overlays other activity content.
    boolean mOverlayActionBar;
    // true if this any action modes should overlay the activity content
    boolean mOverlayActionMode;
    // true if this activity is floating (e.g. Dialog)
    boolean mIsFloating;
    // true if this activity has no title
    boolean mWindowNoTitle;

    private CharSequence mTitle;

    private boolean mIsDestroyed;

    AppCompatDelegateImplBase(Context context, Window window, AppCompatCallback callback) {
        mContext = context;
        mWindow = window;
        mAppCompatCallback = callback;

        mOriginalWindowCallback = mWindow.getCallback();
        if (mOriginalWindowCallback instanceof AppCompatWindowCallbackBase) {
            throw new IllegalStateException(
                    "AppCompat has already installed itself into the Window");
        }
        // Now install the new callback
        mWindow.setCallback(wrapWindowCallback(mOriginalWindowCallback));
    }

    abstract ActionBar createSupportActionBar();

    Window.Callback wrapWindowCallback(Window.Callback callback) {
        return new AppCompatWindowCallbackBase(callback);
    }

    @Override
    public ActionBar getSupportActionBar() {
        // The Action Bar should be lazily created as hasActionBar
        // could change after onCreate
        if (mHasActionBar) {
            if (mActionBar == null) {
                mActionBar = createSupportActionBar();
            }
        } else {
            mActionBar = null;
        }
        return mActionBar;
    }

    final ActionBar peekSupportActionBar() {
        return mActionBar;
    }

    final void setSupportActionBar(ActionBar actionBar) {
        mActionBar = actionBar;
    }

    @Override
    public MenuInflater getMenuInflater() {
        if (mMenuInflater == null) {
            mMenuInflater = new SupportMenuInflater(getActionBarThemedContext());
        }
        return mMenuInflater;
    }

    @Override
    public void onCreate(Bundle savedInstanceState) {
        TypedArray a = mContext.obtainStyledAttributes(R.styleable.Theme);

        if (!a.hasValue(R.styleable.Theme_windowActionBar)) {
            a.recycle();
            throw new IllegalStateException(
                    "You need to use a Theme.AppCompat theme (or descendant) with this activity.");
        }

        if (a.getBoolean(R.styleable.Theme_windowActionBar, false)) {
            mHasActionBar = true;
        }
        if (a.getBoolean(R.styleable.Theme_windowActionBarOverlay, false)) {
            mOverlayActionBar = true;
        }
        if (a.getBoolean(R.styleable.Theme_windowActionModeOverlay, false)) {
            mOverlayActionMode = true;
        }
        mIsFloating = a.getBoolean(R.styleable.Theme_android_windowIsFloating, false);
        mWindowNoTitle = a.getBoolean(R.styleable.Theme_windowNoTitle, false);
        a.recycle();
    }

    // Methods used to create and respond to options menu
    abstract boolean onPanelClosed(int featureId, Menu menu);

    abstract boolean onMenuOpened(int featureId, Menu menu);

    abstract boolean dispatchKeyEvent(KeyEvent event);

    abstract boolean onKeyShortcut(int keyCode, KeyEvent event);

    @Override
    public final ActionBarDrawerToggle.Delegate getDrawerToggleDelegate() {
        return new ActionBarDrawableToggleImpl();
    }

    final Context getActionBarThemedContext() {
        Context context = null;

        // If we have an action bar, let it return a themed context
        ActionBar ab = getSupportActionBar();
        if (ab != null) {
            context = ab.getThemedContext();
        }

        if (context == null) {
            context = mContext;
        }
        return context;
    }

    private class ActionBarDrawableToggleImpl implements ActionBarDrawerToggle.Delegate {
        @Override
        public Drawable getThemeUpIndicator() {
            final TintTypedArray a = TintTypedArray.obtainStyledAttributes(
                    getActionBarThemedContext(), null, new int[]{ R.attr.homeAsUpIndicator });
            final Drawable result = a.getDrawable(0);
            a.recycle();
            return result;
        }

        @Override
        public Context getActionBarThemedContext() {
            return AppCompatDelegateImplBase.this.getActionBarThemedContext();
        }

        @Override
        public boolean isNavigationVisible() {
            final ActionBar ab = getSupportActionBar();
            return ab != null && (ab.getDisplayOptions() & ActionBar.DISPLAY_HOME_AS_UP) != 0;
        }

        @Override
        public void setActionBarUpIndicator(Drawable upDrawable, int contentDescRes) {
            ActionBar ab = getSupportActionBar();
            if (ab != null) {
                ab.setHomeAsUpIndicator(upDrawable);
                ab.setHomeActionContentDescription(contentDescRes);
            }
        }

        @Override
        public void setActionBarDescription(int contentDescRes) {
            ActionBar ab = getSupportActionBar();
            if (ab != null) {
                ab.setHomeActionContentDescription(contentDescRes);
            }
        }
    }

    abstract ActionMode startSupportActionModeFromWindow(ActionMode.Callback callback);

    @Override
    public final void onDestroy() {
        mIsDestroyed = true;
    }

    @Override
    public void setHandleNativeActionModesEnabled(boolean enabled) {
        // no-op pre-v14
    }

    @Override
    public boolean isHandleNativeActionModesEnabled() {
        // Always false pre-v14
        return false;
    }

    final boolean isDestroyed() {
        return mIsDestroyed;
    }

    final Window.Callback getWindowCallback() {
        return mWindow.getCallback();
    }

    @Override
    public final void setTitle(CharSequence title) {
        mTitle = title;
        onTitleChanged(title);
    }

    abstract void onTitleChanged(CharSequence title);

    final CharSequence getTitle() {
        // If the original window callback is an Activity, we'll use it's title
        if (mOriginalWindowCallback instanceof Activity) {
            return ((Activity) mOriginalWindowCallback).getTitle();
        }
        // Else, we'll return the title we have recorded ourselves
        return mTitle;
    }

    class AppCompatWindowCallbackBase extends WindowCallbackWrapper {
        AppCompatWindowCallbackBase(Window.Callback callback) {
            super(callback);
        }

        @Override
        public boolean dispatchKeyEvent(KeyEvent event) {
            if (super.dispatchKeyEvent(event)) {
                // First, let the wrapped Callback attempt to handle it
                return true;
            }
            // If we reach here, we can now try
            return AppCompatDelegateImplBase.this.dispatchKeyEvent(event);
        }

        @Override
        public boolean onCreatePanelMenu(int featureId, Menu menu) {
            if (featureId == Window.FEATURE_OPTIONS_PANEL && !(menu instanceof MenuBuilder)) {
                // If this is an options menu but it's not an AppCompat menu, we eat the event
                // and return false
                return false;
            }
            return super.onCreatePanelMenu(featureId, menu);
        }

        @Override
        public boolean onPreparePanel(int featureId, View view, Menu menu) {
            if (featureId == Window.FEATURE_OPTIONS_PANEL && !(menu instanceof MenuBuilder)) {
                // If this is an options menu but it's not an AppCompat menu, we eat the event
                // and return false
                return false;
            }

            if (featureId == Window.FEATURE_OPTIONS_PANEL && bypassPrepareOptionsPanelIfNeeded()) {
                // If this is an options menu and we need to bypass onPreparePanel, do so
                if (mOriginalWindowCallback instanceof Activity) {
                    return ((Activity) mOriginalWindowCallback).onPrepareOptionsMenu(menu);
                } else if (mOriginalWindowCallback instanceof Dialog) {
                    return ((Dialog) mOriginalWindowCallback).onPrepareOptionsMenu(menu);
                }
                return false;
            }

            // Else, defer to the default handling
            return super.onPreparePanel(featureId, view, menu);
        }

        @Override
        public boolean onMenuOpened(int featureId, Menu menu) {
            if (AppCompatDelegateImplBase.this.onMenuOpened(featureId, menu)) {
                return true;
            }
            return super.onMenuOpened(featureId, menu);
        }

        @Override
        public boolean dispatchKeyShortcutEvent(KeyEvent event) {
            if (AppCompatDelegateImplBase.this.onKeyShortcut(event.getKeyCode(), event)) {
                return true;
            }
            return super.dispatchKeyShortcutEvent(event);
        }

        @Override
        public void onContentChanged() {
            // We purposely do not propagate this call as this is called when we install
            // our sub-decor rather than the user's content
        }

        @Override
        public void onPanelClosed(int featureId, Menu menu) {
            if (AppCompatDelegateImplBase.this.onPanelClosed(featureId, menu)) {
                return;
            }
            super.onPanelClosed(featureId, menu);
        }

        /**
         * For the options menu, we may need to call onPrepareOptionsMenu() directly,
         * bypassing onPreparePanel(). This is because onPreparePanel() in certain situations
         * calls menu.hasVisibleItems(), which interferes with any initial invisible items.
         *
         * @return true if onPrepareOptionsMenu should be called directly.
         */
        private boolean bypassPrepareOptionsPanelIfNeeded() {
            if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN
                    && mOriginalWindowCallback instanceof Activity) {
                // For Activities, we only need to bypass onPreparePanel if we're running pre-JB
                return true;
            } else if (mOriginalWindowCallback instanceof Dialog) {
                // For Dialogs, we always need to bypass onPreparePanel
                return true;
            }
            return false;
        }
    }
}
<commit_msg>am ba79f059: Fix getSupportActionBar() returning null for Toolbars<commit_after>/*
 * 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 android.support.v7.app;

import android.app.Activity;
import android.app.Dialog;
import android.content.Context;
import android.content.res.TypedArray;
import android.graphics.drawable.Drawable;
import android.os.Build;
import android.os.Bundle;
import android.support.v7.appcompat.R;
import android.support.v7.internal.app.WindowDecorActionBar;
import android.support.v7.internal.view.SupportMenuInflater;
import android.support.v7.internal.view.WindowCallbackWrapper;
import android.support.v7.internal.view.menu.MenuBuilder;
import android.support.v7.internal.widget.TintTypedArray;
import android.support.v7.view.ActionMode;
import android.view.KeyEvent;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.View;
import android.view.Window;

abstract class AppCompatDelegateImplBase extends AppCompatDelegate {

    final Context mContext;
    final Window mWindow;
    final Window.Callback mOriginalWindowCallback;
    final AppCompatCallback mAppCompatCallback;

    private ActionBar mActionBar;
    private MenuInflater mMenuInflater;

    // true if this activity has an action bar.
    boolean mHasActionBar;
    // true if this activity's action bar overlays other activity content.
    boolean mOverlayActionBar;
    // true if this any action modes should overlay the activity content
    boolean mOverlayActionMode;
    // true if this activity is floating (e.g. Dialog)
    boolean mIsFloating;
    // true if this activity has no title
    boolean mWindowNoTitle;

    private CharSequence mTitle;

    private boolean mIsDestroyed;

    AppCompatDelegateImplBase(Context context, Window window, AppCompatCallback callback) {
        mContext = context;
        mWindow = window;
        mAppCompatCallback = callback;

        mOriginalWindowCallback = mWindow.getCallback();
        if (mOriginalWindowCallback instanceof AppCompatWindowCallbackBase) {
            throw new IllegalStateException(
                    "AppCompat has already installed itself into the Window");
        }
        // Now install the new callback
        mWindow.setCallback(wrapWindowCallback(mOriginalWindowCallback));
    }

    abstract ActionBar createSupportActionBar();

    Window.Callback wrapWindowCallback(Window.Callback callback) {
        return new AppCompatWindowCallbackBase(callback);
    }

    @Override
    public ActionBar getSupportActionBar() {
        // The Action Bar should be lazily created as hasActionBar
        // could change after onCreate
        if (mHasActionBar) {
            if (mActionBar == null) {
                mActionBar = createSupportActionBar();
            }
        } else {
            if (mActionBar instanceof WindowDecorActionBar) {
                mActionBar = null;
            }
        }
        return mActionBar;
    }

    final ActionBar peekSupportActionBar() {
        return mActionBar;
    }

    final void setSupportActionBar(ActionBar actionBar) {
        mActionBar = actionBar;
    }

    @Override
    public MenuInflater getMenuInflater() {
        if (mMenuInflater == null) {
            mMenuInflater = new SupportMenuInflater(getActionBarThemedContext());
        }
        return mMenuInflater;
    }

    @Override
    public void onCreate(Bundle savedInstanceState) {
        TypedArray a = mContext.obtainStyledAttributes(R.styleable.Theme);

        if (!a.hasValue(R.styleable.Theme_windowActionBar)) {
            a.recycle();
            throw new IllegalStateException(
                    "You need to use a Theme.AppCompat theme (or descendant) with this activity.");
        }

        if (a.getBoolean(R.styleable.Theme_windowActionBar, false)) {
            mHasActionBar = true;
        }
        if (a.getBoolean(R.styleable.Theme_windowActionBarOverlay, false)) {
            mOverlayActionBar = true;
        }
        if (a.getBoolean(R.styleable.Theme_windowActionModeOverlay, false)) {
            mOverlayActionMode = true;
        }
        mIsFloating = a.getBoolean(R.styleable.Theme_android_windowIsFloating, false);
        mWindowNoTitle = a.getBoolean(R.styleable.Theme_windowNoTitle, false);
        a.recycle();
    }

    // Methods used to create and respond to options menu
    abstract boolean onPanelClosed(int featureId, Menu menu);

    abstract boolean onMenuOpened(int featureId, Menu menu);

    abstract boolean dispatchKeyEvent(KeyEvent event);

    abstract boolean onKeyShortcut(int keyCode, KeyEvent event);

    @Override
    public final ActionBarDrawerToggle.Delegate getDrawerToggleDelegate() {
        return new ActionBarDrawableToggleImpl();
    }

    final Context getActionBarThemedContext() {
        Context context = null;

        // If we have an action bar, let it return a themed context
        ActionBar ab = getSupportActionBar();
        if (ab != null) {
            context = ab.getThemedContext();
        }

        if (context == null) {
            context = mContext;
        }
        return context;
    }

    private class ActionBarDrawableToggleImpl implements ActionBarDrawerToggle.Delegate {
        @Override
        public Drawable getThemeUpIndicator() {
            final TintTypedArray a = TintTypedArray.obtainStyledAttributes(
                    getActionBarThemedContext(), null, new int[]{ R.attr.homeAsUpIndicator });
            final Drawable result = a.getDrawable(0);
            a.recycle();
            return result;
        }

        @Override
        public Context getActionBarThemedContext() {
            return AppCompatDelegateImplBase.this.getActionBarThemedContext();
        }

        @Override
        public boolean isNavigationVisible() {
            final ActionBar ab = getSupportActionBar();
            return ab != null && (ab.getDisplayOptions() & ActionBar.DISPLAY_HOME_AS_UP) != 0;
        }

        @Override
        public void setActionBarUpIndicator(Drawable upDrawable, int contentDescRes) {
            ActionBar ab = getSupportActionBar();
            if (ab != null) {
                ab.setHomeAsUpIndicator(upDrawable);
                ab.setHomeActionContentDescription(contentDescRes);
            }
        }

        @Override
        public void setActionBarDescription(int contentDescRes) {
            ActionBar ab = getSupportActionBar();
            if (ab != null) {
                ab.setHomeActionContentDescription(contentDescRes);
            }
        }
    }

    abstract ActionMode startSupportActionModeFromWindow(ActionMode.Callback callback);

    @Override
    public final void onDestroy() {
        mIsDestroyed = true;
    }

    @Override
    public void setHandleNativeActionModesEnabled(boolean enabled) {
        // no-op pre-v14
    }

    @Override
    public boolean isHandleNativeActionModesEnabled() {
        // Always false pre-v14
        return false;
    }

    final boolean isDestroyed() {
        return mIsDestroyed;
    }

    final Window.Callback getWindowCallback() {
        return mWindow.getCallback();
    }

    @Override
    public final void setTitle(CharSequence title) {
        mTitle = title;
        onTitleChanged(title);
    }

    abstract void onTitleChanged(CharSequence title);

    final CharSequence getTitle() {
        // If the original window callback is an Activity, we'll use it's title
        if (mOriginalWindowCallback instanceof Activity) {
            return ((Activity) mOriginalWindowCallback).getTitle();
        }
        // Else, we'll return the title we have recorded ourselves
        return mTitle;
    }

    class AppCompatWindowCallbackBase extends WindowCallbackWrapper {
        AppCompatWindowCallbackBase(Window.Callback callback) {
            super(callback);
        }

        @Override
        public boolean dispatchKeyEvent(KeyEvent event) {
            if (super.dispatchKeyEvent(event)) {
                // First, let the wrapped Callback attempt to handle it
                return true;
            }
            // If we reach here, we can now try
            return AppCompatDelegateImplBase.this.dispatchKeyEvent(event);
        }

        @Override
        public boolean onCreatePanelMenu(int featureId, Menu menu) {
            if (featureId == Window.FEATURE_OPTIONS_PANEL && !(menu instanceof MenuBuilder)) {
                // If this is an options menu but it's not an AppCompat menu, we eat the event
                // and return false
                return false;
            }
            return super.onCreatePanelMenu(featureId, menu);
        }

        @Override
        public boolean onPreparePanel(int featureId, View view, Menu menu) {
            if (featureId == Window.FEATURE_OPTIONS_PANEL && !(menu instanceof MenuBuilder)) {
                // If this is an options menu but it's not an AppCompat menu, we eat the event
                // and return false
                return false;
            }

            if (featureId == Window.FEATURE_OPTIONS_PANEL && bypassPrepareOptionsPanelIfNeeded()) {
                // If this is an options menu and we need to bypass onPreparePanel, do so
                if (mOriginalWindowCallback instanceof Activity) {
                    return ((Activity) mOriginalWindowCallback).onPrepareOptionsMenu(menu);
                } else if (mOriginalWindowCallback instanceof Dialog) {
                    return ((Dialog) mOriginalWindowCallback).onPrepareOptionsMenu(menu);
                }
                return false;
            }

            // Else, defer to the default handling
            return super.onPreparePanel(featureId, view, menu);
        }

        @Override
        public boolean onMenuOpened(int featureId, Menu menu) {
            if (AppCompatDelegateImplBase.this.onMenuOpened(featureId, menu)) {
                return true;
            }
            return super.onMenuOpened(featureId, menu);
        }

        @Override
        public boolean dispatchKeyShortcutEvent(KeyEvent event) {
            if (AppCompatDelegateImplBase.this.onKeyShortcut(event.getKeyCode(), event)) {
                return true;
            }
            return super.dispatchKeyShortcutEvent(event);
        }

        @Override
        public void onContentChanged() {
            // We purposely do not propagate this call as this is called when we install
            // our sub-decor rather than the user's content
        }

        @Override
        public void onPanelClosed(int featureId, Menu menu) {
            if (AppCompatDelegateImplBase.this.onPanelClosed(featureId, menu)) {
                return;
            }
            super.onPanelClosed(featureId, menu);
        }

        /**
         * For the options menu, we may need to call onPrepareOptionsMenu() directly,
         * bypassing onPreparePanel(). This is because onPreparePanel() in certain situations
         * calls menu.hasVisibleItems(), which interferes with any initial invisible items.
         *
         * @return true if onPrepareOptionsMenu should be called directly.
         */
        private boolean bypassPrepareOptionsPanelIfNeeded() {
            if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN
                    && mOriginalWindowCallback instanceof Activity) {
                // For Activities, we only need to bypass onPreparePanel if we're running pre-JB
                return true;
            } else if (mOriginalWindowCallback instanceof Dialog) {
                // For Dialogs, we always need to bypass onPreparePanel
                return true;
            }
            return false;
        }
    }
}

{'fraction_non_alphanumeric': 0.07196876284422524, 'fraction_numerical': 0.001972872996300863, 'mean_word_length': 2.335298149417409, 'pattern_counts': {'":': 0, '<': 5, '<?xml version=': 0, '>': 3, 'https://': 0, 'lorem ipsum': 0, 'www.': 2, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '5833020', 'n_tokens_mistral': 6224, 'n_tokens_neox': 6001, 'n_words': 1761}