return View when picking, use uint32_t for morphIndices

This commit is contained in:
Nick Fisher
2024-10-10 08:42:16 +08:00
parent f7da303d29
commit 5087cc48f5
7 changed files with 88 additions and 114 deletions

View File

@@ -16,16 +16,6 @@ external ffi.Pointer<ffi.Void> make_resource_loader(
ffi.Pointer<ffi.Void> owner, ffi.Pointer<ffi.Void> owner,
); );
@ffi.Native<
ffi.Pointer<TViewer> Function(ffi.Pointer<ffi.Void>, ffi.Pointer<ffi.Void>,
ffi.Pointer<ffi.Void>, ffi.Pointer<ffi.Char>)>(isLeaf: true)
external ffi.Pointer<TViewer> Viewer_create(
ffi.Pointer<ffi.Void> context,
ffi.Pointer<ffi.Void> loader,
ffi.Pointer<ffi.Void> platform,
ffi.Pointer<ffi.Char> uberArchivePath,
);
@ffi.Native<ffi.Void Function(ffi.Pointer<TViewer>)>(isLeaf: true) @ffi.Native<ffi.Void Function(ffi.Pointer<TViewer>)>(isLeaf: true)
external void destroy_filament_viewer( external void destroy_filament_viewer(
ffi.Pointer<TViewer> viewer, ffi.Pointer<TViewer> viewer,
@@ -152,6 +142,28 @@ external void Viewer_setViewRenderable(
bool renderable, bool renderable,
); );
@ffi.Native<
ffi.Void Function(
ffi.Pointer<TViewer>,
ffi.Pointer<TView>,
ffi.Int,
ffi.Int,
ffi.Pointer<
ffi.NativeFunction<
ffi.Void Function(EntityId entityId, ffi.Int x, ffi.Int y,
ffi.Pointer<TView> tView)>>)>(isLeaf: true)
external void Viewer_pick(
ffi.Pointer<TViewer> viewer,
ffi.Pointer<TView> tView,
int x,
int y,
ffi.Pointer<
ffi.NativeFunction<
ffi.Void Function(EntityId entityId, ffi.Int x, ffi.Int y,
ffi.Pointer<TView> tView)>>
callback,
);
@ffi.Native<ffi.Pointer<TEngine> Function(ffi.Pointer<TViewer>)>(isLeaf: true) @ffi.Native<ffi.Pointer<TEngine> Function(ffi.Pointer<TViewer>)>(isLeaf: true)
external ffi.Pointer<TEngine> Viewer_getEngine( external ffi.Pointer<TEngine> Viewer_getEngine(
ffi.Pointer<TViewer> viewer, ffi.Pointer<TViewer> viewer,
@@ -398,25 +410,6 @@ external bool set_morph_target_weights(
int numWeights, int numWeights,
); );
@ffi.Native<
ffi.Bool Function(
ffi.Pointer<TSceneManager>,
EntityId,
ffi.Pointer<ffi.Float>,
ffi.Pointer<ffi.Int>,
ffi.Int,
ffi.Int,
ffi.Float)>(isLeaf: true)
external bool set_morph_animation(
ffi.Pointer<TSceneManager> sceneManager,
int entity,
ffi.Pointer<ffi.Float> morphData,
ffi.Pointer<ffi.Int> morphIndices,
int numMorphTargets,
int numFrames,
double frameLengthInMs,
);
@ffi.Native< @ffi.Native<
ffi.Pointer<TMaterialInstance> Function( ffi.Pointer<TMaterialInstance> Function(
ffi.Pointer<TSceneManager>, TMaterialKey)>(isLeaf: true) ffi.Pointer<TSceneManager>, TMaterialKey)>(isLeaf: true)
@@ -669,6 +662,25 @@ external int SceneManager_loadGlbFromBuffer(
int layer, int layer,
); );
@ffi.Native<
ffi.Bool Function(
ffi.Pointer<TSceneManager>,
EntityId,
ffi.Pointer<ffi.Float>,
ffi.Pointer<ffi.Uint32>,
ffi.Int,
ffi.Int,
ffi.Float)>(isLeaf: true)
external bool SceneManager_setMorphAnimation(
ffi.Pointer<TSceneManager> sceneManager,
int entity,
ffi.Pointer<ffi.Float> morphData,
ffi.Pointer<ffi.Uint32> morphIndices,
int numMorphTargets,
int numFrames,
double frameLengthInMs,
);
@ffi.Native<ffi.Bool Function(ffi.Pointer<TSceneManager>, EntityId)>( @ffi.Native<ffi.Bool Function(ffi.Pointer<TSceneManager>, EntityId)>(
isLeaf: true) isLeaf: true)
external bool update_bone_matrices( external bool update_bone_matrices(
@@ -841,27 +853,6 @@ external int reveal_mesh(
ffi.Pointer<ffi.Char> meshName, ffi.Pointer<ffi.Char> meshName,
); );
@ffi.Native<
ffi.Void Function(
ffi.Pointer<TViewer>,
ffi.Pointer<TView>,
ffi.Int,
ffi.Int,
ffi.Pointer<
ffi.NativeFunction<
ffi.Void Function(
EntityId entityId, ffi.Int x, ffi.Int y)>>)>(isLeaf: true)
external void filament_pick(
ffi.Pointer<TViewer> viewer,
ffi.Pointer<TView> tView,
int x,
int y,
ffi.Pointer<
ffi.NativeFunction<
ffi.Void Function(EntityId entityId, ffi.Int x, ffi.Int y)>>
callback,
);
@ffi.Native< @ffi.Native<
ffi.Pointer<ffi.Char> Function( ffi.Pointer<ffi.Char> Function(
ffi.Pointer<TSceneManager>, EntityId)>(isLeaf: true) ffi.Pointer<TSceneManager>, EntityId)>(isLeaf: true)
@@ -1430,7 +1421,7 @@ external void Viewer_requestFrameRenderThread(
external void View_setToneMappingRenderThread( external void View_setToneMappingRenderThread(
ffi.Pointer<TView> tView, ffi.Pointer<TView> tView,
ffi.Pointer<TEngine> tEngine, ffi.Pointer<TEngine> tEngine,
int arg2, int thermion,
); );
@ffi.Native<ffi.Void Function(ffi.Pointer<TView>, ffi.Double)>(isLeaf: true) @ffi.Native<ffi.Void Function(ffi.Pointer<TView>, ffi.Double)>(isLeaf: true)

View File

@@ -83,9 +83,9 @@ class ThermionViewerFFI extends ThermionViewer {
this._driver = driver ?? nullptr; this._driver = driver ?? nullptr;
this._sharedContext = sharedContext ?? nullptr; this._sharedContext = sharedContext ?? nullptr;
// _onPickResultCallable = _onPickResultCallable =
// NativeCallable<Void Function(EntityId entityId, Int x, Int y)>.listener( NativeCallable<Void Function(EntityId entityId, Int x, Int y, Pointer<TView> view)>.listener(
// _onPickResult); _onPickResult);
_initialize(); _initialize();
} }
@@ -523,8 +523,8 @@ class ThermionViewerFFI extends ThermionViewer {
throw Exception("Not yet implemented"); throw Exception("Not yet implemented");
} }
final pathPtr = path.toNativeUtf8(allocator: allocator).cast<Char>(); final pathPtr = path.toNativeUtf8(allocator: allocator).cast<Char>();
var entity = await withIntCallback((callback)=> load_glb_render_thread( var entity = await withIntCallback((callback) => load_glb_render_thread(
_sceneManager!, pathPtr, numInstances, keepData, callback)); _sceneManager!, pathPtr, numInstances, keepData, callback));
allocator.free(pathPtr); allocator.free(pathPtr);
if (entity == _FILAMENT_ASSET_ERROR) { if (entity == _FILAMENT_ASSET_ERROR) {
@@ -729,7 +729,7 @@ class ThermionViewerFFI extends ThermionViewer {
var meshEntity = meshEntities[i]; var meshEntity = meshEntities[i];
if (targetMeshNames?.contains(meshName) == false) { if (targetMeshNames?.contains(meshName) == false) {
_logger.info("Skipping $meshName, not contained in target"); // _logger.info("Skipping $meshName, not contained in target");
continue; continue;
} }
@@ -749,39 +749,24 @@ class ThermionViewerFFI extends ThermionViewer {
Child meshes: ${meshNames}"""); Child meshes: ${meshNames}""");
} }
var indices = var indices = Uint32List.fromList(
intersection.map((m) => meshMorphTargets.indexOf(m)).toList(); intersection.map((m) => meshMorphTargets.indexOf(m)).toList());
var frameData = animation.extract(morphTargets: intersection); // var frameData = animation.data;
var frameData = animation.subset(intersection);
assert(frameData.length == animation.numFrames * intersection.length); assert(
frameData.data.length == animation.numFrames * intersection.length);
var dataPtr = allocator<Float>(frameData.length); var result = SceneManager_setMorphAnimation(
// not currently working on WASM :( wasted a lot of time figuring that out as no error is thrown
// dataPtr
// .asTypedList(frameData.length)
// .setRange(0, frameData.length, frameData);
for (int i = 0; i < frameData.length; i++) {
dataPtr[i] = frameData[i];
}
final idxPtr = allocator<Int>(indices.length);
for (int i = 0; i < indices.length; i++) {
idxPtr[i] = indices[i];
}
var result = set_morph_animation(
_sceneManager!, _sceneManager!,
meshEntity, meshEntity,
dataPtr, frameData.data.address,
idxPtr, indices.address,
indices.length, indices.length,
animation.numFrames, animation.numFrames,
animation.frameLengthInMs); animation.frameLengthInMs);
allocator.free(dataPtr);
allocator.free(idxPtr);
if (!result) { if (!result) {
throw Exception("Failed to set morph animation data for ${meshName}"); throw Exception("Failed to set morph animation data for ${meshName}");
} }
@@ -1484,14 +1469,11 @@ class ThermionViewerFFI extends ThermionViewer {
final view = FFIView(viewPtr, _viewer!); final view = FFIView(viewPtr, _viewer!);
final viewport = await view.getViewport(); final viewport = await view.getViewport();
// _pickResultController.add(( _pickResultController
// entity: entityId, .add((entity: entityId, x: x.ceil(), y: (viewport.height - y).ceil()));
// x: (x / pixelRatio).toDouble(),
// y: (viewport.height - y) / pixelRatio
// ));
} }
late NativeCallable<Void Function(EntityId entityId, Int x, Int y)> late NativeCallable<Void Function(EntityId entityId, Int x, Int y, Pointer<TView> view)>
_onPickResultCallable; _onPickResultCallable;
/// ///
@@ -1499,11 +1481,11 @@ class ThermionViewerFFI extends ThermionViewer {
/// ///
@override @override
void pick(int x, int y) async { void pick(int x, int y) async {
// x = (x * pixelRatio).ceil(); final view = (await getViewAt(0)) as FFIView;
// y = (viewportDimensions.$2 - (y * pixelRatio)).ceil(); var viewport = await view.getViewport();
// final view = (await getViewAt(0)) as FFIView; y = (viewport.height - y).ceil();
// filament_pick( Viewer_pick(
// _viewer!, view.view, x, y, _onPickResultCallable.nativeFunction); _viewer!, view.view, x, y, _onPickResultCallable.nativeFunction);
} }
/// ///

View File

@@ -98,7 +98,7 @@ namespace thermion
void clearBackgroundImage(); void clearBackgroundImage();
void setBackgroundImagePosition(float x, float y, bool clamp, uint32_t width, uint32_t height); void setBackgroundImagePosition(float x, float y, bool clamp, uint32_t width, uint32_t height);
void pick(View *view, uint32_t x, uint32_t y, void (*callback)(EntityId entityId, int x, int y)); void pick(View *view, uint32_t x, uint32_t y, void (*callback)(EntityId entityId, int x, int y, View *view));
Engine* getEngine() { Engine* getEngine() {
return _engine; return _engine;
} }

View File

@@ -125,7 +125,7 @@ namespace thermion
bool setMorphAnimationBuffer( bool setMorphAnimationBuffer(
EntityId entityId, EntityId entityId,
const float *const morphData, const float *const morphData,
const int *const morphIndices, const uint32_t *const morphIndices,
int numMorphTargets, int numMorphTargets,
int numFrames, int numFrames,
float frameLengthInMs); float frameLengthInMs);

View File

@@ -85,6 +85,7 @@ extern "C"
EMSCRIPTEN_KEEPALIVE void Viewer_setMainCamera(TViewer *tViewer, TView *tView); EMSCRIPTEN_KEEPALIVE void Viewer_setMainCamera(TViewer *tViewer, TView *tView);
EMSCRIPTEN_KEEPALIVE TSwapChain* Viewer_getSwapChainAt(TViewer *tViewer, int index); EMSCRIPTEN_KEEPALIVE TSwapChain* Viewer_getSwapChainAt(TViewer *tViewer, int index);
EMSCRIPTEN_KEEPALIVE void Viewer_setViewRenderable(TViewer *viewer, TSwapChain *swapChain, TView* view, bool renderable); EMSCRIPTEN_KEEPALIVE void Viewer_setViewRenderable(TViewer *viewer, TSwapChain *swapChain, TView* view, bool renderable);
EMSCRIPTEN_KEEPALIVE void Viewer_pick(TViewer *viewer, TView* tView, int x, int y, void (*callback)(EntityId entityId, int x, int y, TView *tView));
// Engine // Engine
EMSCRIPTEN_KEEPALIVE TEngine *Viewer_getEngine(TViewer* viewer); EMSCRIPTEN_KEEPALIVE TEngine *Viewer_getEngine(TViewer* viewer);
@@ -146,14 +147,6 @@ extern "C"
EntityId entity, EntityId entity,
const float *const morphData, const float *const morphData,
int numWeights); int numWeights);
EMSCRIPTEN_KEEPALIVE bool set_morph_animation(
TSceneManager *sceneManager,
EntityId entity,
const float *const morphData,
const int *const morphIndices,
int numMorphTargets,
int numFrames,
float frameLengthInMs);
EMSCRIPTEN_KEEPALIVE TMaterialInstance *create_material_instance(TSceneManager *sceneManager, TMaterialKey materialConfig); EMSCRIPTEN_KEEPALIVE TMaterialInstance *create_material_instance(TSceneManager *sceneManager, TMaterialKey materialConfig);
EMSCRIPTEN_KEEPALIVE TMaterialInstance *create_unlit_material_instance(TSceneManager *sceneManager); EMSCRIPTEN_KEEPALIVE TMaterialInstance *create_unlit_material_instance(TSceneManager *sceneManager);
@@ -210,6 +203,14 @@ extern "C"
EMSCRIPTEN_KEEPALIVE void SceneManager_setVisibilityLayer(TSceneManager *tSceneManager, EntityId entity, int layer); EMSCRIPTEN_KEEPALIVE void SceneManager_setVisibilityLayer(TSceneManager *tSceneManager, EntityId entity, int layer);
EMSCRIPTEN_KEEPALIVE TScene* SceneManager_getScene(TSceneManager *tSceneManager); EMSCRIPTEN_KEEPALIVE TScene* SceneManager_getScene(TSceneManager *tSceneManager);
EMSCRIPTEN_KEEPALIVE EntityId SceneManager_loadGlbFromBuffer(TSceneManager *sceneManager, const uint8_t *const, size_t length, bool keepData, int priority, int layer); EMSCRIPTEN_KEEPALIVE EntityId SceneManager_loadGlbFromBuffer(TSceneManager *sceneManager, const uint8_t *const, size_t length, bool keepData, int priority, int layer);
EMSCRIPTEN_KEEPALIVE bool SceneManager_setMorphAnimation(
TSceneManager *sceneManager,
EntityId entity,
const float *const morphData,
const uint32_t *const morphIndices,
int numMorphTargets,
int numFrames,
float frameLengthInMs);
EMSCRIPTEN_KEEPALIVE bool update_bone_matrices(TSceneManager *sceneManager, EntityId entityId); EMSCRIPTEN_KEEPALIVE bool update_bone_matrices(TSceneManager *sceneManager, EntityId entityId);
@@ -239,7 +240,7 @@ extern "C"
EMSCRIPTEN_KEEPALIVE int hide_mesh(TSceneManager *sceneManager, EntityId entity, const char *meshName); EMSCRIPTEN_KEEPALIVE int hide_mesh(TSceneManager *sceneManager, EntityId entity, const char *meshName);
EMSCRIPTEN_KEEPALIVE int reveal_mesh(TSceneManager *sceneManager, EntityId entity, const char *meshName); EMSCRIPTEN_KEEPALIVE int reveal_mesh(TSceneManager *sceneManager, EntityId entity, const char *meshName);
EMSCRIPTEN_KEEPALIVE void filament_pick(TViewer *viewer, TView* tView, int x, int y, void (*callback)(EntityId entityId, int x, int y));
EMSCRIPTEN_KEEPALIVE const char *get_name_for_entity(TSceneManager *sceneManager, const EntityId entityId); EMSCRIPTEN_KEEPALIVE const char *get_name_for_entity(TSceneManager *sceneManager, const EntityId entityId);
EMSCRIPTEN_KEEPALIVE EntityId find_child_entity_by_name(TSceneManager *sceneManager, const EntityId parent, const char *name); EMSCRIPTEN_KEEPALIVE EntityId find_child_entity_by_name(TSceneManager *sceneManager, const EntityId parent, const char *name);
EMSCRIPTEN_KEEPALIVE int get_entity_count(TSceneManager *sceneManager, const EntityId target, bool renderableOnly); EMSCRIPTEN_KEEPALIVE int get_entity_count(TSceneManager *sceneManager, const EntityId target, bool renderableOnly);

