Android View 이동 의 3 가지 방식 요약

머리말
안 드 로 이 드 개발 에서 View 는 안 드 로 이 드 개발 자의 마음의 병 이 었 다.한편 으로 는 진급 을 원 하고,한편 으로 는 진급 을 두려워 했다.안 드 로 이 드 의 View 는 진급 로 의 가장 큰 걸림돌 이 라 고 할 수 있다.왜냐하면 이것 은 관련 된 것 이 너무 많 기 때문이다.예 를 들 어 이번에 우리 가 쓸 View 이동,그리고 View 의 터치 이벤트 전달,사용자 정의 View 를 만 드 는 것 도 포함한다.이것들 은 모두 매우 중요 하고 직면 해 야 할 난제 들이다.그러나 어쨌든 지금 극복 하지 못 하 는 어려움 은 앞으로 극복 하기 어 려 울 것 이다.
그 전에 우 리 는 안 드 로 이 드 좌표계 의 정의 규칙 과 View 의 일부 위치 변 수 를 알 아야 한다.

Android 좌표계
View 의 위치 와 크기 는 네 개의 매개 변수 에 의 해 결정 된다.즉,left,top,right,bottom 이 고 이 네 개의 매개 변 수 는 모두 아버지 View 에 비해 결정 된다.

int width = right-left;
 int height = bottom-top;
Activity 에서 레이아웃 이 완 료 된 후에 저 희 는 View 를 통 해 이러한 매개 변수 정 보 를 얻 을 수 있 습 니 다.

//left,top,right,bottom    
 int left = getLeft();
 int top = getTop();
 int right = getRight();
 int bottom = getBottom();
또한 Android 3.0 이후 x,y,translationX,translationY 등 인 자 를 추가 합 니 다.(x,y)는 View 가 View Group 의 왼쪽 상단 에 있 는 x,y 의 값,translationX,translationY 가 View 를 평평 하 게 이동 하 는 데 사용 되 는 것 을 나타 낸다.기본 값 은 모두 0 으로 ViewsetTranslationX()/setTranslationY()를 호출 한 후에 변 경 됩 니 다.

//x,y,translationX,translationY     
 int x = getX();
 int y = getY();
 int translationX = getTranslationX();
 int translationY = getTranslationY();
PS:View 를 호출 하 는setTranslationX()방법 과setTranslationY()방법 은 View 를 지정 한 거 리 를 이동 시 킬 수 있 지만 이 과정 은 순식간에 이 루어 집 니 다.View 의 이동 을 더욱 부 드 럽 게 하기 위해 View 의 속성 애니메이션 을 사용 하여 translationX 와 translationY 를 지정 할 수 있 습 니 다.

ObjectAnimator valueAnimator = ObjectAnimator.ofFloat(textView, "translationX", 200);
 valueAnimator.setDuration(2000);
 valueAnimator.start();
또 뷰 설정setTranslationX()setTranslationY()을 준 뒤 설정 한 값 이 변 하지 않 으 면 한 번,즉 처음 지 정 된 이동 거리 만 이동한다.원본 코드 를 본 후에 우 리 는 이 유 를 발 견 했 습 니 다.원래 값 을 설정 한 후에 설 정 된 값 과 현재 translationX,translationY 를 비교 하고 일치 하지 않 을 때 만 이동 합 니 다.

View 의 기본 적 인 매개 변 수 를 알 아 본 후에 우 리 는 View 에 관 한 세 가지 이동 방식 을 보 았 다.
1.Android 시스템 에서 제공 하 는 scrollTo()/scrollBy()방법 으로 View 의 이동 을 실현 합 니 다.scrollTo()이 든scrollBy()이동 의 본질은 모두 View/View Group 의 내용 이다.또한 이동 하 는 과정 이 순식간에 이 루어 지기 때문에 더 좋 은 이동 효 과 를 내기 위해 서 는 Scroller 류 와 결합 해 사용 해 야 한다.또한 위의 Translation 과 달리 View 자 체 를 이동 한 다 는 점 을 잘 이해 해 야 한다.scrollTo()scrollBy()는 모두 View 의 방법 으로 Scroller 의 방법 이 아니 지만 View 의 부 드 러 운 이동 과 Scroller 류 의 밀 도 를 제어 할 수 없습니다.scrollTo() :이동 의 절대 위 치 를 말 하 는데 위치 가 변 하지 않 으 면 여러 번 호출 하면 소 용이 없다.

scrollTo 이동 프로 세 스 설명도scrollBy() :그 본질은 여전히 호출 된 것 이다scrollTo() .현재 위 치 를 이동 하 는 상대 적 인 거 리 를 말한다(매번 현재 위치 와 설 정 된 거 리 를 추가 하고 scrollto()를 호출 한다.이렇게 여러 번 호출 하면 매번 거 리 를 이동 하 는 것 을 발견 할 수 있다.이것 은 scrollto()와 본질 적 인 차이 이다)

