2012-05-27 4 views
0

Я пытаюсь переместить представление, действующее в качестве фона из его текущего местоположения в указанное место (местоположение кнопки, нажатой) с помощью TranslateAnimation, однако он начинает перемещать ящик откуда-то случайным образом. См. Мой код ниже.Android - перемещение просмотров

Layout XML:

<?xml version="1.0" encoding="utf-8"?> 
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" 
android:layout_width="match_parent" 
android:layout_height="match_parent" 
android:orientation="vertical" > 

<ScrollView 
    android:layout_width="match_parent" 
    android:layout_height="100dp" 
    > 

    <FrameLayout 
     android:id="@+id/frame1" 
     android:layout_width="match_parent" 
     android:layout_height="wrap_content" > 

     <LinearLayout 
      android:id="@+id/linearLayout_test" 
      android:layout_width="100dp" 
      android:layout_height="100dp" 
      android:background="#E02111" > 
     </LinearLayout> 

     <TableLayout 
      android:layout_width="match_parent" 
      android:layout_height="match_parent" > 

      <TableRow 
       android:id="@+id/tableRow1" 
       android:layout_width="match_parent" 
       android:layout_height="wrap_content" > 

       <Button 
        android:id="@+id/button1" 
        android:layout_width="wrap_content" 
        android:layout_height="wrap_content" 
        android:text="Button 1" /> 

       <Button 
        android:id="@+id/button2" 
        android:layout_width="wrap_content" 
        android:layout_height="wrap_content" 
        android:text="Button 2" /> 
      </TableRow> 

      <TableRow 
       android:id="@+id/tableRow2" 
       android:layout_width="wrap_content" 
       android:layout_height="wrap_content" > 

       <Button 
        android:id="@+id/button3" 
        android:layout_width="wrap_content" 
        android:layout_height="wrap_content" 
        android:text="Button 3" /> 

       <Button 
        android:id="@+id/button4" 
        android:layout_width="wrap_content" 
        android:layout_height="wrap_content" 
        android:text="Button 4" /> 
      </TableRow> 

      <TableRow 
       android:id="@+id/tableRow3" 
       android:layout_width="wrap_content" 
       android:layout_height="wrap_content" > 

       <Button 
        android:id="@+id/button5" 
        android:layout_width="wrap_content" 
        android:layout_height="wrap_content" 
        android:text="Button 5" /> 

       <Button 
        android:id="@+id/button6" 
        android:layout_width="wrap_content" 
        android:layout_height="wrap_content" 
        android:text="Button 6" /> 
      </TableRow> 
     </TableLayout> 
    </FrameLayout> 
</ScrollView> 

</LinearLayout> 

Java код:

import android.app.Activity; 
import android.os.Bundle; 
import android.view.*; 
import android.view.View.OnClickListener; 
import android.view.animation.Animation; 
import android.view.animation.TranslateAnimation; 
import android.widget.*; 

public class TestAnimation extends Activity { 

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

    @Override 
    public void onWindowFocusChanged(boolean hasFocus) { 
     super.onWindowFocusChanged(hasFocus); 

     //the red box 
     View box = findViewById(R.id.linearLayout_test); 

     //Initially move the background box to button 1 
     Button button1 = (Button) findViewById(R.id.button1); 
     int[] button1Loc = new int[2]; 
     button1.getLocationOnScreen(button1Loc); 
     int[] boxLocation = new int[2]; 
     box.getLocationInWindow(boxLocation); 
     box.setLayoutParams(new FrameLayout.LayoutParams(button1.getWidth() + 1,button1.getHeight() + 1)); 
     TranslateAnimation animation = new TranslateAnimation(0, boxLocation[0] - button1Loc[0] , 0,boxLocation[1] - button1Loc[1]); 
     animation.setFillAfter(true); 
     animation.setDuration(400); 
     box.startAnimation(animation); 


     //add click handler on all buttons 
     Button button = (Button)findViewById(R.id.button1); 
     button.setOnClickListener(buttonClick); 
     button = (Button)findViewById(R.id.button1); 
     button.setOnClickListener(buttonClick);  
     button = (Button)findViewById(R.id.button2); 
     button.setOnClickListener(buttonClick); 
     button = (Button)findViewById(R.id.button3); 
     button.setOnClickListener(buttonClick); 
     button = (Button)findViewById(R.id.button4); 
     button.setOnClickListener(buttonClick); 
     button = (Button)findViewById(R.id.button5); 
     button.setOnClickListener(buttonClick); 
     button = (Button)findViewById(R.id.button6); 
     button.setOnClickListener(buttonClick); 

    } 
    // This is the problem - it should start moving the box from its current location to the clicked button's location 
    // right now it starts moving it from somewhere random :) 
    private OnClickListener buttonClick = new OnClickListener() { 
     public void onClick(View v) { 
      View box = findViewById(R.id.linearLayout_test); 
      int[] buttonLoc = new int[2]; 
      v.getLocationOnScreen(buttonLoc); 

      int[] boxLocation = new int[2]; 
      box.getLocationOnScreen(boxLocation); 

      TranslateAnimation animation = new TranslateAnimation(
         Animation.ABSOLUTE, 0,Animation.ABSOLUTE, buttonLoc[0] - boxLocation[0], 
         Animation.ABSOLUTE, 0,Animation.ABSOLUTE, buttonLoc[1] - boxLocation[1] 
         ); 
      animation.setFillAfter(true); 
      animation.setDuration(400); 
      box.startAnimation(animation); 

     } 

    }; 
} 

ответ

0

Это просто. Вы передаете некоторый переводный вектор, введённое начальное положение и положение фиано. Обратите внимание, что имя аргумента xValue не xDelta, как в другом конструкторе TranslateAnimation, и вы используете абсолютные координаты не локально.

Fix:

TranslateAnimation animation = new TranslateAnimation( 
    Animation.ABSOLUTE, boxLocation[0], Animation.ABSOLUTE, buttonLoc[0] , 
    Animation.ABSOLUTE, boxLocation[1], Animation.ABSOLUTE, buttonLoc[1]); 

Edit:

private int[] oldPos = new int[2]; 
private OnClickListener buttonClick = new OnClickListener() { 
    public void onClick(View v) { 
    View box = findViewById(R.id.linearLayout_test); 

    int[] newPos = new int[2]; 
    v.getLocationInWindow(newPos); 
    newPos[1] -= box.getTop(); 
    TranslateAnimation animation = new TranslateAnimation(
      Animation.ABSOLUTE, oldPos[0], 
      Animation.ABSOLUTE, newPos[0], 
      Animation.ABSOLUTE, oldPos[1], 
      Animation.ABSOLUTE, newPos[1]); 

    oldPos = newPos; 

    animation.setFillAfter(true); 
    animation.setDuration(400); 
    box.startAnimation(animation); 
} 

Существует непоследовательность в андроида. Animation.ABSOLUTE не учитывает высоту строки состояния, но getLocationInWindow и getLocationOnScreen. Постарайтесь исправить это самостоятельно.

Помните, что эта анимация не перемещается. Показывается, но обновляет матрицу, поэтому linearLayout_test возвращает всегда ту же позицию.

+0

Marek R, Спасибо за указание xValue vs xDelta in (http://developer.android.com/reference/android/view/animation/TranslateAnimation.html#TranslateAnimation%28int,%20float,%20int,%20float ,% 20int,% 20float,% 20int,% 20float% 29). Код, который вы предложили, не работает. Запустите его и посмотрите на него для себя. – idopaging

+0

Проверьте изменения в моем ответе. –

Смежные вопросы