/// <summary> /// Add all (sub)meshes to the tracking system. If a sub mesh has its own /// VLModelTrackableBehaviour, it will not be added, but this behaviour should /// manage the relevant submeshes. /// </summary> public void UpdateModel(bool success = true) { if (success && this.modelTrackerBehaviour.workerBehaviour) { VLWorker worker = this.modelTrackerBehaviour.workerBehaviour.GetWorker(); if (worker == null) { Debug.Log("[vlUnitySDK] VLModelTrackableBehaviour.UpdateModel: Worker is not correctly initialized\n"); return; } AddModelDataCommandDescription command = this.GenerateModelDataDescriptor(true); byte[] binaryData = this.GenerateBinaryData( this.modelData, this.binaryOffset); GCHandle binaryDataHandle = GCHandle.Alloc(binaryData, GCHandleType.Pinned); IntPtr data = binaryDataHandle.AddrOfPinnedObject(); UInt32 dataLength = Convert.ToUInt32(binaryData.Length); gcHandleQueue.Enqueue(binaryDataHandle); worker.PushJsonAndBinaryCommand( VLJsonUtility.ToJson(command), data, dataLength, dispatchAddModelCallbackDelegate, GCHandle.ToIntPtr(this.gcHandle)); } }
/// <summary> /// Initializes the <see cref="workerBehaviour"/> and <see cref="worker"/> /// member variables. /// </summary> /// <returns> /// <c>true</c>, on success; <c>false</c> otherwise. /// </returns> protected bool InitWorkerReference() { // Worker already found? if (this.worker != null) { return(true); } // VLWorkerBeahaviour specified explicitly? if (this.workerBehaviour != null) { this.worker = this.workerBehaviour.GetWorker(); return(this.worker != null); } // Look for it at the same GameObject first this.workerBehaviour = GetComponent <VLWorkerBehaviour>(); if (this.workerBehaviour != null) { this.worker = this.workerBehaviour.GetWorker(); return(this.worker != null); } // Try to find it anywhere in the scene this.workerBehaviour = FindObjectOfType <VLWorkerBehaviour>(); if (this.workerBehaviour != null) { this.worker = this.workerBehaviour.GetWorker(); return(this.worker != null); } return(false); }
private void OnDestroy() { // Explicitly remove the listeners, so we know if everything went well if (!this.worker.RemovePerformanceInfoListener( dispatchPerformanceInfoCallbackDelegate, GCHandle.ToIntPtr(this.gcHandle))) { Debug.LogWarning("[vlUnitySDK] Failed to remove performance info listener"); } if (!this.worker.RemoveTrackingStateListener( dispatchTrackingStateCallbackDelegate, GCHandle.ToIntPtr(this.gcHandle))) { Debug.LogWarning("[vlUnitySDK] Failed to remove tracking state listener"); } if (!this.worker.RemoveIntrinsicDataListener( dispatchIntrinsicDataCallbackDelegate, GCHandle.ToIntPtr(this.gcHandle))) { Debug.LogWarning("[vlUnitySDK] Failed to remove intrinsic data listener"); } if (!this.worker.RemoveExtrinsicDataListener( dispatchExtrinsicDataCallbackDelegate, GCHandle.ToIntPtr(this.gcHandle))) { Debug.LogWarning("[vlUnitySDK] Failed to remove extrinsic data listener"); } if (!this.worker.RemoveImageListener( dispatchImageCallbackDelegate, GCHandle.ToIntPtr(this.gcHandle))) { Debug.LogWarning("[vlUnitySDK] Failed to remove image listener"); } // Release the worker reference (this is necessary, because it // references native resources) this.worker.Dispose(); this.worker = null; // Release the log listener, because we will add a new one during the // next call to Awake this.logger.Dispose(); this.logger = null; // Release the AbstractApplication reference (this is necessary, // because it references native resources) this.aap.Dispose(); this.aap = null; // Release the handle to the current object this.gcHandle.Free(); }
/// <summary> /// Updates the transformation of all (sub)meshes in the tracking system. /// It has to be called after each update in a transform which is relevant /// for the location of a related mesh. /// </summary> /// <param name="useAllChildNodes"> /// If useAllChildNodes is true, this will update all locations of /// submeshes, even if they have their own VLModelTrackableBehaviour. It does /// not update the modelDescriptions of this behaviour. /// </param> public void UpdateTransformation(bool useAllChildNodes) { if (this.modelTrackerBehaviour.HasWorkerReference()) { VLWorker worker = this.modelTrackerBehaviour.workerBehaviour.GetWorker(); if (worker == null) { Debug.Log("[vlUnitySDK] VLModelTrackableBehaviour: Worker is not correctly initialized\n"); return; } AddModelDataCommandDescription command = this.GenerateModelDataDescriptor(false, useAllChildNodes); worker.PushJsonAndBinaryCommand( VLJsonUtility.ToJson(command), IntPtr.Zero, 0, null, IntPtr.Zero); } }
private void Awake() { // Get a handle to the current object and make sure, that the object // doesn't get deleted by the garbage collector. We then use this // handle as client data for the native callbacks. This allows us to // retrieve the current address of the actual object during the // callback execution. GCHandleType.Pinned is not necessary, because we // are accessing the address only through the handle object, which gets // stored in a global handle table. this.gcHandle = GCHandle.Alloc(this); // Print the version of the vlUnitySDK. If this works, then we can be // quite certain, that other things also work. string version; string versionTimestamp; string versionHash; if (VLUnitySdk.GetVersionString(out version) && VLUnitySdk.GetVersionTimestampString(out versionTimestamp) && VLUnitySdk.GetVersionHashString(out versionHash)) { Debug.Log("[vlUnitySDK] v" + version + " (" + versionTimestamp + ", " + versionHash + ")"); } else { Debug.LogWarning("[vlUnitySDK] Failed to get version strings"); } // Construct the path to the directory with the tracking configurations, // if it wasn't specified explicitly if (String.IsNullOrEmpty(this.baseDir)) { #if UNITY_ANDROID && !UNITY_EDITOR this.baseDir = "file:///android_asset/VisionLib"; #else this.baseDir = Path.Combine( Application.streamingAssetsPath, "VisionLib"); #endif } // Construct the path to the Resources folder (the Resource folder is // only used by certain platforms) #if UNITY_ANDROID && !UNITY_EDITOR this.resourceDir = "file:///android_asset/VisionLib/Resources"; #else this.resourceDir = Path.Combine( Application.streamingAssetsPath, "VisionLib/Resources"); #endif // Create an AbstractApplication, which will manage the ActionPipe and // DataSet this.aap = new VLAbstractApplicationWrapper(); this.deviceInfo = this.aap.GetDeviceInfo(); // Set the path to the license file #if UNITY_ANDROID && !UNITY_EDITOR string absoluteLicenseFilePath = Path.Combine( "file:///android_asset/", this.licenseFile.path); #else string absoluteLicenseFilePath = Path.Combine( Application.streamingAssetsPath, this.licenseFile.path); #endif this.aap.SetLicenseFilePath(absoluteLicenseFilePath); // Add a log listener, which will write all VisionLib logs to the // Unity console this.logger = new VLLogger(); #if UNITY_2017_1_OR_NEWER // Unity 2017 with Mono .NET 4.6 as scripting runtime version can't // properly handle callbacks from external threads. Until this is // fixed, we need to buffer the log messages and fetch them from the // main thread inside the update function. this.logger.EnableLogBuffer(); #else this.logger.DisableLogBuffer(); #endif this.logger.SetLogLevel(this.logLevel); // Print the host ID. This ID is needed for generating a license file. string hostID; if (this.aap.GetHostID(out hostID)) { Debug.Log("[vlUnitySDK] HostID=" + hostID); } else { Debug.LogWarning("[vlUnitySDK] Failed to get host ID"); } // Many VisionLib features are implemented as plugins, which we need // to load first string pluginPath = Application.dataPath + Path.DirectorySeparatorChar + "Plugins"; // The plugins are in architecture specific sub-directories before the // deployment #if UNITY_EDITOR pluginPath += Path.DirectorySeparatorChar + VLUnitySdk.subDir; #endif this.aap.AutoLoadPlugins(pluginPath); // Create worker instance and register listeners for it this.worker = new VLWorker(this.aap); if (!this.worker.AddImageListener( dispatchImageCallbackDelegate, GCHandle.ToIntPtr(this.gcHandle))) { Debug.LogWarning("[vlUnitySDK] Failed to add image listener"); } if (!this.worker.AddExtrinsicDataListener( dispatchExtrinsicDataCallbackDelegate, GCHandle.ToIntPtr(this.gcHandle))) { Debug.LogWarning("[vlUnitySDK] Failed to add extrinsic data listener"); } if (!this.worker.AddIntrinsicDataListener( dispatchIntrinsicDataCallbackDelegate, GCHandle.ToIntPtr(this.gcHandle))) { Debug.LogWarning("[vlUnitySDK] Failed to add intrinsic data listener"); } if (!this.worker.AddTrackingStateListener( dispatchTrackingStateCallbackDelegate, GCHandle.ToIntPtr(this.gcHandle))) { Debug.LogWarning("[vlUnitySDK] Failed to add tracking state listener"); } if (!this.worker.AddPerformanceInfoListener( dispatchPerformanceInfoCallbackDelegate, GCHandle.ToIntPtr(this.gcHandle))) { Debug.LogWarning("[vlUnitySDK] Failed to add performance info listener"); } }