ARToolkit: Load and Unload Markers

Hi there!

I’m working on a project that have a lot of NFT markers (40+), which are used in sets of 8, and I’m trying to load/unload them by demand, instead of having all them loaded from start (it takes a lot on Android devices in that scenario) to speed up startup process.

I can load them the fist time and unload them, but the time I try to load a new set (even the previously unloaded) Unity crashes. The output error on the editor.log is:

ARController (native): [error]Loading /Users/sam/ScanProject/Assets/StreamingAssets/nftmarker01/nftmarker01.fset.

### Surface No.1 ###
  Read ImageSet.
Imageset contains 17 images.
    end.
  Read FeatureSet.
    end.
ARController (native): [info]First NFT marker added; enabling NFT marker detection.
ARController (native): [info]Added marker (UID=9), total markers loaded: 1.
ARController (native): [error]Loading /Users/sam/ScanProject/Assets/StreamingAssets/nftmarker02/nftmarker02.fset.

### Surface No.1 ###
  Read ImageSet.
Imageset contains 17 images.
    end.
  Read FeatureSet.
    end.
ARController (native): [info]Added marker (UID=10), total markers loaded: 2.
ARController (native): [error]Loading /Users/sam/ScanProject/Assets/StreamingAssets/nftmarker03/nftmarker03.fset.

### Surface No.1 ###
  Read ImageSet.
Imageset contains 7 images.
    end.
  Read FeatureSet.
    end.

ARController (native): [info]Added marker (UID=11), total markers loaded: 3.
ARController (native): [info]Loading NFT data
ARController (native): [info]Reading /Users/sam/ScanProject/Assets/StreamingAssets/nftmarker01/nftmarker01.fset3
ARController (native): [info]  Assigned page no. 0.
ARController (native): [info]Done
ARController (native): [info]Reading /Users/sam/ScanProject/Assets/StreamingAssets/nftmarker02/nftmarker02.fset3
ARController (native): [info]  Assigned page no. 1.
ARController (native): [info]Done
ARController (native): [info]Reading /Users/sam/ScanProject/Assets/StreamingAssets/nftmarker03/nftmarker03.fset3
ARController (native): [info]  Assigned page no. 2.
ARController (native): [info]Done
points-573
libc++abi.dylib: terminating with uncaught exception of type vision::Exception: ID already exists
Unity/TreeEditor/Editor/UnityEditor.TreeEditor.dll.mdb doesn't match image /Applications/Unity/Unity.app/Contents/UnityExtensions/Unity/TreeEditor/Editor/UnityEditor.TreeEditor.dll
Stacktrace:

  at (wrapper managed-to-native) ARNativePlugin.arwUpdateAR () <IL 0x00008, 0x000be>
  at (wrapper managed-to-native) ARNativePlugin.arwUpdateAR () <IL 0x00008, 0x000be>
  at PluginFunctions.arwUpdateAR () [0x00011] in /Users/sam/ScanProject/Assets/ARToolKit5-Unity/Scripts/PluginFunctions.cs:184
  at ARController.UpdateAR () [0x00896] in /Users/sam/ScanProject/Assets/ARToolKit5-Unity/Scripts/ARController.cs:1538
  at ARController.Update () [0x00027] in /Users/sam/ScanProject/Assets/ARToolKit5-Unity/Scripts/ARController.cs:582
  at (wrapper runtime-invoke) object.runtime_invoke_void__this__ (object,intptr,intptr,intptr) <IL 0x0001c, 0x000f9>

