Flutter 3D场景构建插件playx_3d_scene的使用

发布于 1周前 作者 yuanlaile 来自 Flutter

Flutter 3D场景构建插件playx_3d_scene的使用

插件介绍

Playx 3D Scene 是一个用于在 Android 上基于 Google filament 渲染交互式 3D 模型的插件。它支持控制环境天空盒、光源、相机、地面等。

安装

pubspec.yaml 的的 dependencies: 部分添加以下行:

dependencies:  
  playx_3d_scene: ^0.1.0  

/android/app/build.gradle 中: 需要设置 minifyEnabledshrinkResourcesfalse,以阻止代码压缩和混淆。

android {
    ndkVersion "26.1.10909125"
}

使用示例

下面是一个基本示例,展示如何从 GLB 文件创建 3D 模型,并带有天空盒和间接照明。

import 'package:flutter/material.dart';
import 'package:playx_3d_scene/playx_3d_scene.dart';

void main() {
  runApp(const MyApp());
}

class MyApp extends StatefulWidget {
  const MyApp({super.key});

  [@override](/user/override)
  State<MyApp> createState() => _MyAppState();
}

class _MyAppState extends State<MyApp> {
  bool isModelLoading = false;
  bool isSceneLoading = false;
  bool isShapeLoading = false;
  late Playx3dSceneController controller;

  [@override](/user/override)
  void initState() {
    super.initState();
  }

  [@override](/user/override)
  Widget build(BuildContext context) {
    return MaterialApp(
      home: Scaffold(
        body: Stack(
          children: [
            Playx3dScene(
              model: GlbModel.asset(
                "assets/models/Fox.glb",
                animation: PlayxAnimation.byIndex(0, autoPlay: true),
                fallback: GlbModel.asset("assets/models/Fox.glb"),
                centerPosition: PlayxPosition(x: 0, y: 0, z: -4),
                scale: 1.0,
              ),
              scene: Scene(
                skybox: HdrSkybox.asset("assets/envs/courtyard.hdr"),
                indirectLight:
                    HdrIndirectLight.asset("assets/envs/courtyard.hdr"),
                light: Light(
                  type: LightType.directional,
                  colorTemperature: 6500,
                  intensity: 10000,
                  castShadows: false,
                  castLight: true,
                  position: PlayxPosition(x: -1, y: 0, z: 0),
                  direction: PlayxDirection(x: -1, y: -1, z: 0)),
                ground: Ground(
                  width: 4.0,
                  height: 4.0,
                  isBelowModel: true,
                  normal: PlayxDirection.y(1.0),
                  material: PlayxMaterial.asset(
                    "assets/materials/textured_pbr.filamat",
                    parameters: [
                      MaterialParameter.texture(
                        value: PlayxTexture.asset(
                          "assets/materials/texture/floor_basecolor.png",
                          type: TextureType.color,
                          sampler: PlayxTextureSampler(anisotropy: 8),
                        ),
                        name: "baseColor",
                      ),
                      MaterialParameter.texture(
                        value: PlayxTexture.asset(
                          "assets/materials/texture/floor_normal.png",
                          type: TextureType.normal,
                          sampler: PlayxTextureSampler(anisotropy: 8),
                        ),
                        name: "normal",
                      ),
                      MaterialParameter.texture(
                        value: PlayxTexture.asset(
                          "assets/materials/texture/floor_ao_roughness_metallic.png",
                          type: TextureType.data,
                          sampler: PlayxTextureSampler(anisotropy: 8),
                        ),
                        name: "aoRoughnessMetallic",
                      ),
                    ],
                  ),
                ),
                camera: Camera.orbit(
                  exposure: Exposure.formAperture(
                    aperture: 116.0,
                    shutterSpeed: 1 / 125,
                    sensitivity: 150,
                  ),
                  targetPosition: PlayxPosition(x: 0.0, y: 0.0, z: -4.0),
                  orbitHomePosition: PlayxPosition(x: 0.0, y: 11.0, z: 1.0),
                  upVector: PlayxPosition(x: 0.0, y: 11.0, z: 0.0),
                ),
              ),
              shapes: [
                Cube(
                  id: 11,
                  length: .5,
                  centerPosition: PlayxPosition(x: -11, y: 0, z: -4),
                  material: PlayxMaterial.asset(
                    "assets/materials/textured_pbr.filamat",
                    parameters: [
                      MaterialParameter.texture(
                        value: PlayxTexture.asset(
                          "assets/materials/texture/floor_basecolor.png",
                          type: TextureType.color,
                          sampler: PlayxTextureSampler(anisotropy: 8),
                        ),
                        name: "baseColor",
                      ),
                      MaterialParameter.texture(
                        value: PlayxTexture.asset(
                          "assets/materials/texture/floor_normal.png",
                          type: TextureType.normal,
                          sampler: PlayxTextureSampler(anisotropy: 8),
                        ),
                        name: "normal",
                      ),
                      MaterialParameter.texture(
                        value: PlayxTexture.asset(
                          "assets/materials/texture/floor_ao_roughness_metallic.png",
                          type: TextureType.data,
                          sampler: PlayxTextureSampler(anisotropy: 8),
                        ),
                        name: "aoRoughnessMetallic",
                      ),
                    ],
                  ),
                ),
                Sphere(
                  id: 2,
                  centerPosition: PlayxPosition(x: 1, y: 0, z: -4),
                  radius: .5,
                  material: PlayxMaterial.asset(
                    "assets/materials/textured_pbr.filamat",
                    parameters: [
                      MaterialParameter.texture(
                        value: PlayxTexture.asset(
                          "assets/materials/texture/floor_basecolor.png",
                          type: TextureType.color,
                          sampler: PlayxTextureSampler(anisotropy: 8),
                        ),
                        name: "baseColor",
                      ),
                      MaterialParameter.texture(
                        value: PlayxTexture.asset(
                          "assets/materials/texture/floor_normal.png",
                          type: TextureType.normal,
                          sampler: PlayxTextureSampler(anisotropy: 8),
                        ),
                        name: "normal",
                      ),
                      MaterialParameter.texture(
                        value: PlayxTexture.asset(
                          "assets/materials/texture/floor_ao_roughness_metallic.png",
                          type: TextureType.data,
                          sampler: PlayxTextureSampler(anisotropy: 8),
                        ),
                        name: "aoRoughnessMetallic",
                      ),
                    ],
                  ),
                )
              ],
              onCreated: (Playx3dSceneController controller) async {
                Future.delayed(const Duration(seconds: 5), () async {
                  Result<int?> result =
                      await controller.changeAnimationByIndex(1);

                  if (result.isSuccess()) {
                    final data = result.data;
                    print("success :$data");
                  } else {
                    print(result.message);
                  }
                });
              },
              onModelStateChanged: (state) {
                print('Playx3dSceneController: onModelStateChanged: $state');
                setState(() {
                  isModelLoading = state == ModelState.loading;
                });
              },
              onSceneStateChanged: (state) {
                print('Playx3dSceneController: onSceneStateChanged: $state');
                setState(() {
                  isSceneLoading = state == SceneState.loading;
                });
              },
              onShapeStateChanged: (state) {
                print('Playx3dSceneController: onShapeStateChanged: $state');
                setState(() {
                  isShapeLoading = state == ShapeState.loading;
                });
              },
              eachRender: (frameTimeNano) {},
            ),
            isModelLoading || isSceneLoading || isShapeLoading
                ? const Center(
                    child: CircularProgressIndicator(
                      color: Colors.pink,
                    ),
                  )
                : Container(),
          ],
        ),
      ),
    );
  }
}