scrollBy 이동 프로 세 스 설명도
PS:위의 두 장의 그림 에 대해 사실은 지금까지 저 자신 이 상대 적 으로 절대적 인 것 이 무엇 인지 완전히 이해 하지 못 했 기 때문에 두 장의 손 그림 은 사람들 로 하여 금 더욱 쉽게 이해 하 게 할 수 있 습 니 다.그리고scrollTo()scrollBy()이동 방향 문제 입 니 다.위 에 우 리 는 안 드 로 이 드 의 좌표 계 를 그 렸 습 니 다.x 축 왼쪽→오른쪽 이 정 이 고 y 축 은 위→아래 가 정 입 니 다.그러나 이것 은 scrollto 와 scrollBy 에 적용 되 지 않 습 니 다.scrollto 와 scrollBy 는 정반 대 입 니 다.즉,x 축 왼쪽→오른쪽 은 마이너스 이 고 y 축 은 위→아래 에서 마이너스 입 니 다.정말 아버 지 를 속 이 는 것 같 습 니 다.
Scroller 클래스 분석:왜 Scroller 클래스 의 방법 으로 View/ViewGroup 의 내용 을 이동 할 수 있 습 니까?다음은 우리 가 분석 해 보 자.
맨 먼저
스크롤 러 클래스 의 대상 mScroller 를 만 듭 니 다.
그리고
View 를 규정된 시간 에 지 정 된 위치 로 이동 시 키 려 면startScroll()방법 을 사용 합 니 다.startScroll()Scroller유형 중의 방법 입 니 다.또한Scroller유형 중 하나filing()방법 도 자주 사용 합 니 다.주로 부 드 러 운 이동 을 처리 하고 보통 미 끄 러 진 후의 관성 효 과 를 조성 하여 View 의 이동 을 더욱 생동감 있 게 합 니 다.다음은startScroll()의 소스 코드 를 보 겠 습 니 다.

//     /    。  duration   ,    。          ,       。
 public void startScroll(int startX, int startY, int dx, int dy, int duration) { 
 ...
 }
일반적으로 우리 가 이 방법 을 호출 한 후에 모두 Viewinvalidate() 를 조정 해 야 하 는데 이 방법 은 Viewdraw()방법 을 촉발 시 킬 수 있다.그리고draw() 호출computeScroll() ,소스 코드 에서 우 리 는computeScroll() 빈 방법 을 발견 했다.이것 도 우리 가 다시 쓰기computeScroll()방법 을 필요 로 하 는 이유 이다.현재 이동 작업 은computeScroll()에서 진행 되 고 있 기 때문이다.

@Override
 public void computeScroll() {
 if (mScroller.computeScrollOffset()) {
  scrollTo(mScroller.getCurrX(), mScroller.getCurrY());
  //    View postInvalidate()/invalidate(),       View        。
  postInvalidate();
 }
 super.computeScroll();
 }
위 에서 우 리 는 Scroller 류 중 하나computeScrollOffset()방법 을 보 았 는데,그것 은 또 무엇 을 하 는 것 입 니까?그것 의 주요 역할 은 mCurrX 와 mCurrY 가 바 뀌 었 는 지,있 으 면 true 로 돌아 가 고 없 으 면 false 로 돌아 가 는 것 이다.이 방법 을 통 해 지속 적 인 호출scrollTo()이 필요 한 지 여 부 를 판단 할 수 있 습 니 다.여기에 예 시 를 하나 더 드 리 겠 습 니 다.scrollTo()를 사용 하여 View 가 손가락 을 따라 이동 하도록 합 니 다.

public class CuView extends LinearLayout {

 private float mStartX;
 private float mStartY;
 private Scroller mScroller;
 /**
 *          
 */
 private boolean isFirstFinish;

 public CuView(Context context) {
 super(context);
 init(context);
 }

 public CuView(Context context, AttributeSet attrs) {
 super(context, attrs);
 init(context);
 }

 private void init(Context context) {
 mScroller = new Scroller(context);
 }

 public CuView(Context context, AttributeSet attrs, int defStyleAttr) {
 super(context, attrs, defStyleAttr);
 init(context);
 }

 @TargetApi(Build.VERSION_CODES.LOLLIPOP)
 public CuView(Context context, AttributeSet attrs, int defStyleAttr, int defStyleRes) {
 super(context, attrs, defStyleAttr, defStyleRes);
 init(context);
 }


 /**
 *  View        
 * @param event
 * @return
 */
 @Override
 public boolean onTouchEvent(MotionEvent event) {
 int action = event.getAction();
 switch (action) {
  case MotionEvent.ACTION_DOWN:
  /**
   *         ,              ,    View           。
   */
  if (!isFirstFinish) {
   mStartX = event.getRawX();
   mStartY = event.getRawY();
  }
  break;
  case MotionEvent.ACTION_MOVE:
  scrollTo((int) (mStartX - event.getRawX()), (int) (mStartY - event.getRawY()));
  break;
  case MotionEvent.ACTION_UP:
  //       
  isFirstFinish = true;
  break;
 }
 return true;
 }

 /**
 *   startScroll
 */
 public void startScroll() {
 /**
  *   Scroller    ,
  */
 mScroller.startScroll(20, 20, -500, -500, 5000);
 invalidate();
 }

 @Override
 public void computeScroll() {
 if (mScroller.computeScrollOffset()) {
  scrollTo(mScroller.getCurrX(), mScroller.getCurrY());
  invalidate();
 }
 super.computeScroll();
 }
}
2.애니메이션 을 사용 하여 View 의 이동 을 실현 합 니 다.
여기 에는 View 의 Tween Animation/Frame Animation 과 3.0 이후 추 가 된 Property Animation 이 포함 된다.그 이동 은 View 의 이미지 입 니 다.View 자체 의 위치 와 크기 는 변 하지 않 았 습 니 다.
3.View 의 LayoutParams 를 설정 하여 View 를 이동 합 니 다.

LinearLayout.LayoutParams layoutParams = (LinearLayout.LayoutParams) textView.getLayoutParams();
 layoutParams.leftMargin = 50;
 textView.requestLayout();
총결산
이상 은 안 드 로 이 드 뷰 모 바 일의 3 가지 방식 의 모든 내용 을 정리 한 것 입 니 다.본 논문 의 내용 이 안 드 로 이 드 를 개발 할 때 도움 이 되 기 를 바 랍 니 다.궁금 한 점 이 있 으 면 댓 글 을 남 겨 주 십시오.

좋은 웹페이지 즐겨찾기