View File

@@ -806,7 +806,7 @@ namespace thermion
bool SceneManager::setMorphAnimationBuffer( bool SceneManager::setMorphAnimationBuffer(
EntityId entityId, EntityId entityId,
const float *const morphData, const float *const morphData,
const int *const morphIndices, const uint32_t *const morphIndices,
int numMorphTargets, int numMorphTargets,
int numFrames, int numFrames,
float frameLengthInMs) float frameLengthInMs)

View File

@@ -50,6 +50,13 @@ extern "C"
viewer->destroyRenderTarget(renderTarget); viewer->destroyRenderTarget(renderTarget);
} }
EMSCRIPTEN_KEEPALIVE void Viewer_pick(TViewer *tViewer, TView* tView, int x, int y, void (*callback)(EntityId entityId, int x, int y, TView *tView))
{
auto *viewer = reinterpret_cast<FilamentViewer*>(tViewer);
auto *view = reinterpret_cast<View*>(tView);
((FilamentViewer *)viewer)->pick(view, static_cast<uint32_t>(x), static_cast<uint32_t>(y), reinterpret_cast<void (*)(EntityId entityId, int x, int y, View *view)>(callback));
}
EMSCRIPTEN_KEEPALIVE void destroy_filament_viewer(TViewer *viewer) EMSCRIPTEN_KEEPALIVE void destroy_filament_viewer(TViewer *viewer)
{ {
delete ((FilamentViewer *)viewer); delete ((FilamentViewer *)viewer);
@@ -446,11 +453,11 @@ extern "C"
return ((SceneManager *)sceneManager)->setMorphTargetWeights(asset, weights, numWeights); return ((SceneManager *)sceneManager)->setMorphTargetWeights(asset, weights, numWeights);
} }
EMSCRIPTEN_KEEPALIVE bool set_morph_animation( EMSCRIPTEN_KEEPALIVE bool SceneManager_setMorphAnimation(
TSceneManager *sceneManager, TSceneManager *sceneManager,
EntityId asset, EntityId asset,
const float *const morphData, const float *const morphData,
const int *const morphIndices, const uint32_t *const morphIndices,
int numMorphTargets, int numMorphTargets,
int numFrames, int numFrames,
float frameLengthInMs) float frameLengthInMs)
@@ -793,13 +800,6 @@ extern "C"
return ((SceneManager *)sceneManager)->reveal(asset, meshName); return ((SceneManager *)sceneManager)->reveal(asset, meshName);
} }
EMSCRIPTEN_KEEPALIVE void filament_pick(TViewer *tViewer, TView* tView, int x, int y, void (*callback)(EntityId entityId, int x, int y))
{
auto *viewer = reinterpret_cast<FilamentViewer*>(tViewer);
auto *view = reinterpret_cast<View*>(tView);
((FilamentViewer *)viewer)->pick(view, static_cast<uint32_t>(x), static_cast<uint32_t>(y), callback);
}
EMSCRIPTEN_KEEPALIVE const char *get_name_for_entity(TSceneManager *sceneManager, const EntityId entityId) EMSCRIPTEN_KEEPALIVE const char *get_name_for_entity(TSceneManager *sceneManager, const EntityId entityId)
{ {
return ((SceneManager *)sceneManager)->getNameForEntity(entityId); return ((SceneManager *)sceneManager)->getNameForEntity(entityId);