更多关于Flutter 3D场景构建插件playx_3d_scene的使用的实战系列教程也可以访问 https://www.itying.com/category-92-b0.html

1 回复

更多关于Flutter 3D场景构建插件playx_3d_scene的使用的实战系列教程也可以访问 https://www.itying.com/category-92-b0.html


当然,以下是如何在Flutter项目中使用playx_3d_scene插件来构建3D场景的一个基本示例。这个插件允许你在Flutter应用中嵌入3D内容。首先,确保你已经在pubspec.yaml文件中添加了playx_3d_scene依赖项:

dependencies:
  flutter:
    sdk: flutter
  playx_3d_scene: ^最新版本号  # 请替换为实际的最新版本号

然后运行flutter pub get来安装依赖。

以下是一个简单的Flutter应用示例,展示了如何使用playx_3d_scene插件来构建和显示一个基本的3D场景:

import 'package:flutter/material.dart';
import 'package:playx_3d_scene/playx_3d_scene.dart';

void main() {
  runApp(MyApp());
}

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      home: Scaffold(
        appBar: AppBar(
          title: Text('Flutter 3D Scene Example'),
        ),
        body: Center(
          child: Playx3DScene(
            // 初始化场景
            sceneBuilder: () {
              // 创建一个新的场景
              final scene = Scene3D();

              // 添加一个简单的立方体
              final cube = Cube3D()
                ..setSize(1.0, 1.0, 1.0)
                ..setPosition(0.0, 0.0, -5.0)
                ..setColor(Colors.blue);

              // 将立方体添加到场景中
              scene.addChild(cube);

              // 添加一个光源
              final light = Light3D()
                ..setType(LightType.directional)
                ..setDirection(0.0, 0.0, 1.0)
                ..setColor(Colors.white);

              // 将光源添加到场景中
              scene.addChild(light);

              // 返回构建好的场景
              return scene;
            },
          ),
        ),
      ),
    );
  }
}

// 自定义的3D场景类(如果需要更复杂的场景,可以在这里扩展)
class Scene3D extends Base3DObject {
  // 你可以在这里添加自定义的场景构建逻辑
}

// 自定义的立方体类(如果需要更复杂的对象,可以在这里扩展)
class Cube3D extends Base3DObject {
  // 你可以在这里添加自定义的立方体构建逻辑
}

// 自定义的光源类(如果需要更复杂的光源,可以在这里扩展)
class Light3D extends Base3DObject {
  // 你可以在这里添加自定义的光源构建逻辑
}

// 注意:由于playx_3d_scene的API可能有所变化,
// 上面的Cube3D, Light3D和Scene3D类仅为示例,
// 实际使用时需要参考playx_3d_scene的最新文档和API。
// 通常情况下,你可能不需要自己定义这些类,
// 而是直接使用插件提供的类和方法。

重要提示

  1. playx_3d_scene插件的具体API可能会有所不同,上面的代码中的Scene3D, Cube3D, Light3D等类仅为示例,实际上你可能需要使用插件提供的具体类和方法。

  2. 上面的示例代码假设playx_3d_scene插件支持直接创建和配置3D对象。然而,根据插件的实际API,你可能需要不同的方式来创建和配置这些对象。

  3. 请查阅playx_3d_scene插件的官方文档和示例代码,以获取最准确和最新的使用指南。

  4. 由于3D渲染通常比较消耗资源,确保在真实应用中进行性能优化,特别是在移动设备上。

  5. 如果插件没有提供你需要的3D对象或功能,你可能需要寻找其他3D引擎或插件,或者自己实现这些功能。

回到顶部