cactus-react-native 0.0.1 → 0.1.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (189) hide show
  1. package/LICENSE.txt +20 -0
  2. package/README.md +3 -1
  3. package/android/src/main/CMakeLists.txt +58 -23
  4. package/android/src/main/java/com/cactus/Cactus.java +484 -16
  5. package/android/src/main/java/com/cactus/LlamaContext.java +199 -0
  6. package/android/src/main/jni.cpp +325 -10
  7. package/android/src/main/jniLibs/arm64-v8a/libcactus.so +0 -0
  8. package/android/src/main/jniLibs/arm64-v8a/libcactus_v8.so +0 -0
  9. package/android/src/main/jniLibs/arm64-v8a/libcactus_v8_2.so +0 -0
  10. package/android/src/main/jniLibs/arm64-v8a/libcactus_v8_2_dotprod.so +0 -0
  11. package/android/src/main/jniLibs/arm64-v8a/libcactus_v8_2_dotprod_i8mm.so +0 -0
  12. package/android/src/main/jniLibs/arm64-v8a/libcactus_v8_2_i8mm.so +0 -0
  13. package/android/src/main/jniLibs/x86_64/libcactus.so +0 -0
  14. package/android/src/main/jniLibs/x86_64/libcactus_x86_64.so +0 -0
  15. package/android/src/newarch/java/com/cactus/CactusModule.java +79 -7
  16. package/android/src/oldarch/java/com/cactus/CactusModule.java +70 -0
  17. package/cactus-react-native.podspec +0 -3
  18. package/ios/CMakeLists.txt +58 -36
  19. package/ios/Cactus.mm +243 -2
  20. package/ios/CactusContext.h +22 -0
  21. package/ios/CactusContext.mm +176 -1
  22. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/cactus.h +92 -5
  23. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/cactus_ffi.h +268 -0
  24. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/chat.h +2 -0
  25. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/common.h +42 -51
  26. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/ggml-backend.h +4 -4
  27. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/ggml-common.h +12 -6
  28. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/ggml-cpp.h +1 -1
  29. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/ggml-cpu.h +5 -0
  30. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/ggml-impl.h +52 -18
  31. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/ggml-metal-impl.h +106 -14
  32. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/ggml-opt.h +49 -28
  33. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/ggml.h +87 -106
  34. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/llama-arch.h +16 -0
  35. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/llama-batch.h +2 -1
  36. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/llama-chat.h +7 -2
  37. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/llama-context.h +44 -33
  38. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/llama-cparams.h +1 -0
  39. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/llama-graph.h +83 -17
  40. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/llama-hparams.h +44 -2
  41. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/llama-kv-cache.h +407 -179
  42. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/llama-memory.h +13 -2
  43. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/llama-model-loader.h +5 -3
  44. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/llama-model-saver.h +37 -0
  45. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/llama-model.h +24 -2
  46. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/llama-vocab.h +6 -0
  47. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/llama.h +102 -142
  48. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/minja/chat-template.hpp +23 -11
  49. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/minja/minja.hpp +186 -127
  50. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Info.plist +0 -0
  51. package/ios/cactus.xcframework/ios-arm64/cactus.framework/cactus +0 -0
  52. package/ios/cactus.xcframework/ios-arm64/cactus.framework/ggml-llama.metallib +0 -0
  53. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/cactus.h +92 -5
  54. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/cactus_ffi.h +268 -0
  55. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/chat.h +2 -0
  56. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/common.h +42 -51
  57. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/ggml-backend.h +4 -4
  58. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/ggml-common.h +12 -6
  59. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/ggml-cpp.h +1 -1
  60. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/ggml-cpu.h +5 -0
  61. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/ggml-impl.h +52 -18
  62. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/ggml-metal-impl.h +106 -14
  63. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/ggml-opt.h +49 -28
  64. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/ggml.h +87 -106
  65. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/llama-arch.h +16 -0
  66. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/llama-batch.h +2 -1
  67. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/llama-chat.h +7 -2
  68. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/llama-context.h +44 -33
  69. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/llama-cparams.h +1 -0
  70. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/llama-graph.h +83 -17
  71. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/llama-hparams.h +44 -2
  72. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/llama-kv-cache.h +407 -179
  73. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/llama-memory.h +13 -2
  74. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/llama-model-loader.h +5 -3
  75. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/llama-model-saver.h +37 -0
  76. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/llama-model.h +24 -2
  77. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/llama-vocab.h +6 -0
  78. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/llama.h +102 -142
  79. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/minja/chat-template.hpp +23 -11
  80. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/minja/minja.hpp +186 -127
  81. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Info.plist +0 -0
  82. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/_CodeSignature/CodeResources +1 -1
  83. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/cactus +0 -0
  84. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/ggml-llama-sim.metallib +0 -0
  85. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/cactus.h +92 -5
  86. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/cactus_ffi.h +268 -0
  87. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/chat.h +2 -0
  88. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/common.h +42 -51
  89. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/ggml-backend.h +4 -4
  90. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/ggml-common.h +12 -6
  91. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/ggml-cpp.h +1 -1
  92. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/ggml-cpu.h +5 -0
  93. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/ggml-impl.h +52 -18
  94. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/ggml-metal-impl.h +106 -14
  95. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/ggml-opt.h +49 -28
  96. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/ggml.h +87 -106
  97. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/llama-arch.h +16 -0
  98. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/llama-batch.h +2 -1
  99. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/llama-chat.h +7 -2
  100. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/llama-context.h +44 -33
  101. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/llama-cparams.h +1 -0
  102. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/llama-graph.h +83 -17
  103. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/llama-hparams.h +44 -2
  104. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/llama-kv-cache.h +407 -179
  105. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/llama-memory.h +13 -2
  106. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/llama-model-loader.h +5 -3
  107. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/llama-model-saver.h +37 -0
  108. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/llama-model.h +24 -2
  109. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/llama-vocab.h +6 -0
  110. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/llama.h +102 -142
  111. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/minja/chat-template.hpp +23 -11
  112. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/minja/minja.hpp +186 -127
  113. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Info.plist +0 -0
  114. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/cactus +0 -0
  115. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/ggml-llama.metallib +0 -0
  116. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/cactus.h +92 -5
  117. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/cactus_ffi.h +268 -0
  118. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/chat.h +2 -0
  119. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/common.h +42 -51
  120. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/ggml-backend.h +4 -4
  121. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/ggml-common.h +12 -6
  122. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/ggml-cpp.h +1 -1
  123. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/ggml-cpu.h +5 -0
  124. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/ggml-impl.h +52 -18
  125. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/ggml-metal-impl.h +106 -14
  126. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/ggml-opt.h +49 -28
  127. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/ggml.h +87 -106
  128. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/llama-arch.h +16 -0
  129. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/llama-batch.h +2 -1
  130. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/llama-chat.h +7 -2
  131. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/llama-context.h +44 -33
  132. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/llama-cparams.h +1 -0
  133. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/llama-graph.h +83 -17
  134. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/llama-hparams.h +44 -2
  135. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/llama-kv-cache.h +407 -179
  136. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/llama-memory.h +13 -2
  137. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/llama-model-loader.h +5 -3
  138. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/llama-model-saver.h +37 -0
  139. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/llama-model.h +24 -2
  140. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/llama-vocab.h +6 -0
  141. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/llama.h +102 -142
  142. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/minja/chat-template.hpp +23 -11
  143. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/minja/minja.hpp +186 -127
  144. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Info.plist +0 -0
  145. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/_CodeSignature/CodeResources +1 -1
  146. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/cactus +0 -0
  147. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/ggml-llama-sim.metallib +0 -0
  148. package/lib/commonjs/NativeCactus.js +1 -0
  149. package/lib/commonjs/NativeCactus.js.map +1 -1
  150. package/lib/commonjs/index.js +112 -0
  151. package/lib/commonjs/index.js.map +1 -1
  152. package/lib/commonjs/tools.js +118 -0
  153. package/lib/commonjs/tools.js.map +1 -0
  154. package/lib/module/NativeCactus.js +3 -0
  155. package/lib/module/NativeCactus.js.map +1 -1
  156. package/lib/module/index.js +87 -1
  157. package/lib/module/index.js.map +1 -1
  158. package/lib/module/tools.js +110 -0
  159. package/lib/module/tools.js.map +1 -0
  160. package/lib/typescript/NativeCactus.d.ts +30 -1
  161. package/lib/typescript/NativeCactus.d.ts.map +1 -1
  162. package/lib/typescript/index.d.ts +21 -2
  163. package/lib/typescript/index.d.ts.map +1 -1
  164. package/lib/typescript/tools.d.ts +38 -0
  165. package/lib/typescript/tools.d.ts.map +1 -0
  166. package/package.json +6 -3
  167. package/src/NativeCactus.ts +62 -1
  168. package/src/index.ts +113 -2
  169. package/src/tools.ts +127 -0
  170. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/ggml-cpu-aarch64.h +0 -8
  171. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/ggml-cpu-impl.h +0 -531
  172. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/ggml-cpu-quants.h +0 -63
  173. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/ggml-cpu-traits.h +0 -38
  174. package/ios/cactus.xcframework/ios-arm64/cactus.framework/Headers/sgemm.h +0 -14
  175. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/ggml-cpu-aarch64.h +0 -8
  176. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/ggml-cpu-impl.h +0 -531
  177. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/ggml-cpu-quants.h +0 -63
  178. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/ggml-cpu-traits.h +0 -38
  179. package/ios/cactus.xcframework/ios-arm64_x86_64-simulator/cactus.framework/Headers/sgemm.h +0 -14
  180. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/ggml-cpu-aarch64.h +0 -8
  181. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/ggml-cpu-impl.h +0 -531
  182. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/ggml-cpu-quants.h +0 -63
  183. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/ggml-cpu-traits.h +0 -38
  184. package/ios/cactus.xcframework/tvos-arm64/cactus.framework/Headers/sgemm.h +0 -14
  185. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/ggml-cpu-aarch64.h +0 -8
  186. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/ggml-cpu-impl.h +0 -531
  187. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/ggml-cpu-quants.h +0 -63
  188. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/ggml-cpu-traits.h +0 -38
  189. package/ios/cactus.xcframework/tvos-arm64_x86_64-simulator/cactus.framework/Headers/sgemm.h +0 -14
