精华内容
下载资源
问答
  • 应用禁用通知栏下拉 做法是在通知栏区域弄一个透明的window,这样下拉的时候触摸的区域就是这个window,系统的就下拉不了了 改做法是需要在应用上方显示一个window 所以需要权限 <uses-permission android:name=...

    应用禁用通知栏下拉
    做法是在通知栏区域弄一个透明的window,这样下拉的时候触摸的区域就是这个window,系统的就下拉不了了
    改做法是需要在应用上方显示一个window 所以需要权限

     <uses-permission android:name="android.permission.SYSTEM_ALERT_WINDOW" />
    
      public static final String STATUS_BAR_HEIGHT = "status_bar_height";
      public static final String DIMEN = "dimen";
      public static final String DEF_PACKAGE = "android";
       public static void preventStatusBarExpansion(Context context) {
        WindowManager manager = ((WindowManager) context.getApplicationContext()
                                                        .getSystemService(Context.WINDOW_SERVICE));
    
        WindowManager.LayoutParams localLayoutParams = new WindowManager.LayoutParams();
        localLayoutParams.type = WindowManager.LayoutParams.TYPE_SYSTEM_ERROR;
        localLayoutParams.gravity = Gravity.TOP;
        localLayoutParams.flags = WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE
            | WindowManager.LayoutParams.FLAG_NOT_TOUCH_MODAL
            | WindowManager.LayoutParams.FLAG_LAYOUT_IN_SCREEN;
    
        localLayoutParams.width = WindowManager.LayoutParams.MATCH_PARENT;
    
        int resId = context.getResources()
                           .getIdentifier(STATUS_BAR_HEIGHT, DIMEN, DEF_PACKAGE);
        int result;
        if (resId > 0) {
          result = context.getResources()
                          .getDimensionPixelSize(resId);
        } else {
          // Use Fallback size:
          result = 60; // 60px Fallback
        }
    
        localLayoutParams.height = result;
        localLayoutParams.format = PixelFormat.TRANSPARENT;
    
        if (view == null) {
          view = new CustomViewGroup(context);
        }
    
        try {
          if (manager != null) {
            manager.addView(view, localLayoutParams);
          }
        } catch (Exception ignored) {
        }
      }
    
      public static void allowStatusBarExpansion(Context context) {
        WindowManager manager = ((WindowManager) context.getApplicationContext()
                                                        .getSystemService(Context.WINDOW_SERVICE));
        try {
          if (manager != null) {
            manager.removeViewImmediate(view);
          }
        } catch (Exception ignored) {
        }
      }
    
      public static class CustomViewGroup extends ViewGroup {
        public CustomViewGroup(Context context) {
          super(context);
        }
    
        @Override
        protected void onLayout(boolean changed,
                                int l,
                                int t,
                                int r,
                                int b) {
        }
    
        @Override
        public boolean onInterceptTouchEvent(MotionEvent ev) {
          // Intercepted touch!
          return true;
        }
      }
    
    展开全文
  • 我得项目需求:下拉不显示通知栏,而是刷新view,下给出我得需求解决方法,后面是参考文章的全部内容及原文地址;...//这个是通知栏下拉的高度,设置为0就不显示,不影响下拉动作的监听  if (Float.isNaN(h)) {

    我得项目需求:下拉不显示通知栏,而是刷新view,下给出我得需求解决方法,后面是参考文章的全部内容及原文地址;

    文件位置Z:\myandroid\frameworks\base\packages\SystemUI\src\com\android\systemui\statusbar\phone\PanelView.java

    方法:

    1,首先屏蔽通知栏,

    在  public void setExpandedHeightInternal(float h) {
    h = 0;//这个是通知栏下拉的高度,设置为0就不显示,不影响下拉动作的监听
            if (Float.isNaN(h)) {
                // If a NaN gets in here, it will freeze the Animators.
                if (DEBUG_NAN) {
                    Log.v(TAG, "setExpandedHeightInternal: warning: h=NaN, using 0 instead",
                            new Throwable());
                }
                h = 0;
            }


            float fh = getFullHeight();
            if (fh == 0) {
                // Hmm, full height hasn't been computed yet
            }


            if (h < 0) h = 0;
            if (!(mRubberbandingEnabled && (mTracking || mRubberbanding)) && h > fh) h = fh;


            mExpandedHeight = h;


            if (DEBUG) logf("setExpansion: height=%.1f fh=%.1f tracking=%s rubber=%s", h, fh, mTracking?"T":"f", mRubberbanding?"T":"f");


            requestLayout();
    //        FrameLayout.LayoutParams lp = (FrameLayout.LayoutParams) getLayoutParams();
    //        lp.height = (int) mExpandedHeight;
    //        setLayoutParams(lp);


            mExpandedFraction = Math.min(1f, (fh == 0) ? 0 : h / fh);
        }

    2,下拉时监听,做自己想做的事

     protected void onFinishInflate() {
            super.onFinishInflate();
            mHandleView = findViewById(R.id.handle);


            loadDimens();


            if (DEBUG) logf("handle view: " + mHandleView);
            if (mHandleView != null) {
                mHandleView.setOnTouchListener(new View.OnTouchListener() {
                    @Override
                    public boolean onTouch(View v, MotionEvent event) {
                        int pointerIndex = event.findPointerIndex(mTrackingPointer);
                        if (pointerIndex < 0) {
                            pointerIndex = 0;
                            mTrackingPointer = event.getPointerId(pointerIndex);
                        }
                        final float y = event.getY(pointerIndex);
                        final float rawDelta = event.getRawY() - event.getY();
                        final float rawY = y + rawDelta;
                        if (DEBUG) logf("handle.onTouch: a=%s p=[%d,%d] y=%.1f rawY=%.1f off=%.1f",
                                MotionEvent.actionToString(event.getAction()),
                                mTrackingPointer, pointerIndex,
                                y, rawY, mTouchOffset);
                        PanelView.this.getLocationOnScreen(mAbsPos);


                        switch (event.getActionMasked()) {
                            case MotionEvent.ACTION_DOWN:
                                mTracking = true;
                                mHandleView.setPressed(true);
                                postInvalidate(); // catch the press state change
                                mInitialTouchY = y;
                                mVelocityTracker = FlingTracker.obtain();
                                trackMovement(event);
                                mTimeAnimator.cancel(); // end any outstanding animations
                                mBar.onTrackingStarted(PanelView.this);
                                mTouchOffset = (rawY - mAbsPos[1]) - mExpandedHeight;
                                if (mExpandedHeight == 0) {
                                    mJustPeeked = true;
                                    runPeekAnimation();
                                }
                                break;


                            case MotionEvent.ACTION_POINTER_UP:
                                final int upPointer = event.getPointerId(event.getActionIndex());
                                if (mTrackingPointer == upPointer) {
                                    // gesture is ongoing, find a new pointer to track
                                    final int newIndex = event.getPointerId(0) != upPointer ? 0 : 1;
                                    final float newY = event.getY(newIndex);
                                    final float newRawY = newY + rawDelta;
                                    mTrackingPointer = event.getPointerId(newIndex);
                                    mTouchOffset = (newRawY - mAbsPos[1]) - mExpandedHeight;
                                    mInitialTouchY = newY;
                                }
                                break;


                            case MotionEvent.ACTION_MOVE:
                                final float h = rawY - mAbsPos[1] - mTouchOffset;
                                if (h > mPeekHeight) {
                                    if (mPeekAnimator != null && mPeekAnimator.isStarted()) {
                                        mPeekAnimator.cancel();
                                    }
                                    mJustPeeked = false;
                                }
                                if (!mJustPeeked) {
                                    PanelView.this.setExpandedHeightInternal(h);
                                    mBar.panelExpansionChanged(PanelView.this, mExpandedFraction);
                                }


                                trackMovement(event);
                                break;


                            case MotionEvent.ACTION_UP:
    Log.i("PanelView", "MotionEvent.ACTION_UP");//在up时添加自己要做的事
    Intent intent = new Intent();
    intent.setAction("RefreshView");
    getContext().sendBroadcast(intent);

                            case MotionEvent.ACTION_CANCEL:
                                mFinalTouchY = y;
                                mTracking = false;
                                mTrackingPointer = -1;
                                mHandleView.setPressed(false);
                                postInvalidate(); // catch the press state change
                                mBar.onTrackingStopped(PanelView.this);
                                trackMovement(event);


    原文地址:http://blog.csdn.net/garment1991/article/details/50437571

    文章内容如下:

    super_status_bar.xml是systemUI的一个总的布局文件。
    下面是super_status_bar.xml的源码:
    <com.android.systemui.statusbar.phone.StatusBarWindowView
        xmlns:android="http://schemas.android.com/apk/res/android"
        xmlns:systemui="http://schemas.android.com/apk/res/com.android.systemui"
        android:focusable="true"
        android:descendantFocusability="afterDescendants"
        android:fitsSystemWindows="true"
        android:background="@android:color/transparent"
        >

        <include layout="@layout/status_bar"
            android:layout_width="match_parent"
            android:layout_height="@*android:dimen/status_bar_height"
            />
        <com.android.systemui.statusbar.phone.PanelHolder
            android:id="@+id/panel_holder"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            >
            <include layout="@layout/status_bar_expanded"
                android:layout_width="match_parent"
                android:layout_height="match_parent"
                />
            <ViewStub android:id="@+id/quick_settings_stub"
                android:layout="@layout/quick_settings"
                android:layout_width="match_parent"
                android:layout_height="match_parent"
                />
        </com.android.systemui.statusbar.phone.PanelHolder>

    </com.android.systemui.statusbar.phone.StatusBarWindowView>

    从上面的源码可以知道,systemUI布局大概分为三个部分
    第一:status_bar,这部分是状态栏。
    第二:status_bar_expanded,这部分是下拉通知栏。
    第三:quick_settings_stub,这部分是下拉快捷设置栏。
    其中,本文中是重点分析下拉通知栏。

    *************************************************分割线**************************************
    下面是下拉通知栏的布局文件status_bar_expended.xml:
    <com.android.systemui.statusbar.phone.NotificationPanelView 
        xmlns:android="http://schemas.android.com/apk/res/android"
        xmlns:systemui="http://schemas.android.com/apk/res/com.android.systemui"
        android:id="@+id/notification_panel"
        android:layout_width="0dp"
        android:layout_height="wrap_content"
        android:background="@drawable/notification_panel_bg"
        android:paddingTop="@dimen/notification_panel_padding_top"
        android:layout_marginStart="@dimen/notification_panel_margin_left"
        >

        <View
            android:id="@+id/handle"
            android:layout_width="match_parent"
            android:layout_height="@dimen/close_handle_height"
            android:background="@drawable/status_bar_close"
            android:visibility="invisible"
            />

        <include
            layout="@layout/carrier_label"
            android:layout_height="@dimen/carrier_label_height"
            android:layout_width="match_parent"
            android:layout_marginBottom="@dimen/close_handle_height"
            android:layout_gravity="bottom"
            />

        <LinearLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:layout_marginBottom="@dimen/close_handle_underlap"
            android:orientation="vertical"
            android:animateLayoutChanges="false"
            >

            <include layout="@layout/status_bar_expanded_header"
                android:layout_width="match_parent"
                android:layout_height="@dimen/notification_panel_header_height"
                />

            <TextView
                android:id="@+id/emergency_calls_only"
                android:textAppearance="@style/TextAppearance.StatusBar.Expanded.Network.EmergencyOnly"
                android:layout_height="wrap_content"
                android:layout_width="match_parent"
                android:padding="4dp"
                android:gravity="center"
                android:visibility="gone"
                />

            <FrameLayout
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                >
                <ViewStub android:id="@+id/flip_settings_stub"
                    android:layout="@layout/flip_settings"
                    android:layout_width="match_parent"
                    android:layout_height="wrap_content"
                    />
        
                <ScrollView
                    android:id="@+id/scroll"
                    android:layout_width="match_parent"
                    android:layout_height="wrap_content"
                    android:fadingEdge="none"
                    android:overScrollMode="ifContentScrolls"
                    >
                    <com.android.systemui.statusbar.policy.NotificationRowLayout
                        android:id="@+id/latestItems"
                        android:layout_width="match_parent"
                        android:layout_height="wrap_content"
                        systemui:rowHeight="@dimen/notification_row_min_height"
                        />
                </ScrollView>
            </FrameLayout>
        </LinearLayout>
    </com.android.systemui.statusbar.phone.NotificationPanelView>

    其中,代码段: <include layout="@layout/status_bar_expanded_header"
                android:layout_width="match_parent"
                android:layout_height="@dimen/notification_panel_header_height"
                />
    该代码段是下拉通知栏的顶部的布局,包括时间,日期和一个清除通知消息的按钮。


    代码段:<com.android.systemui.statusbar.policy.NotificationRowLayout
                        android:id="@+id/latestItems"
                        android:layout_width="match_parent"
                        android:layout_height="wrap_content"
                        systemui:rowHeight="@dimen/notification_row_min_height"
                        />
    该代码段是用于存放下拉通知栏里面的各种通知消息。


    下面主要分析com.android.systemui.statusbar.phone.NotificationPanelView下拉通知栏的实现类的源码:
    public class NotificationPanelView extends PanelView {};由类定义的代码可以知道该类是继承PanelView类,PanelView类则是继承于FrameLayout。
    下拉菜单栏的主要实现都是在NotificationPanelView的父类PanelView中实现。
    看以下的代码段:
    protected void onFinishInflate() {
            super.onFinishInflate();
            mHandleView = findViewById(R.id.handle);

            loadDimens();

            if (DEBUG) logf("handle view: " + mHandleView);
            if (mHandleView != null) {
                mHandleView.setOnTouchListener(new View.OnTouchListener() {
                    @Override
                    public boolean onTouch(View v, MotionEvent event) {
                                Log.i("Garment30", "onTouch");
                        int pointerIndex = event.findPointerIndex(mTrackingPointer);
                        if (pointerIndex < 0) {
                            pointerIndex = 0;
                            mTrackingPointer = event.getPointerId(pointerIndex);
                        }
                        final float y = event.getY(pointerIndex);
                        final float rawDelta = event.getRawY() - event.getY();
                        final float rawY = y + rawDelta;
                        if (DEBUG) logf("handle.onTouch: a=%s p=[%d,%d] y=%.1f rawY=%.1f off=%.1f",
                                MotionEvent.actionToString(event.getAction()),
                                mTrackingPointer, pointerIndex,
                                y, rawY, mTouchOffset);
                        PanelView.this.getLocationOnScreen(mAbsPos);

                        switch (event.getActionMasked()) {
                            case MotionEvent.ACTION_DOWN:
                                Log.i("Garment30", "ACTION_DOWN");
                                mTracking = true;
                                mHandleView.setPressed(true);
                                postInvalidate(); // catch the press state change
                                mInitialTouchY = y;
                                mVelocityTracker = FlingTracker.obtain();
                                trackMovement(event);
                                mTimeAnimator.cancel(); // end any outstanding animations
                                mBar.onTrackingStarted(PanelView.this);
                                mTouchOffset = (rawY - mAbsPos[1]) - mExpandedHeight;
                                if (mExpandedHeight == 0) {
                                    mJustPeeked = true;
                                    runPeekAnimation();
                                }
                                break;

                            case MotionEvent.ACTION_POINTER_UP:
                                Log.i("Garment30", "ACTION_POINTER_UP");
                                final int upPointer = event.getPointerId(event.getActionIndex());
                                if (mTrackingPointer == upPointer) {
                                    // gesture is ongoing, find a new pointer to track
                                    final int newIndex = event.getPointerId(0) != upPointer ? 0 : 1;
                                    final float newY = event.getY(newIndex);
                                    final float newRawY = newY + rawDelta;
                                    mTrackingPointer = event.getPointerId(newIndex);
                                    mTouchOffset = (newRawY - mAbsPos[1]) - mExpandedHeight;
                                    mInitialTouchY = newY;
                                }
                                break;

                            case MotionEvent.ACTION_MOVE:
                                Log.i("Garment30", "ACTION_MOVE");

                                                    Log.i("Garment28", "PanelView---ACTION_MOVE");
                                final float h = rawY - mAbsPos[1] - mTouchOffset;
                                if (h > mPeekHeight) {
                                                    Log.i("Garment28", "PanelView---h > mPeekHeight");
                                    if (mPeekAnimator != null && mPeekAnimator.isStarted()) {
                                        mPeekAnimator.cancel();
                                    }
                                    mJustPeeked = false;
                                }
                                if (!mJustPeeked) {
                                                                Log.i("Garment28", "PanelView---!mJustPeeked--h:"+h);
                                                                //下面两段代码需要同时使用
                                  PanelView.this.setExpandedHeightInternal(h);//屏蔽了这段代码,下拉菜单无法随手的移动一起下拉,松手后菜单移动到默认的长度
                                  mBar.panelExpansionChanged(PanelView.this, mExpandedFraction);//屏蔽了这段代码,下拉通知栏显示为透明,松手后才正常
                                }

                                trackMovement(event);
                                break;

                            case MotionEvent.ACTION_UP:
                            case MotionEvent.ACTION_CANCEL:
                                Log.i("Garment30", "ACTION_CANCEL");
                                mFinalTouchY = y;
                                mTracking = false;
                                mTrackingPointer = -1;
                                mHandleView.setPressed(false);
                                postInvalidate(); // catch the press state change
                                mBar.onTrackingStopped(PanelView.this);
                                trackMovement(event);

                                float vel = 0, yVel = 0, xVel = 0;
                                boolean negative = false;

                                if (mVelocityTracker != null) {
                                    // the velocitytracker might be null if we got a bad input stream
                                    mVelocityTracker.computeCurrentVelocity(1000);

                                    yVel = mVelocityTracker.getYVelocity();
                                    negative = yVel < 0;

                                    xVel = mVelocityTracker.getXVelocity();
                                    if (xVel < 0) {
                                        xVel = -xVel;
                                    }
                                    if (xVel > mFlingGestureMaxXVelocityPx) {
                                        xVel = mFlingGestureMaxXVelocityPx; // limit how much we care about the x axis
                                    }

                                    vel = (float)Math.hypot(yVel, xVel);
                                    if (vel > mFlingGestureMaxOutputVelocityPx) {
                                        vel = mFlingGestureMaxOutputVelocityPx;
                                    }

                                    mVelocityTracker.recycle();
                                    mVelocityTracker = null;
                                }

                                // if you've barely moved your finger, we treat the velocity as 0
                                // preventing spurious flings due to touch screen jitter
                                final float deltaY = Math.abs(mFinalTouchY - mInitialTouchY);
                                if (deltaY < mFlingGestureMinDistPx
                                        || vel < mFlingExpandMinVelocityPx
                                        ) {
                                    vel = 0;
                                }

                                if (negative) {
                                    vel = -vel;
                                }

                                if (DEBUG) logf("gesture: dy=%f vel=(%f,%f) vlinear=%f",
                                        deltaY,
                                        xVel, yVel,
                                        vel);

                                fling(vel, true);    //松手后下拉通知栏回弹的动画

                                break;
                        }
                        return true;
                    }});
            }
        }
    其中,mHandleView = findViewById(R.id.handle);代码用于初始化下拉通知栏最下面的那一条直线,可以知道该view的触摸事件用于控制下拉通知栏的拉动时的高度的变化。
    在MotionEvent.ACTION_MOVE事件中PanelView.this.setExpandedHeightInternal(h);这段代码实现了拉动过程在中下拉通知栏的大小的改变,传入的h变量就是下拉通知栏的高度。看该方法的实现:
    public void setExpandedHeightInternal(float h) {
            if (Float.isNaN(h)) {
                // If a NaN gets in here, it will freeze the Animators.
                if (DEBUG_NAN) {
                    Log.v(TAG, "setExpandedHeightInternal: warning: h=NaN, using 0 instead",
                            new Throwable());
                }
                h = 0;
            }

            float fh = getFullHeight();
            if (fh == 0) {
                // Hmm, full height hasn't been computed yet
            }

            if (h < 0) h = 0;
            if (!(mRubberbandingEnabled && (mTracking || mRubberbanding)) && h > fh) h = fh;

            mExpandedHeight = h; //更新最新的通知栏的长度,屏蔽了这段代码,通知栏无法拉出

            if (DEBUG) logf("setExpansion: height=%.1f fh=%.1f tracking=%s rubber=%s", h, fh, mTracking?"T":"f", mRubberbanding?"T":"f");
            Log.i("Garment30", "PanelView---setExpandedHeightInternal--h:"+h);
            requestLayout(); //触发OnMeasure()和onLayout()进行View的重绘, 屏蔽这段代码,下拉通知栏无法显示,初始时h=0,默认状态时,h=729,最大为1919
    //        FrameLayout.LayoutParams lp = (FrameLayout.LayoutParams) getLayoutParams();
    //        lp.height = (int) mExpandedHeight;
    //        setLayoutParams(lp);

            mExpandedFraction = Math.min(1f, (fh == 0) ? 0 : h / fh);
        }
    在setExpandedHeightInternal()函数中,mExpandedHeight = h;这段代码用于更新需要重画的最新的下拉菜单栏的高度。
     requestLayout();该函数触发了OnMeasure()和onLayout()函数,对该View进行重新测量并重新布局。

    当手松开的时候,通知栏会有一个回弹的动作,看到fling(vel, true);这段代码:
    public void fling(float vel, boolean always) {
            if (DEBUG) logf("fling: vel=%.3f, this=%s", vel, this);
            mVel = vel;

            if (always||mVel != 0) {
                animationTick(0); // begin the animation  开始执行回弹的动画
            }
        }
    其中animationTick(0);是回弹动画的实现方法:
     private void animationTick(long dtms) {
            if (!mTimeAnimator.isStarted()) {
                // XXX HAX to work around bug in TimeAnimator.end() not resetting its last time
                mTimeAnimator = new TimeAnimator();
                mTimeAnimator.setTimeListener(mAnimationCallback);

                if (mPeekAnimator != null) mPeekAnimator.cancel();

                mTimeAnimator.start();

                mRubberbanding = mRubberbandingEnabled // is it enabled at all?
                        && mExpandedHeight > getFullHeight() // are we past the end?
                        && mVel >= -mFlingGestureMinDistPx; // was this not possibly a "close" gesture?
                if (mRubberbanding) {
                    mClosing = true;
                } else if (mVel == 0) {
                    // if the panel is less than halfway open, close it
                    mClosing = (mFinalTouchY / getFullHeight()) < 0.5f;
                } else {
                    mClosing = mExpandedHeight > 0 && mVel < 0;
                }
            } else if (dtms > 0) {
                final float dt = dtms * 0.001f;                  // ms -> s
                if (DEBUG) logf("tick: v=%.2fpx/s dt=%.4fs", mVel, dt);
                if (DEBUG) logf("tick: before: h=%d", (int) mExpandedHeight);

                final float fh = getFullHeight();
                boolean braking = false;
                if (BRAKES) {
                    if (mClosing) {
                        braking = mExpandedHeight <= mCollapseBrakingDistancePx;
                        mAccel = braking ? 10*mCollapseAccelPx : -mCollapseAccelPx;
                    } else {
                        braking = mExpandedHeight >= (fh-mExpandBrakingDistancePx);
                        mAccel = braking ? 10*-mExpandAccelPx : mExpandAccelPx;
                    }
                } else {
                    mAccel = mClosing ? -mCollapseAccelPx : mExpandAccelPx;
                }

                mVel += mAccel * dt;

                if (braking) {
                    if (mClosing && mVel > -mBrakingSpeedPx) {
                        mVel = -mBrakingSpeedPx;
                    } else if (!mClosing && mVel < mBrakingSpeedPx) {
                        mVel = mBrakingSpeedPx;
                    }
                } else {
                    if (mClosing && mVel > -mFlingCollapseMinVelocityPx) {
                        mVel = -mFlingCollapseMinVelocityPx;
                    } else if (!mClosing && mVel > mFlingGestureMaxOutputVelocityPx) {
                        mVel = mFlingGestureMaxOutputVelocityPx;
                    }
                }

                float h = mExpandedHeight + mVel * dt;

                if (mRubberbanding && h < fh) {
                    h = fh;
                }

                if (DEBUG) logf("tick: new h=%d closing=%s", (int) h, mClosing?"true":"false");
                Log.i("Garment30", "PanelView---animationTick--h:"+h);  //end at 729

                setExpandedHeightInternal(h);

                mBar.panelExpansionChanged(PanelView.this, mExpandedFraction);

                if (mVel == 0
                        || (mClosing && mExpandedHeight == 0)
                        || ((mRubberbanding || !mClosing) && mExpandedHeight == fh)) {
                    post(mStopAnimator);       //回弹动画停止
                }
            } else {
                Log.v(TAG, "animationTick called with dtms=" + dtms + "; nothing to do (h="
                        + mExpandedHeight + " v=" + mVel + ")");
            }
        }
    可以看到,setExpandedHeightInternal(h); mBar.panelExpansionChanged(PanelView.this, mExpandedFraction);该方法中有调用这两个方法对下拉菜单栏的长度进行更新的操作。mTimeAnimator = new TimeAnimator();mTimeAnimator.setTimeListener(mAnimationCallback);也初始化了一个TimeAnimator对象,并设置了监听器。
    private final TimeListener mAnimationCallback = new TimeListener() {
            @Override
            public void onTimeUpdate(TimeAnimator animation, long totalTime, long deltaTime) {
                animationTick(deltaTime);
            }
        };
    该监听器中的回调函数调用了animationTick(deltaTime)下拉通知栏的回弹动画的方法,所以我们松开手后通知栏会有一个回弹的动作。
    当满足一定条件时,回弹动画停止。
    if (mVel == 0|| (mClosing && mExpandedHeight == 0)|| ((mRubberbanding || !mClosing) && mExpandedHeight == fh)) {
                    post(mStopAnimator);       //回弹动画停止
                }

    ------------------------------------分割线----------------------------------------------------
    注意:下拉快捷设置栏的实现和下拉通知栏的实现是差不多,只是装载的内容不同。所以也可以通过类似的方法来分析下拉快速设置栏。

    展开全文
  • 应用禁用通知栏下拉 statusbar用了后但是效果不是很满意 其他的方法试过但是没有效果,所以换个思路 做法是在通知栏区域弄一个透明的window,这样下拉的时候触摸的区域就是这个window,系统的就下拉不了了 改做法是...

    应用禁用通知栏下拉这个需求让我头疼了好几天
    statusbar用了后但是效果不是很满意
    其他的方法试过但是没有效果,所以就换个思路吧
    做法是在通知栏区域弄一个透明的window,这样下拉的时候触摸的区域就是这个window,系统的就下拉不了了
    该做法是需要在应用上方显示一个window 所以需要权限

     <uses-permission android:name="android.permission.SYSTEM_ALERT_WINDOW" />
    
     public static final String STATUS_BAR_HEIGHT = "status_bar_height";
      public static final String DIMEN = "dimen";
      public static final String DEF_PACKAGE = "android";
       public static void preventStatusBarExpansion(Context context) {
        WindowManager manager = ((WindowManager) context.getApplicationContext()
                                                        .getSystemService(Context.WINDOW_SERVICE));
    
        WindowManager.LayoutParams localLayoutParams = new WindowManager.LayoutParams();
        localLayoutParams.type = WindowManager.LayoutParams.TYPE_SYSTEM_ERROR;
        localLayoutParams.gravity = Gravity.TOP;
        localLayoutParams.flags = WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE
            | WindowManager.LayoutParams.FLAG_NOT_TOUCH_MODAL
            | WindowManager.LayoutParams.FLAG_LAYOUT_IN_SCREEN;
    
        localLayoutParams.width = WindowManager.LayoutParams.MATCH_PARENT;
    
        int resId = context.getResources()
                           .getIdentifier(STATUS_BAR_HEIGHT, DIMEN, DEF_PACKAGE);
        int result;
        if (resId > 0) {
          result = context.getResources()
                          .getDimensionPixelSize(resId);
        } else {
          // Use Fallback size:
          result = 60; // 60px Fallback
        }
    
        localLayoutParams.height = result;
        localLayoutParams.format = PixelFormat.TRANSPARENT;
    
        if (view == null) {
          view = new CustomViewGroup(context);
        }
    
        try {
          if (manager != null) {
            manager.addView(view, localLayoutParams);
          }
        } catch (Exception ignored) {
        }
      }
    
      public static void allowStatusBarExpansion(Context context) {
        WindowManager manager = ((WindowManager) context.getApplicationContext()
                                                        .getSystemService(Context.WINDOW_SERVICE));
        try {
          if (manager != null) {
            manager.removeViewImmediate(view);
          }
        } catch (Exception ignored) {
        }
      }
    
      public static class CustomViewGroup extends ViewGroup {
        public CustomViewGroup(Context context) {
          super(context);
        }
    
        @Override
        protected void onLayout(boolean changed,
                                int l,
                                int t,
                                int r,
                                int b) {
        }
    
        @Override
        public boolean onInterceptTouchEvent(MotionEvent ev) {
          // Intercepted touch!
          return true;
        }
      }
    
    展开全文
  • 如何设置通知栏下拉不可用 有时候在一个界面不想让通知栏下拉的消息就是这个代码了, NotificaionManager里的一个方法。[java] view plaincopyNotificationMgr.getDefault().getStatusBarMgr().enableExpandedView...
    如何设置通知栏下拉不可用

            有时候在一个界面不想让通知栏下拉的消息就是这个代码了, NotificaionManager里的一个方法。

    1. NotificationMgr.getDefault().getStatusBarMgr().enableExpandedView(false);     




    展开全文
  • 问题背景 ...但,对于通知栏下拉这种情况,以上方法无法收到回调监听。 解决方法 /** * Called when the current {@link Window} of the activity gains or loses * focus. This is the best i
  • Android 6.0 SystemUI之通知栏下拉时周边全透明
  • android通知栏下拉

    2013-02-19 14:27:32
    一个很好的android popupwindow的实例,代码实用简单,很适合初学者学习
  • android 禁止通知栏下拉

    千次阅读 2016-03-15 09:36:25
    最近做了一个项目,需要把系统进行封装,也就是说程序是开机启动的,通知栏不让下拉,不让用户点击通知栏上面的通知进入系统。之前也试了好多方法。终于成功了。 系统:android 4.4  1.需要在程序中添加 status...
  • Android 4.4.2 禁用通知栏下拉

    千次阅读 2018-06-08 10:18:13
    最近做了一个项目,需要进入软件中,禁止下拉菜单,经查证,以下方法实现了我的需求: 系统:Android 4.4.2 1. 需要在程序中添加 service_interanl.jar 下载地址:...
  • 公司app里有h5游戏,在玩游戏时,在上面和下面有拖动手势时,总是拉出系统通知栏和工具栏,这时候会导致cocos卡顿,再操作游戏时就会卡死了,直接不动了。一开始的思路是,在appledelegate里面监听通知栏通过...
  • 在做锁屏的时候,要禁用通知栏下拉功能! 在网上找了一下资料,大致有下面两种方法 1) Object service = getSystemService ("statusbar");  try {  Class statusBarManager = Class.forName  (...
  • 如题 andriod 如何屏蔽home键 并且 屏蔽通知栏下拉 屏蔽home键 我找到的源码都是支持 andriod 3.0的 andriod 4.0直接报错 求助各位能否给点帮助
  • Android 使用动画效果后的控件位置处理 类似系统通知栏下拉动画 http://www.pocketdigi.com/20111028/556.html   下拉通知效果-Android源码下载 http://www.eoeandroid.com/thread-239825-1-1.html  ...
  • 按下下拉显示按钮时,那个白色的View会以向下移动,就是下拉动画的效果,显示在屏幕上,如下图: 当点击隐藏后,这个View又会上拉,恢复到第一张图片的样子,显示出原来的下拉显示按钮。 源代码: 布局 main....
  • 设定了RemoteViews view_custom = new RemoteViews(getPackageName(), R.layout.view_custom); RemoteViews 有个设置图标的方法view_custom.setImageViewResource(R.id.custom_icon, R.drawable.icon);...
  • 按下下拉显示按钮时,那个白色的View会以向下移动,就是下拉动画的效果,显示在屏幕上,如下图: 当点击隐藏后,这个View又会上拉,恢复到第一张图片的样子,显示出原来的下拉显示按钮。 源代码: 布局 ...
  • 1.未锁屏时禁止状态栏和通知栏下拉 vendor/mediatek/proprietary/packages/apps/SystemUI/src/com/android/systemui/keyguard/KeyguardViewMediator.java @@ -2179,7 +2179,7 @@ public class KeyguardViewMediator...
  • 我用网络上的方法移植红米的miui到我的THL手机。移植的miui最新的稳定版后,所有功能均正常运行,...现在的问题是,通知栏下拉菜单是被禁用了吗?如果是,应该如何激活呢? 可能我的问题很不专业。请谅解。谢谢帮助
  • 1.未锁屏时禁止状态栏和通知栏下拉 vendor/mediatek/proprietary/packages/apps/SystemUI/src/com/android/systemui/keyguard/KeyguardViewMediator.java @@ -2179,7 +2179,7 @@ public class ...
  • 类似手机通知栏全局下拉,只要继承BaseActivity的Activity都能实现下拉view,可以根据需要修改相应参数 demo地址
  • 标签:注意collapsePanels这里不是 collapse,否则会报//NoSuchMethodException: collapse []这是屏蔽下拉的方法try {Object service = getSystemService("statusbar");Class> claz = Class.forName("android.app....
  • 根据SystemUI下的PanelView,他就是下拉通知栏下拉快捷设置栏所继承的父类,这里面实现了下拉的动作监听,即是对status bar最下面那根横线的监听,当对她进行OnTouch时间时,判断下拉的状态,当return true表示,...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 785
精华内容 314
关键字:

通知栏下拉