diff --git a/example/assets/background.ktx b/example/assets/background.ktx index 4f13ac3a..af9b04df 100644 Binary files a/example/assets/background.ktx and b/example/assets/background.ktx differ diff --git a/example/assets/background.png b/example/assets/background.png index 2ca89ebb..4e8e2737 100644 Binary files a/example/assets/background.png and b/example/assets/background.png differ diff --git a/example/assets/cube.glb b/example/assets/cube.glb index 78aa6102..e11031c8 100644 Binary files a/example/assets/cube.glb and b/example/assets/cube.glb differ diff --git a/ios/Classes/SwiftPolyvoxFilamentPlugin-Bridging-Header.h b/ios/Classes/SwiftPolyvoxFilamentPlugin-Bridging-Header.h deleted file mode 100644 index ce9a1d8f..00000000 --- a/ios/Classes/SwiftPolyvoxFilamentPlugin-Bridging-Header.h +++ /dev/null @@ -1 +0,0 @@ -#import "PolyvoxFilamentApi.h" \ No newline at end of file diff --git a/ios/Classes/SwiftPolyvoxFilamentPlugin.swift b/ios/Classes/SwiftPolyvoxFilamentPlugin.swift deleted file mode 100644 index 3135ebaf..00000000 --- a/ios/Classes/SwiftPolyvoxFilamentPlugin.swift +++ /dev/null @@ -1,295 +0,0 @@ -import Flutter -import UIKit -import OpenGLES.ES3 -import GLKit - - -public class SwiftPolyvoxFilamentPlugin: NSObject, FlutterPlugin, FlutterTexture { - - var registrar : FlutterPluginRegistrar - var textureId: Int64? - var registry: FlutterTextureRegistry - - var width: Double = 0 - var height: Double = 0 - - var context: EAGLContext?; - var targetPixelBuffer: CVPixelBuffer?; - var textureCache: CVOpenGLESTextureCache?; - var texture: CVOpenGLESTexture? = nil; - var frameBuffer: GLuint = 0; - - - var pixelBufferAttrs = [ - kCVPixelBufferPixelFormatTypeKey: NSNumber(value: kCVPixelFormatType_32BGRA), - kCVPixelBufferOpenGLCompatibilityKey: kCFBooleanTrue, - kCVPixelBufferOpenGLESCompatibilityKey: kCFBooleanTrue, - kCVPixelBufferIOSurfacePropertiesKey: [:] - ] as CFDictionary - - var resources:NSMutableDictionary = [:] - var viewer:UnsafeMutableRawPointer? = nil - - var displayLink:CADisplayLink? = nil - - static var messenger : FlutterBinaryMessenger? = nil; - - var loadResourcePtr: UnsafeMutableRawPointer? = nil - var freeResourcePtr: UnsafeMutableRawPointer? = nil - var resourcesPtr : UnsafeMutableRawPointer? = nil - - var loadResource : @convention(c) (UnsafeRawPointer, UnsafeMutableRawPointer) -> ResourceBuffer = { uri, resourcesPtr in - print("Loading resource buffer") - - let instance:SwiftPolyvoxFilamentPlugin = Unmanaged.fromOpaque(resourcesPtr).takeUnretainedValue() - - let uriString = String(cString:uri.assumingMemoryBound(to: UInt8.self)) - - let key = instance.registrar.lookupKey(forAsset:uriString) - - let path = Bundle.main.path(forResource: key, ofType:nil) - do { - let foo: String = path! - let data = try Data(contentsOf: URL(fileURLWithPath:foo)) - let resId = instance.resources.count - let nsData = data as NSData - instance.resources[resId] = nsData - let rawPtr = nsData.bytes - return ResourceBuffer(data:rawPtr, size:UInt32(nsData.count), id:UInt32(resId)) - } catch { - print("Error opening file: \(error)") - return ResourceBuffer() - } - return ResourceBuffer() - } - - var freeResource : @convention(c) (UInt32,UnsafeMutableRawPointer) -> () = { rid, resourcesPtr in - let instance:SwiftPolyvoxFilamentPlugin = Unmanaged.fromOpaque(resourcesPtr).takeUnretainedValue() - instance.resources.removeObject(forKey:rid) - } - - func createDisplayLink() { - displayLink = CADisplayLink(target: self, - selector: #selector(doRender)) - - displayLink!.add(to: .current, forMode: RunLoop.Mode.default) - } - - @objc func doRender() { - if(viewer != nil) { - render(viewer) - self.registry.textureFrameAvailable(self.textureId!) - } - } - - public func copyPixelBuffer() -> Unmanaged? { - if(targetPixelBuffer == nil) { - print("empty") - return nil; - } - return Unmanaged.passRetained(targetPixelBuffer!); - } - - - - public static func register(with registrar: FlutterPluginRegistrar) { - let _messenger = registrar.messenger(); - messenger = _messenger; - let channel = FlutterMethodChannel(name: "app.polyvox.filament/event", binaryMessenger: _messenger) - let instance = SwiftPolyvoxFilamentPlugin(textureRegistry: registrar.textures(), registrar:registrar) - registrar.addMethodCallDelegate(instance, channel: channel) - } - - init(textureRegistry: FlutterTextureRegistry, registrar:FlutterPluginRegistrar) { - self.registry = textureRegistry; - self.registrar = registrar - } - - private func createPixelBuffer(width:Int, height:Int) { - - if(targetPixelBuffer != nil) { - destroy_swap_chain(self.viewer) - } - if(CVPixelBufferCreate(kCFAllocatorDefault, Int(width), Int(height), - kCVPixelFormatType_32BGRA, pixelBufferAttrs, &targetPixelBuffer) != kCVReturnSuccess) { - print("Error allocating pixel buffer") - } - if(self.viewer != nil) { - create_swap_chain(self.viewer, unsafeBitCast(targetPixelBuffer!, to: UnsafeMutableRawPointer.self)) - update_viewport_and_camera_projection(self.viewer!, Int32(width), Int32(height), 1.0); - } - - print("Pixel buffer created") - } - - private func initialize(width:Int32, height:Int32) { - - createPixelBuffer(width:Int(width), height:Int(height)) - self.textureId = self.registry.register(self) - - loadResourcePtr = unsafeBitCast(loadResource, to: UnsafeMutableRawPointer.self) - freeResourcePtr = unsafeBitCast(freeResource, to: UnsafeMutableRawPointer.self) - - viewer = filament_viewer_new_ios( - unsafeBitCast(targetPixelBuffer!, to: UnsafeMutableRawPointer.self), - loadResourcePtr!, - freeResourcePtr!, - Unmanaged.passUnretained(self).toOpaque() - ) - - update_viewport_and_camera_projection(self.viewer!, Int32(width), Int32(height), 1.0); - - createDisplayLink() - - } - - public func handle(_ call: FlutterMethodCall, result: @escaping FlutterResult) { - let methodName = call.method; - - switch methodName { - case "initialize": - let args = call.arguments as! Array - initialize(width:args[0], height:args[1]) - result(self.textureId); - case "setBackgroundImage": - let uri = call.arguments as! String - set_background_image(self.viewer!, uri) - render(self.viewer!) - self.registry.textureFrameAvailable(self.textureId!) - result("OK") - case "resize": - let args = call.arguments as! Array - let width = Int(args[0]) - let height = Int(args[1]) - createPixelBuffer(width: width, height:height) - result("OK") - case "loadSkybox": - load_skybox(self.viewer!, call.arguments as! String) - result("OK"); - case "removeSkybox": - remove_skybox(self.viewer!) - result("OK"); - case "loadGlb": - let assetPtr = load_glb(self.viewer, call.arguments as! String) - result(unsafeBitCast(assetPtr, to:Int64.self)); - case "loadGltf": - let args = call.arguments as! Array - result(load_gltf(self.viewer, args[0] as! String, args[1] as! String)); - case "removeAsset": - let assetPtr = UnsafeMutableRawPointer.init(bitPattern: call.arguments as! Int) - remove_asset(viewer!, assetPtr) - result("OK") - case "clearAssets": - clear_assets(viewer!) - result("OK") - case "loadIbl": - load_ibl(self.viewer, call.arguments as! String) - result("OK"); - case "removeIbl": - remove_ibl(self.viewer) - result("OK"); - case "setCamera": - let args = call.arguments as! Array - let assetPtr = UnsafeMutableRawPointer.init(bitPattern: args[0] as! Int) - set_camera(self.viewer, assetPtr, args[1] as! String) - result("OK"); - case "playAnimation": - let args = call.arguments as! Array - let assetPtr = UnsafeMutableRawPointer.init(bitPattern: args[0] as! Int) - let animationIndex = args[1] as! Int32; - let loop = args[2] as! Bool; - play_animation(assetPtr, animationIndex, loop) - result("OK"); - case "stopAnimation": - let args = call.arguments as! Array - let assetPtr = UnsafeMutableRawPointer.init(bitPattern: args[0] as! Int) - let animationIndex = args[1] as! Int32 - stop_animation(assetPtr, animationIndex) // TODO - result("OK"); - case "getTargetNames": - let args = call.arguments as! Array - let assetPtr = UnsafeMutableRawPointer.init(bitPattern: args[0] as! Int) - let meshName = args[1] as! String - let numNames = get_target_name_count(assetPtr, meshName) - var names = [String]() - for i in 0...numNames - 1{ - let outPtr = UnsafeMutablePointer.allocate(capacity:256) - get_target_name(assetPtr, meshName, outPtr, i) - names.append(String(cString:outPtr)) - } - result(names); - case "getAnimationNames": - let assetPtr = UnsafeMutableRawPointer.init(bitPattern: call.arguments as! Int) - let numNames = get_animation_count(assetPtr) - var names = [String]() - for i in 0...numNames - 1{ - let outPtr = UnsafeMutablePointer.allocate(capacity:256) - get_animation_name(assetPtr, outPtr, i) - names.append(String(cString:outPtr)) - } - result(names); - case "applyWeights": - let args = call.arguments as! Array - let assetPtr = UnsafeMutableRawPointer.init(bitPattern: args[0] as! Int) - let weights = args[1] as! Array - weights.map { Float($0) }.withUnsafeBufferPointer { - apply_weights(assetPtr, UnsafeMutablePointer.init(mutating:$0.baseAddress), Int32(weights.count)) - - } - result("OK") - case "zoom": - let args = call.arguments as! Array - let assetPtr = UnsafeMutableRawPointer.init(bitPattern: args[0] as! Int) - let factor = args[1] as! Double - scroll(assetPtr, 0,0, Float(factor)) - result("OK") - case "animateWeights": - let args = call.arguments as! Array - let assetPtr = UnsafeMutableRawPointer.init(bitPattern: args[0] as! Int) - let frameData = args[1] as! Array - let numWeights = args[2] as! Int - let numFrames = args[3] as! Int - let frameLenInMs = args[4] as! Double - frameData.map { Float($0)}.withUnsafeBufferPointer { - animate_weights(assetPtr, UnsafeMutablePointer.init(mutating:$0.baseAddress), Int32(numWeights), Int32(numFrames), Float(frameLenInMs)) - } - result("OK") - case "panStart": - let args = call.arguments as! Array - grab_begin(self.viewer, args[0] as! Int32, args[1] as! Int32, true) - result("OK") - case "panUpdate": - let args = call.arguments as! Array - grab_update(self.viewer, args[0] as! Int32, args[1] as! Int32) - result("OK") - case "panEnd": - grab_end(self.viewer) - result("OK") - case "rotateStart": - let args = call.arguments as! Array - grab_begin(self.viewer, args[0] as! Int32, args[1] as! Int32, false) - result("OK") - case "rotateUpdate": - let args = call.arguments as! Array - grab_update(self.viewer, args[0] as! Int32, args[1] as! Int32) - result("OK") - case "rotateEnd": - grab_end(self.viewer) - result("OK") - case "setPosition": - let args = call.arguments as! Array - let assetPtr = UnsafeMutableRawPointer.init(bitPattern: args[0] as! Int) - let x = Float(args[1] as! Double) - set_position(assetPtr, x, Float(args[2] as! Double), Float(args[3] as! Double)) - result("OK") - case "setRotation": - let args = call.arguments as! Array - let assetPtr = UnsafeMutableRawPointer.init(bitPattern: args[0] as! Int) - set_rotation(assetPtr, Float(args[1] as! Double), Float(args[2] as! Double), Float(args[3] as! Double), Float(args[4] as! Double)) - result("OK") - default: - result(FlutterMethodNotImplemented) - } - } -} - diff --git a/ios/src/FilamentViewer.hpp b/ios/include/FilamentViewer.hpp similarity index 100% rename from ios/src/FilamentViewer.hpp rename to ios/include/FilamentViewer.hpp diff --git a/ios/src/Log.hpp b/ios/include/Log.hpp similarity index 100% rename from ios/src/Log.hpp rename to ios/include/Log.hpp diff --git a/ios/src/PolyvoxFilamentApi.hpp b/ios/include/PolyvoxFilamentApi.h similarity index 94% rename from ios/src/PolyvoxFilamentApi.hpp rename to ios/include/PolyvoxFilamentApi.h index 200182fc..6f0091dd 100644 --- a/ios/src/PolyvoxFilamentApi.hpp +++ b/ios/include/PolyvoxFilamentApi.h @@ -2,7 +2,6 @@ #define _POLYVOX_FILAMENT_API_H #include "ResourceBuffer.hpp" -#include "LightManager.hpp" typedef struct ResourceBuffer ResourceBuffer; @@ -31,11 +30,10 @@ void scroll_begin(void* viewer); void scroll_update(void* viewer, float x, float y , float z); void scroll_end(void* viewer); -void grab_begin(void* viewer, int x, int y, bool pan); -void grab_update(void* viewer, int x, int y); +void grab_begin(void* viewer, float x, float y, bool pan); +void grab_update(void* viewer, float x, float y); void grab_end(void* viewer); - void apply_weights(void* asset, float* const weights, int count); void animate_weights(void* asset, float* data, int numWeights, int numFrames, float frameRate); @@ -61,11 +59,10 @@ void set_texture(void* asset); void transform_to_unit_cube(void* asset); void set_position(void* asset, float x, float y, float z); - void set_rotation(void* asset, float rads, float x, float y, float z); +void set_scale(void* asset, float scale); void set_camera_position(void* viewer, float x, float y, float z); - void set_camera_rotation(void* viewer, float rads, float x, float y, float z); void set_camera_focal_length(void* viewer, float focalLength); void set_camera_focus_distance(void* viewer, float focusDistance); diff --git a/ios/Classes/PolyvoxFilamentIOSApi.h b/ios/include/PolyvoxFilamentIOSApi.h similarity index 100% rename from ios/Classes/PolyvoxFilamentIOSApi.h rename to ios/include/PolyvoxFilamentIOSApi.h index 0b97842c..aa80a94b 100644 --- a/ios/Classes/PolyvoxFilamentIOSApi.h +++ b/ios/include/PolyvoxFilamentIOSApi.h @@ -1,3 +1,3 @@ void* filament_viewer_new_ios(void* texture, void* loadResource, void* freeResource, void* resources); - void create_swap_chain(void* viewer, void* texture); + diff --git a/ios/Classes/PolyvoxFilamentPlugin.h b/ios/include/PolyvoxFilamentPlugin.h similarity index 100% rename from ios/Classes/PolyvoxFilamentPlugin.h rename to ios/include/PolyvoxFilamentPlugin.h diff --git a/ios/src/ResourceBuffer.hpp b/ios/include/ResourceBuffer.hpp similarity index 100% rename from ios/src/ResourceBuffer.hpp rename to ios/include/ResourceBuffer.hpp diff --git a/ios/src/SceneAsset.hpp b/ios/include/SceneAsset.hpp similarity index 100% rename from ios/src/SceneAsset.hpp rename to ios/include/SceneAsset.hpp diff --git a/ios/src/SceneAssetLoader.hpp b/ios/include/SceneAssetLoader.hpp similarity index 100% rename from ios/src/SceneAssetLoader.hpp rename to ios/include/SceneAssetLoader.hpp diff --git a/ios/src/SceneResources.hpp b/ios/include/SceneResources.hpp similarity index 99% rename from ios/src/SceneResources.hpp rename to ios/include/SceneResources.hpp index 745254ba..58ff4f7b 100644 --- a/ios/src/SceneResources.hpp +++ b/ios/include/SceneResources.hpp @@ -2,6 +2,7 @@ #include #include +#include #include "ResourceBuffer.hpp" diff --git a/ios/src/StreamBufferAdapter.hpp b/ios/include/StreamBufferAdapter.hpp similarity index 100% rename from ios/src/StreamBufferAdapter.hpp rename to ios/include/StreamBufferAdapter.hpp diff --git a/ios/include/SwiftPolyvoxFilamentPlugin-Bridging-Header.h b/ios/include/SwiftPolyvoxFilamentPlugin-Bridging-Header.h new file mode 100644 index 00000000..6ec7b624 --- /dev/null +++ b/ios/include/SwiftPolyvoxFilamentPlugin-Bridging-Header.h @@ -0,0 +1,10 @@ +#ifndef SwiftPolyvoxFilamentPlugin_Bridging_Header_h +#define SwiftPolyvoxFilamentPlugin_Bridging_Header_h + +void* filament_viewer_new_ios(void* texture, void* loadResource, void* freeResource, void* resources); + +#import "PolyvoxFilamentIOSApi.h" +#import "PolyvoxFilamentApi.h" + +#endif + diff --git a/ios/src/image/imagematerial.S b/ios/include/material/imagematerial.S similarity index 100% rename from ios/src/image/imagematerial.S rename to ios/include/material/imagematerial.S diff --git a/ios/src/image/imagematerial.apple.S b/ios/include/material/imagematerial.apple.S similarity index 100% rename from ios/src/image/imagematerial.apple.S rename to ios/include/material/imagematerial.apple.S diff --git a/ios/src/image/imagematerial.bin b/ios/include/material/imagematerial.bin similarity index 100% rename from ios/src/image/imagematerial.bin rename to ios/include/material/imagematerial.bin diff --git a/ios/src/image/imagematerial.c b/ios/include/material/imagematerial.c similarity index 100% rename from ios/src/image/imagematerial.c rename to ios/include/material/imagematerial.c diff --git a/ios/src/image/imagematerial.h b/ios/include/material/imagematerial.h similarity index 100% rename from ios/src/image/imagematerial.h rename to ios/include/material/imagematerial.h diff --git a/ios/src/image/imagematerials_ios.S b/ios/include/material/imagematerials_ios.S similarity index 100% rename from ios/src/image/imagematerials_ios.S rename to ios/include/material/imagematerials_ios.S diff --git a/ios/src/image/imagematerials_ios.apple.S b/ios/include/material/imagematerials_ios.apple.S similarity index 100% rename from ios/src/image/imagematerials_ios.apple.S rename to ios/include/material/imagematerials_ios.apple.S diff --git a/ios/src/image/imagematerials_ios.bin b/ios/include/material/imagematerials_ios.bin similarity index 100% rename from ios/src/image/imagematerials_ios.bin rename to ios/include/material/imagematerials_ios.bin diff --git a/ios/src/image/imagematerials_ios.c b/ios/include/material/imagematerials_ios.c similarity index 100% rename from ios/src/image/imagematerials_ios.c rename to ios/include/material/imagematerials_ios.c diff --git a/ios/src/image/imagematerials_ios.h b/ios/include/material/imagematerials_ios.h similarity index 100% rename from ios/src/image/imagematerials_ios.h rename to ios/include/material/imagematerials_ios.h diff --git a/ios/src/shaders/unlitopaque.S b/ios/include/material/unlitopaque.S similarity index 100% rename from ios/src/shaders/unlitopaque.S rename to ios/include/material/unlitopaque.S diff --git a/ios/src/shaders/unlitopaque.apple.S b/ios/include/material/unlitopaque.apple.S similarity index 100% rename from ios/src/shaders/unlitopaque.apple.S rename to ios/include/material/unlitopaque.apple.S diff --git a/ios/src/shaders/unlitopaque.bin b/ios/include/material/unlitopaque.bin similarity index 100% rename from ios/src/shaders/unlitopaque.bin rename to ios/include/material/unlitopaque.bin diff --git a/ios/src/shaders/unlitopaque.c b/ios/include/material/unlitopaque.c similarity index 100% rename from ios/src/shaders/unlitopaque.c rename to ios/include/material/unlitopaque.c diff --git a/ios/src/shaders/unlitopaque.h b/ios/include/material/unlitopaque.h similarity index 100% rename from ios/src/shaders/unlitopaque.h rename to ios/include/material/unlitopaque.h diff --git a/ios/polyvox_filament.podspec b/ios/polyvox_filament.podspec index 2a55e30a..ab1d6c13 100644 --- a/ios/polyvox_filament.podspec +++ b/ios/polyvox_filament.podspec @@ -13,39 +13,36 @@ A new flutter plugin project. s.license = { :file => '../LICENSE' } s.author = { 'Your Company' => 'email@example.com' } s.source = { :path => '.' } - s.source_files = 'Classes/**/*', 'src/ResourceBuffer.hpp', 'src/FilamentViewer.cpp', 'src/SceneAsset.cpp', 'src/SceneAssetLoader.cpp', 'src/StreamBufferAdapter.cpp', 'src/image/imagematerial.c', 'src/image/imagematerials_ios.c' - #s.header_dir = "include" - #s.header_mappings_dir = "include" + s.source_files = 'src/*', 'src/ios/*', 'src/shaders/*.c', 'src/shaders/*.h', 'include/filament/*', 'include/*', 'include/material/*.h', 'include/material/*.c' + s.public_header_files = 'include/SwiftPolyvoxFilamentPlugin-Bridging-Header.h', 'include/PolyvoxFilamentIOSApi.h', 'include/PolyvoxFilamentApi.h', 'include/ResourceBuffer.hpp' #, 'include/filament/*' +# s.header_mappings_dir = 'include' s.dependency 'Flutter' s.platform = :ios, '12.1' s.static_framework = true s.vendored_libraries = "lib/*.a" s.library = "c++" - s.user_target_xcconfig = { 'DEFINES_MODULE' => 'YES', 'EXCLUDED_ARCHS[sdk=iphonesimulator*]' => 'i386', "CLANG_CXX_LANGUAGE_STANDARD" => "c++17", 'OTHER_CXXFLAGS' => '"--std=c++17" "-fmodules" "-fcxx-modules" "$(inherited)"', - 'USER_HEADER_SEARCH_PATHS' => '"${PODS_ROOT}/../.symlinks/plugins/polyvox_filament/ios/include" "${PODS_ROOT}/../.symlinks/plugins/polyvox_filament/ios/src" "${PODS_ROOT}/../.symlinks/plugins/polyvox_filament/ios/src/image "$(inherited)"', + 'USER_HEADER_SEARCH_PATHS' => '"${PODS_ROOT}/../.symlinks/plugins/polyvox_filament/ios/include" "${PODS_ROOT}/../.symlinks/plugins/polyvox_filament/ios/src" "${PODS_ROOT}/../.symlinks/plugins/polyvox_filament/ios/src/image" "${PODS_ROOT}/../.symlinks/plugins/polyvox_filament/ios/src/shaders" "$(inherited)"', 'ALWAYS_SEARCH_USER_PATHS' => 'YES', "OTHER_LDFLAGS" => '-lfilament -lbackend -lfilameshio -lviewer -lfilamat -lgeometry -lutils -lfilabridge -lgltfio_core -lfilament-iblprefilter -limage -lcamutils -lgltfio_core -lfilaflat -ldracodec -libl -lktxreader -limageio -lpng -lpng16 -ltinyexr -lz -lstb -luberzlib -lsmol-v -luberarchive -lzstd', 'LIBRARY_SEARCH_PATHS' => '"${PODS_ROOT}/../.symlinks/plugins/polyvox_filament/ios/lib" "$(inherited)"', } - - # Flutter.framework does not contain a i386 slice. s.pod_target_xcconfig = { 'DEFINES_MODULE' => 'YES', 'EXCLUDED_ARCHS[sdk=iphonesimulator*]' => 'i386', "CLANG_CXX_LANGUAGE_STANDARD" => "c++17", 'OTHER_CXXFLAGS' => '"--std=c++17" "-fmodules" "-fcxx-modules" "$(inherited)"', - 'USER_HEADER_SEARCH_PATHS' => '"${PODS_ROOT}/../.symlinks/plugins/polyvox_filament/ios/include" "${PODS_ROOT}/../.symlinks/plugins/polyvox_filament/ios/src" "${PODS_ROOT}/../.symlinks/plugins/polyvox_filament/ios/src/image "$(inherited)"', + 'USER_HEADER_SEARCH_PATHS' => '"${PODS_ROOT}/../.symlinks/plugins/polyvox_filament/ios/include" "${PODS_ROOT}/../.symlinks/plugins/polyvox_filament/ios/src" "${PODS_ROOT}/../.symlinks/plugins/polyvox_filament/ios/src/image" "${PODS_ROOT}/../.symlinks/plugins/polyvox_filament/ios/src/shaders" "$(inherited)"', 'ALWAYS_SEARCH_USER_PATHS' => 'YES', "OTHER_LDFLAGS" => '-lfilament -lbackend -lfilameshio -lviewer -lfilamat -lgeometry -lutils -lfilabridge -lgltfio_core -lfilament-iblprefilter -limage -lcamutils -lgltfio_core -lfilaflat -ldracodec -libl -lktxreader -limageio -lpng -lpng16 -ltinyexr -lz -lstb -luberzlib -lsmol-v -luberarchive -lzstd', 'LIBRARY_SEARCH_PATHS' => '"${PODS_ROOT}/../.symlinks/plugins/polyvox_filament/ios/lib" "$(inherited)"', } - + s.swift_version = '5.0' end diff --git a/ios/src/FilamentViewer.cpp b/ios/src/FilamentViewer.cpp index 3754ffbf..c8ea459e 100644 --- a/ios/src/FilamentViewer.cpp +++ b/ios/src/FilamentViewer.cpp @@ -69,7 +69,8 @@ #include "Log.hpp" #include "SceneResources.hpp" #if TARGET_OS_IPHONE -#include "image/imagematerials_ios.h" +#include "material/imagematerials_ios.h" +#include "material/unlitopaque.h" #else #include "image/imagematerial.h" #include "shaders/unlitopaque.h" @@ -98,7 +99,7 @@ namespace polyvox { public: UnlitMaterialProvider(Engine* engine) { _m = Material::Builder() - .package(UNLITOPAQUE_UNLIT_OPAQUE_DATA, UNLITOPAQUE_UNLIT_OPAQUE_SIZE) + .package( UNLITOPAQUE_UNLIT_OPAQUE_DATA, UNLITOPAQUE_UNLIT_OPAQUE_SIZE) .build(*engine); _ms[0] = _m; } diff --git a/ios/src/HDRLoader.cpp b/ios/src/HDRLoader.cpp deleted file mode 100644 index eca50e76..00000000 --- a/ios/src/HDRLoader.cpp +++ /dev/null @@ -1,91 +0,0 @@ -/* - * Copyright (C) 2021 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#include - -#include -#include - -#include - -#include - -#include - -#include "common/NioUtils.h" - -using namespace filament; -using namespace image; -using namespace utils; - -using PixelBufferDescriptor = Texture::PixelBufferDescriptor; - -jlong nCreateHDRTexture(JNIEnv* env, jclass, - jlong nativeEngine, jobject javaBuffer, jint remaining, jint internalFormat) { - slog.e << "Creating HDR texture." << io::endl; - Engine* engine = (Engine*) nativeEngine; - AutoBuffer buffer(env, javaBuffer, remaining); - Texture::InternalFormat textureFormat = (Texture::InternalFormat) internalFormat; - - auto dataPtr = (char const*) buffer.getData(); - const size_t byteCount = buffer.getSize(); - - // This creates a copy but it's the easest way to create a memory stream. - std::string ins(dataPtr, byteCount); - std::istringstream in(ins); - - LinearImage* image = new LinearImage(ImageDecoder::decode(in, "memory.hdr")); - - // This can happen if a decoding error occurs. - if (image->getChannels() != 3) { - delete image; - return 0; - } - - Texture* texture = Texture::Builder() - .width(image->getWidth()) - .height(image->getHeight()) - .levels(0xff) - .sampler(Texture::Sampler::SAMPLER_2D) - .format(textureFormat) - .build(*engine); - - if (texture == nullptr) { - slog.e << "Unable to create Filament Texture from HDR image." << io::endl; - delete image; - return 0; - } - - PixelBufferDescriptor::Callback freeCallback = [](void* buf, size_t, void* userdata) { - delete (LinearImage*) userdata; - }; - - PixelBufferDescriptor pbd( - (void const* ) image->getPixelRef(), - image->getWidth() * image->getHeight() * 3 * sizeof(float), - PixelBufferDescriptor::PixelDataFormat::RGB, - PixelBufferDescriptor::PixelDataType::FLOAT, - freeCallback, - image); - - // Note that the setImage call could fail (e.g. due to an invalid combination of internal format - // and PixelDataFormat) but there is no way of detecting such a failure. - texture->setImage(*engine, 0, std::move(pbd)); - - texture->generateMipmaps(*engine); - - return (jlong) texture; -} diff --git a/ios/src/Utils.cpp b/ios/src/Utils.cpp deleted file mode 100644 index ce504600..00000000 --- a/ios/src/Utils.cpp +++ /dev/null @@ -1,160 +0,0 @@ -/* - * Copyright (C) 2020 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#include - -#include -#include -#include - -#include - -#include -#include - -#include "common/NioUtils.h" - -#include - -using namespace filament; -using namespace filament::math; -using namespace image; - -jlong nCreateHDRTexture(JNIEnv* env, jclass, - jlong nativeEngine, jobject javaBuffer, jint remaining, jint internalFormat); - -static jlong nCreateKTXTexture(JNIEnv* env, jclass, - jlong nativeEngine, jobject javaBuffer, jint remaining, jboolean srgb) { - Engine* engine = (Engine*) nativeEngine; - AutoBuffer buffer(env, javaBuffer, remaining); - KtxBundle* bundle = new KtxBundle((const uint8_t*) buffer.getData(), buffer.getSize()); - return (jlong) ktx::createTexture(engine, *bundle, srgb, [](void* userdata) { - KtxBundle* bundle = (KtxBundle*) userdata; - delete bundle; - }, bundle); -} - -static jlong nCreateIndirectLight(JNIEnv* env, jclass, - jlong nativeEngine, jobject javaBuffer, jint remaining, jboolean srgb) { - Engine* engine = (Engine*) nativeEngine; - AutoBuffer buffer(env, javaBuffer, remaining); - KtxBundle* bundle = new KtxBundle((const uint8_t*) buffer.getData(), buffer.getSize()); - Texture* cubemap = ktx::createTexture(engine, *bundle, srgb, [](void* userdata) { - KtxBundle* bundle = (KtxBundle*) userdata; - delete bundle; - }, bundle); - - float3 harmonics[9]; - bundle->getSphericalHarmonics(harmonics); - - IndirectLight* indirectLight = IndirectLight::Builder() - .reflections(cubemap) - .irradiance(3, harmonics) - .intensity(30000) - .build(*engine); - - return (jlong) indirectLight; -} - -static jlong nCreateSkybox(JNIEnv* env, jclass, - jlong nativeEngine, jobject javaBuffer, jint remaining, jboolean srgb, jobject assetManager, jstring outpath) { - - AAssetManager *mgr = AAssetManager_fromJava(env, assetManager); - - AAsset *asset = AAssetManager_open(mgr, "envs/default_env/default_env_skybox.ktx", AASSET_MODE_BUFFER); - if(asset == nullptr) { - __android_log_print(ANDROID_LOG_VERBOSE, "filament_api", "Couldn't open asset"); - return 0; - } - - off_t length = AAsset_getLength(asset); - const void * buffer = AAsset_getBuffer(asset); - jboolean isCopy = (jboolean)false; - const char* out_cstr = env->GetStringUTFChars(outpath, &isCopy); - - __android_log_print(ANDROID_LOG_VERBOSE, "filament_api", "Opening outfile %s for writing", out_cstr); - - FILE* outfile = fopen(out_cstr, "w"); - - fwrite(buffer, 1, length, outfile); - - fclose(outfile); - - __android_log_print(ANDROID_LOG_VERBOSE, "filament_api", "Closed outfile %s", out_cstr); - - Engine* engine = (Engine*) nativeEngine; - // __android_log_print(ANDROID_LOG_VERBOSE, "UTILS", "CREATing autobuffer"); - // AutoBuffer buffer(env, javaBuffer, remaining); - // __android_log_print(ANDROID_LOG_VERBOSE, "UTILS", "CREATied autobuffer"); - - KtxBundle* bundle = new KtxBundle((const uint8_t*) buffer, length); - // KtxBundle* bundle = new KtxBundle((const uint8_t*) buffer.getData(), buffer.getSize()); - __android_log_print(ANDROID_LOG_VERBOSE, "UTILS", "CREATED BUNDLE FROM API"); - - - Texture* cubemap = ktx::createTexture(engine, *bundle, srgb, [](void* userdata) { - KtxBundle* bundle = (KtxBundle*) userdata; - delete bundle; - }, bundle); - __android_log_print(ANDROID_LOG_VERBOSE, "UTILS", "CREATED TEXTURE"); - return (jlong) Skybox::Builder().environment(cubemap).showSun(true).build(*engine); -} - -static jboolean nGetSphericalHarmonics(JNIEnv* env, jclass, jobject javaBuffer, jint remaining, - jfloatArray outSphericalHarmonics_) { - AutoBuffer buffer(env, javaBuffer, remaining); - KtxBundle bundle((const uint8_t*) buffer.getData(), buffer.getSize()); - - jfloat* outSphericalHarmonics = env->GetFloatArrayElements(outSphericalHarmonics_, nullptr); - const auto success = bundle.getSphericalHarmonics( - reinterpret_cast(outSphericalHarmonics) - ); - env->ReleaseFloatArrayElements(outSphericalHarmonics_, outSphericalHarmonics, JNI_ABORT); - - return success ? JNI_TRUE : JNI_FALSE; -} - -JNIEXPORT jint JNI_OnLoad(JavaVM* vm, void*) { - JNIEnv* env; - if (vm->GetEnv(reinterpret_cast(&env), JNI_VERSION_1_6) != JNI_OK) { - return -1; - } - - int rc; - - // KTXLoader - jclass ktxloaderClass = env->FindClass("app/polyvox/filament/KTXLoader2"); - if (ktxloaderClass == nullptr) return JNI_ERR; - static const JNINativeMethod ktxMethods[] = { - {(char*)"nCreateKTXTexture", (char*)"(JLjava/nio/Buffer;IZ)J", reinterpret_cast(nCreateKTXTexture)}, - {(char*)"nCreateIndirectLight", (char*)"(JLjava/nio/Buffer;IZ)J", reinterpret_cast(nCreateIndirectLight)}, - {(char*)"nCreateSkybox", (char*)"(JLjava/nio/Buffer;IZLandroid/content/res/AssetManager;Ljava/lang/String;)J", reinterpret_cast(nCreateSkybox)}, - {(char*)"nGetSphericalHarmonics", (char*)"(Ljava/nio/Buffer;I[F)Z", reinterpret_cast(nGetSphericalHarmonics)}, - }; - rc = env->RegisterNatives(ktxloaderClass, ktxMethods, sizeof(ktxMethods) / sizeof(JNINativeMethod)); - if (rc != JNI_OK) return rc; - - // HDRLoader - jclass hdrloaderClass = env->FindClass("com/google/android/filament/utils/HDRLoader"); - if (hdrloaderClass == nullptr) return JNI_ERR; - static const JNINativeMethod hdrMethods[] = { - {(char*)"nCreateHDRTexture", (char*)"(JLjava/nio/Buffer;II)J", reinterpret_cast(nCreateHDRTexture)}, - }; - rc = env->RegisterNatives(hdrloaderClass, hdrMethods, sizeof(hdrMethods) / sizeof(JNINativeMethod)); - if (rc != JNI_OK) return rc; - - return JNI_VERSION_1_6; -} diff --git a/ios/src/image/materials/image.filamat b/ios/src/image/materials/image.filamat deleted file mode 100644 index b2287483..00000000 Binary files a/ios/src/image/materials/image.filamat and /dev/null differ diff --git a/ios/src/image/materials/image.filamat.metal b/ios/src/image/materials/image.filamat.metal deleted file mode 100644 index 36f41af2..00000000 Binary files a/ios/src/image/materials/image.filamat.metal and /dev/null differ diff --git a/ios/src/image/materials/image.mat b/ios/src/image/materials/image.mat deleted file mode 100644 index 5acabd9f..00000000 --- a/ios/src/image/materials/image.mat +++ /dev/null @@ -1,54 +0,0 @@ -material { - name : Image, - parameters : [ - { - type : sampler2d, - name : image - }, - { - type : mat4, - name : transform, - precision : high - }, - { - type : float3, - name : backgroundColor - }, - { - type : int, - name : showImage - } - ], - variables : [ - imageUV - ], - vertexDomain : device, - depthWrite : false, - shadingModel : unlit, - variantFilter : [ skinning, shadowReceiver, vsm ], - culling: none -} - -vertex { - void materialVertex(inout MaterialVertexInputs material) { - material.imageUV.st = getPosition().st * 0.5 + 0.5; - } -} - -fragment { - void material(inout MaterialInputs material) { - prepareMaterial(material); - - vec4 bg = vec4(materialParams.backgroundColor, 1.0); - highp vec2 uv = (materialParams.transform * vec4(saturate(variable_imageUV.st), 1.0, 1.0)).st; - if (materialParams.showImage == 0 || uv.s > 1.0 || uv.s < 0.0 || uv.t < 0.0 || uv.t > 1.0) { - material.baseColor = bg; - } else { - uv.t = 1.0 - uv.t; - vec4 color = max(texture(materialParams_image, uv.st), 0.0); - color.rgb *= color.a; - // Manual, pre-multiplied srcOver with opaque destination optimization - material.baseColor.rgb = color.rgb + bg.rgb * (1.0 - color.a); - } - } -} diff --git a/ios/Classes/PolyvoxFilamentIOSApi.cc b/ios/src/ios/PolyvoxFilamentIOSApi.cpp similarity index 100% rename from ios/Classes/PolyvoxFilamentIOSApi.cc rename to ios/src/ios/PolyvoxFilamentIOSApi.cpp diff --git a/ios/Classes/PolyvoxFilamentPlugin.m b/ios/src/ios/PolyvoxFilamentPlugin.m similarity index 100% rename from ios/Classes/PolyvoxFilamentPlugin.m rename to ios/src/ios/PolyvoxFilamentPlugin.m diff --git a/ios/src/ios/SwiftPolyvoxFilamentPlugin.swift b/ios/src/ios/SwiftPolyvoxFilamentPlugin.swift new file mode 100644 index 00000000..411de877 --- /dev/null +++ b/ios/src/ios/SwiftPolyvoxFilamentPlugin.swift @@ -0,0 +1,353 @@ +import Flutter +import UIKit +import OpenGLES.ES3 +import GLKit + +public class SwiftPolyvoxFilamentPlugin: NSObject, FlutterPlugin, FlutterTexture { + + var registrar : FlutterPluginRegistrar + var textureId: Int64? + var registry: FlutterTextureRegistry + + var width: Double = 0 + var height: Double = 0 + + var context: EAGLContext?; + var targetPixelBuffer: CVPixelBuffer?; + var textureCache: CVOpenGLESTextureCache?; + var texture: CVOpenGLESTexture? = nil; + var frameBuffer: GLuint = 0; + + + var pixelBufferAttrs = [ + kCVPixelBufferPixelFormatTypeKey: NSNumber(value: kCVPixelFormatType_32BGRA), + kCVPixelBufferOpenGLCompatibilityKey: kCFBooleanTrue, + kCVPixelBufferOpenGLESCompatibilityKey: kCFBooleanTrue, + kCVPixelBufferIOSurfacePropertiesKey: [:] + ] as CFDictionary + + var resources:NSMutableDictionary = [:] + var viewer:UnsafeMutableRawPointer? = nil + + var displayLink:CADisplayLink? = nil + + static var messenger : FlutterBinaryMessenger? = nil; + + var loadResourcePtr: UnsafeMutableRawPointer? = nil + var freeResourcePtr: UnsafeMutableRawPointer? = nil + var resourcesPtr : UnsafeMutableRawPointer? = nil + + var _rendering = true + + var loadResource : @convention(c) (UnsafeRawPointer, UnsafeMutableRawPointer) -> ResourceBuffer = { uri, resourcesPtr in + + let instance:SwiftPolyvoxFilamentPlugin = Unmanaged.fromOpaque(resourcesPtr).takeUnretainedValue() + + let uriString = String(cString:uri.assumingMemoryBound(to: UInt8.self)) + + let key = instance.registrar.lookupKey(forAsset:uriString) + + let path = Bundle.main.path(forResource: key, ofType:nil) + do { + let foo: String = path! + let data = try Data(contentsOf: URL(fileURLWithPath:foo)) + let resId = instance.resources.count + let nsData = data as NSData + instance.resources[resId] = nsData + let rawPtr = nsData.bytes + return ResourceBuffer(data:rawPtr, size:UInt32(nsData.count), id:UInt32(resId)) + } catch { + print("Error opening file: \(error)") + return ResourceBuffer() + } + return ResourceBuffer() + } + + var freeResource : @convention(c) (UInt32,UnsafeMutableRawPointer) -> () = { rid, resourcesPtr in + let instance:SwiftPolyvoxFilamentPlugin = Unmanaged.fromOpaque(resourcesPtr).takeUnretainedValue() + instance.resources.removeObject(forKey:rid) + } + + func createDisplayLink() { + displayLink = CADisplayLink(target: self, + selector: #selector(doRender)) + displayLink!.add(to: .current, forMode: RunLoop.Mode.default) + } + + @objc func doRender() { + if(viewer != nil && _rendering) { + render(viewer, 0) + self.registry.textureFrameAvailable(self.textureId!) + } + } + + public func copyPixelBuffer() -> Unmanaged? { + if(targetPixelBuffer == nil) { + print("empty") + return nil; + } + return Unmanaged.passRetained(targetPixelBuffer!); + } + + public static func register(with registrar: FlutterPluginRegistrar) { + let _messenger = registrar.messenger(); + messenger = _messenger; + let channel = FlutterMethodChannel(name: "app.polyvox.filament/event", binaryMessenger: _messenger) + let instance = SwiftPolyvoxFilamentPlugin(textureRegistry: registrar.textures(), registrar:registrar) + registrar.addMethodCallDelegate(instance, channel: channel) + } + + init(textureRegistry: FlutterTextureRegistry, registrar:FlutterPluginRegistrar) { + self.registry = textureRegistry; + self.registrar = registrar + } + + private func createPixelBuffer(width:Int, height:Int) { + + if(targetPixelBuffer != nil) { + destroy_swap_chain(self.viewer) + } + if(CVPixelBufferCreate(kCFAllocatorDefault, Int(width), Int(height), + kCVPixelFormatType_32BGRA, pixelBufferAttrs, &targetPixelBuffer) != kCVReturnSuccess) { + print("Error allocating pixel buffer") + } + if(self.viewer != nil) { + create_swap_chain(self.viewer, unsafeBitCast(targetPixelBuffer!, to: UnsafeMutableRawPointer.self)) + update_viewport_and_camera_projection(self.viewer!, Int32(width), Int32(height), 1.0); + } + + print("Pixel buffer created") + } + + private func initialize(width:Int32, height:Int32) { + + createPixelBuffer(width:Int(width), height:Int(height)) + self.textureId = self.registry.register(self) + + loadResourcePtr = unsafeBitCast(loadResource, to: UnsafeMutableRawPointer.self) + freeResourcePtr = unsafeBitCast(freeResource, to: UnsafeMutableRawPointer.self) + + viewer = filament_viewer_new_ios( + unsafeBitCast(targetPixelBuffer!, to: UnsafeMutableRawPointer.self), + loadResourcePtr!, + freeResourcePtr!, + Unmanaged.passUnretained(self).toOpaque() + ) + + update_viewport_and_camera_projection(self.viewer!, Int32(width), Int32(height), 1.0); + + createDisplayLink() + + } + + public func handle(_ call: FlutterMethodCall, result: @escaping FlutterResult) { + let methodName = call.method; + + switch methodName { + case "initialize": + let args = call.arguments as! Array + initialize(width:args[0], height:args[1]) + result(self.textureId); + case "setBackgroundImage": + let uri = call.arguments as! String + set_background_image(self.viewer!, uri) + render(self.viewer!, 0) + self.registry.textureFrameAvailable(self.textureId!) + result("OK") + case "setBackgroundImagePosition": + let args = call.arguments as! Array + set_background_image_position(self.viewer, Float(args[0] as! Double), Float(args[1] as! Double), args[2] as! Bool) + result("OK"); + case "resize": + let args = call.arguments as! Array + let width = Int(args[0]) + let height = Int(args[1]) + createPixelBuffer(width: width, height:height) + result("OK") + case "loadSkybox": + load_skybox(self.viewer!, call.arguments as! String) + result("OK"); + case "removeSkybox": + remove_skybox(self.viewer!) + result("OK"); + case "loadGlb": + let assetPtr = load_glb(self.viewer, call.arguments as! String) + result(unsafeBitCast(assetPtr, to:Int64.self)); + case "loadGltf": + let args = call.arguments as! Array + result(load_gltf(self.viewer, args[0] as! String, args[1] as! String)); + case "removeAsset": + let assetPtr = UnsafeMutableRawPointer.init(bitPattern: call.arguments as! Int) + remove_asset(viewer!, assetPtr) + result("OK") + case "clearAssets": + clear_assets(viewer!) + result("OK") + case "loadIbl": + load_ibl(self.viewer, call.arguments as! String) + result("OK"); + case "removeIbl": + remove_ibl(self.viewer) + result("OK"); + case "setCamera": + let args = call.arguments as! Array + let assetPtr = UnsafeMutableRawPointer.init(bitPattern: args[0] as! Int) + set_camera(self.viewer, assetPtr, args[1] as! String) + result("OK"); + case "playAnimation": + let args = call.arguments as! Array + let assetPtr = UnsafeMutableRawPointer.init(bitPattern: args[0] as! Int) + let animationIndex = args[1] as! Int32; + let loop = args[2] as! Bool; + let reverse = args[3] as! Bool; + play_animation(assetPtr, animationIndex, loop, reverse) + result("OK"); + case "stopAnimation": + let args = call.arguments as! Array + let assetPtr = UnsafeMutableRawPointer.init(bitPattern: args[0] as! Int) + let animationIndex = args[1] as! Int32 + stop_animation(assetPtr, animationIndex) // TODO + result("OK"); + case "getTargetNames": + let args = call.arguments as! Array + let assetPtr = UnsafeMutableRawPointer.init(bitPattern: args[0] as! Int) + let meshName = args[1] as! String + let numNames = get_target_name_count(assetPtr, meshName) + var names = [String]() + for i in 0...numNames - 1{ + let outPtr = UnsafeMutablePointer.allocate(capacity:256) + get_target_name(assetPtr, meshName, outPtr, i) + names.append(String(cString:outPtr)) + } + result(names); + case "getAnimationNames": + let assetPtr = UnsafeMutableRawPointer.init(bitPattern: call.arguments as! Int) + let numNames = get_animation_count(assetPtr) + var names = [String]() + for i in 0...numNames - 1{ + let outPtr = UnsafeMutablePointer.allocate(capacity:256) + get_animation_name(assetPtr, outPtr, i) + names.append(String(cString:outPtr)) + } + result(names); + case "applyWeights": + let args = call.arguments as! Array + let assetPtr = UnsafeMutableRawPointer.init(bitPattern: args[0] as! Int) + let weights = args[1] as! Array + weights.map { Float($0) }.withUnsafeBufferPointer { + apply_weights(assetPtr, UnsafeMutablePointer.init(mutating:$0.baseAddress), Int32(weights.count)) + + } + result("OK") + case "zoomBegin": + scroll_begin(self.viewer) + result("OK") + case "zoomUpdate": + let args = call.arguments as! Array + scroll_update(self.viewer, Float(args[0] as! Double), Float(args[1] as! Double),Float(args[2] as! Double)) + result("OK") + case "zoomEnd": + scroll_end(self.viewer) + result("OK") + case "animateWeights": + let args = call.arguments as! Array + let assetPtr = UnsafeMutableRawPointer.init(bitPattern: args[0] as! Int) + let frameData = args[1] as! Array + let numWeights = args[2] as! Int + let numFrames = args[3] as! Int + let frameLenInMs = args[4] as! Double + frameData.map { Float($0)}.withUnsafeBufferPointer { + animate_weights(assetPtr, UnsafeMutablePointer.init(mutating:$0.baseAddress), Int32(numWeights), Int32(numFrames), Float(frameLenInMs)) + } + result("OK") + case "panStart": + let args = call.arguments as! Array + grab_begin(self.viewer, Float(args[0] as! Double), Float(args[1] as! Double), true) + result("OK") + case "panUpdate": + let args = call.arguments as! Array + grab_update(self.viewer, Float(args[0] as! Double), Float(args[1] as! Double)) + result("OK") + case "panEnd": + grab_end(self.viewer) + result("OK") + case "rotateStart": + let args = call.arguments as! Array + grab_begin(self.viewer, Float(args[0] as! Double), Float(args[1] as! Double), false) + result("OK") + case "rotateUpdate": + let args = call.arguments as! Array + grab_update(self.viewer, Float(args[0] as! Double), Float(args[1] as! Double)) + result("OK") + case "rotateEnd": + grab_end(self.viewer) + result("OK") + case "setPosition": + let args = call.arguments as! Array + let assetPtr = UnsafeMutableRawPointer.init(bitPattern: args[0] as! Int) + let x = Float(args[1] as! Double) + set_position(assetPtr, x, Float(args[2] as! Double), Float(args[3] as! Double)) + result("OK") + case "setRotation": + let args = call.arguments as! Array + let assetPtr = UnsafeMutableRawPointer.init(bitPattern: args[0] as! Int) + set_rotation(assetPtr, Float(args[1] as! Double), Float(args[2] as! Double), Float(args[3] as! Double), Float(args[4] as! Double)) + result("OK") + case "setScale": + let args = call.arguments as! Array + let assetPtr = UnsafeMutableRawPointer.init(bitPattern: args[0] as! Int) + set_scale(assetPtr, Float(args[1] as! Double)) + result("OK"); + case "setCameraPosition": + let args = call.arguments as! Array + set_camera_position(self.viewer, Float(args[0] as! Double), Float(args[1] as! Double), Float(args[2] as! Double)) + result("OK"); + case "setCameraRotation": + let args = call.arguments as! Array + set_camera_rotation(self.viewer, Float(args[0] as! Double), Float(args[1] as! Double), Float(args[2] as! Double),Float(args[3] as! Double)) + case "setCameraFocalLength": + set_camera_focal_length(self.viewer, Float(call.arguments as! Double)) + result("OK"); + case "setCameraFocusDistance": + // TODO + // set_camera_focus_distance(self.viewer, Float(call.arguments as! Double)) + // result("OK"); + break + case "setRendering": + _rendering = call.arguments as! Bool + result("OK") + case "render": + doRender() + result("OK") + case "addLight": + let args = call.arguments as! Array + let entity = add_light( + self.viewer, + args[0] as! UInt8, + Float(args[1] as! Double), + Float(args[2] as! Double), + Float(args[3] as! Double), + Float(args[4] as! Double), + Float(args[5] as! Double), + Float(args[6] as! Double), + Float(args[7] as! Double), + Float(args[8] as! Double), + args[9] as! Bool) + result(entity); + case "removeLight": + remove_light(self.viewer,call.arguments as! Int32) + result(true); + case "clearLights": + clear_lights(self.viewer); + result(true); + case "setTexture": + let args = call.arguments as! Array + let assetPtr = UnsafeMutableRawPointer.init(bitPattern: args[0] as! Int) + load_texture(assetPtr, args[1] as! String, args[2] as! Int32) + result("OK"); + default: + result(FlutterMethodNotImplemented) + } + } +} +