add setBoneTransform method
This commit is contained in:
@@ -1,3 +1,3 @@
|
|||||||
version https://git-lfs.github.com/spec/v1
|
version https://git-lfs.github.com/spec/v1
|
||||||
oid sha256:9cd37bd5152ca0d7bde93663e188a537b2ac2bad58eaf69fbac00d9bc2da9f43
|
oid sha256:1a28d8328f7881c6bfc57d18c55b5f347058e9c3a8ff69202e528eecb4728ac0
|
||||||
size 93896
|
size 100960
|
||||||
|
|||||||
@@ -1,3 +1,3 @@
|
|||||||
version https://git-lfs.github.com/spec/v1
|
version https://git-lfs.github.com/spec/v1
|
||||||
oid sha256:3fa9367e8955a1e47e704e56f267854019f0135199a06d8e25f62cec503d67d6
|
oid sha256:b728c8fe0ce9eb06290dc37034404a952df8ea360b014b76c82fe8b9d695e85a
|
||||||
size 136160
|
size 113124
|
||||||
|
|||||||
@@ -1,3 +1,3 @@
|
|||||||
version https://git-lfs.github.com/spec/v1
|
version https://git-lfs.github.com/spec/v1
|
||||||
oid sha256:cf4bf82fd77a54fd6573cded79d1d4db0d0e000c4200c0eadee9ce29425449de
|
oid sha256:ab3dc6ca4dcfcd660b3a4dce20347ad1154844fe95fc7b47781288a22b0cd75b
|
||||||
size 32690
|
size 32437
|
||||||
|
|||||||
@@ -93,8 +93,12 @@ class ExampleWidgetState extends State<ExampleWidget> {
|
|||||||
await _filamentController!.createViewer();
|
await _filamentController!.createViewer();
|
||||||
await _filamentController!
|
await _filamentController!
|
||||||
.loadSkybox("assets/default_env/default_env_skybox.ktx");
|
.loadSkybox("assets/default_env/default_env_skybox.ktx");
|
||||||
|
|
||||||
await _filamentController!.setRendering(true);
|
await _filamentController!.setRendering(true);
|
||||||
await _filamentController!.loadGlb("assets/shapes/shapes.glb");
|
shapes =
|
||||||
|
await _filamentController!.loadGlb("assets/shapes/shapes.glb");
|
||||||
|
hasSkybox = true;
|
||||||
|
rendering = true;
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -55,6 +55,17 @@ class _AssetSubmenuState extends State<AssetSubmenu> {
|
|||||||
.transformToUnitCube(ExampleWidgetState.shapes!);
|
.transformToUnitCube(ExampleWidgetState.shapes!);
|
||||||
},
|
},
|
||||||
child: const Text('Transform to unit cube')),
|
child: const Text('Transform to unit cube')),
|
||||||
|
MenuItemButton(
|
||||||
|
onPressed: ExampleWidgetState.shapes == null
|
||||||
|
? null
|
||||||
|
: () async {
|
||||||
|
await widget.controller.setBoneTransform(
|
||||||
|
ExampleWidgetState.shapes!,
|
||||||
|
"Cylinder",
|
||||||
|
0,
|
||||||
|
Matrix4.rotationX(pi / 2));
|
||||||
|
},
|
||||||
|
child: const Text('Set bone tranform to identity for Cylinder')),
|
||||||
MenuItemButton(
|
MenuItemButton(
|
||||||
onPressed: () async {
|
onPressed: () async {
|
||||||
var names = await widget.controller
|
var names = await widget.controller
|
||||||
|
|||||||
@@ -73,6 +73,8 @@ namespace polyvox {
|
|||||||
bool hide(EntityId entity, const char* meshName);
|
bool hide(EntityId entity, const char* meshName);
|
||||||
bool reveal(EntityId entity, const char* meshName);
|
bool reveal(EntityId entity, const char* meshName);
|
||||||
const char* getNameForEntity(EntityId entityId);
|
const char* getNameForEntity(EntityId entityId);
|
||||||
|
|
||||||
|
bool setBoneTransform(EntityId entityId, const char* entityName, int skinIndex, int boneIndex, math::mat4f transform);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
AssetLoader* _assetLoader = nullptr;
|
AssetLoader* _assetLoader = nullptr;
|
||||||
@@ -96,9 +98,7 @@ namespace polyvox {
|
|||||||
|
|
||||||
inline void updateTransform(SceneAsset& asset);
|
inline void updateTransform(SceneAsset& asset);
|
||||||
|
|
||||||
inline void setBoneTransform(SceneAsset& asset, int frameNumber);
|
inline void setBoneTransformFromAnimation(SceneAsset& asset, int frameNumber);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -125,6 +125,13 @@ FLUTTER_PLUGIN_EXPORT void set_bone_animation(
|
|||||||
const char** const meshName,
|
const char** const meshName,
|
||||||
int numMeshTargets,
|
int numMeshTargets,
|
||||||
float frameLengthInMs);
|
float frameLengthInMs);
|
||||||
|
FLUTTER_PLUGIN_EXPORT bool set_bone_transform(
|
||||||
|
void* assetManager,
|
||||||
|
EntityId asset,
|
||||||
|
const char* entityName,
|
||||||
|
const float* const transform,
|
||||||
|
int boneIndex
|
||||||
|
);
|
||||||
FLUTTER_PLUGIN_EXPORT void play_animation(void* assetManager, EntityId asset, int index, bool loop, bool reverse, bool replaceActive, float crossfade);
|
FLUTTER_PLUGIN_EXPORT void play_animation(void* assetManager, EntityId asset, int index, bool loop, bool reverse, bool replaceActive, float crossfade);
|
||||||
FLUTTER_PLUGIN_EXPORT void set_animation_frame(void* assetManager, EntityId asset, int animationIndex, int animationFrame);
|
FLUTTER_PLUGIN_EXPORT void set_animation_frame(void* assetManager, EntityId asset, int animationIndex, int animationFrame);
|
||||||
FLUTTER_PLUGIN_EXPORT void stop_animation(void* assetManager, EntityId asset, int index);
|
FLUTTER_PLUGIN_EXPORT void stop_animation(void* assetManager, EntityId asset, int index);
|
||||||
|
|||||||
@@ -318,7 +318,7 @@ void AssetManager::updateAnimations() {
|
|||||||
if(anim.mReverse) {
|
if(anim.mReverse) {
|
||||||
frameNumber = lengthInFrames - frameNumber;
|
frameNumber = lengthInFrames - frameNumber;
|
||||||
}
|
}
|
||||||
setBoneTransform(
|
setBoneTransformFromAnimation(
|
||||||
asset,
|
asset,
|
||||||
frameNumber
|
frameNumber
|
||||||
);
|
);
|
||||||
@@ -343,7 +343,73 @@ void AssetManager::updateAnimations() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void AssetManager::setBoneTransform(SceneAsset& asset, int frameNumber) {
|
bool AssetManager::setBoneTransform(EntityId entityId, const char* entityName, int32_t skinIndex, int32_t boneIndex, math::mat4f localTransform) {
|
||||||
|
|
||||||
|
Log("Setting transform for bone %d/skin %d for mesh target %s", boneIndex, skinIndex, entityName);
|
||||||
|
|
||||||
|
const auto& pos = _entityIdLookup.find(entityId);
|
||||||
|
if(pos == _entityIdLookup.end()) {
|
||||||
|
Log("Couldn't find asset under specified entity id.");
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
SceneAsset& sceneAsset = _assets[pos->second];
|
||||||
|
|
||||||
|
const auto& entity = findEntityByName(sceneAsset, entityName);
|
||||||
|
|
||||||
|
RenderableManager& rm = _engine->getRenderableManager();
|
||||||
|
|
||||||
|
const auto& renderableInstance = rm.getInstance(entity);
|
||||||
|
|
||||||
|
TransformManager &transformManager = _engine->getTransformManager();
|
||||||
|
|
||||||
|
const auto& filamentInstance = sceneAsset.mAsset->getInstance();
|
||||||
|
utils::Entity joint = filamentInstance->getJointsAt(skinIndex)[boneIndex];
|
||||||
|
|
||||||
|
if(joint.isNull()) {
|
||||||
|
Log("ERROR : joint not found");
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
rm.setBones(
|
||||||
|
renderableInstance,
|
||||||
|
&localTransform,
|
||||||
|
1,
|
||||||
|
boneIndex
|
||||||
|
);
|
||||||
|
|
||||||
|
return true;
|
||||||
|
|
||||||
|
// auto& inverseBindMatrix = filamentInstance->getInverseBindMatricesAt(skinIndex)[boneIndex];
|
||||||
|
|
||||||
|
// auto jointInstance = transformManager.getInstance(joint);
|
||||||
|
|
||||||
|
// auto globalJointTransform = transformManager.getWorldTransform(jointInstance);
|
||||||
|
|
||||||
|
// transformManager.setTransform(jointInstance, xform * localTransform);
|
||||||
|
|
||||||
|
// auto inverseGlobalTransform = inverse(
|
||||||
|
// transformManager.getWorldTransform(
|
||||||
|
// transformManager.getInstance(target)
|
||||||
|
// )
|
||||||
|
// );
|
||||||
|
|
||||||
|
// auto boneTransform = inverseGlobalTransform * globalJointTransform * localTransform * inverseBindMatrix;
|
||||||
|
// auto renderable = rm.getInstance(target);
|
||||||
|
|
||||||
|
// 1.0f, 0.0f, 0.0f, 0.0f,
|
||||||
|
// 0.0f, 0.0f, 1.0f, 0.0f,
|
||||||
|
// 0.0f, -1.0f, 0.0f, 0.0f,
|
||||||
|
// 0.0f, 0.0f, 0.0f, 1.0f
|
||||||
|
// };
|
||||||
|
// Log("TRANSFORM");
|
||||||
|
// Log("%f %f %f %f", localTransform[0][0], localTransform[1][0], localTransform[2][0], localTransform[3][0] ) ;
|
||||||
|
// Log("%f %f %f %f", localTransform[0][1], localTransform[1][1], localTransform[2][1], localTransform[3][1] ) ;
|
||||||
|
// Log("%f %f %f %f", localTransform[0][2], localTransform[1][2], localTransform[2][2], localTransform[3][2] ) ;
|
||||||
|
// Log("%f %f %f %f", localTransform[0][3], localTransform[1][3], localTransform[2][3], localTransform[3][3] ) ;
|
||||||
|
// }
|
||||||
|
}
|
||||||
|
|
||||||
|
void AssetManager::setBoneTransformFromAnimation(SceneAsset& asset, int frameNumber) {
|
||||||
|
|
||||||
RenderableManager& rm = _engine->getRenderableManager();
|
RenderableManager& rm = _engine->getRenderableManager();
|
||||||
|
|
||||||
@@ -969,39 +1035,3 @@ const char* AssetManager::getNameForEntity(EntityId entityId) {
|
|||||||
|
|
||||||
} // namespace polyvox
|
} // namespace polyvox
|
||||||
|
|
||||||
|
|
||||||
// auto& inverseBindMatrix = filamentInstance->getInverseBindMatricesAt(skinIndex)[mBoneIndex];
|
|
||||||
|
|
||||||
// auto globalJointTransform = transformManager.getWorldTransform(jointInstance);
|
|
||||||
|
|
||||||
// for(auto& target : asset.mBoneAnimationBuffer.mMeshTargets) {
|
|
||||||
|
|
||||||
// auto inverseGlobalTransform = inverse(
|
|
||||||
// transformManager.getWorldTransform(
|
|
||||||
// transformManager.getInstance(target)
|
|
||||||
// )
|
|
||||||
// );
|
|
||||||
|
|
||||||
// auto boneTransform = inverseGlobalTransform * globalJointTransform * localTransform * inverseBindMatrix;
|
|
||||||
// auto renderable = rm.getInstance(target);
|
|
||||||
// rm.setBones(
|
|
||||||
// renderable,
|
|
||||||
// &boneTransform,
|
|
||||||
// 1,
|
|
||||||
// mBoneIndex
|
|
||||||
// );
|
|
||||||
// }
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
// 1.0f, 0.0f, 0.0f, 0.0f,
|
|
||||||
// 0.0f, 0.0f, 1.0f, 0.0f,
|
|
||||||
// 0.0f, -1.0f, 0.0f, 0.0f,
|
|
||||||
// 0.0f, 0.0f, 0.0f, 1.0f
|
|
||||||
// };
|
|
||||||
// Log("TRANSFORM");
|
|
||||||
// Log("%f %f %f %f", localTransform[0][0], localTransform[1][0], localTransform[2][0], localTransform[3][0] ) ;
|
|
||||||
// Log("%f %f %f %f", localTransform[0][1], localTransform[1][1], localTransform[2][1], localTransform[3][1] ) ;
|
|
||||||
// Log("%f %f %f %f", localTransform[0][2], localTransform[1][2], localTransform[2][2], localTransform[3][2] ) ;
|
|
||||||
// Log("%f %f %f %f", localTransform[0][3], localTransform[1][3], localTransform[2][3], localTransform[3][3] ) ;
|
|
||||||
// transformManager.getTransform(jointInstance);
|
|
||||||
|
|||||||
@@ -148,7 +148,7 @@ extern "C"
|
|||||||
return array;
|
return array;
|
||||||
}
|
}
|
||||||
|
|
||||||
void set_camera_projection_matrix(const void *const viewer, const double* const matrix, double near, double far)
|
void set_camera_projection_matrix(const void *const viewer, const double *const matrix, double near, double far)
|
||||||
{
|
{
|
||||||
((FilamentViewer *)viewer)->setCameraProjectionMatrix(matrix, near, far);
|
((FilamentViewer *)viewer)->setCameraProjectionMatrix(matrix, near, far);
|
||||||
}
|
}
|
||||||
@@ -157,19 +157,20 @@ extern "C"
|
|||||||
{
|
{
|
||||||
((FilamentViewer *)viewer)->setCameraCulling(near, far);
|
((FilamentViewer *)viewer)->setCameraCulling(near, far);
|
||||||
}
|
}
|
||||||
|
|
||||||
const double *const get_camera_frustum(const void *const viewer)
|
const double *const get_camera_frustum(const void *const viewer)
|
||||||
{
|
{
|
||||||
const auto frustum = ((FilamentViewer *)viewer)->getCameraFrustum();
|
const auto frustum = ((FilamentViewer *)viewer)->getCameraFrustum();
|
||||||
const math::float4* planes = frustum.getNormalizedPlanes();
|
const math::float4 *planes = frustum.getNormalizedPlanes();
|
||||||
double *array = (double *)calloc(24, sizeof(double));
|
double *array = (double *)calloc(24, sizeof(double));
|
||||||
for(int i =0; i < 6; i++) {
|
for (int i = 0; i < 6; i++)
|
||||||
array[i*4] = planes[i].x;
|
{
|
||||||
array[i*4+1] = planes[i].y;
|
array[i * 4] = planes[i].x;
|
||||||
array[i*4+2] = planes[i].z;
|
array[i * 4 + 1] = planes[i].y;
|
||||||
array[i*4+3] = planes[i].w;
|
array[i * 4 + 2] = planes[i].z;
|
||||||
|
array[i * 4 + 3] = planes[i].w;
|
||||||
}
|
}
|
||||||
|
|
||||||
return array;
|
return array;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -339,6 +340,32 @@ extern "C"
|
|||||||
((FilamentViewer *)viewer)->setPostProcessing(enabled);
|
((FilamentViewer *)viewer)->setPostProcessing(enabled);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
FLUTTER_PLUGIN_EXPORT bool set_bone_transform(
|
||||||
|
void *assetManager,
|
||||||
|
EntityId entityId,
|
||||||
|
const char *entityName,
|
||||||
|
const float *const transform,
|
||||||
|
int boneIndex)
|
||||||
|
{
|
||||||
|
|
||||||
|
auto matrix = math::mat4f(
|
||||||
|
transform[0], transform[1], transform[2],
|
||||||
|
transform[3],
|
||||||
|
transform[4],
|
||||||
|
transform[5],
|
||||||
|
transform[6],
|
||||||
|
transform[7],
|
||||||
|
transform[8],
|
||||||
|
transform[9],
|
||||||
|
transform[10],
|
||||||
|
transform[11],
|
||||||
|
transform[12],
|
||||||
|
transform[13],
|
||||||
|
transform[14],
|
||||||
|
transform[15]);
|
||||||
|
return ((AssetManager *)assetManager)->setBoneTransform(entityId, entityName, 0, boneIndex, matrix);
|
||||||
|
}
|
||||||
|
|
||||||
// void set_bone_transform(
|
// void set_bone_transform(
|
||||||
// EntityId asset,
|
// EntityId asset,
|
||||||
// const char* boneName,
|
// const char* boneName,
|
||||||
@@ -489,10 +516,8 @@ extern "C"
|
|||||||
Log("Dummy called");
|
Log("Dummy called");
|
||||||
}
|
}
|
||||||
|
|
||||||
FLUTTER_PLUGIN_EXPORT void flutter_filament_free(void* ptr)
|
FLUTTER_PLUGIN_EXPORT void flutter_filament_free(void *ptr)
|
||||||
{
|
{
|
||||||
free(ptr);
|
free(ptr);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -279,6 +279,12 @@ abstract class FilamentController {
|
|||||||
///
|
///
|
||||||
Future setBoneAnimation(FilamentEntity entity, BoneAnimationData animation);
|
Future setBoneAnimation(FilamentEntity entity, BoneAnimationData animation);
|
||||||
|
|
||||||
|
///
|
||||||
|
/// Sets the local joint transform for the bone at the given index in [entity] for the mesh under [meshName].
|
||||||
|
///
|
||||||
|
Future setBoneTransform(
|
||||||
|
FilamentEntity entity, String meshName, int boneIndex, Matrix4 data);
|
||||||
|
|
||||||
///
|
///
|
||||||
/// Removes/destroys the specified entity from the scene.
|
/// Removes/destroys the specified entity from the scene.
|
||||||
/// [entity] will no longer be a valid handle after this method is called; ensure you immediately discard all references once this method is complete.
|
/// [entity] will no longer be a valid handle after this method is called; ensure you immediately discard all references once this method is complete.
|
||||||
|
|||||||
@@ -1160,4 +1160,18 @@ class FilamentControllerFFI extends FilamentController {
|
|||||||
|
|
||||||
return frustum;
|
return frustum;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@override
|
||||||
|
Future setBoneTransform(FilamentEntity entity, String meshName, int boneIndex,
|
||||||
|
Matrix4 data) async {
|
||||||
|
var ptr = calloc<Float>(16);
|
||||||
|
for (int i = 0; i < 16; i++) {
|
||||||
|
ptr.elementAt(i).value = data.storage[i];
|
||||||
|
}
|
||||||
|
|
||||||
|
set_bone_transform(_assetManager!, entity,
|
||||||
|
meshName.toNativeUtf8().cast<Char>(), ptr, boneIndex);
|
||||||
|
|
||||||
|
calloc.free(ptr);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -388,6 +388,18 @@ external void set_bone_animation(
|
|||||||
double frameLengthInMs,
|
double frameLengthInMs,
|
||||||
);
|
);
|
||||||
|
|
||||||
|
@ffi.Native<
|
||||||
|
ffi.Bool Function(ffi.Pointer<ffi.Void>, EntityId,
|
||||||
|
ffi.Pointer<ffi.Char>, ffi.Pointer<ffi.Float>, ffi.Int)>(
|
||||||
|
symbol: 'set_bone_transform', assetId: 'flutter_filament_plugin')
|
||||||
|
external bool set_bone_transform(
|
||||||
|
ffi.Pointer<ffi.Void> assetManager,
|
||||||
|
int asset,
|
||||||
|
ffi.Pointer<ffi.Char> entityName,
|
||||||
|
ffi.Pointer<ffi.Float> transform,
|
||||||
|
int boneIndex,
|
||||||
|
);
|
||||||
|
|
||||||
@ffi.Native<
|
@ffi.Native<
|
||||||
ffi.Void Function(ffi.Pointer<ffi.Void>, EntityId, ffi.Int, ffi.Bool,
|
ffi.Void Function(ffi.Pointer<ffi.Void>, EntityId, ffi.Int, ffi.Bool,
|
||||||
ffi.Bool, ffi.Bool, ffi.Float)>(
|
ffi.Bool, ffi.Bool, ffi.Float)>(
|
||||||
|
|||||||
@@ -139,18 +139,18 @@ class _SizedFilamentWidgetState extends State<_SizedFilamentWidget> {
|
|||||||
);
|
);
|
||||||
|
|
||||||
WidgetsBinding.instance.addPostFrameCallback((timeStamp) async {
|
WidgetsBinding.instance.addPostFrameCallback((timeStamp) async {
|
||||||
try {
|
try {
|
||||||
widget.controller.setDimensions(_rect, MediaQuery.of(context).devicePixelRatio);
|
widget.controller
|
||||||
|
.setDimensions(_rect, MediaQuery.of(context).devicePixelRatio);
|
||||||
} catch (err) {
|
} catch (err) {
|
||||||
dev.log("Fatal error : $err");
|
dev.log("Fatal error : $err");
|
||||||
_error = err.toString();
|
_error = err.toString();
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
super.initState();
|
super.initState();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
Timer? _resizeTimer;
|
Timer? _resizeTimer;
|
||||||
bool _resizing = false;
|
bool _resizing = false;
|
||||||
|
|
||||||
@@ -162,26 +162,29 @@ class _SizedFilamentWidgetState extends State<_SizedFilamentWidget> {
|
|||||||
// any subsequent widget resizes will cancel the timer and replace with a new one.
|
// any subsequent widget resizes will cancel the timer and replace with a new one.
|
||||||
// debug mode does need a longer timeout.
|
// debug mode does need a longer timeout.
|
||||||
_resizeTimer?.cancel();
|
_resizeTimer?.cancel();
|
||||||
_resizeTimer = Timer(Duration(milliseconds: (kReleaseMode || Platform.isWindows) ? 10 : 100), () async {
|
await widget.controller
|
||||||
|
.setDimensions(_rect, MediaQuery.of(context).devicePixelRatio);
|
||||||
|
_resizeTimer = Timer(
|
||||||
|
Duration(milliseconds: (kReleaseMode || Platform.isWindows) ? 10 : 100),
|
||||||
|
() async {
|
||||||
try {
|
try {
|
||||||
|
while (_resizing) {
|
||||||
while(_resizing) {
|
|
||||||
await Future.delayed(const Duration(milliseconds: 20));
|
await Future.delayed(const Duration(milliseconds: 20));
|
||||||
}
|
}
|
||||||
_resizing = true;
|
_resizing = true;
|
||||||
await widget.controller.setDimensions(_rect, MediaQuery.of(context).devicePixelRatio);
|
await widget.controller
|
||||||
|
.setDimensions(_rect, MediaQuery.of(context).devicePixelRatio);
|
||||||
await widget.controller.resize();
|
await widget.controller.resize();
|
||||||
_resizeTimer = null;
|
_resizeTimer = null;
|
||||||
setState(() {});
|
setState(() {});
|
||||||
} catch (err) {
|
} catch (err) {
|
||||||
dev.log("Error resizing FilamentWidget: $err");
|
dev.log("Error resizing FilamentWidget: $err");
|
||||||
} finally {
|
} finally {
|
||||||
_resizing = false;
|
_resizing = false;
|
||||||
completer.complete();
|
completer.complete();
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
return completer.future;
|
return completer.future;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@override
|
@override
|
||||||
|
|||||||
Reference in New Issue
Block a user