android 實(shí)現(xiàn)仿IOS桌面背景動效果

注:https://stackoverflow.com/questions/56141981/how-to-implement-background-motion-effect-parallax-effect

gifhome_616x1280_2s.gif

如圖,蘋果手機(jī)桌面背景動圖。
自定義ImageView,實(shí)現(xiàn)SensorEventListener,在onSensorChanged方法中通過 SensorManager做處理。動態(tài)改變x、y值。上代碼~

============================================================
public class ParallaxImageView extends AppCompatImageView implements SensorEventListener {
float[] rotMat = new float[16];
float[] vals = new float[3];

private SensorManager senSensorManager;
private Sensor senAccelerometer;
private int sideVerticalMargin, sideHorizontalMargin;
private float verticalMultiplier=1, horizontalMultiplier=1;

public ParallaxImageView(Context context, AttributeSet attrs) {
    super(context, attrs);

    senSensorManager = (SensorManager) context.getSystemService(Context.SENSOR_SERVICE);
    senAccelerometer = senSensorManager.getDefaultSensor(Sensor.TYPE_ROTATION_VECTOR);
    senSensorManager.registerListener(this, senAccelerometer , SensorManager.SENSOR_DELAY_FASTEST);

}

public ParallaxImageView(Context context) {
    super(context);
}

public void setMargins(int VM, int HM){
    this.sideVerticalMargin = -VM;
    this.sideHorizontalMargin = -HM;
    LinearLayout.LayoutParams params = (LinearLayout.LayoutParams)this.getLayoutParams();
    params.setMargins(-HM, -VM, -HM, -VM);
    this.setLayoutParams(params);
}

public void setMultipliers(float Vertical, float Horizontal){
    this.verticalMultiplier = Vertical;
    this.horizontalMultiplier = Horizontal;
}

@Override
public void onSensorChanged(SensorEvent event) {
    Sensor mySensor = event.sensor;

    if (mySensor.getType() == Sensor.TYPE_ROTATION_VECTOR) {

        // Convert the rotation-vector to a 4x4 matrix.
        try {
            SensorManager.getRotationMatrixFromVector(rotMat, event.values);
        } catch (IllegalArgumentException e) {
            if (event.values.length > 3) {
                // Note 3 bug
                float[] newVector = new float[] {
                        event.values[0],
                        event.values[1],
                        event.values[2]
                };
                SensorManager.getRotationMatrixFromVector(rotMat, newVector);
            }
        }
        SensorManager.remapCoordinateSystem(rotMat,
                SensorManager.AXIS_Y, SensorManager.AXIS_X,
                rotMat);

        SensorManager.getOrientation(rotMat, vals);

        vals[0] = (float) Math.toDegrees(vals[0]);
        vals[1] = (float) Math.toDegrees(vals[1]);
        vals[2] = (float) Math.toDegrees(vals[2]);

        int leftfloat = (int) (this.sideHorizontalMargin-(vals[1]*this.horizontalMultiplier));

        int topfloat;

        if(vals[2]>0){
            topfloat=(int) (this.sideVerticalMargin+(vals[2]*this.verticalMultiplier));
        }else{
            topfloat=(int) (this.sideVerticalMargin-(vals[2]*this.verticalMultiplier));
        }

        this.setX(leftfloat);
        this.setY(topfloat);
    }

}

@Override
public void onAccuracyChanged(Sensor sensor, int accuracy) {
    // TODO Auto-generated method stub

}

/**
 * 在生命周期調(diào)用onPause時(shí)調(diào)用
 */
public void onPause() {
    senSensorManager.unregisterListener(this);
}
/**
 * 在生命周期調(diào)用onResume時(shí)調(diào)用
 */
public void onResume() {
    senSensorManager.registerListener(this, senAccelerometer, SensorManager.SENSOR_DELAY_FASTEST);
}

}

<com.ingeek.tsmproject.test.ParallaxImageView
    android:id="@+id/iv_background"
    android:src="@drawable/background"
    android:layout_height="fill_parent"
    android:layout_width="fill_parent"
    android:scaleType="centerCrop"
    android:adjustViewBounds="true"/>

============================================================
ParallaxImageView ivBackground = findViewById(R.id.iv_background);
ivBackground.setMargins(300, 200);
ivBackground.setMultipliers(1.6f, 1.8f);//動的幅度
============================================================
我是放在LinearLayout中,如果是在RelativeLayout 中需要將LinearLayout.LayoutParams改為RelativeLayout .LayoutParams。

另外還有一個(gè)庫可以使用
https://github.com/gjiazhe/PanoramaImageView

以后如果做這個(gè)需求可以借鑒參考了。

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

友情鏈接更多精彩內(nèi)容