Android 사용자 정의 View QQ 사 이 드 슬라이드 메뉴 구현 코드

QQ 의 사 이 드 스 케 이 트 효 과 를 살 펴 보 겠 습 니 다.
这里写图片描述
분석 해 봐.
먼저 원리 도 를 올리다.
这里写图片描述
-우선 안 드 로 이 드 의HorizontalScrollView수평 슬라이딩 레이아웃 을 용기 로 사 용 했 습 니 다.물론 사 이 드 슬라이딩 보 기 를 사용자 정의 해 야 합 니 다.
-이 용기 안에 부모 레이아웃(일반적으로 LinerLayout,이 demo 는 사용)이 있 습 니 다.이 부모 레이아웃 에는 두 개의 키 컨트롤(레이아웃)만 있 고 초기 상태 메뉴 페이지 의 위 치 는 Y 축 에 오프셋 이 존재 합 니 다.그러면 홈 페이지 가 메뉴 페이지 위 에 접 혀 있 는 시각 적 효 과 를 형성 할 수 있 습 니 다.그 다음 에 미 끄 러 지 는 과정 에서 오프셋 을 점차적으로 수정 하고 마지막 메뉴 페이지 와 홈 페이지 를 나란히 배열 합 니 다.원리 가 밝 혀 지면 이 루어 지 는 건 일이 아니 야..
구체 적 실현
레이아웃 코드

<fierce_luk.com.sideslipviewdemo2.SideslipView
    android:id="@+id/my_veiw"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:scrollbars="none"
    luk:leftPanding="200dp">
    <!--           LinearLayout-->
    <FrameLayout
      android:layout_width="match_parent"
      android:layout_height="match_parent"
      android:orientation="horizontal">
      <TextView
        android:id="@+id/image2"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:background="@mipmap/homepage"
        android:gravity="center"
        android:tag="0"
        android:text="  "
        android:textColor="@color/colorAccent"
        android:textSize="60sp" />
      <TextView
        android:id="@+id/image1"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:background="@color/color1"
        android:gravity="center"
        android:tag="1"
        android:text="   "
        android:textColor="@color/colorAccent"
        android:textSize="60sp" />
    </FrameLayout>
    <!--<fragment-->
    <!--android:name="com.luk.bluetoothapp.fragment.MyBluetoothDevice"-->
    <!--android:layout_width="match_parent"-->
    <!--android:layout_height="match_parent"-->
    <!--android:tag="1" />-->
    <!--<fragment-->
    <!--android:name="com.luk.bluetoothapp.fragment.HomeFragment"-->
    <!--android:layout_width="match_parent"-->
    <!--android:layout_height="match_parent"-->
    <!--android:tag="0" />-->
  </fierce_luk.com.sideslipviewdemo2.SideslipView>
사용자 정의 사 이 드 슬라이드 보기
가장 핵심 적 인 부분