Native stacktrace:

   0   libsystem_kernel.dylib              0x00007fff972eaf06 __pthread_kill + 10
   1   libsystem_c.dylib                   0x00007fff977736e7 abort + 129
   2   libc++abi.dylib                     0x00007fff87a91f81 __cxa_bad_cast + 0
   3   libc++abi.dylib                     0x00007fff87ab7a2f _ZL25default_terminate_handlerv + 243
   4   libobjc.A.dylib                     0x00007fff8a5986c3 _ZL15_objc_terminatev + 124
   5   libc++abi.dylib                     0x00007fff87ab519e _ZSt11__terminatePFvvE + 8
   6   libc++abi.dylib                     0x00007fff87ab4c12 _ZN10__cxxabiv1L22exception_cleanup_funcE19_Unwind_Reason_CodeP17_Unwind_Exception + 0
   7   ARWrapper                           0x00000001316a6df5 _ZN6vision14VisualDatabaseINS_14FREAKExtractorENS_18BinaryFeatureStoreENS_20BinaryFeatureMatcherILi96EEEE11addKeyframeENSt3__110shared_ptrINS_8KeyframeILi96EEEEEi + 183
   8   ARWrapper                           0x00000001316a66c6 _ZN6vision20VisualDatabaseFacade30addFreakFeaturesAndDescriptorsERKNSt3__16vectorINS_12FeaturePointENS1_9allocatorIS3_EEEERKNS2_IhNS4_IhEEEERKNS2_INS_7Point3dIfEENS4_ISE_EEEEmmi + 266
   9   ARWrapper                           0x000000013168b28d kpmSetRefDataSet + 1440
   10  ARWrapper                           0x000000013167e4af _ZN12ARController11loadNFTDataEv + 407
   11  ARWrapper                           0x000000013167dc69 _ZN12ARController6updateEv + 1087
   12  ARWrapper                           0x00000001316807ab arwUpdateAR + 21
   13  ???                                 0x00000001124037fe 0x0 + 4601165822
   14  ???                                 0x0000000112403714 0x0 + 4601165588
   15  ???                                 0x0000000112402c80 0x0 + 4601162880
   16  ???                                 0x00000001121a0d8a 0x0 + 4598664586
   17  ???                                 0x0000000111c8038a 0x0 + 4593288074
   18  libmono.0.dylib                     0x0000000109bcd17a mono_get_runtime_build_info + 3654
   19  libmono.0.dylib                     0x0000000109cf7416 mono_runtime_invoke + 117
   20  Unity                               0x0000000101163505 _ZN25ScriptingInvocationNoArgs6InvokeEPP13MonoException + 117
   21  Unity                               0x0000000101163489 _ZN25ScriptingInvocationNoArgs6InvokeEv + 25
   22  Unity                               0x000000010113ad57 _ZN13MonoBehaviour16CallUpdateMethodEi + 839
   23  Unity                               0x0000000100d2a87c _ZN20BaseBehaviourManager12CommonUpdateI16BehaviourManagerEEvv + 508
   24  Unity                               0x000000010101508c _Z10PlayerLoopbbP10IHookEvent + 1660
   25  Unity                               0x00000001019fbfe2 _ZN11Application11UpdateSceneEb + 722
   26  Unity                               0x00000001019f94b9 _ZN11Application19UpdateSceneIfNeededEv + 89
   27  Unity                               0x00000001019f8b47 _ZN11Application9TickTimerEv + 2967
   28  Foundation                          0x00007fff92c70d6c __NSFireTimer + 95
   29  CoreFoundation                      0x00007fff8cc6db94 __CFRUNLOOP_IS_CALLING_OUT_TO_A_TIMER_CALLBACK_FUNCTION__ + 20
   30  CoreFoundation                      0x00007fff8cc6d823 __CFRunLoopDoTimer + 1075
   31  CoreFoundation                      0x00007fff8cc6d37a __CFRunLoopDoTimers + 298
   32  CoreFoundation                      0x00007fff8cc64871 __CFRunLoopRun + 1841
   33  CoreFoundation                      0x00007fff8cc63ed8 CFRunLoopRunSpecific + 296
   34  HIToolbox                           0x00007fff89485935 RunCurrentEventLoopInMode + 235
   35  HIToolbox                           0x00007fff89485677 ReceiveNextEventCommon + 184
   36  HIToolbox                           0x00007fff894855af _BlockUntilNextEventMatchingListInModeWithFilter + 71
   37  AppKit                              0x00007fff8b2f7efa _DPSNextEvent + 1067
   38  AppKit                              0x00007fff8b2f732a -[NSApplication _nextEventMatchingEventMask:untilDate:inMode:dequeue:] + 454
   39  AppKit                              0x00007fff8b2ebe84 -[NSApplication run] + 682
   40  AppKit                              0x00007fff8b2b546c NSApplicationMain + 1176
   41  Unity                               0x0000000101c5e139 _Z10EditorMainiPPKc + 1401
   42  Unity                               0x0000000101c5e7f9 main + 9
   43  Unity                               0x0000000100002504 start + 52

ARMarkers are created in runtime and work properly. They are destroyed way before the second creation process.

This is the code I use to build markers and unload/load them:

using UnityEngine;
using System.Collections;

public class MarkerBuilder : MonoBehaviour {

   public string[] names; // <----- contains the names of the desired markers
   public ARMarker[] markers; // <------- Markers created. They are added as new component in the same object (this)


   public void LoadAll() {
      markers = new ARMarker[names.Length];

      for (int i = 0; i < names.Length; i++) {
         if (markers  *!= null) {*

markers .Load ();
continue;
}

ARMarker newMarker = this.gameObject.AddComponent ();
newMarker.Tag = “marker” + i.ToString();
newMarker.MarkerType = MarkerType.NFT;
newMarker.NFTDataName = names*;*

ARTrackedObject trackedObject = new GameObject (names ).AddComponent ();
trackedObject.MarkerTag = newMarker.NFTDataName;

newMarker.Load ();

markers = newMarker;
}

}

public void UnloadAll() {
PluginFunctions.arwRemoveAllMarkers (); // ← Nothing changes with this

for (int i = 0; i < markers.Length; i++) {
markers .Unload ();
}

}
}

Thanks everyone!

Hello any news on this topic?
I need to do a similar thing, although it’s with more markers loading sets of 40 at a time.