跳到主要内容
极客日志极客日志面向AI+效率的开发者社区
首页博客我的书AI学习GitHub 精选镜像AI 生图工具UI配色美学关于
搜索内容 / 工具 / 仓库 / 镜像...⌘K搜索
注册
博客列表
Java大前端java

Android 使用 Rotate3dAnimation 实现 3D 旋转动画效果

如何在 Android 中使用 Rotate3dAnimation 类实现图片的 3D 旋转动画。内容涵盖了核心的 Java 代码实现,包括自定义动画类 Rotate3dAnimation 和 Activity 控制逻辑,以及对应的 XML 布局文件。文章深入解析了 Camera 类和 Matrix 变换的原理,解释了如何通过 preTranslate 和 postTranslate 操作实现围绕指定中心点的旋转。此外,还补充了关于 API 兼容性、硬件加速开启建议以及现代属性动画替代方案的说明,帮助开发者全面理解并应用该动画技术。

王者发布于 2025/2/7更新于 2026/10/2095 浏览
Android 使用 Rotate3dAnimation 实现 3D 旋转动画效果

Android 使用 Rotate3dAnimation 实现 3D 旋转动画效果

在 Android 开发中,Rotate3dAnimation 类允许开发者创建围绕 Y 轴或 Z 轴的 3D 旋转动画。通过结合 Camera 类和 Matrix 变换,可以实现具有深度感的图片旋转效果,例如点击开始按钮进行 360 度旋转,点击结束按钮停止。

核心代码实现

1. 自定义 3D 旋转动画类 (Rotate3dAnimation.java)

该类继承自 Animation,利用 Camera 对象来模拟摄像机移动,从而产生 3D 透视效果。

public class Rotate3dAnimation extends Animation {
    private final float mFromDegrees;
    private final float mToDegrees;
    private final float mCenterX;
    private final float mCenterY;
    private final float mDepthZ;
    private final boolean mReverse;
    private Camera mCamera;

    /**
     * 创建一个围绕 Y 轴的 3D 旋转。
     *
     * @param fromDegrees 起始角度
     * @param toDegrees   结束角度
     * @param centerX     X 轴中心点
     * @param centerY     Y 轴中心点
     * @param depthZ      Z 轴深度平移量
     * @param reverse     是否反转深度平移时间
     */
    public Rotate3dAnimation(float fromDegrees, float toDegrees,
                             float centerX,  centerY,  depthZ,  reverse) {
        mFromDegrees = fromDegrees;
        mToDegrees = toDegrees;
        mCenterX = centerX;
        mCenterY = centerY;
        mDepthZ = depthZ;
        mReverse = reverse;
    }

    
       {
        .initialize(width, height, parentWidth, parentHeight);
        mCamera =  ();
    }

    
       {
            mFromDegrees;
           fromDegrees + ((mToDegrees - fromDegrees) * interpolatedTime);
            mCenterX;
            mCenterY;
            mCamera;
            t.getMatrix();

        
        camera.save();
         (mReverse) {
            camera.translate(, , mDepthZ * interpolatedTime);
        }  {
            camera.translate(, , mDepthZ * ( - interpolatedTime));
        }
        
        camera.rotateY(degrees);
        
        camera.getMatrix(matrix);
        
        camera.restore();
        
        
        matrix.preTranslate(-centerX, -centerY);
        matrix.postTranslate(centerX, centerY);
    }
}
float
float
boolean
@Override
public
void
initialize
(int width, int height, int parentWidth, int parentHeight)
super
new
Camera
@Override
protected
void
applyTransformation
(float interpolatedTime, Transformation t)
final
float
fromDegrees
=
float
degrees
=
final
float
centerX
=
final
float
centerY
=
final
Camera
camera
=
final
Matrix
matrix
=
// 保存一次 camera 初始状态,用于 restore()
if
0.0f
0.0f
else
0.0f
0.0f
1.0f
// 围绕 Y 轴旋转 degrees 度
// 从 camera 中取出矩阵,赋值给 matrix
// camera 恢复到初始状态,继续用于下次的计算
// 调整矩阵以围绕指定中心点旋转

2. 活动逻辑控制 (Test3DRotateActivity.java)

此 Activity 负责初始化视图、绑定按钮事件并启动动画。

public class Test3DRotateActivity extends Activity {
    private static final String TAG = "Test3DRotateActivity";
    private ImageView image;
    private Button start, stop;
    private Rotate3dAnimation rotation;
    private StartNextRotate startNext;

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);
        image = (ImageView) findViewById(R.id.image);
        start = (Button) findViewById(R.id.start);
        stop = (Button) findViewById(R.id.stop);

        start.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                // 进行 360 度的旋转
                startRotation(0, 360);
            }
        });

        stop.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                image.clearAnimation();
            }
        });
    }

    private void startRotation(float start, float end) {
        // 计算中心点
        final float centerX = image.getWidth() / 2.0f;
        final float centerY = image.getHeight() / 2.0f;
        Log.d(TAG, "centerX=" + centerX + ", centerY=" + centerY);

        // 创建新的 3D 旋转动画
        // depthZ 为 0 表示无 Z 轴缩放,可调整为非零值以增强立体感
        rotation = new Rotate3dAnimation(start, end, centerX, centerY, 0f, true);
        rotation.setDuration(2000);
        rotation.setFillAfter(true);
        // 匀速旋转
        rotation.setInterpolator(new LinearInterpolator());
        
        // 设置监听器以实现循环播放
        startNext = new StartNextRotate();
        rotation.setAnimationListener(startNext);
        
        image.startAnimation(rotation);
    }

    private class StartNextRotate implements AnimationListener {
        @Override
        public void onAnimationEnd(Animation animation) {
            Log.d(TAG, "onAnimationEnd......");
            // 动画结束后重新开始,实现无限循环
            image.startAnimation(rotation);
        }

        @Override
        public void onAnimationRepeat(Animation animation) {
        }

        @Override
        public void onAnimationStart(Animation animation) {
        }
    }
}