@@ -220,10 +220,14 @@ public class LlamaContext {
220
220
  }
221
221
 
222
222
  public WritableMap completion(ReadableMap params) {
223
+ Log.d(NAME, "🔵 ANDROID: completion() called");
223
224
  if (!params.hasKey("prompt")) {
224
225
  throw new IllegalArgumentException("Missing required parameter: prompt");
225
226
  }
226
227
 
228
+ Log.d(NAME, "📝 ANDROID: prompt length = " + params.getString("prompt").length());
229
+ Log.d(NAME, "🧮 ANDROID: context ptr = " + this.context);
230
+
227
231
  double[][] logit_bias = new double[0][0];
228
232
  if (params.hasKey("logit_bias")) {
229
233
  ReadableArray logit_bias_array = params.getArray("logit_bias");
@@ -237,6 +241,7 @@ public class LlamaContext {
237
241
  }
238
242
  }
239
243
 
244
+ Log.d(NAME, "🚀 ANDROID: About to call doCompletion native method...");
240
245
  WritableMap result = doCompletion(
241
246
  this.context,
242
247
  // String prompt,
@@ -313,9 +318,12 @@ public class LlamaContext {
313
318
  params.hasKey("emit_partial_completion") ? params.getBoolean("emit_partial_completion") : false
314
319
  )
315
320
  );
321
+ Log.d(NAME, "✅ ANDROID: doCompletion returned successfully");
316
322
  if (result.hasKey("error")) {
323
+ Log.e(NAME, "❌ ANDROID: doCompletion returned error: " + result.getString("error"));
317
324
  throw new IllegalStateException(result.getString("error"));
318
325
  }
326
+ Log.d(NAME, "📤 ANDROID: completion() returning result");
319
327
  return result;
320
328
  }