public class SideslipView extends HorizontalScrollView {
  private int mScreenWidth;//    
  private int mMenuLeftPadding;
  private int mBluetoothWidth;//     
  private int mHalfMenuWidth;
  View home;
  View bluetooth;
  protected boolean isOpen;
  protected boolean isFirst = true;
  public SideslipView(Context context) {
    // super   this
    this(context, null);
  }
  public SideslipView(Context context, AttributeSet attrs) {
    // super   this
    this(context, attrs, 0);
  }
  public SideslipView(Context context, AttributeSet attrs, int defStyleAttr) {
    super(context, attrs, defStyleAttr);
    //      
    WindowManager wm = (WindowManager) context.getSystemService(Context.WINDOW_SERVICE);
    DisplayMetrics metrics = new DisplayMetrics();
    wm.getDefaultDisplay().getMetrics(metrics);
    mScreenWidth = metrics.widthPixels;
    // mScreenWidth = context.getResources().getDisplayMetrics().widthPixels;
    Log.e("TAG", "MyScrollView: mScreenWidth" + mScreenWidth);
    //          
    TypedArray a = context.obtainStyledAttributes(attrs, R.styleable.MyScrollView);
    int n = a.length();
    for (int i = 0; i < n; i++) {
      int arrt = a.getIndex(i);
      switch (arrt) {
        case R.styleable.MyScrollView_leftPanding:
          mMenuLeftPadding = (int) a.getDimension(R.styleable.MyScrollView_leftPanding, 0);
          break;
        default:
          break;
      }
    }
    Log.e("TAG", "MyScrollView: mMenuLeftPadding" + mMenuLeftPadding);
    a.recycle();
  }
  @Override
  protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
    if (isFirst) {
      //           
      //         LinearLayout  
//      LinearLayout layout = (LinearLayout) this.getChildAt(0);
      /**                       FrameLayout
       *                           */
      FrameLayout layout = (FrameLayout) this.getChildAt(0);
      home = layout.getChildAt(1);
      bluetooth = layout.getChildAt(0);
      LayoutParams params = new LayoutParams(mBluetoothWidth,
          getResources().getDisplayMetrics().heightPixels);
      params.setMargins(mScreenWidth, 0, 0, 0);
      bluetooth.setLayoutParams(params);
      mBluetoothWidth = mScreenWidth - mMenuLeftPadding;
      home.getLayoutParams().width = mScreenWidth;
      bluetooth.getLayoutParams().width = mBluetoothWidth;
      mHalfMenuWidth = mBluetoothWidth / 2;
      isFirst = false;
    }
    super.onMeasure(widthMeasureSpec, heightMeasureSpec);
  }
  @Override
  protected void onLayout(boolean changed, int l, int t, int r, int b) {
    super.onLayout(changed, l, t, r, b);
    //     Bluetooth
    if (changed)
      this.scrollTo(0, mBluetoothWidth);
  }
  Animation anim;
  @Override
  public boolean onTouchEvent(MotionEvent ev) {
    switch (ev.getAction()) {
      case MotionEvent.ACTION_UP:
        int scrollX = getScrollX();
        if (scrollX >= mHalfMenuWidth) {
          Log.e("TAG", "====");
          this.smoothScrollTo(mBluetoothWidth, 0);
          isOpen = true;
        } else {
          this.smoothScrollTo(0, 0);
          isOpen = false;
        }
        //      
        return true;
    }
    return super.onTouchEvent(ev);
    //return true;
  }
  /**
   *      
   */
  protected void openMenu() {
    if (isOpen)
      return;
    this.smoothScrollTo(mBluetoothWidth, 0);
    isOpen = true;
  }
  /**
   *      
   */
  protected void closeMenu() {
    if (!isOpen)
      return;
    this.smoothScrollTo(0, 0);
    isOpen = false;
  }
  /**
   *       
   */
  public void toggleMenu() {
    if (isOpen)
      closeMenu();
    else
      openMenu();
  }
  @Override
  protected void onScrollChanged(int l, int t, int oldl, int oldt) {
    super.onScrollChanged(l, t, oldl, oldt);
//   l      (    )
    Log.e("TAG", "l=" + l + " t=" + t);
    Log.e("TAG", "oldl=" + oldl + " oldt=" + oldt);
    // scale   1   0   
    float scale = l * 1.0f / mBluetoothWidth;
    /**
     *      
     * scaleLeft              
     *  
     * */
    float scaleLeft = 0.4f - 0.4f * scale;
    /**   X        **/
    ViewHelper.setTranslationX(bluetooth, -(mBluetoothWidth * scaleLeft));
    Log.e("TAG", "mBluetoothWidth+" + mBluetoothWidth);
    Log.e("TAG", "=============" + mBluetoothWidth * scale + "scale" + scale);
/*
    *//**          **//*
    //           
    ViewHelper.setPivotY(home, mScreenWidth);
    ViewHelper.setPivotX(home, home.getHeight() / 2);
    *//**   XY         (  1   0.9)**//*
    float pivoXY = 1 - 0.4f * scale;
    ViewHelper.setScaleX(home, pivoXY);
    ViewHelper.setScaleY(home, pivoXY);*/
/*
    *//**     **//*
    //  1   0.6;
    float alpha = 1 - 0.4f * scale;
    ViewHelper.setAlpha(home, alpha);*/
  }
}
넓히다
정의 속성 을 추가 하여 메뉴 의 오른쪽 여백 값 을 설정 합 니 다.
우선 values 폴 더 아래 에 attr.xml 를 새로 만 들 고 다음 내용 을 기록 합 니 다.

<resources>
  <declare-styleable name="MyScrollView">
    <attr name="rightPanding" format="dimension" />
    <attr name="leftPanding" format="dimension" />
  </declare-styleable>
</resources>
레이아웃 에 여백 설정

 <fierce_luk.com.sideslipviewdemo2.SideslipView
    android:id="@+id/my_veiw"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:scrollbars="none"
    luk:leftPanding="200dp">
다른 것 은 군말 하지 않 고 효 과 를 보 자.
-원본 다운로드 데모 원본 클릭 다운로드
这里写图片描述
총결산
위 에서 말 한 것 은 소 편 이 소개 한 안 드 로 이 드 사용자 정의 View 가 QQ 사 이 드 슬라이드 메뉴 를 모방 한 실현 코드 입 니 다.여러분 에 게 도움 이 되 기 를 바 랍 니 다.궁금 한 점 이 있 으 시 면 메 시 지 를 남 겨 주세요.소 편 은 바로 답 해 드 리 겠 습 니 다.여기 서도 저희 사이트 에 대한 여러분 의 지지 에 감 사 드 립 니 다!

좋은 웹페이지 즐겨찾기