3. 布局文件 (main.xml)

定义了包含两个按钮和一个图片的垂直线性布局。

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

    <Button
        android:id="@+id/start"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="开始" />

    <Button
        android:id="@+id/stop"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="结束" />

    <ImageView
        android:id="@+id/image"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:src="@drawable/t1" />

</LinearLayout>

原理详解

代码中使用 Camera 来实现动画。Camera 是一个虚拟摄像机,物体原地不动,我们带着摄像机按设定的角度进行移动,之后从 Camera 中取出完成该动画的 Matrix,然后绘制我们的物体。

关于坐标中心的处理

由于旋转默认是以 (0,0) 为中心的,而我们需要围绕图片的中心点旋转。因此需要执行以下两步矩阵操作:

  1. matrix.preTranslate(-centerX, -centerY); 将坐标系原点平移到图片中心,使旋转中心与 (0,0) 对齐。
  2. matrix.postTranslate(centerX, centerY); 旋转完成后,将图片移回原位。

这样看到的动画效果就是图片围绕其界面中心绕 Y 轴旋转。

修改旋转轴心

你可以尝试修改上述代码中的平移参数来观察不同效果。例如,仅沿 X 轴对齐:

matrix.preTranslate(-centerX, 0);
matrix.postTranslate(centerX, 0);

这将导致图片围绕水平中心线旋转,而非几何中心。

注意事项与现代替代方案

  1. API 兼容性:Rotate3dAnimation 属于较早期的动画框架(View Animation)。在 Android 3.0 (API 11) 及以上版本中,虽然仍可用,但性能不如属性动画(Property Animation)。
  2. 硬件加速:确保在 AndroidManifest.xml 或 Application 中开启了硬件加速 (android:hardwareAccelerated="true"),否则 3D 动画可能无法正确渲染。
  3. 现代替代:对于新开发项目,推荐使用 ObjectAnimator 配合 setRotationX/Y/Z 方法,或者使用 ValueAnimator 手动更新 View 的 transform 属性,以获得更好的性能和更灵活的交互。
  4. 内存管理:在 onDestroy 中应清除正在运行的动画,防止内存泄漏。

通过以上步骤,即可在 Android 应用中实现流畅的 3D 旋转动画效果。

目录

  1. Android 使用 Rotate3dAnimation 实现 3D 旋转动画效果
  2. 核心代码实现
  3. 1. 自定义 3D 旋转动画类 (Rotate3dAnimation.java)
  4. 2. 活动逻辑控制 (Test3DRotateActivity.java)
  5. 3. 布局文件 (main.xml)
  6. 原理详解
  7. 关于坐标中心的处理
  8. 修改旋转轴心
  9. 注意事项与现代替代方案

更多推荐文章

查看全部
  • GLM-4.6V-Flash-WEB:单卡运行与双环境部署实践
  • Hello-Algo 本地部署及 cpolar 公网访问教程
  • 高校 AIGC 检测新规解读:AI 率合格标准与应对策略
  • AIGC 镜头控制教程:Next Scene Qwen Image LoRA 实现视角变换
  • Python 数据分析与可视化实战指南
  • MySQL 事务与隔离级别深度解析:ACID、MVCC 与间隙锁实战
  • 使用 Trae IDE 与 MCP Server - Figma AI Bridge 将 Figma 转为前端代码
  • VS Code + WSL 下 GitHub 访问不稳定及 Copilot 卡死解决方案
  • 2026 年 AI 论文写作工具盘点与实操流程
  • Python 文件操作:open() 函数详解
  • 基于 Trae 插件 Builder 模式开发端午包粽子小游戏
  • Clawdbot(Moltbot)源码部署实战:从环境搭建到 WebChat 验证
  • VS Code Copilot 接入第三方 OpenAI 兼容模型实战
  • Spring AI 深入解析 MCP 协议、开发部署与安全最佳实践
  • 使用 FlatLaf 打造现代化 Java Swing 界面指南
  • MySQL 联合查询详解:JOIN 类型与多表关联实战
  • OpenAI 与 LangChain 集成实战使用详解
  • GitHub Copilot 超级定制化 AI 编程助手工具集
  • TurboQuant 与 RWKV-6:大模型部署的两条降本路线
  • GitHub 开源风潮:“蒸馏 Skill”复刻数字分身,是技术还是隐私边界?

相关免费在线工具

  • Keycode 信息

    查找任何按下的键的javascript键代码、代码、位置和修饰符。 在线工具,Keycode 信息在线工具,online

  • Escape 与 Native 编解码

    JavaScript 字符串转义/反转义;Java 风格 \uXXXX(Native2Ascii)编码与解码。 在线工具,Escape 与 Native 编解码在线工具,online

  • JavaScript / HTML 格式化

    使用 Prettier 在浏览器内格式化 JavaScript 或 HTML 片段。 在线工具,JavaScript / HTML 格式化在线工具,online

  • JavaScript 压缩与混淆

    Terser 压缩、变量名混淆,或 javascript-obfuscator 高强度混淆(体积会增大)。 在线工具,JavaScript 压缩与混淆在线工具,online

  • Base64 字符串编码/解码

    将字符串编码和解码为其 Base64 格式表示形式即可。 在线工具,Base64 字符串编码/解码在线工具,online

  • Base64 文件转换器

    将字符串、文件或图像转换为其 Base64 表示形式。 在线工具,Base64 文件转换器在线工具,online