321
329
 
@@ -381,6 +389,141 @@ public class LlamaContext {
381
389
  freeContext(context);
382
390
  }
383
391
 
392
+ // Multimodal methods
393
+ public boolean initMultimodal(String mmprojPath, boolean useGpu) {
394
+ return initMultimodal(this.context, mmprojPath, useGpu);
395
+ }
396
+
397
+ public boolean isMultimodalEnabled() {
398
+ return isMultimodalEnabled(this.context);
399
+ }
400
+
401
+ public boolean isMultimodalSupportVision() {
402
+ return isMultimodalSupportVision(this.context);
403
+ }
404
+
405
+ public boolean isMultimodalSupportAudio() {
406
+ return isMultimodalSupportAudio(this.context);
407
+ }
408
+
409
+ public void releaseMultimodal() {
410
+ releaseMultimodal(this.context);
411
+ }
412
+
413
+ public WritableMap multimodalCompletion(String prompt, ReadableArray mediaPaths, ReadableMap params) {
414
+ if (!params.hasKey("prompt")) {
415
+ params = Arguments.createMap();
416
+ ((WritableMap) params).putString("prompt", prompt);
417
+ }
418
+
419
+ String[] mediaPathsArray = new String[mediaPaths.size()];
420
+ for (int i = 0; i < mediaPaths.size(); i++) {
421
+ mediaPathsArray[i] = mediaPaths.getString(i);
422
+ }
423
+
424
+ double[][] logit_bias = new double[0][0];
425
+ if (params.hasKey("logit_bias")) {
426
+ ReadableArray logit_bias_array = params.getArray("logit_bias");
427
+ logit_bias = new double[logit_bias_array.size()][];
428
+ for (int i = 0; i < logit_bias_array.size(); i++) {
429
+ ReadableArray logit_bias_row = logit_bias_array.getArray(i);
430
+ logit_bias[i] = new double[logit_bias_row.size()];
431
+ for (int j = 0; j < logit_bias_row.size(); j++) {
432
+ logit_bias[i][j] = logit_bias_row.getDouble(j);
433
+ }
434
+ }
435
+ }
436
+
437
+ WritableMap result = doMultimodalCompletion(
438
+ this.context,
439
+ prompt,
440
+ mediaPathsArray,
441
+ params.hasKey("chat_format") ? params.getInt("chat_format") : 0,
442
+ params.hasKey("grammar") ? params.getString("grammar") : "",
443
+ params.hasKey("json_schema") ? params.getString("json_schema") : "",
444
+ params.hasKey("grammar_lazy") ? params.getBoolean("grammar_lazy") : false,
445
+ params.hasKey("grammar_triggers") ? params.getArray("grammar_triggers") : null,
446
+ params.hasKey("preserved_tokens") ? params.getArray("preserved_tokens") : null,
447
+ params.hasKey("temperature") ? (float) params.getDouble("temperature") : 0.7f,
448
+ params.hasKey("n_threads") ? params.getInt("n_threads") : 0,
449
+ params.hasKey("n_predict") ? params.getInt("n_predict") : -1,
450
+ params.hasKey("n_probs") ? params.getInt("n_probs") : 0,
451
+ params.hasKey("penalty_last_n") ? params.getInt("penalty_last_n") : 64,
452
+ params.hasKey("penalty_repeat") ? (float) params.getDouble("penalty_repeat") : 1.00f,
453
+ params.hasKey("penalty_freq") ? (float) params.getDouble("penalty_freq") : 0.00f,
454
+ params.hasKey("penalty_present") ? (float) params.getDouble("penalty_present") : 0.00f,
455
+ params.hasKey("mirostat") ? (float) params.getDouble("mirostat") : 0.00f,
456
+ params.hasKey("mirostat_tau") ? (float) params.getDouble("mirostat_tau") : 5.00f,
457
+ params.hasKey("mirostat_eta") ? (float) params.getDouble("mirostat_eta") : 0.10f,
458
+ params.hasKey("top_k") ? params.getInt("top_k") : 40,
459
+ params.hasKey("top_p") ? (float) params.getDouble("top_p") : 0.95f,
460
+ params.hasKey("min_p") ? (float) params.getDouble("min_p") : 0.05f,
461
+ params.hasKey("xtc_threshold") ? (float) params.getDouble("xtc_threshold") : 0.00f,
462
+ params.hasKey("xtc_probability") ? (float) params.getDouble("xtc_probability") : 0.00f,
463
+ params.hasKey("typical_p") ? (float) params.getDouble("typical_p") : 1.00f,
464
+ params.hasKey("seed") ? params.getInt("seed") : -1,
465
+ params.hasKey("stop") ? params.getArray("stop").toArrayList().toArray(new String[0]) : new String[0],
466
+ params.hasKey("ignore_eos") ? params.getBoolean("ignore_eos") : false,
467
+ logit_bias,
468
+ params.hasKey("dry_multiplier") ? (float) params.getDouble("dry_multiplier") : 0.00f,
469
+ params.hasKey("dry_base") ? (float) params.getDouble("dry_base") : 1.75f,
470
+ params.hasKey("dry_allowed_length") ? params.getInt("dry_allowed_length") : 2,
471
+ params.hasKey("dry_penalty_last_n") ? params.getInt("dry_penalty_last_n") : -1,
472
+ params.hasKey("top_n_sigma") ? (float) params.getDouble("top_n_sigma") : -1.0f,
473
+ params.hasKey("dry_sequence_breakers") ? params.getArray("dry_sequence_breakers").toArrayList().toArray(new String[0]) : new String[]{"\n", ":", "\"", "*"},
474
+ new PartialCompletionCallback(
475
+ this,
476
+ params.hasKey("emit_partial_completion") ? params.getBoolean("emit_partial_completion") : false
477
+ )
478
+ );
479
+ if (result.hasKey("error")) {
480
+ throw new IllegalStateException(result.getString("error"));
481
+ }
482
+ return result;
483
+ }
484
+
485
+ public WritableMap tokenize(String text, ReadableArray mediaPaths) {
486
+ String[] mediaPathsArray = new String[mediaPaths.size()];
487
+ for (int i = 0; i < mediaPaths.size(); i++) {
488
+ mediaPathsArray[i] = mediaPaths.getString(i);
489
+ }
490
+ WritableMap result = tokenize(this.context, text, mediaPathsArray);
491
+ return result;
492
+ }
493
+
494
+ // TTS/Vocoder methods
495
+ public boolean initVocoder(String vocoderModelPath) {
496
+ return initVocoder(this.context, vocoderModelPath);
497
+ }
498
+
499
+ public boolean isVocoderEnabled() {
500
+ return isVocoderEnabled(this.context);
501
+ }
502
+
503
+ public int getTTSType() {
504
+ return getTTSType(this.context);
505
+ }
506
+
507
+ public String getFormattedAudioCompletion(String speakerJsonStr, String textToSpeak) {
508
+ return getFormattedAudioCompletion(this.context, speakerJsonStr, textToSpeak);
509
+ }
510
+
511
+ public WritableArray getAudioCompletionGuideTokens(String textToSpeak) {
512
+ return getAudioCompletionGuideTokens(this.context, textToSpeak);
513
+ }
514
+
515
+ public WritableArray decodeAudioTokens(ReadableArray tokens) {
516
+ int[] toks = new int[tokens.size()];
517
+ for (int i = 0; i < tokens.size(); i++) {
518
+ toks[i] = (int) tokens.getDouble(i);
519
+ }
520
+ return decodeAudioTokens(this.context, toks);
521
+ }
522
+
523
+ public void releaseVocoder() {
524
+ releaseVocoder(this.context);
525
+ }
526
+
384
527
  static {
385
528
  Log.d(NAME, "Primary ABI: " + Build.SUPPORTED_ABIS[0]);
386
529
 
@@ -576,4 +719,60 @@ public class LlamaContext {
576
719
  protected static native void freeContext(long contextPtr);
577
720
  protected static native void setupLog(NativeLogCallback logCallback);
578
721
  protected static native void unsetLog();
722
+
723
+ // Multimodal native methods
724
+ protected static native boolean initMultimodal(long contextPtr, String mmprojPath, boolean useGpu);
725
+ protected static native boolean isMultimodalEnabled(long contextPtr);
726
+ protected static native boolean isMultimodalSupportVision(long contextPtr);
727
+ protected static native boolean isMultimodalSupportAudio(long contextPtr);
728
+ protected static native void releaseMultimodal(long contextPtr);
729
+ protected static native WritableMap doMultimodalCompletion(
730
+ long contextPtr,
731
+ String prompt,
732
+ String[] mediaPaths,
733
+ int chat_format,
734
+ String grammar,
735
+ String json_schema,
736
+ boolean grammar_lazy,
737
+ ReadableArray grammar_triggers,
738
+ ReadableArray preserved_tokens,
739
+ float temperature,
740
+ int n_threads,
741
+ int n_predict,
742
+ int n_probs,
743
+ int penalty_last_n,
744
+ float penalty_repeat,
745
+ float penalty_freq,
746
+ float penalty_present,
747
+ float mirostat,
748
+ float mirostat_tau,
749
+ float mirostat_eta,
750
+ int top_k,
751
+ float top_p,
752
+ float min_p,
753
+ float xtc_threshold,
754
+ float xtc_probability,
755
+ float typical_p,
756
+ int seed,
757
+ String[] stop,
758
+ boolean ignore_eos,
759
+ double[][] logit_bias,
760
+ float dry_multiplier,
761
+ float dry_base,
762
+ int dry_allowed_length,
763
+ int dry_penalty_last_n,
764
+ float top_n_sigma,
765
+ String[] dry_sequence_breakers,
766
+ PartialCompletionCallback partial_completion_callback
767
+ );
768
+ protected static native WritableMap tokenize(long contextPtr, String text, String[] mediaPaths);
769
+
770
+ // TTS/Vocoder native methods
771
+ protected static native boolean initVocoder(long contextPtr, String vocoderModelPath);
772
+ protected static native boolean isVocoderEnabled(long contextPtr);
773
+ protected static native int getTTSType(long contextPtr);
774
+ protected static native String getFormattedAudioCompletion(long contextPtr, String speakerJsonStr, String textToSpeak);
775
+ protected static native WritableArray getAudioCompletionGuideTokens(long contextPtr, String textToSpeak);
776
+ protected static native WritableArray decodeAudioTokens(long contextPtr, int[] tokens);
777
+ protected static native void releaseVocoder(long contextPtr);
579
778
  }
@@ -255,7 +255,7 @@ Java_com_cactus_LlamaContext_initContext(
255
255
  }
256
256
 
257
257
  const char *model_path_chars = env->GetStringUTFChars(model_path_str, nullptr);
258
- defaultParams.model = model_path_chars;
258
+ defaultParams.model.path = model_path_chars;
259
259
 
260
260
  const char *chat_template_chars = env->GetStringUTFChars(chat_template, nullptr);
261
261
  defaultParams.chat_template = chat_template_chars;
@@ -978,6 +978,134 @@ Java_com_cactus_LlamaContext_doCompletion(
978
978
  return reinterpret_cast<jobject>(result);
979
979
  }
980
980
 
981
+ // ===== MULTIMODAL COMPLETION SUPPORT =====
982
+ JNIEXPORT jobject JNICALL
983
+ Java_com_cactus_LlamaContext_doMultimodalCompletion(
984
+ JNIEnv *env, jobject thiz, jlong context_ptr, jstring prompt, jobjectArray media_paths,
985
+ jint chat_format, jstring grammar, jstring json_schema, jboolean grammar_lazy,
986
+ jobject grammar_triggers, jobject preserved_tokens, jfloat temperature, jint n_threads,
987
+ jint n_predict, jint n_probs, jint penalty_last_n, jfloat penalty_repeat,
988
+ jfloat penalty_freq, jfloat penalty_present, jfloat mirostat, jfloat mirostat_tau,
989
+ jfloat mirostat_eta, jint top_k, jfloat top_p, jfloat min_p, jfloat xtc_threshold,
990
+ jfloat xtc_probability, jfloat typical_p, jint seed, jobjectArray stop,
991
+ jboolean ignore_eos, jobjectArray logit_bias, jfloat dry_multiplier, jfloat dry_base,
992
+ jint dry_allowed_length, jint dry_penalty_last_n, jfloat top_n_sigma,
993
+ jobjectArray dry_sequence_breakers, jobject partial_completion_callback) {
994
+
995
+ UNUSED(thiz);
996
+ auto llama = context_map[(long) context_ptr];
997
+
998
+ if (!llama->isMultimodalEnabled()) {
999
+ auto result = createWriteableMap(env);
1000
+ putString(env, result, "error", "Multimodal is not enabled");
1001
+ return reinterpret_cast<jobject>(result);
1002
+ }
1003
+
1004
+ // Set all parameters (same as regular doCompletion)
1005
+ const char *prompt_chars = env->GetStringUTFChars(prompt, nullptr);
1006
+ llama->params.prompt = prompt_chars;
1007
+ llama->params.sampling.seed = seed == -1 ? LLAMA_DEFAULT_SEED : seed;
1008
+ llama->params.cpuparams.n_threads = n_threads;
1009
+ llama->params.n_predict = n_predict;
1010
+ llama->params.sampling.ignore_eos = ignore_eos;
1011
+
1012
+ auto & sparams = llama->params.sampling;
1013
+ sparams.temp = temperature;
1014
+ sparams.n_probs = n_probs;
1015
+ sparams.penalty_last_n = penalty_last_n;
1016
+ sparams.penalty_repeat = penalty_repeat;
1017
+ sparams.penalty_freq = penalty_freq;
1018
+ sparams.penalty_present = penalty_present;
1019
+ sparams.mirostat = mirostat;
1020
+ sparams.mirostat_tau = mirostat_tau;
1021
+ sparams.mirostat_eta = mirostat_eta;
1022
+ sparams.top_k = top_k;
1023
+ sparams.top_p = top_p;
1024
+ sparams.min_p = min_p;
1025
+ sparams.xtc_threshold = xtc_threshold;
1026
+ sparams.xtc_probability = xtc_probability;
1027
+ sparams.typ_p = typical_p;
1028
+
1029
+ // Convert media paths
1030
+ std::vector<std::string> media_paths_vector;
1031
+ if (media_paths != nullptr) {
1032
+ jsize media_paths_len = env->GetArrayLength(media_paths);
1033
+ for (jsize i = 0; i < media_paths_len; i++) {
1034
+ jstring media_path = (jstring) env->GetObjectArrayElement(media_paths, i);
1035
+ if (media_path != nullptr) {
1036
+ const char *media_path_chars = env->GetStringUTFChars(media_path, nullptr);
1037
+ media_paths_vector.push_back(std::string(media_path_chars));
1038
+ env->ReleaseStringUTFChars(media_path, media_path_chars);
1039
+ env->DeleteLocalRef(media_path);
1040
+ }
1041
+ }
1042
+ }
1043
+
1044
+ // Initialize sampling and begin completion with media
1045
+ if (!llama->initSampling()) {
1046
+ auto result = createWriteableMap(env);
1047
+ putString(env, result, "error", "Failed to initialize sampling");
1048
+ env->ReleaseStringUTFChars(prompt, prompt_chars);
1049
+ return reinterpret_cast<jobject>(result);
1050
+ }
1051
+
1052
+ llama->beginCompletion();
1053
+
1054
+ try {
1055
+ llama->loadPrompt(media_paths_vector); // Use media-aware loadPrompt
1056
+ } catch (const std::exception& e) {
1057
+ auto result = createWriteableMap(env);
1058
+ putString(env, result, "error", e.what());
1059
+ env->ReleaseStringUTFChars(prompt, prompt_chars);
1060
+ return reinterpret_cast<jobject>(result);
1061
+ }
1062
+
1063
+ // Rest of completion logic (same as doCompletion but simplified for key parts)
1064
+ size_t sent_count = 0;
1065
+ while (llama->has_next_token && !llama->is_interrupted) {
1066
+ const cactus::completion_token_output token_with_probs = llama->doCompletion();
1067
+ if (token_with_probs.tok == -1 || llama->incomplete) {
1068
+ continue;
1069
+ }
1070
+
1071
+ const std::string token_text = common_token_to_piece(llama->ctx, token_with_probs.tok);
1072
+ size_t pos = std::min(sent_count, llama->generated_text.size());
1073
+ const std::string str_test = llama->generated_text.substr(pos);
1074
+
1075
+ size_t stop_pos = llama->findStoppingStrings(str_test, token_text.size(), cactus::STOP_FULL);
1076
+
1077
+ if (stop_pos == std::string::npos || (!llama->has_next_token && stop_pos > 0)) {
1078
+ const std::string to_send = llama->generated_text.substr(pos, std::string::npos);
1079
+ sent_count += to_send.size();
1080
+
1081
+ if (partial_completion_callback != nullptr) {
1082
+ auto tokenResult = createWriteableMap(env);
1083
+ putString(env, tokenResult, "token", to_send.c_str());
1084
+
1085
+ jclass cb_class = env->GetObjectClass(partial_completion_callback);
1086
+ jmethodID onPartialCompletion = env->GetMethodID(cb_class, "onPartialCompletion", "(Lcom/facebook/react/bridge/WritableMap;)V");
1087
+ env->CallVoidMethod(partial_completion_callback, onPartialCompletion, tokenResult);
1088
+ }
1089
+ }
1090
+ }
1091
+
1092
+ llama->is_predicting = false;
1093
+
1094
+ auto result = createWriteableMap(env);
1095
+ putString(env, result, "text", llama->generated_text.c_str());
1096
+ putInt(env, result, "tokens_predicted", llama->num_tokens_predicted);
1097
+ putInt(env, result, "tokens_evaluated", llama->num_prompt_tokens);
1098
+ putInt(env, result, "truncated", llama->truncated);
1099
+ putInt(env, result, "stopped_eos", llama->stopped_eos);
1100
+ putInt(env, result, "stopped_word", llama->stopped_word);
1101
+ putInt(env, result, "stopped_limit", llama->stopped_limit);
1102
+ putString(env, result, "stopping_word", llama->stopping_word.c_str());
1103
+ putInt(env, result, "tokens_cached", llama->n_past);
1104
+
1105
+ env->ReleaseStringUTFChars(prompt, prompt_chars);
1106
+ return reinterpret_cast<jobject>(result);
1107
+ }
1108
+
981
1109
  JNIEXPORT void JNICALL
982
1110
  Java_com_cactus_LlamaContext_stopCompletion(
983
1111
  JNIEnv *env, jobject thiz, jlong context_ptr) {
@@ -998,21 +1126,58 @@ Java_com_cactus_LlamaContext_isPredicting(
998
1126
 
999
1127
  JNIEXPORT jobject JNICALL
1000
1128
  Java_com_cactus_LlamaContext_tokenize(
1001
- JNIEnv *env, jobject thiz, jlong context_ptr, jstring text) {
1129
+ JNIEnv *env, jobject thiz, jlong context_ptr, jstring text, jobjectArray media_paths) {
1002
1130
  UNUSED(thiz);
1003
1131
  auto llama = context_map[(long) context_ptr];
1004
1132
 
1005
1133
  const char *text_chars = env->GetStringUTFChars(text, nullptr);
1134
+
1135
+ std::vector<std::string> media_paths_vector;
1136
+ if (media_paths != nullptr) {
1137
+ jsize media_paths_len = env->GetArrayLength(media_paths);
1138
+ for (jsize i = 0; i < media_paths_len; i++) {
1139
+ jstring media_path = (jstring) env->GetObjectArrayElement(media_paths, i);
1140
+ if (media_path != nullptr) {
1141
+ const char *media_path_chars = env->GetStringUTFChars(media_path, nullptr);
1142
+ media_paths_vector.push_back(std::string(media_path_chars));
1143
+ env->ReleaseStringUTFChars(media_path, media_path_chars);
1144
+ env->DeleteLocalRef(media_path);
1145
+ }
1146
+ }
1147
+ }
1006
1148
 
1007
- const std::vector<llama_token> toks = common_tokenize(
1008
- llama->ctx,
1009
- text_chars,
1010
- false
1011
- );
1149
+ cactus::cactus_tokenize_result tokenize_result = llama->tokenize(text_chars, media_paths_vector);
1012
1150
 
1013
- jobject result = createWritableArray(env);
1014
- for (const auto &tok : toks) {
1015
- pushInt(env, result, tok);
1151
+ auto result = createWriteableMap(env);
1152
+
1153
+ // Add tokens array
1154
+ auto tokens_array = createWritableArray(env);
1155
+ for (const auto &tok : tokenize_result.tokens) {
1156
+ pushInt(env, tokens_array, tok);
1157
+ }
1158
+ putArray(env, result, "tokens", tokens_array);
1159
+
1160
+ // Add media info if present
1161
+ putBoolean(env, result, "has_media", tokenize_result.has_media);
1162
+
1163
+ if (tokenize_result.has_media) {
1164
+ auto bitmap_hashes_array = createWritableArray(env);
1165
+ for (const auto &hash : tokenize_result.bitmap_hashes) {
1166
+ pushString(env, bitmap_hashes_array, hash.c_str());
1167
+ }
1168
+ putArray(env, result, "bitmap_hashes", bitmap_hashes_array);
1169
+
1170
+ auto chunk_pos_array = createWritableArray(env);
1171
+ for (const auto &pos : tokenize_result.chunk_pos) {
1172
+ pushInt(env, chunk_pos_array, static_cast<int>(pos));
1173
+ }
1174
+ putArray(env, result, "chunk_pos", chunk_pos_array);
1175
+
1176
+ auto chunk_pos_media_array = createWritableArray(env);
1177
+ for (const auto &pos : tokenize_result.chunk_pos_media) {
1178
+ pushInt(env, chunk_pos_media_array, static_cast<int>(pos));
1179
+ }
1180
+ putArray(env, result, "chunk_pos_media", chunk_pos_media_array);
1016
1181
  }
1017
1182
 
1018
1183
  env->ReleaseStringUTFChars(text, text_chars);
@@ -1179,6 +1344,156 @@ Java_com_cactus_LlamaContext_freeContext(
1179
1344
  delete llama;
1180
1345
  }
1181
1346
 
1347
+ // ===== MULTIMODAL SUPPORT =====
1348
+ JNIEXPORT jboolean JNICALL
1349
+ Java_com_cactus_LlamaContext_initMultimodal(
1350
+ JNIEnv *env, jobject thiz, jlong context_ptr, jstring mmproj_path, jboolean use_gpu) {
1351
+ UNUSED(thiz);
1352
+ auto llama = context_map[(long) context_ptr];
1353
+
1354
+ const char *mmproj_path_chars = env->GetStringUTFChars(mmproj_path, nullptr);
1355
+ bool result = llama->initMultimodal(mmproj_path_chars, use_gpu);
1356
+ env->ReleaseStringUTFChars(mmproj_path, mmproj_path_chars);
1357
+
1358
+ return result;
1359
+ }
1360
+
1361
+ JNIEXPORT jboolean JNICALL
1362
+ Java_com_cactus_LlamaContext_isMultimodalEnabled(
1363
+ JNIEnv *env, jobject thiz, jlong context_ptr) {
1364
+ UNUSED(env);
1365
+ UNUSED(thiz);
1366
+ auto llama = context_map[(long) context_ptr];
1367
+ return llama->isMultimodalEnabled();
1368
+ }
1369
+
1370
+ JNIEXPORT jboolean JNICALL
1371
+ Java_com_cactus_LlamaContext_isMultimodalSupportVision(
1372
+ JNIEnv *env, jobject thiz, jlong context_ptr) {
1373
+ UNUSED(env);
1374
+ UNUSED(thiz);
1375
+ auto llama = context_map[(long) context_ptr];
1376
+ return llama->isMultimodalSupportVision();
1377
+ }
1378
+
1379
+ JNIEXPORT jboolean JNICALL
1380
+ Java_com_cactus_LlamaContext_isMultimodalSupportAudio(
1381
+ JNIEnv *env, jobject thiz, jlong context_ptr) {
1382
+ UNUSED(env);
1383
+ UNUSED(thiz);
1384
+ auto llama = context_map[(long) context_ptr];
1385
+ return llama->isMultimodalSupportAudio();
1386
+ }
1387
+
1388
+ JNIEXPORT void JNICALL
1389
+ Java_com_cactus_LlamaContext_releaseMultimodal(
1390
+ JNIEnv *env, jobject thiz, jlong context_ptr) {
1391
+ UNUSED(env);
1392
+ UNUSED(thiz);
1393
+ auto llama = context_map[(long) context_ptr];
1394
+ llama->releaseMultimodal();
1395
+ }
1396
+
1397
+ // ===== TTS/VOCODER SUPPORT =====
1398
+ JNIEXPORT jboolean JNICALL
1399
+ Java_com_cactus_LlamaContext_initVocoder(
1400
+ JNIEnv *env, jobject thiz, jlong context_ptr, jstring vocoder_model_path) {
1401
+ UNUSED(thiz);
1402
+ auto llama = context_map[(long) context_ptr];
1403
+
1404
+ const char *vocoder_path_chars = env->GetStringUTFChars(vocoder_model_path, nullptr);
1405
+ bool result = llama->initVocoder(vocoder_path_chars);
1406
+ env->ReleaseStringUTFChars(vocoder_model_path, vocoder_path_chars);
1407
+
1408
+ return result;
1409
+ }
1410
+
1411
+ JNIEXPORT jboolean JNICALL
1412
+ Java_com_cactus_LlamaContext_isVocoderEnabled(
1413
+ JNIEnv *env, jobject thiz, jlong context_ptr) {
1414
+ UNUSED(env);
1415
+ UNUSED(thiz);
1416
+ auto llama = context_map[(long) context_ptr];
1417
+ return llama->isVocoderEnabled();
1418
+ }
1419
+
1420
+ JNIEXPORT jint JNICALL
1421
+ Java_com_cactus_LlamaContext_getTTSType(
1422
+ JNIEnv *env, jobject thiz, jlong context_ptr) {
1423
+ UNUSED(env);
1424
+ UNUSED(thiz);
1425
+ auto llama = context_map[(long) context_ptr];
1426
+ return static_cast<jint>(llama->getTTSType());
1427
+ }
1428
+
1429
+ JNIEXPORT jstring JNICALL
1430
+ Java_com_cactus_LlamaContext_getFormattedAudioCompletion(
1431
+ JNIEnv *env, jobject thiz, jlong context_ptr, jstring speaker_json_str, jstring text_to_speak) {
1432
+ UNUSED(thiz);
1433
+ auto llama = context_map[(long) context_ptr];
1434
+
1435
+ const char *speaker_chars = env->GetStringUTFChars(speaker_json_str, nullptr);
1436
+ const char *text_chars = env->GetStringUTFChars(text_to_speak, nullptr);
1437
+
1438
+ std::string result = llama->getFormattedAudioCompletion(speaker_chars, text_chars);
1439
+
1440
+ env->ReleaseStringUTFChars(speaker_json_str, speaker_chars);
1441
+ env->ReleaseStringUTFChars(text_to_speak, text_chars);
1442
+
1443
+ return env->NewStringUTF(result.c_str());
1444
+ }
1445
+
1446
+ JNIEXPORT jobject JNICALL
1447
+ Java_com_cactus_LlamaContext_getAudioCompletionGuideTokens(
1448
+ JNIEnv *env, jobject thiz, jlong context_ptr, jstring text_to_speak) {
1449
+ UNUSED(thiz);
1450
+ auto llama = context_map[(long) context_ptr];
1451
+
1452
+ const char *text_chars = env->GetStringUTFChars(text_to_speak, nullptr);
1453
+ std::vector<llama_token> tokens = llama->getAudioCompletionGuideTokens(text_chars);
1454
+ env->ReleaseStringUTFChars(text_to_speak, text_chars);
1455
+
1456
+ jobject result = createWritableArray(env);
1457
+ for (const auto &token : tokens) {
1458
+ pushInt(env, result, token);
1459
+ }
1460
+
1461
+ return result;
1462
+ }
1463
+
1464
+ JNIEXPORT jobject JNICALL
1465
+ Java_com_cactus_LlamaContext_decodeAudioTokens(
1466
+ JNIEnv *env, jobject thiz, jlong context_ptr, jintArray tokens) {
1467
+ UNUSED(thiz);
1468
+ auto llama = context_map[(long) context_ptr];
1469
+
1470
+ jsize tokens_len = env->GetArrayLength(tokens);
1471
+ jint *tokens_ptr = env->GetIntArrayElements(tokens, 0);
1472
+ std::vector<llama_token> token_vector;
1473
+ for (int i = 0; i < tokens_len; i++) {
1474
+ token_vector.push_back(tokens_ptr[i]);
1475
+ }
1476
+ env->ReleaseIntArrayElements(tokens, tokens_ptr, 0);
1477
+
1478
+ std::vector<float> audio_data = llama->decodeAudioTokens(token_vector);
1479
+
1480
+ jobject result = createWritableArray(env);
1481
+ for (const auto &sample : audio_data) {
1482
+ pushDouble(env, result, static_cast<double>(sample));
1483
+ }
1484
+
1485
+ return result;
1486
+ }
1487
+
1488
+ JNIEXPORT void JNICALL
1489
+ Java_com_cactus_LlamaContext_releaseVocoder(
1490
+ JNIEnv *env, jobject thiz, jlong context_ptr) {
1491
+ UNUSED(env);
1492
+ UNUSED(thiz);
1493
+ auto llama = context_map[(long) context_ptr];
1494
+ llama->releaseVocoder();
1495
+ }
1496
+
1182
1497
  struct log_callback_context {
1183
1498
  JavaVM *jvm;
1184
1499
  jobject callback;