├── Library ├── BuildPlayer.prefs ├── FailedAssetImports.txt ├── AssetImportState ├── LibraryFormatVersion.txt ├── ScriptMapper ├── expandedItems ├── ShaderCache.db ├── assetDatabase3 ├── AnnotationManager ├── AssetServerCacheV3 ├── AssetVersioning.db ├── CurrentLayout.dwlt ├── MonoManager.asset ├── BuildSettings.asset ├── ProjectSettings.asset ├── EditorUserSettings.asset ├── LastSceneManagerSetup.txt ├── InspectorExpandedItems.asset └── EditorUserBuildSettings.asset ├── native └── Android │ └── UnityHelper │ ├── settings.gradle │ ├── app │ ├── src │ │ ├── main │ │ │ ├── res │ │ │ │ ├── values │ │ │ │ │ ├── strings.xml │ │ │ │ │ └── styles.xml │ │ │ │ ├── drawable-hdpi │ │ │ │ │ └── ic_launcher.png │ │ │ │ ├── drawable-mdpi │ │ │ │ │ └── ic_launcher.png │ │ │ │ ├── drawable-xhdpi │ │ │ │ │ └── ic_launcher.png │ │ │ │ └── drawable-xxhdpi │ │ │ │ │ └── ic_launcher.png │ │ │ ├── AndroidManifest.xml │ │ │ └── java │ │ │ │ └── ai │ │ │ │ └── api │ │ │ │ └── unityhelper │ │ │ │ ├── RecognitionResultObject.java │ │ │ │ ├── RecognizerChecker.java │ │ │ │ └── RecognitionHelper.java │ │ └── androidTest │ │ │ └── java │ │ │ └── ai │ │ │ └── api │ │ │ └── unityhelper │ │ │ └── ApplicationTest.java │ ├── proguard-rules.pro │ └── build.gradle │ ├── build.gradle │ ├── gradle.properties │ ├── gradlew.bat │ └── gradlew ├── ProjectSettings ├── ProjectVersion.txt ├── AudioManager.asset ├── InputManager.asset ├── NavMeshAreas.asset ├── TagManager.asset ├── TimeManager.asset ├── EditorSettings.asset ├── NavMeshLayers.asset ├── NetworkManager.asset ├── DynamicsManager.asset ├── GraphicsSettings.asset ├── Physics2DSettings.asset ├── ProjectSettings.asset ├── QualitySettings.asset ├── UnityAdsSettings.asset ├── ClusterInputManager.asset ├── EditorBuildSettings.asset └── UnityConnectSettings.asset ├── docs └── images │ ├── bundle.png │ ├── buttonOnClick.png │ ├── create_script.png │ └── runningSample.png ├── Assets ├── Audio │ └── beep.wav.wav ├── ApiAiSDK │ ├── lib │ │ ├── ApiAiSDK.dll │ │ └── fastJSON.dll │ ├── AndroidRecognitionResult.cs │ ├── ResultWrapper.cs │ ├── AndroidRecognizer.cs │ └── ApiAiUnity.cs ├── AssetStoreTools │ ├── Labels.asset │ └── Editor │ │ ├── icon.png │ │ ├── AssetStoreTools.dll │ │ ├── DroidSansMono.ttf │ │ └── AssetStoreToolsExtra.dll ├── Examples │ ├── ServiceSample.unity │ └── ApiAiModule.cs ├── Plugins │ └── Android │ │ ├── libs │ │ └── app.jar │ │ └── AndroidManifest.xml └── README.md ├── .gitignore ├── CONTRIBUTING.md ├── Assembly-CSharp.csproj ├── Assembly-CSharp-vs.csproj ├── api-ai-unity-example-csharp.sln ├── api-ai-unity-example.sln ├── LICENSE └── README.md /Library/BuildPlayer.prefs: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /Library/FailedAssetImports.txt: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /Library/AssetImportState: -------------------------------------------------------------------------------- 1 | 27;0;196609;-1 -------------------------------------------------------------------------------- /native/Android/UnityHelper/settings.gradle: -------------------------------------------------------------------------------- 1 | include ':app' 2 | -------------------------------------------------------------------------------- /ProjectSettings/ProjectVersion.txt: -------------------------------------------------------------------------------- 1 | m_EditorVersion: 5.3.3f1 2 | m_StandardAssetsVersion: 0 3 | -------------------------------------------------------------------------------- /Library/LibraryFormatVersion.txt: -------------------------------------------------------------------------------- 1 | unityRebuildLibraryVersion: 11 2 | unityForwardCompatibleVersion: 40 3 | -------------------------------------------------------------------------------- /Library/ScriptMapper: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/Library/ScriptMapper -------------------------------------------------------------------------------- /Library/expandedItems: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/Library/expandedItems -------------------------------------------------------------------------------- /Library/ShaderCache.db: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/Library/ShaderCache.db -------------------------------------------------------------------------------- /Library/assetDatabase3: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/Library/assetDatabase3 -------------------------------------------------------------------------------- /docs/images/bundle.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/docs/images/bundle.png -------------------------------------------------------------------------------- /Assets/Audio/beep.wav.wav: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/Assets/Audio/beep.wav.wav -------------------------------------------------------------------------------- /Library/AnnotationManager: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/Library/AnnotationManager -------------------------------------------------------------------------------- /Library/AssetServerCacheV3: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/Library/AssetServerCacheV3 -------------------------------------------------------------------------------- /Library/AssetVersioning.db: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/Library/AssetVersioning.db -------------------------------------------------------------------------------- /Library/CurrentLayout.dwlt: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/Library/CurrentLayout.dwlt -------------------------------------------------------------------------------- /Library/MonoManager.asset: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/Library/MonoManager.asset -------------------------------------------------------------------------------- /Library/BuildSettings.asset: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/Library/BuildSettings.asset -------------------------------------------------------------------------------- /Library/ProjectSettings.asset: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/Library/ProjectSettings.asset -------------------------------------------------------------------------------- /docs/images/buttonOnClick.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/docs/images/buttonOnClick.png -------------------------------------------------------------------------------- /docs/images/create_script.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/docs/images/create_script.png -------------------------------------------------------------------------------- /docs/images/runningSample.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/docs/images/runningSample.png -------------------------------------------------------------------------------- /Assets/ApiAiSDK/lib/ApiAiSDK.dll: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/Assets/ApiAiSDK/lib/ApiAiSDK.dll -------------------------------------------------------------------------------- /Assets/ApiAiSDK/lib/fastJSON.dll: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/Assets/ApiAiSDK/lib/fastJSON.dll -------------------------------------------------------------------------------- /Library/EditorUserSettings.asset: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/Library/EditorUserSettings.asset -------------------------------------------------------------------------------- /Library/LastSceneManagerSetup.txt: -------------------------------------------------------------------------------- 1 | sceneSetups: 2 | - path: Assets/Examples/ServiceSample.unity 3 | isLoaded: 1 4 | isActive: 1 5 | -------------------------------------------------------------------------------- /ProjectSettings/AudioManager.asset: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/ProjectSettings/AudioManager.asset -------------------------------------------------------------------------------- /ProjectSettings/InputManager.asset: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/ProjectSettings/InputManager.asset -------------------------------------------------------------------------------- /ProjectSettings/NavMeshAreas.asset: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/ProjectSettings/NavMeshAreas.asset -------------------------------------------------------------------------------- /ProjectSettings/TagManager.asset: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/ProjectSettings/TagManager.asset -------------------------------------------------------------------------------- /ProjectSettings/TimeManager.asset: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/ProjectSettings/TimeManager.asset -------------------------------------------------------------------------------- /Assets/AssetStoreTools/Labels.asset: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/Assets/AssetStoreTools/Labels.asset -------------------------------------------------------------------------------- /Assets/Examples/ServiceSample.unity: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/Assets/Examples/ServiceSample.unity -------------------------------------------------------------------------------- /Assets/Plugins/Android/libs/app.jar: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/Assets/Plugins/Android/libs/app.jar -------------------------------------------------------------------------------- /Library/InspectorExpandedItems.asset: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/Library/InspectorExpandedItems.asset -------------------------------------------------------------------------------- /ProjectSettings/EditorSettings.asset: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/ProjectSettings/EditorSettings.asset -------------------------------------------------------------------------------- /ProjectSettings/NavMeshLayers.asset: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/ProjectSettings/NavMeshLayers.asset -------------------------------------------------------------------------------- /ProjectSettings/NetworkManager.asset: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/ProjectSettings/NetworkManager.asset -------------------------------------------------------------------------------- /Assets/AssetStoreTools/Editor/icon.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/Assets/AssetStoreTools/Editor/icon.png -------------------------------------------------------------------------------- /Library/EditorUserBuildSettings.asset: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/Library/EditorUserBuildSettings.asset -------------------------------------------------------------------------------- /ProjectSettings/DynamicsManager.asset: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/ProjectSettings/DynamicsManager.asset -------------------------------------------------------------------------------- /ProjectSettings/GraphicsSettings.asset: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/ProjectSettings/GraphicsSettings.asset -------------------------------------------------------------------------------- /ProjectSettings/Physics2DSettings.asset: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/ProjectSettings/Physics2DSettings.asset -------------------------------------------------------------------------------- /ProjectSettings/ProjectSettings.asset: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/ProjectSettings/ProjectSettings.asset -------------------------------------------------------------------------------- /ProjectSettings/QualitySettings.asset: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/ProjectSettings/QualitySettings.asset -------------------------------------------------------------------------------- /ProjectSettings/UnityAdsSettings.asset: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/ProjectSettings/UnityAdsSettings.asset -------------------------------------------------------------------------------- /native/Android/UnityHelper/app/src/main/res/values/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | UnityHelper 3 | 4 | -------------------------------------------------------------------------------- /ProjectSettings/ClusterInputManager.asset: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/ProjectSettings/ClusterInputManager.asset -------------------------------------------------------------------------------- /ProjectSettings/EditorBuildSettings.asset: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/ProjectSettings/EditorBuildSettings.asset -------------------------------------------------------------------------------- /ProjectSettings/UnityConnectSettings.asset: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/ProjectSettings/UnityConnectSettings.asset -------------------------------------------------------------------------------- /Assets/AssetStoreTools/Editor/AssetStoreTools.dll: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/Assets/AssetStoreTools/Editor/AssetStoreTools.dll -------------------------------------------------------------------------------- /Assets/AssetStoreTools/Editor/DroidSansMono.ttf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/Assets/AssetStoreTools/Editor/DroidSansMono.ttf -------------------------------------------------------------------------------- /Assets/AssetStoreTools/Editor/AssetStoreToolsExtra.dll: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/Assets/AssetStoreTools/Editor/AssetStoreToolsExtra.dll -------------------------------------------------------------------------------- /native/Android/UnityHelper/app/src/main/res/drawable-hdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/native/Android/UnityHelper/app/src/main/res/drawable-hdpi/ic_launcher.png -------------------------------------------------------------------------------- /native/Android/UnityHelper/app/src/main/res/drawable-mdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/native/Android/UnityHelper/app/src/main/res/drawable-mdpi/ic_launcher.png -------------------------------------------------------------------------------- /native/Android/UnityHelper/app/src/main/res/drawable-xhdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/native/Android/UnityHelper/app/src/main/res/drawable-xhdpi/ic_launcher.png -------------------------------------------------------------------------------- /native/Android/UnityHelper/app/src/main/res/drawable-xxhdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dialogflow/dialogflow-unity-client/HEAD/native/Android/UnityHelper/app/src/main/res/drawable-xxhdpi/ic_launcher.png -------------------------------------------------------------------------------- /native/Android/UnityHelper/app/src/main/AndroidManifest.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /native/Android/UnityHelper/app/src/main/res/values/styles.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | Testing/bin 2 | Testing/obj 3 | *.meta 4 | obj 5 | Library/metadata 6 | Library/ScriptAssemblies 7 | Temp 8 | Builds 9 | Library/ShaderCache 10 | Library/shadercompiler*.log 11 | ios-build 12 | *.apk 13 | api-ai-unity-example.userprefs 14 | api-ai-unity-example.v12.suo 15 | -------------------------------------------------------------------------------- /native/Android/UnityHelper/build.gradle: -------------------------------------------------------------------------------- 1 | // Top-level build file where you can add configuration options common to all sub-projects/modules. 2 | 3 | buildscript { 4 | repositories { 5 | jcenter() 6 | } 7 | dependencies { 8 | classpath 'com.android.tools.build:gradle:1.0.0' 9 | 10 | // NOTE: Do not place your application dependencies here; they belong 11 | // in the individual module build.gradle files 12 | } 13 | } 14 | 15 | allprojects { 16 | repositories { 17 | jcenter() 18 | } 19 | } 20 | -------------------------------------------------------------------------------- /native/Android/UnityHelper/app/proguard-rules.pro: -------------------------------------------------------------------------------- 1 | # Add project specific ProGuard rules here. 2 | # By default, the flags in this file are appended to flags specified 3 | # in /Users/xvir/sdk/android/tools/proguard/proguard-android.txt 4 | # You can edit the include path and order by changing the proguardFiles 5 | # directive in build.gradle. 6 | # 7 | # For more details, see 8 | # http://developer.android.com/guide/developing/tools/proguard.html 9 | 10 | # Add any project specific keep options here: 11 | 12 | # If your project uses WebView with JS, uncomment the following 13 | # and specify the fully qualified class name to the JavaScript interface 14 | # class: 15 | #-keepclassmembers class fqcn.of.javascript.interface.for.webview { 16 | # public *; 17 | #} 18 | -------------------------------------------------------------------------------- /native/Android/UnityHelper/gradle.properties: -------------------------------------------------------------------------------- 1 | # Project-wide Gradle settings. 2 | 3 | # IDE (e.g. Android Studio) users: 4 | # Gradle settings configured through the IDE *will override* 5 | # any settings specified in this file. 6 | 7 | # For more details on how to configure your build environment visit 8 | # http://www.gradle.org/docs/current/userguide/build_environment.html 9 | 10 | # Specifies the JVM arguments used for the daemon process. 11 | # The setting is particularly useful for tweaking memory settings. 12 | # Default value: -Xmx10248m -XX:MaxPermSize=256m 13 | # org.gradle.jvmargs=-Xmx2048m -XX:MaxPermSize=512m -XX:+HeapDumpOnOutOfMemoryError -Dfile.encoding=UTF-8 14 | 15 | # When configured, Gradle will run in incubating parallel mode. 16 | # This option should only be used with decoupled projects. More details, visit 17 | # http://www.gradle.org/docs/current/userguide/multi_project_builds.html#sec:decoupled_projects 18 | # org.gradle.parallel=true -------------------------------------------------------------------------------- /Assets/Plugins/Android/AndroidManifest.xml: -------------------------------------------------------------------------------- 1 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | -------------------------------------------------------------------------------- /native/Android/UnityHelper/app/src/androidTest/java/ai/api/unityhelper/ApplicationTest.java: -------------------------------------------------------------------------------- 1 | /** 2 | * Copyright 2017 Google Inc. All Rights Reserved. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * http://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | package ai.api.unityhelper; 18 | 19 | import android.app.Application; 20 | import android.test.ApplicationTestCase; 21 | 22 | /** 23 | * Testing Fundamentals 24 | */ 25 | public class ApplicationTest extends ApplicationTestCase { 26 | public ApplicationTest() { 27 | super(Application.class); 28 | } 29 | } -------------------------------------------------------------------------------- /native/Android/UnityHelper/app/src/main/java/ai/api/unityhelper/RecognitionResultObject.java: -------------------------------------------------------------------------------- 1 | /** 2 | * Copyright 2017 Google Inc. All Rights Reserved. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * http://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | package ai.api.unityhelper; 18 | 19 | public class RecognitionResultObject { 20 | 21 | private boolean ready; 22 | private String result; 23 | 24 | public boolean isReady() { 25 | return ready; 26 | } 27 | 28 | public void setReady(boolean ready) { 29 | this.ready = ready; 30 | } 31 | 32 | public String getResult() { 33 | return result; 34 | } 35 | 36 | public void setResult(String result) { 37 | this.result = result; 38 | 39 | setReady(true); 40 | } 41 | } 42 | -------------------------------------------------------------------------------- /native/Android/UnityHelper/app/build.gradle: -------------------------------------------------------------------------------- 1 | apply plugin: 'com.android.library' 2 | 3 | android { 4 | compileSdkVersion 24 5 | buildToolsVersion "24.0.1" 6 | 7 | defaultConfig { 8 | minSdkVersion 10 9 | targetSdkVersion 24 10 | versionCode 1 11 | versionName "1.0" 12 | } 13 | buildTypes { 14 | release { 15 | minifyEnabled false 16 | proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' 17 | } 18 | } 19 | compileOptions { 20 | sourceCompatibility JavaVersion.VERSION_1_6 21 | targetCompatibility JavaVersion.VERSION_1_6 22 | } 23 | packagingOptions { 24 | exclude 'META-INF/LICENSE.txt' 25 | exclude 'META-INF/LICENSE' 26 | exclude 'META-INF/NOTICE' 27 | exclude 'META-INF/NOTICE.txt' 28 | exclude 'LICENSE.txt' 29 | } 30 | } 31 | 32 | dependencies { 33 | compile fileTree(dir: 'libs', include: ['*.jar']) 34 | compile 'com.android.support:appcompat-v7:24.1.1' 35 | compile files('libs/unity-classes.jar') 36 | } 37 | 38 | // block for building library jars 39 | android.libraryVariants.all { variant -> 40 | def name = variant.buildType.name 41 | def task = project.tasks.create "jar${name.capitalize()}", Jar 42 | task.dependsOn variant.javaCompile 43 | task.from variant.javaCompile.destinationDir 44 | artifacts.add('archives', task); 45 | } -------------------------------------------------------------------------------- /Assets/ApiAiSDK/AndroidRecognitionResult.cs: -------------------------------------------------------------------------------- 1 | /** 2 | * Copyright 2017 Google Inc. All Rights Reserved. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * http://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | using System; 18 | using Newtonsoft.Json; 19 | 20 | namespace ApiAiSDK.Unity.Android 21 | { 22 | 23 | #if UNITY_ANDROID 24 | [JsonObject] 25 | public class AndroidRecognitionResult 26 | { 27 | [JsonProperty("status")] 28 | public string Status { get; set; } 29 | 30 | [JsonProperty("errorMessage")] 31 | public string ErrorMessage { get; set; } 32 | 33 | [JsonProperty("recognitionResults")] 34 | public string[] RecognitionResults { get; set; } 35 | 36 | [JsonProperty("confidence")] 37 | public float[] Confidence{ get; set; } 38 | 39 | public bool IsError { 40 | get { 41 | if (Status == "success") { 42 | return false; 43 | } 44 | 45 | return true; 46 | } 47 | } 48 | 49 | public AndroidRecognitionResult() 50 | { 51 | } 52 | } 53 | #endif 54 | 55 | } 56 | 57 | -------------------------------------------------------------------------------- /Assets/ApiAiSDK/ResultWrapper.cs: -------------------------------------------------------------------------------- 1 | /** 2 | * Copyright 2017 Google Inc. All Rights Reserved. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * http://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | using System; 18 | using UnityEngine; 19 | using Newtonsoft.Json; 20 | 21 | namespace ApiAiSDK.Unity.Android 22 | { 23 | 24 | #if UNITY_ANDROID 25 | public class ResultWrapper 26 | { 27 | private AndroidJavaObject resultObject; 28 | 29 | public ResultWrapper(AndroidJavaObject resultObject) 30 | { 31 | if(resultObject == null) 32 | { 33 | throw new ArgumentNullException("resultObject"); 34 | } 35 | 36 | this.resultObject = resultObject; 37 | } 38 | 39 | public bool IsReady 40 | { 41 | get { 42 | var ready = resultObject.Call("isReady"); 43 | return ready; 44 | } 45 | } 46 | 47 | public AndroidRecognitionResult GetResult() 48 | { 49 | var recognitionResultString = resultObject.Call("getResult"); 50 | return JsonConvert.DeserializeObject(recognitionResultString); 51 | } 52 | } 53 | #endif 54 | 55 | } 56 | 57 | -------------------------------------------------------------------------------- /CONTRIBUTING.md: -------------------------------------------------------------------------------- 1 | # How to become a contributor and submit your own code 2 | 3 | ## Contributor License Agreements 4 | 5 | We'd love to accept your sample apps and patches! Before we can take them, we 6 | have to jump a couple of legal hurdles. 7 | 8 | Please fill out either the individual or corporate Contributor License Agreement 9 | (CLA). 10 | 11 | * If you are an individual writing original source code and you're sure you 12 | own the intellectual property, then you'll need to sign an [individual CLA](https://developers.google.com/open-source/cla/individual). 13 | * If you work for a company that wants to allow you to contribute your work, 14 | then you'll need to sign a [corporate CLA](https://developers.google.com/open-source/cla/corporate). 15 | 16 | Follow either of the two links above to access the appropriate CLA and 17 | instructions for how to sign and return it. Once we receive it, we'll be able to 18 | accept your pull requests. 19 | 20 | ## Contributing A Patch 21 | 22 | 1. Submit an issue describing your proposed change to the repo in question. 23 | 1. The repo owner will respond to your issue promptly. 24 | 1. If your proposed change is accepted, and you haven't already done so, sign a 25 | Contributor License Agreement (see details above). 26 | 1. Fork the desired repo, develop and test your code changes. 27 | 1. Ensure that your code adheres to the existing style in the sample to which 28 | you are contributing. Refer to the 29 | [Google Cloud Platform Samples Style Guide](https://github.com/GoogleCloudPlatform/Template/wiki/style.html) for the 30 | recommended coding standards for this organization. 31 | 1. Ensure that your code has an appropriate set of unit tests which all pass. 32 | 1. Submit a pull request. 33 | -------------------------------------------------------------------------------- /Assets/ApiAiSDK/AndroidRecognizer.cs: -------------------------------------------------------------------------------- 1 | /** 2 | * Copyright 2017 Google Inc. All Rights Reserved. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * http://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | using System; 18 | using UnityEngine; 19 | using Newtonsoft.Json; 20 | 21 | namespace ApiAiSDK.Unity.Android 22 | { 23 | #if UNITY_ANDROID 24 | public class AndroidRecognizer 25 | { 26 | private AndroidJavaObject recognitionHelper; 27 | 28 | public AndroidRecognizer() 29 | { 30 | if (Application.platform != RuntimePlatform.Android) { 31 | throw new InvalidOperationException("AndroidRecognizer can't be used on other platforms than Android"); 32 | } 33 | 34 | recognitionHelper = new AndroidJavaObject("ai.api.unityhelper.RecognitionHelper"); 35 | } 36 | 37 | public void Initialize() 38 | { 39 | AndroidJavaClass unityPlayerClass = new AndroidJavaClass("com.unity3d.player.UnityPlayer"); 40 | AndroidJavaObject currentActivity = unityPlayerClass.GetStatic("currentActivity"); 41 | 42 | recognitionHelper.Call("initialize", currentActivity); 43 | } 44 | 45 | public ResultWrapper Recognize(string lang) 46 | { 47 | var recognitionResultObject = recognitionHelper.Call("recognize", lang); 48 | var wrapper = new ResultWrapper(recognitionResultObject); 49 | return wrapper; 50 | } 51 | 52 | public void Clean() 53 | { 54 | recognitionHelper.Call("clean"); 55 | } 56 | } 57 | #endif 58 | 59 | } 60 | 61 | -------------------------------------------------------------------------------- /native/Android/UnityHelper/gradlew.bat: -------------------------------------------------------------------------------- 1 | @if "%DEBUG%" == "" @echo off 2 | @rem ########################################################################## 3 | @rem 4 | @rem Gradle startup script for Windows 5 | @rem 6 | @rem ########################################################################## 7 | 8 | @rem Set local scope for the variables with windows NT shell 9 | if "%OS%"=="Windows_NT" setlocal 10 | 11 | @rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script. 12 | set DEFAULT_JVM_OPTS= 13 | 14 | set DIRNAME=%~dp0 15 | if "%DIRNAME%" == "" set DIRNAME=. 16 | set APP_BASE_NAME=%~n0 17 | set APP_HOME=%DIRNAME% 18 | 19 | @rem Find java.exe 20 | if defined JAVA_HOME goto findJavaFromJavaHome 21 | 22 | set JAVA_EXE=java.exe 23 | %JAVA_EXE% -version >NUL 2>&1 24 | if "%ERRORLEVEL%" == "0" goto init 25 | 26 | echo. 27 | echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH. 28 | echo. 29 | echo Please set the JAVA_HOME variable in your environment to match the 30 | echo location of your Java installation. 31 | 32 | goto fail 33 | 34 | :findJavaFromJavaHome 35 | set JAVA_HOME=%JAVA_HOME:"=% 36 | set JAVA_EXE=%JAVA_HOME%/bin/java.exe 37 | 38 | if exist "%JAVA_EXE%" goto init 39 | 40 | echo. 41 | echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME% 42 | echo. 43 | echo Please set the JAVA_HOME variable in your environment to match the 44 | echo location of your Java installation. 45 | 46 | goto fail 47 | 48 | :init 49 | @rem Get command-line arguments, handling Windowz variants 50 | 51 | if not "%OS%" == "Windows_NT" goto win9xME_args 52 | if "%@eval[2+2]" == "4" goto 4NT_args 53 | 54 | :win9xME_args 55 | @rem Slurp the command line arguments. 56 | set CMD_LINE_ARGS= 57 | set _SKIP=2 58 | 59 | :win9xME_args_slurp 60 | if "x%~1" == "x" goto execute 61 | 62 | set CMD_LINE_ARGS=%* 63 | goto execute 64 | 65 | :4NT_args 66 | @rem Get arguments from the 4NT Shell from JP Software 67 | set CMD_LINE_ARGS=%$ 68 | 69 | :execute 70 | @rem Setup the command line 71 | 72 | set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar 73 | 74 | @rem Execute Gradle 75 | "%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %CMD_LINE_ARGS% 76 | 77 | :end 78 | @rem End local scope for the variables with windows NT shell 79 | if "%ERRORLEVEL%"=="0" goto mainEnd 80 | 81 | :fail 82 | rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of 83 | rem the _cmd.exe /c_ return code! 84 | if not "" == "%GRADLE_EXIT_CONSOLE%" exit 1 85 | exit /b 1 86 | 87 | :mainEnd 88 | if "%OS%"=="Windows_NT" endlocal 89 | 90 | :omega 91 | -------------------------------------------------------------------------------- /native/Android/UnityHelper/app/src/main/java/ai/api/unityhelper/RecognizerChecker.java: -------------------------------------------------------------------------------- 1 | /** 2 | * Copyright 2017 Google Inc. All Rights Reserved. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * http://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | package ai.api.unityhelper; 18 | 19 | import android.content.ComponentName; 20 | import android.content.Context; 21 | import android.content.Intent; 22 | import android.content.pm.PackageInfo; 23 | import android.content.pm.PackageManager; 24 | import android.content.pm.ResolveInfo; 25 | import android.content.pm.ServiceInfo; 26 | import android.os.Build; 27 | import android.speech.RecognitionService; 28 | 29 | import java.util.LinkedList; 30 | import java.util.List; 31 | 32 | public class RecognizerChecker { 33 | 34 | public static final String GOOGLE_RECOGNIZER_PACKAGE_NAME = "com.google.android.googlequicksearchbox"; 35 | public static final String GOOGLE_VOICE_SEARCH_PACKAGE_NAME = "com.google.android.voicesearch"; 36 | 37 | public static ComponentName findGoogleRecognizer(final Context context) { 38 | return findRecognizerByPackage(context, getPackageName()); 39 | } 40 | 41 | private static ComponentName findRecognizerByPackage(final Context context, final String prefPackage) { 42 | final PackageManager pm = context.getPackageManager(); 43 | final List available = pm != null ? pm.queryIntentServices(new Intent(RecognitionService.SERVICE_INTERFACE), 0) : new LinkedList(); 44 | final int numAvailable = available.size(); 45 | 46 | if (numAvailable == 0) { 47 | // no available voice recognition services found 48 | return null; 49 | } else { 50 | if (prefPackage != null) { 51 | for (final ResolveInfo anAvailable : available) { 52 | final ServiceInfo serviceInfo = anAvailable.serviceInfo; 53 | 54 | if (serviceInfo != null && prefPackage.equals(serviceInfo.packageName)) { 55 | return new ComponentName(serviceInfo.packageName, serviceInfo.name); 56 | } 57 | } 58 | } 59 | // Do not pick up first available, but use default one 60 | return null; 61 | } 62 | } 63 | 64 | public static String getGoogleRecognizerVersion(final Context context) { 65 | try { 66 | final PackageManager pm = context.getPackageManager(); 67 | 68 | final ComponentName recognizerComponentName = findGoogleRecognizer(context); 69 | if (recognizerComponentName != null) { 70 | final PackageInfo packageInfo = pm.getPackageInfo(recognizerComponentName.getPackageName(), 0); 71 | final String versionName = packageInfo.versionName; 72 | return versionName; 73 | } 74 | 75 | return ""; 76 | } catch (final PackageManager.NameNotFoundException ignored) { 77 | return ""; 78 | } 79 | } 80 | 81 | public static boolean isGoogleRecognizerAvailable(final Context context) { 82 | return findGoogleRecognizer(context) != null; 83 | //return false; 84 | } 85 | 86 | private static String getPackageName() { 87 | if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) { 88 | return GOOGLE_RECOGNIZER_PACKAGE_NAME; 89 | } else { 90 | return GOOGLE_VOICE_SEARCH_PACKAGE_NAME; 91 | } 92 | } 93 | 94 | } -------------------------------------------------------------------------------- /Assets/Examples/ApiAiModule.cs: -------------------------------------------------------------------------------- 1 | /** 2 | * Copyright 2017 Google Inc. All Rights Reserved. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * http://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | using UnityEngine; 18 | using UnityEngine.UI; 19 | using System; 20 | using System.IO; 21 | using System.Collections; 22 | using System.Reflection; 23 | using ApiAiSDK; 24 | using ApiAiSDK.Model; 25 | using ApiAiSDK.Unity; 26 | using Newtonsoft.Json; 27 | using System.Net; 28 | using System.Collections.Generic; 29 | 30 | public class ApiAiModule : MonoBehaviour 31 | { 32 | 33 | public Text answerTextField; 34 | public Text inputTextField; 35 | private ApiAiUnity apiAiUnity; 36 | private AudioSource aud; 37 | public AudioClip listeningSound; 38 | 39 | private readonly JsonSerializerSettings jsonSettings = new JsonSerializerSettings 40 | { 41 | NullValueHandling = NullValueHandling.Ignore, 42 | }; 43 | 44 | private readonly Queue ExecuteOnMainThread = new Queue(); 45 | 46 | // Use this for initialization 47 | IEnumerator Start() 48 | { 49 | // check access to the Microphone 50 | yield return Application.RequestUserAuthorization(UserAuthorization.Microphone); 51 | if (!Application.HasUserAuthorization(UserAuthorization.Microphone)) 52 | { 53 | throw new NotSupportedException("Microphone using not authorized"); 54 | } 55 | 56 | ServicePointManager.ServerCertificateValidationCallback = (a, b, c, d) => 57 | { 58 | return true; 59 | }; 60 | 61 | const string ACCESS_TOKEN = "3485a96fb27744db83e78b8c4bc9e7b7"; 62 | 63 | var config = new AIConfiguration(ACCESS_TOKEN, SupportedLanguage.English); 64 | 65 | apiAiUnity = new ApiAiUnity(); 66 | apiAiUnity.Initialize(config); 67 | 68 | apiAiUnity.OnError += HandleOnError; 69 | apiAiUnity.OnResult += HandleOnResult; 70 | } 71 | 72 | void HandleOnResult(object sender, AIResponseEventArgs e) 73 | { 74 | RunInMainThread(() => { 75 | var aiResponse = e.Response; 76 | if (aiResponse != null) 77 | { 78 | Debug.Log(aiResponse.Result.ResolvedQuery); 79 | var outText = JsonConvert.SerializeObject(aiResponse, jsonSettings); 80 | 81 | Debug.Log(outText); 82 | 83 | answerTextField.text = outText; 84 | 85 | } else 86 | { 87 | Debug.LogError("Response is null"); 88 | } 89 | }); 90 | } 91 | 92 | void HandleOnError(object sender, AIErrorEventArgs e) 93 | { 94 | RunInMainThread(() => { 95 | Debug.LogException(e.Exception); 96 | Debug.Log(e.ToString()); 97 | answerTextField.text = e.Exception.Message; 98 | }); 99 | } 100 | 101 | // Update is called once per frame 102 | void Update() 103 | { 104 | if (apiAiUnity != null) 105 | { 106 | apiAiUnity.Update(); 107 | } 108 | 109 | // dispatch stuff on main thread 110 | while (ExecuteOnMainThread.Count > 0) 111 | { 112 | ExecuteOnMainThread.Dequeue().Invoke(); 113 | } 114 | } 115 | 116 | private void RunInMainThread(Action action) 117 | { 118 | ExecuteOnMainThread.Enqueue(action); 119 | } 120 | 121 | public void PluginInit() 122 | { 123 | 124 | } 125 | 126 | public void StartListening() 127 | { 128 | Debug.Log("StartListening"); 129 | 130 | if (answerTextField != null) 131 | { 132 | answerTextField.text = "Listening..."; 133 | } 134 | 135 | aud = GetComponent(); 136 | apiAiUnity.StartListening(aud); 137 | 138 | } 139 | 140 | public void StopListening() 141 | { 142 | try 143 | { 144 | Debug.Log("StopListening"); 145 | 146 | if (answerTextField != null) 147 | { 148 | answerTextField.text = ""; 149 | } 150 | 151 | apiAiUnity.StopListening(); 152 | } catch (Exception ex) 153 | { 154 | Debug.LogException(ex); 155 | } 156 | } 157 | 158 | public void SendText() 159 | { 160 | var text = inputTextField.text; 161 | 162 | Debug.Log(text); 163 | 164 | AIResponse response = apiAiUnity.TextRequest(text); 165 | 166 | if (response != null) 167 | { 168 | Debug.Log("Resolved query: " + response.Result.ResolvedQuery); 169 | var outText = JsonConvert.SerializeObject(response, jsonSettings); 170 | 171 | Debug.Log("Result: " + outText); 172 | 173 | answerTextField.text = outText; 174 | } else 175 | { 176 | Debug.LogError("Response is null"); 177 | } 178 | 179 | } 180 | 181 | public void StartNativeRecognition() 182 | { 183 | try 184 | { 185 | apiAiUnity.StartNativeRecognition(); 186 | } catch (Exception ex) 187 | { 188 | Debug.LogException(ex); 189 | } 190 | } 191 | } 192 | -------------------------------------------------------------------------------- /Assembly-CSharp.csproj: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | Debug 5 | AnyCPU 6 | 10.0.20506 7 | 2.0 8 | 9 | {45A17122-20EC-1E17-ADB5-C4501FB0AE71} 10 | Library 11 | Properties 12 | Assembly-CSharp 13 | v3.5 14 | 512 15 | Assets 16 | 17 | 18 | true 19 | full 20 | false 21 | Temp\bin\Debug\ 22 | DEBUG;TRACE;UNITY_5_3_3;UNITY_5_3;UNITY_5;UNITY_64;ENABLE_NEW_BUGREPORTER;ENABLE_AUDIO;ENABLE_CACHING;ENABLE_CLOTH;ENABLE_DUCK_TYPING;ENABLE_FRAME_DEBUGGER;ENABLE_GENERICS;ENABLE_HOME_SCREEN;ENABLE_IMAGEEFFECTS;ENABLE_LIGHT_PROBES_LEGACY;ENABLE_MICROPHONE;ENABLE_MULTIPLE_DISPLAYS;ENABLE_PHYSICS;ENABLE_PLUGIN_INSPECTOR;ENABLE_SHADOWS;ENABLE_SINGLE_INSTANCE_BUILD_SETTING;ENABLE_SPRITERENDERER_FLIPPING;ENABLE_SPRITES;ENABLE_SPRITE_POLYGON;ENABLE_TERRAIN;ENABLE_RAKNET;ENABLE_UNET;ENABLE_UNITYEVENTS;ENABLE_VR;ENABLE_WEBCAM;ENABLE_WWW;ENABLE_CLOUD_SERVICES;ENABLE_CLOUD_SERVICES_ADS;ENABLE_CLOUD_HUB;ENABLE_CLOUD_PROJECT_ID;ENABLE_CLOUD_SERVICES_PURCHASING;ENABLE_CLOUD_SERVICES_ANALYTICS;ENABLE_CLOUD_SERVICES_UNET;ENABLE_CLOUD_SERVICES_BUILD;ENABLE_CLOUD_LICENSE;ENABLE_EDITOR_METRICS;ENABLE_EDITOR_METRICS_CACHING;INCLUDE_DYNAMIC_GI;INCLUDE_GI;INCLUDE_IL2CPP;INCLUDE_DIRECTX12;PLATFORM_SUPPORTS_MONO;RENDER_SOFTWARE_CURSOR;ENABLE_LOCALIZATION;ENABLE_ANDROID_ATLAS_ETC1_COMPRESSION;ENABLE_EDITOR_TESTS_RUNNER;UNITY_STANDALONE_OSX;UNITY_STANDALONE;ENABLE_SUBSTANCE;ENABLE_GAMECENTER;ENABLE_TEXTUREID_MAP;ENABLE_RUNTIME_GI;ENABLE_MOVIES;ENABLE_NETWORK;ENABLE_CRUNCH_TEXTURE_COMPRESSION;ENABLE_LOG_MIXED_STACKTRACE;ENABLE_UNITYWEBREQUEST;ENABLE_CLUSTERINPUT;ENABLE_WEBSOCKET_HOST;ENABLE_MONO;ENABLE_PROFILER;UNITY_ASSERTIONS;UNITY_EDITOR;UNITY_EDITOR_64;UNITY_EDITOR_OSX 23 | prompt 24 | 4 25 | 0169 26 | 27 | 28 | pdbonly 29 | true 30 | Temp\bin\Release\ 31 | prompt 32 | 4 33 | 0169 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | /Applications/Unity/Unity.app/Contents/Frameworks/Managed/UnityEngine.dll 42 | 43 | 44 | /Applications/Unity/Unity.app/Contents/Frameworks/Managed/UnityEditor.dll 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | /Applications/Unity/Unity.app/Contents/UnityExtensions/Unity/GUISystem/UnityEngine.UI.dll 56 | 57 | 58 | /Applications/Unity/Unity.app/Contents/UnityExtensions/Unity/Networking/UnityEngine.Networking.dll 59 | 60 | 61 | /Users/xvir/Projects/apiai-solution/api-ai-unity-example/Assets/ApiAiSDK/lib/ApiAiSDK.dll 62 | 63 | 64 | /Users/xvir/Projects/apiai-solution/api-ai-unity-example/Assets/ApiAiSDK/lib/fastJSON.dll 65 | 66 | 67 | 68 | 75 | 76 | 77 | 78 | -------------------------------------------------------------------------------- /native/Android/UnityHelper/gradlew: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env bash 2 | 3 | ############################################################################## 4 | ## 5 | ## Gradle start up script for UN*X 6 | ## 7 | ############################################################################## 8 | 9 | # Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script. 10 | DEFAULT_JVM_OPTS="" 11 | 12 | APP_NAME="Gradle" 13 | APP_BASE_NAME=`basename "$0"` 14 | 15 | # Use the maximum available, or set MAX_FD != -1 to use that value. 16 | MAX_FD="maximum" 17 | 18 | warn ( ) { 19 | echo "$*" 20 | } 21 | 22 | die ( ) { 23 | echo 24 | echo "$*" 25 | echo 26 | exit 1 27 | } 28 | 29 | # OS specific support (must be 'true' or 'false'). 30 | cygwin=false 31 | msys=false 32 | darwin=false 33 | case "`uname`" in 34 | CYGWIN* ) 35 | cygwin=true 36 | ;; 37 | Darwin* ) 38 | darwin=true 39 | ;; 40 | MINGW* ) 41 | msys=true 42 | ;; 43 | esac 44 | 45 | # For Cygwin, ensure paths are in UNIX format before anything is touched. 46 | if $cygwin ; then 47 | [ -n "$JAVA_HOME" ] && JAVA_HOME=`cygpath --unix "$JAVA_HOME"` 48 | fi 49 | 50 | # Attempt to set APP_HOME 51 | # Resolve links: $0 may be a link 52 | PRG="$0" 53 | # Need this for relative symlinks. 54 | while [ -h "$PRG" ] ; do 55 | ls=`ls -ld "$PRG"` 56 | link=`expr "$ls" : '.*-> \(.*\)$'` 57 | if expr "$link" : '/.*' > /dev/null; then 58 | PRG="$link" 59 | else 60 | PRG=`dirname "$PRG"`"/$link" 61 | fi 62 | done 63 | SAVED="`pwd`" 64 | cd "`dirname \"$PRG\"`/" >&- 65 | APP_HOME="`pwd -P`" 66 | cd "$SAVED" >&- 67 | 68 | CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar 69 | 70 | # Determine the Java command to use to start the JVM. 71 | if [ -n "$JAVA_HOME" ] ; then 72 | if [ -x "$JAVA_HOME/jre/sh/java" ] ; then 73 | # IBM's JDK on AIX uses strange locations for the executables 74 | JAVACMD="$JAVA_HOME/jre/sh/java" 75 | else 76 | JAVACMD="$JAVA_HOME/bin/java" 77 | fi 78 | if [ ! -x "$JAVACMD" ] ; then 79 | die "ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME 80 | 81 | Please set the JAVA_HOME variable in your environment to match the 82 | location of your Java installation." 83 | fi 84 | else 85 | JAVACMD="java" 86 | which java >/dev/null 2>&1 || die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH. 87 | 88 | Please set the JAVA_HOME variable in your environment to match the 89 | location of your Java installation." 90 | fi 91 | 92 | # Increase the maximum file descriptors if we can. 93 | if [ "$cygwin" = "false" -a "$darwin" = "false" ] ; then 94 | MAX_FD_LIMIT=`ulimit -H -n` 95 | if [ $? -eq 0 ] ; then 96 | if [ "$MAX_FD" = "maximum" -o "$MAX_FD" = "max" ] ; then 97 | MAX_FD="$MAX_FD_LIMIT" 98 | fi 99 | ulimit -n $MAX_FD 100 | if [ $? -ne 0 ] ; then 101 | warn "Could not set maximum file descriptor limit: $MAX_FD" 102 | fi 103 | else 104 | warn "Could not query maximum file descriptor limit: $MAX_FD_LIMIT" 105 | fi 106 | fi 107 | 108 | # For Darwin, add options to specify how the application appears in the dock 109 | if $darwin; then 110 | GRADLE_OPTS="$GRADLE_OPTS \"-Xdock:name=$APP_NAME\" \"-Xdock:icon=$APP_HOME/media/gradle.icns\"" 111 | fi 112 | 113 | # For Cygwin, switch paths to Windows format before running java 114 | if $cygwin ; then 115 | APP_HOME=`cygpath --path --mixed "$APP_HOME"` 116 | CLASSPATH=`cygpath --path --mixed "$CLASSPATH"` 117 | 118 | # We build the pattern for arguments to be converted via cygpath 119 | ROOTDIRSRAW=`find -L / -maxdepth 1 -mindepth 1 -type d 2>/dev/null` 120 | SEP="" 121 | for dir in $ROOTDIRSRAW ; do 122 | ROOTDIRS="$ROOTDIRS$SEP$dir" 123 | SEP="|" 124 | done 125 | OURCYGPATTERN="(^($ROOTDIRS))" 126 | # Add a user-defined pattern to the cygpath arguments 127 | if [ "$GRADLE_CYGPATTERN" != "" ] ; then 128 | OURCYGPATTERN="$OURCYGPATTERN|($GRADLE_CYGPATTERN)" 129 | fi 130 | # Now convert the arguments - kludge to limit ourselves to /bin/sh 131 | i=0 132 | for arg in "$@" ; do 133 | CHECK=`echo "$arg"|egrep -c "$OURCYGPATTERN" -` 134 | CHECK2=`echo "$arg"|egrep -c "^-"` ### Determine if an option 135 | 136 | if [ $CHECK -ne 0 ] && [ $CHECK2 -eq 0 ] ; then ### Added a condition 137 | eval `echo args$i`=`cygpath --path --ignore --mixed "$arg"` 138 | else 139 | eval `echo args$i`="\"$arg\"" 140 | fi 141 | i=$((i+1)) 142 | done 143 | case $i in 144 | (0) set -- ;; 145 | (1) set -- "$args0" ;; 146 | (2) set -- "$args0" "$args1" ;; 147 | (3) set -- "$args0" "$args1" "$args2" ;; 148 | (4) set -- "$args0" "$args1" "$args2" "$args3" ;; 149 | (5) set -- "$args0" "$args1" "$args2" "$args3" "$args4" ;; 150 | (6) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" ;; 151 | (7) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" ;; 152 | (8) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" ;; 153 | (9) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" "$args8" ;; 154 | esac 155 | fi 156 | 157 | # Split up the JVM_OPTS And GRADLE_OPTS values into an array, following the shell quoting and substitution rules 158 | function splitJvmOpts() { 159 | JVM_OPTS=("$@") 160 | } 161 | eval splitJvmOpts $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS 162 | JVM_OPTS[${#JVM_OPTS[*]}]="-Dorg.gradle.appname=$APP_BASE_NAME" 163 | 164 | exec "$JAVACMD" "${JVM_OPTS[@]}" -classpath "$CLASSPATH" org.gradle.wrapper.GradleWrapperMain "$@" 165 | -------------------------------------------------------------------------------- /Assembly-CSharp-vs.csproj: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | Debug 5 | AnyCPU 6 | 10.0.20506 7 | 2.0 8 | {45A17122-20EC-1E17-ADB5-C4501FB0AE71} 9 | Library 10 | Properties 11 | 12 | Assembly-CSharp 13 | v3.5 14 | 512 15 | Assets 16 | 17 | 18 | true 19 | full 20 | false 21 | Temp\bin\Debug\ 22 | DEBUG;TRACE;UNITY_5_1_1;UNITY_5_1;UNITY_5;ENABLE_NEW_BUGREPORTER;ENABLE_2D_PHYSICS;ENABLE_4_6_FEATURES;ENABLE_AUDIO;ENABLE_CACHING;ENABLE_CLOTH;ENABLE_FRAME_DEBUGGER;ENABLE_GENERICS;ENABLE_HOME_SCREEN;ENABLE_IMAGEEFFECTS;ENABLE_LIGHT_PROBES_LEGACY;ENABLE_MICROPHONE;ENABLE_MULTIPLE_DISPLAYS;ENABLE_PHYSICS;ENABLE_PHYSICS_PHYSX3;ENABLE_PLUGIN_INSPECTOR;ENABLE_SHADOWS;ENABLE_SINGLE_INSTANCE_BUILD_SETTING;ENABLE_SPRITES;ENABLE_TERRAIN;ENABLE_UNET;ENABLE_UNITYEVENTS;ENABLE_VR;ENABLE_WEBCAM;ENABLE_WWW;ENABLE_CLOUD_SERVICES;ENABLE_CLOUD_SERVICES_ANALYTICS;ENABLE_CLOUD_SERVICES_UNET;ENABLE_CLOUD_LICENSE;ENABLE_AUDIOMIXER_SUSPEND;ENABLE_EDITOR_METRICS;INCLUDE_DYNAMIC_GI;INCLUDE_GI;INCLUDE_IL2CPP;INCLUDE_DIRECTX12;PLATFORM_SUPPORTS_MONO;ENABLE_LOCALIZATION;UNITY_IPHONE;ENABLE_RUNTIME_GI;ENABLE_SUBSTANCE;ENABLE_GAMECENTER;ENABLE_NETWORK;UNITY_IPHONE_API;UNITY_IOS;ENABLE_TEXTUREID_MAP;PLAYERCONNECTION_LISTENS_FIXED_PORT;DEBUGGER_LISTENS_FIXED_PORT;ENABLE_MONO;DEVELOPMENT_BUILD;ENABLE_PROFILER;DEBUG;TRACE;UNITY_ASSERTIONS;UNITY_EDITOR;UNITY_EDITOR_64;UNITY_EDITOR_OSX 23 | prompt 24 | 4 25 | 0169 26 | 27 | 28 | pdbonly 29 | true 30 | Temp\bin\Release\ 31 | TRACE 32 | prompt 33 | 4 34 | 0169 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | /Applications/Unity/Unity.app/Contents/Frameworks/Managed/UnityEngine.dll 43 | 44 | 45 | /Applications/Unity/Unity.app/Contents/Frameworks/Managed/UnityEditor.dll 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | /Applications/Unity/Unity.app/Contents/UnityExtensions/Unity/GUISystem/UnityEngine.UI.dll 57 | 58 | 59 | /Applications/Unity/Unity.app/Contents/UnityExtensions/Unity/Networking/UnityEngine.Networking.dll 60 | 61 | 62 | /Applications/Unity/Unity.app/Contents/UnityExtensions/Unity/UnityAnalytics/UnityEngine.Analytics.dll 63 | 64 | 65 | /Users/xvir/Projects/apiai-solution/api-ai-unity-example/Assets/ApiAiSDK/lib/ApiAiSDK.dll 66 | 67 | 68 | /Users/xvir/Projects/apiai-solution/api-ai-unity-example/Assets/ApiAiSDK/lib/fastJSON.dll 69 | 70 | 71 | /Applications/Unity/Unity.app/Contents/PlaybackEngines/iOSSupport/UnityEditor.iOS.Extensions.Xcode.dll 72 | 73 | 74 | 75 | 82 | 83 | 84 | 85 | -------------------------------------------------------------------------------- /Assets/README.md: -------------------------------------------------------------------------------- 1 | # api-ai-unity 2 | 3 | The API.AI Unity Plugin makes it easy to integrate the API.AI natural language processing API (http://api.ai) into your Unity project. API.AI allows using voice commands and integration with dialog scenarios defined for a particular agent in API.AI. 4 | 5 | Library provides simple programming interface for making text and voice requests to the API.AI service. 6 | 7 | ## Getting started 8 | 9 | ### Create helper module 10 | 11 | * Add new script to the Assets folder (ApiAiModule, for example) 12 | * Your new module should looks like 13 | ```csharp 14 | using UnityEngine; 15 | using System.Collections; 16 | 17 | public class ApiAiModule : MonoBehaviour { 18 | 19 | // Use this for initialization 20 | void Start () { 21 | 22 | } 23 | 24 | // Update is called once per frame 25 | void Update () { 26 | 27 | } 28 | } 29 | ``` 30 | 31 | * First, add API.AI usings 32 | 33 | ```csharp 34 | using ApiAiSDK; 35 | using ApiAiSDK.Model; 36 | using ApiAiSDK.Unity; 37 | ``` 38 | 39 | * Add private field to your module to keep reference to the SDK object 40 | 41 | ```csharp 42 | private ApiAiUnity apiAiUnity; 43 | ``` 44 | 45 | * On the start of your module ApiAiUnity object must be initialized. Required data for initialization is client access token from your development console on the api.ai website and one of supported languages 46 | 47 | ```csharp 48 | // Use this for initialization 49 | void Start() 50 | { 51 | const string ACCESS_TOKEN = "your_access_token"; 52 | 53 | var config = new AIConfiguration(ACCESS_TOKEN, SupportedLanguage.English); 54 | 55 | apiAiUnity = new ApiAiUnity(); 56 | apiAiUnity.Initialize(config); 57 | 58 | apiAiUnity.OnResult += HandleOnResult; 59 | apiAiUnity.OnError += HandleOnError; 60 | } 61 | ``` 62 | 63 | * `OnError` and `OnResult` events used for processing service results. So, handling functions must look like 64 | 65 | ```csharp 66 | void HandleOnResult(object sender, AIResponseEventArgs e) 67 | { 68 | var aiResponse = e.Response; 69 | if (aiResponse != null) { 70 | // get data from aiResponse 71 | } else { 72 | Debug.LogError("Response is null"); 73 | } 74 | } 75 | 76 | void HandleOnError(object sender, AIErrorEventArgs e) 77 | { 78 | Debug.LogException(e.Exception); 79 | } 80 | ``` 81 | 82 | ### Usage 83 | 84 | ApiAi Unity SDK let you to perform the following actions: 85 | 1. Start listening process and then send voice data to the api.ai service for recognition and processing 86 | 2. Send simple text request to the api.ai service 87 | 3. Use integrated Android recognition engine for recognition and send recognized text to the api.ai service for processing 88 | 89 | #### Using Speaktoit recognition 90 | 91 | To use Speaktoit voice recognition service you need to provide ApiAiUnity object with valid `AudioSource` object. It can be usually recieved using `GetComponent()` function. 92 | Temporary limitation of this case is if you using Speaktoit recognition you need to stop listening manually. So, use this code snippets to start and stop listening. 93 | 94 | ```csharp 95 | public void StartListening() 96 | { 97 | try { 98 | var aud = GetComponent(); 99 | apiAiUnity.StartListening(aud); 100 | } catch (Exception ex) { 101 | Debug.LogException(ex); 102 | } 103 | } 104 | 105 | public void StopListening() 106 | { 107 | try { 108 | apiAiUnity.StopListening(); 109 | } catch (Exception ex) { 110 | Debug.LogException(ex); 111 | } 112 | } 113 | ``` 114 | 115 | After start/stop listening you will receive api.ai result in the `OnResult` handler. 116 | 117 | **Note**: In some cases Unity application must get Sound Recording priviledges for using Microphone. To do this, change your helper module Start function in the following way 118 | 119 | ```csharp 120 | IEnumerator Start() 121 | { 122 | // check access to the Microphone 123 | yield return Application.RequestUserAuthorization (UserAuthorization.Microphone); 124 | if (!Application.HasUserAuthorization(UserAuthorization.Microphone)) { 125 | throw new NotSupportedException ("Microphone using not authorized"); 126 | } 127 | 128 | ... // apiAiUnity initialization... 129 | } 130 | ``` 131 | 132 | #### Simple text requests 133 | 134 | Usage of text requests is very simple, all you need is text query. 135 | 136 | ```csharp 137 | public void SendText() 138 | { 139 | var text = "hello"; 140 | try { 141 | var response = apiAiUnity.TextRequest(text); 142 | if (response != null) { 143 | // process response 144 | } else { 145 | Debug.LogError("Response is null"); 146 | } 147 | } catch (Exception ex) { 148 | Debug.LogException(ex); 149 | } 150 | } 151 | ``` 152 | 153 | **Note**, what you will receive api.ai result immediatly, not in the `OnResult` handler. 154 | 155 | #### Using native Android recognition 156 | 157 | This case only applicable for the Android Unity applications. You can check if the application is running on the Android platform using this simple code snippet 158 | 159 | ```csharp 160 | if (Application.platform == RuntimePlatform.Android) { 161 | // you can use Android recognition here 162 | } 163 | ``` 164 | 165 | Because of native recognition uses Unity-to-Native bridge, you need add following code to the script `Update` method. This code used for checking recognition results from native layer, because of callbacks is not supported in this case. 166 | 167 | ```csharp 168 | if (apiAiUnity != null) { 169 | apiAiUnity.Update(); 170 | } 171 | ``` 172 | 173 | To start recognition process use simple call of the `StartNativeRecognition` method. 174 | 175 | ```csharp 176 | public void StartNativeRecognition(){ 177 | try { 178 | apiAiUnity.StartNativeRecognition(); 179 | } catch (Exception ex) { 180 | Debug.LogException (ex); 181 | } 182 | } 183 | ``` 184 | 185 | You don't need to call `StopListening`, because of Android End-of-Speech detection used in this case. 186 | -------------------------------------------------------------------------------- /api-ai-unity-example-csharp.sln: -------------------------------------------------------------------------------- 1 | Microsoft Visual Studio Solution File, Format Version 11.00 2 | # Visual Studio 2008 3 | 4 | Project("{386615F4-6515-A27D-A436-BEDCD55A1B6B}") = "api-ai-unity-example", "Assembly-CSharp-vs.csproj", "{45A17122-20EC-1E17-ADB5-C4501FB0AE71}" 5 | EndProject 6 | Global 7 | GlobalSection(SolutionConfigurationPlatforms) = preSolution 8 | Debug|Any CPU = Debug|Any CPU 9 | Release|Any CPU = Release|Any CPU 10 | EndGlobalSection 11 | GlobalSection(ProjectConfigurationPlatforms) = postSolution 12 | {45A17122-20EC-1E17-ADB5-C4501FB0AE71}.Debug|Any CPU.ActiveCfg = Debug|Any CPU 13 | {45A17122-20EC-1E17-ADB5-C4501FB0AE71}.Debug|Any CPU.Build.0 = Debug|Any CPU 14 | {45A17122-20EC-1E17-ADB5-C4501FB0AE71}.Release|Any CPU.ActiveCfg = Release|Any CPU 15 | {45A17122-20EC-1E17-ADB5-C4501FB0AE71}.Release|Any CPU.Build.0 = Release|Any CPU 16 | EndGlobalSection 17 | GlobalSection(SolutionProperties) = preSolution 18 | HideSolutionNode = FALSE 19 | EndGlobalSection 20 | GlobalSection(MonoDevelopProperties) = preSolution 21 | StartupItem = Assembly-CSharp.csproj 22 | Policies = $0 23 | $0.TextStylePolicy = $1 24 | $1.inheritsSet = VisualStudio 25 | $1.inheritsScope = text/plain 26 | $1.scope = text/x-csharp 27 | $0.CSharpFormattingPolicy = $2 28 | $2.IndentSwitchBody = True 29 | $2.AnonymousMethodBraceStyle = NextLine 30 | $2.PropertyBraceStyle = NextLine 31 | $2.PropertyGetBraceStyle = NextLine 32 | $2.PropertySetBraceStyle = NextLine 33 | $2.EventBraceStyle = NextLine 34 | $2.EventAddBraceStyle = NextLine 35 | $2.EventRemoveBraceStyle = NextLine 36 | $2.StatementBraceStyle = NextLine 37 | $2.ArrayInitializerBraceStyle = NextLine 38 | $2.BeforeMethodDeclarationParentheses = False 39 | $2.BeforeMethodCallParentheses = False 40 | $2.BeforeConstructorDeclarationParentheses = False 41 | $2.BeforeDelegateDeclarationParentheses = False 42 | $2.NewParentheses = False 43 | $2.inheritsSet = Mono 44 | $2.inheritsScope = text/x-csharp 45 | $2.scope = text/x-csharp 46 | $0.TextStylePolicy = $3 47 | $3.EolMarker = Unix 48 | $3.inheritsSet = VisualStudio 49 | $3.inheritsScope = text/plain 50 | $3.scope = text/plain 51 | $0.TextStylePolicy = $4 52 | $4.inheritsSet = null 53 | $4.scope = application/xml 54 | $0.XmlFormattingPolicy = $5 55 | $5.inheritsSet = Mono 56 | $5.inheritsScope = application/xml 57 | $5.scope = application/xml 58 | $0.StandardHeader = $6 59 | $6.Text = 60 | $6.IncludeInNewFiles = True 61 | $0.NameConventionPolicy = $7 62 | $7.Rules = $8 63 | $8.NamingRule = $9 64 | $9.Name = Namespaces 65 | $9.AffectedEntity = Namespace 66 | $9.VisibilityMask = VisibilityMask 67 | $9.NamingStyle = PascalCase 68 | $9.IncludeInstanceMembers = True 69 | $9.IncludeStaticEntities = True 70 | $8.NamingRule = $10 71 | $10.Name = Types 72 | $10.AffectedEntity = Class, Struct, Enum, Delegate 73 | $10.VisibilityMask = Public 74 | $10.NamingStyle = PascalCase 75 | $10.IncludeInstanceMembers = True 76 | $10.IncludeStaticEntities = True 77 | $8.NamingRule = $11 78 | $11.Name = Interfaces 79 | $11.RequiredPrefixes = $12 80 | $12.String = I 81 | $11.AffectedEntity = Interface 82 | $11.VisibilityMask = Public 83 | $11.NamingStyle = PascalCase 84 | $11.IncludeInstanceMembers = True 85 | $11.IncludeStaticEntities = True 86 | $8.NamingRule = $13 87 | $13.Name = Attributes 88 | $13.RequiredSuffixes = $14 89 | $14.String = Attribute 90 | $13.AffectedEntity = CustomAttributes 91 | $13.VisibilityMask = Public 92 | $13.NamingStyle = PascalCase 93 | $13.IncludeInstanceMembers = True 94 | $13.IncludeStaticEntities = True 95 | $8.NamingRule = $15 96 | $15.Name = Event Arguments 97 | $15.RequiredSuffixes = $16 98 | $16.String = EventArgs 99 | $15.AffectedEntity = CustomEventArgs 100 | $15.VisibilityMask = Public 101 | $15.NamingStyle = PascalCase 102 | $15.IncludeInstanceMembers = True 103 | $15.IncludeStaticEntities = True 104 | $8.NamingRule = $17 105 | $17.Name = Exceptions 106 | $17.RequiredSuffixes = $18 107 | $18.String = Exception 108 | $17.AffectedEntity = CustomExceptions 109 | $17.VisibilityMask = VisibilityMask 110 | $17.NamingStyle = PascalCase 111 | $17.IncludeInstanceMembers = True 112 | $17.IncludeStaticEntities = True 113 | $8.NamingRule = $19 114 | $19.Name = Methods 115 | $19.AffectedEntity = Methods 116 | $19.VisibilityMask = Protected, Public 117 | $19.NamingStyle = PascalCase 118 | $19.IncludeInstanceMembers = True 119 | $19.IncludeStaticEntities = True 120 | $8.NamingRule = $20 121 | $20.Name = Static Readonly Fields 122 | $20.AffectedEntity = ReadonlyField 123 | $20.VisibilityMask = Protected, Public 124 | $20.NamingStyle = PascalCase 125 | $20.IncludeInstanceMembers = False 126 | $20.IncludeStaticEntities = True 127 | $8.NamingRule = $21 128 | $21.Name = Fields 129 | $21.AffectedEntity = Field 130 | $21.VisibilityMask = Protected, Public 131 | $21.NamingStyle = PascalCase 132 | $21.IncludeInstanceMembers = True 133 | $21.IncludeStaticEntities = True 134 | $8.NamingRule = $22 135 | $22.Name = ReadOnly Fields 136 | $22.AffectedEntity = ReadonlyField 137 | $22.VisibilityMask = Protected, Public 138 | $22.NamingStyle = PascalCase 139 | $22.IncludeInstanceMembers = True 140 | $22.IncludeStaticEntities = False 141 | $8.NamingRule = $23 142 | $23.Name = Constant Fields 143 | $23.AffectedEntity = ConstantField 144 | $23.VisibilityMask = Protected, Public 145 | $23.NamingStyle = PascalCase 146 | $23.IncludeInstanceMembers = True 147 | $23.IncludeStaticEntities = True 148 | $8.NamingRule = $24 149 | $24.Name = Properties 150 | $24.AffectedEntity = Property 151 | $24.VisibilityMask = Protected, Public 152 | $24.NamingStyle = PascalCase 153 | $24.IncludeInstanceMembers = True 154 | $24.IncludeStaticEntities = True 155 | $8.NamingRule = $25 156 | $25.Name = Events 157 | $25.AffectedEntity = Event 158 | $25.VisibilityMask = Protected, Public 159 | $25.NamingStyle = PascalCase 160 | $25.IncludeInstanceMembers = True 161 | $25.IncludeStaticEntities = True 162 | $8.NamingRule = $26 163 | $26.Name = Enum Members 164 | $26.AffectedEntity = EnumMember 165 | $26.VisibilityMask = VisibilityMask 166 | $26.NamingStyle = PascalCase 167 | $26.IncludeInstanceMembers = True 168 | $26.IncludeStaticEntities = True 169 | $8.NamingRule = $27 170 | $27.Name = Parameters 171 | $27.AffectedEntity = Parameter 172 | $27.VisibilityMask = VisibilityMask 173 | $27.NamingStyle = CamelCase 174 | $27.IncludeInstanceMembers = True 175 | $27.IncludeStaticEntities = True 176 | $8.NamingRule = $28 177 | $28.Name = Type Parameters 178 | $28.RequiredPrefixes = $29 179 | $29.String = T 180 | $28.AffectedEntity = TypeParameter 181 | $28.VisibilityMask = VisibilityMask 182 | $28.NamingStyle = PascalCase 183 | $28.IncludeInstanceMembers = True 184 | $28.IncludeStaticEntities = True 185 | EndGlobalSection 186 | 187 | EndGlobal 188 | -------------------------------------------------------------------------------- /api-ai-unity-example.sln: -------------------------------------------------------------------------------- 1 | Microsoft Visual Studio Solution File, Format Version 11.00 2 | # Visual Studio 2008 3 | 4 | Project("{386615F4-6515-A27D-A436-BEDCD55A1B6B}") = "api-ai-unity-example", "Assembly-CSharp.csproj", "{45A17122-20EC-1E17-ADB5-C4501FB0AE71}" 5 | EndProject 6 | Global 7 | GlobalSection(SolutionConfigurationPlatforms) = preSolution 8 | Debug|Any CPU = Debug|Any CPU 9 | Release|Any CPU = Release|Any CPU 10 | EndGlobalSection 11 | GlobalSection(ProjectConfigurationPlatforms) = postSolution 12 | {45A17122-20EC-1E17-ADB5-C4501FB0AE71}.Debug|Any CPU.ActiveCfg = Debug|Any CPU 13 | {45A17122-20EC-1E17-ADB5-C4501FB0AE71}.Debug|Any CPU.Build.0 = Debug|Any CPU 14 | {45A17122-20EC-1E17-ADB5-C4501FB0AE71}.Release|Any CPU.ActiveCfg = Release|Any CPU 15 | {45A17122-20EC-1E17-ADB5-C4501FB0AE71}.Release|Any CPU.Build.0 = Release|Any CPU 16 | EndGlobalSection 17 | GlobalSection(SolutionProperties) = preSolution 18 | HideSolutionNode = FALSE 19 | EndGlobalSection 20 | GlobalSection(MonoDevelopProperties) = preSolution 21 | StartupItem = Assembly-CSharp.csproj 22 | Policies = $0 23 | $0.TextStylePolicy = $1 24 | $1.inheritsSet = VisualStudio 25 | $1.inheritsScope = text/plain 26 | $1.scope = text/x-csharp 27 | $0.CSharpFormattingPolicy = $2 28 | $2.IndentSwitchBody = True 29 | $2.AnonymousMethodBraceStyle = NextLine 30 | $2.PropertyBraceStyle = NextLine 31 | $2.PropertyGetBraceStyle = NextLine 32 | $2.PropertySetBraceStyle = NextLine 33 | $2.EventBraceStyle = NextLine 34 | $2.EventAddBraceStyle = NextLine 35 | $2.EventRemoveBraceStyle = NextLine 36 | $2.StatementBraceStyle = NextLine 37 | $2.ArrayInitializerBraceStyle = NextLine 38 | $2.BeforeMethodDeclarationParentheses = False 39 | $2.BeforeMethodCallParentheses = False 40 | $2.BeforeConstructorDeclarationParentheses = False 41 | $2.BeforeDelegateDeclarationParentheses = False 42 | $2.NewParentheses = False 43 | $2.inheritsSet = Mono 44 | $2.inheritsScope = text/x-csharp 45 | $2.scope = text/x-csharp 46 | $0.TextStylePolicy = $3 47 | $3.EolMarker = Unix 48 | $3.inheritsSet = VisualStudio 49 | $3.inheritsScope = text/plain 50 | $3.scope = text/plain 51 | $0.TextStylePolicy = $4 52 | $4.inheritsSet = null 53 | $4.scope = application/xml 54 | $0.XmlFormattingPolicy = $5 55 | $5.inheritsSet = Mono 56 | $5.inheritsScope = application/xml 57 | $5.scope = application/xml 58 | $0.StandardHeader = $6 59 | $6.Text = 60 | $6.IncludeInNewFiles = True 61 | $0.NameConventionPolicy = $7 62 | $7.Rules = $8 63 | $8.NamingRule = $9 64 | $9.Name = Namespaces 65 | $9.AffectedEntity = Namespace 66 | $9.VisibilityMask = VisibilityMask 67 | $9.NamingStyle = PascalCase 68 | $9.IncludeInstanceMembers = True 69 | $9.IncludeStaticEntities = True 70 | $8.NamingRule = $10 71 | $10.Name = Types 72 | $10.AffectedEntity = Class, Struct, Enum, Delegate 73 | $10.VisibilityMask = Public 74 | $10.NamingStyle = PascalCase 75 | $10.IncludeInstanceMembers = True 76 | $10.IncludeStaticEntities = True 77 | $8.NamingRule = $11 78 | $11.Name = Interfaces 79 | $11.RequiredPrefixes = $12 80 | $12.String = I 81 | $11.AffectedEntity = Interface 82 | $11.VisibilityMask = Public 83 | $11.NamingStyle = PascalCase 84 | $11.IncludeInstanceMembers = True 85 | $11.IncludeStaticEntities = True 86 | $8.NamingRule = $13 87 | $13.Name = Attributes 88 | $13.RequiredSuffixes = $14 89 | $14.String = Attribute 90 | $13.AffectedEntity = CustomAttributes 91 | $13.VisibilityMask = Public 92 | $13.NamingStyle = PascalCase 93 | $13.IncludeInstanceMembers = True 94 | $13.IncludeStaticEntities = True 95 | $8.NamingRule = $15 96 | $15.Name = Event Arguments 97 | $15.RequiredSuffixes = $16 98 | $16.String = EventArgs 99 | $15.AffectedEntity = CustomEventArgs 100 | $15.VisibilityMask = Public 101 | $15.NamingStyle = PascalCase 102 | $15.IncludeInstanceMembers = True 103 | $15.IncludeStaticEntities = True 104 | $8.NamingRule = $17 105 | $17.Name = Exceptions 106 | $17.RequiredSuffixes = $18 107 | $18.String = Exception 108 | $17.AffectedEntity = CustomExceptions 109 | $17.VisibilityMask = VisibilityMask 110 | $17.NamingStyle = PascalCase 111 | $17.IncludeInstanceMembers = True 112 | $17.IncludeStaticEntities = True 113 | $8.NamingRule = $19 114 | $19.Name = Methods 115 | $19.AffectedEntity = Methods 116 | $19.VisibilityMask = Protected, Public 117 | $19.NamingStyle = PascalCase 118 | $19.IncludeInstanceMembers = True 119 | $19.IncludeStaticEntities = True 120 | $8.NamingRule = $20 121 | $20.Name = Static Readonly Fields 122 | $20.AffectedEntity = ReadonlyField 123 | $20.VisibilityMask = Protected, Public 124 | $20.NamingStyle = PascalCase 125 | $20.IncludeInstanceMembers = False 126 | $20.IncludeStaticEntities = True 127 | $8.NamingRule = $21 128 | $21.Name = Fields 129 | $21.AffectedEntity = Field 130 | $21.VisibilityMask = Protected, Public 131 | $21.NamingStyle = PascalCase 132 | $21.IncludeInstanceMembers = True 133 | $21.IncludeStaticEntities = True 134 | $8.NamingRule = $22 135 | $22.Name = ReadOnly Fields 136 | $22.AffectedEntity = ReadonlyField 137 | $22.VisibilityMask = Protected, Public 138 | $22.NamingStyle = PascalCase 139 | $22.IncludeInstanceMembers = True 140 | $22.IncludeStaticEntities = False 141 | $8.NamingRule = $23 142 | $23.Name = Constant Fields 143 | $23.AffectedEntity = ConstantField 144 | $23.VisibilityMask = Protected, Public 145 | $23.NamingStyle = PascalCase 146 | $23.IncludeInstanceMembers = True 147 | $23.IncludeStaticEntities = True 148 | $8.NamingRule = $24 149 | $24.Name = Properties 150 | $24.AffectedEntity = Property 151 | $24.VisibilityMask = Protected, Public 152 | $24.NamingStyle = PascalCase 153 | $24.IncludeInstanceMembers = True 154 | $24.IncludeStaticEntities = True 155 | $8.NamingRule = $25 156 | $25.Name = Events 157 | $25.AffectedEntity = Event 158 | $25.VisibilityMask = Protected, Public 159 | $25.NamingStyle = PascalCase 160 | $25.IncludeInstanceMembers = True 161 | $25.IncludeStaticEntities = True 162 | $8.NamingRule = $26 163 | $26.Name = Enum Members 164 | $26.AffectedEntity = EnumMember 165 | $26.VisibilityMask = VisibilityMask 166 | $26.NamingStyle = PascalCase 167 | $26.IncludeInstanceMembers = True 168 | $26.IncludeStaticEntities = True 169 | $8.NamingRule = $27 170 | $27.Name = Parameters 171 | $27.AffectedEntity = Parameter 172 | $27.VisibilityMask = VisibilityMask 173 | $27.NamingStyle = CamelCase 174 | $27.IncludeInstanceMembers = True 175 | $27.IncludeStaticEntities = True 176 | $8.NamingRule = $28 177 | $28.Name = Type Parameters 178 | $28.RequiredPrefixes = $29 179 | $29.String = T 180 | $28.AffectedEntity = TypeParameter 181 | $28.VisibilityMask = VisibilityMask 182 | $28.NamingStyle = PascalCase 183 | $28.IncludeInstanceMembers = True 184 | $28.IncludeStaticEntities = True 185 | EndGlobalSection 186 | EndGlobal 187 | -------------------------------------------------------------------------------- /Assets/ApiAiSDK/ApiAiUnity.cs: -------------------------------------------------------------------------------- 1 | /** 2 | * Copyright 2017 Google Inc. All Rights Reserved. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * http://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | using System; 18 | using UnityEngine; 19 | using ApiAiSDK; 20 | using ApiAiSDK.Model; 21 | using System.Threading; 22 | using System.Linq; 23 | using System.ComponentModel; 24 | 25 | #if UNITY_ANDROID 26 | using ApiAiSDK.Unity.Android; 27 | #endif 28 | 29 | namespace ApiAiSDK.Unity 30 | { 31 | public class ApiAiUnity 32 | { 33 | private ApiAi apiAi; 34 | private AIConfiguration config; 35 | private AudioSource audioSource; 36 | private volatile bool recordingActive; 37 | private readonly object thisLock = new object(); 38 | 39 | #if UNITY_ANDROID 40 | private ResultWrapper androidResultWrapper; 41 | private AndroidRecognizer androidRecognizer; 42 | #endif 43 | 44 | public event EventHandler OnResult; 45 | public event EventHandler OnError; 46 | public event EventHandler OnListeningStarted; 47 | public event EventHandler OnListeningFinished; 48 | 49 | public ApiAiUnity() 50 | { 51 | 52 | } 53 | 54 | public void Initialize(AIConfiguration config) 55 | { 56 | this.config = config; 57 | 58 | apiAi = new ApiAi(this.config); 59 | 60 | #if UNITY_ANDROID 61 | 62 | if(Application.platform == RuntimePlatform.Android) 63 | { 64 | InitializeAndroid(); 65 | } 66 | 67 | #endif 68 | 69 | } 70 | 71 | #if UNITY_ANDROID 72 | private void InitializeAndroid(){ 73 | androidRecognizer = new AndroidRecognizer(); 74 | androidRecognizer.Initialize(); 75 | } 76 | #endif 77 | 78 | public void Update() 79 | { 80 | 81 | #if UNITY_ANDROID 82 | if (androidResultWrapper != null) { 83 | UpdateAndroidResult(); 84 | } 85 | #endif 86 | 87 | } 88 | 89 | #if UNITY_ANDROID 90 | private void UpdateAndroidResult(){ 91 | Debug.Log("UpdateAndroidResult"); 92 | var wrapper = androidResultWrapper; 93 | if (wrapper.IsReady) { 94 | var recognitionResult = wrapper.GetResult(); 95 | androidResultWrapper = null; 96 | androidRecognizer.Clean(); 97 | 98 | if (recognitionResult.IsError) { 99 | FireOnError(new Exception(recognitionResult.ErrorMessage)); 100 | } else { 101 | var request = new AIRequest { 102 | Query = recognitionResult.RecognitionResults, 103 | Confidence = recognitionResult.Confidence 104 | }; 105 | 106 | var aiResponse = apiAi.TextRequest(request); 107 | ProcessResult(aiResponse); 108 | } 109 | } 110 | } 111 | #endif 112 | 113 | public void StartListening(AudioSource audioSource) 114 | { 115 | lock (thisLock) { 116 | if (!recordingActive) { 117 | this.audioSource = audioSource; 118 | StartRecording(); 119 | } else { 120 | Debug.LogWarning("Can't start new recording session while another recording session active"); 121 | } 122 | } 123 | } 124 | 125 | public void StartNativeRecognition(){ 126 | if (Application.platform != RuntimePlatform.Android) { 127 | throw new InvalidOperationException("Now only Android supported"); 128 | } 129 | 130 | #if UNITY_ANDROID 131 | if (androidResultWrapper == null) { 132 | androidResultWrapper = androidRecognizer.Recognize(config.Language.code); 133 | } 134 | #endif 135 | } 136 | 137 | public void StopListening() 138 | { 139 | if (recordingActive) { 140 | 141 | float[] samples = null; 142 | 143 | lock (thisLock) { 144 | if (recordingActive) { 145 | StopRecording(); 146 | samples = new float[audioSource.clip.samples]; 147 | audioSource.clip.GetData(samples, 0); 148 | audioSource = null; 149 | } 150 | } 151 | 152 | new Thread(StartVoiceRequest).Start(samples); 153 | } 154 | } 155 | 156 | private void StartVoiceRequest(object parameter){ 157 | float[] samples = (float[])parameter; 158 | if (samples != null) { 159 | try { 160 | var aiResponse = apiAi.VoiceRequest(samples); 161 | ProcessResult(aiResponse); 162 | } catch (Exception ex) { 163 | FireOnError(ex); 164 | } 165 | } 166 | } 167 | 168 | private void ProcessResult(AIResponse aiResponse) 169 | { 170 | if (aiResponse != null) { 171 | FireOnResult(aiResponse); 172 | } else { 173 | FireOnError(new Exception("API.AI Service returns null")); 174 | } 175 | } 176 | 177 | private void StartRecording() 178 | { 179 | audioSource.clip = Microphone.Start(null, true, 20, 16000); 180 | recordingActive = true; 181 | FireOnListeningStarted(); 182 | } 183 | 184 | private void StopRecording() 185 | { 186 | Microphone.End(null); 187 | recordingActive = false; 188 | FireOnListeningFinished(); 189 | } 190 | 191 | private void FireOnResult(AIResponse aiResponse){ 192 | var onResult = OnResult; 193 | if (onResult != null) { 194 | onResult(this, new AIResponseEventArgs(aiResponse)); 195 | } 196 | } 197 | 198 | private void FireOnError(Exception e){ 199 | var onError = OnError; 200 | if (onError != null) { 201 | onError(this, new AIErrorEventArgs(e)); 202 | } 203 | } 204 | 205 | private void FireOnListeningStarted(){ 206 | var onListeningStarted = OnListeningStarted; 207 | if (onListeningStarted != null) { 208 | onListeningStarted(this, EventArgs.Empty); 209 | } 210 | } 211 | 212 | private void FireOnListeningFinished(){ 213 | var onListeningFinished = OnListeningFinished; 214 | if (onListeningFinished != null) { 215 | onListeningFinished(this, EventArgs.Empty); 216 | } 217 | } 218 | 219 | public AIResponse TextRequest(string request) 220 | { 221 | return apiAi.TextRequest(request); 222 | } 223 | 224 | private void ResetContexts() 225 | { 226 | // TODO 227 | } 228 | 229 | } 230 | 231 | public class AIResponseEventArgs : EventArgs 232 | { 233 | private readonly AIResponse response; 234 | 235 | public AIResponse Response { 236 | get { 237 | return response; 238 | } 239 | } 240 | 241 | public AIResponseEventArgs(AIResponse response) 242 | { 243 | this.response = response; 244 | } 245 | } 246 | 247 | public class AIErrorEventArgs : EventArgs 248 | { 249 | 250 | private readonly Exception exception; 251 | 252 | public Exception Exception { 253 | get { 254 | return exception; 255 | } 256 | } 257 | 258 | public AIErrorEventArgs(Exception ex) 259 | { 260 | exception = ex; 261 | } 262 | } 263 | } 264 | 265 | -------------------------------------------------------------------------------- /native/Android/UnityHelper/app/src/main/java/ai/api/unityhelper/RecognitionHelper.java: -------------------------------------------------------------------------------- 1 | /** 2 | * Copyright 2017 Google Inc. All Rights Reserved. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * http://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | package ai.api.unityhelper; 18 | 19 | import android.annotation.TargetApi; 20 | import android.content.ComponentName; 21 | import android.content.Context; 22 | import android.content.Intent; 23 | import android.os.Build; 24 | import android.os.Bundle; 25 | import android.os.Handler; 26 | import android.speech.RecognitionListener; 27 | import android.speech.RecognizerIntent; 28 | import android.speech.SpeechRecognizer; 29 | import android.util.Log; 30 | 31 | import org.json.JSONArray; 32 | import org.json.JSONException; 33 | import org.json.JSONObject; 34 | 35 | import java.util.ArrayList; 36 | import java.util.HashMap; 37 | import java.util.Map; 38 | 39 | 40 | public class RecognitionHelper { 41 | 42 | private static final String TAG = RecognitionHelper.class.getName(); 43 | 44 | private SpeechRecognizer speechRecognizer; 45 | private final Object speechRecognizerLock = new Object(); 46 | private volatile boolean recognitionActive = false; 47 | private Context context; 48 | private Handler handler; 49 | 50 | private RecognitionResultObject resultObject; 51 | 52 | private final Map errorMessages = new HashMap(); 53 | 54 | { 55 | errorMessages.put(1, "Network operation timed out."); 56 | errorMessages.put(2, "Other network related errors."); 57 | errorMessages.put(3, "Audio recording error."); 58 | errorMessages.put(4, "Server sends error status."); 59 | errorMessages.put(5, "Other client side errors."); 60 | errorMessages.put(6, "No speech input."); 61 | errorMessages.put(7, "No recognition result matched."); 62 | errorMessages.put(8, "RecognitionService busy."); 63 | errorMessages.put(9, "Insufficient permissions."); 64 | } 65 | 66 | public RecognitionHelper() { 67 | } 68 | 69 | public void initialize(Context context){ 70 | this.context = context; 71 | handler = new Handler(context.getMainLooper()); 72 | } 73 | 74 | public RecognitionResultObject recognize(final String lang) { 75 | try { 76 | if (!recognitionActive) { 77 | resultObject = new RecognitionResultObject(); 78 | startListening(lang); 79 | } 80 | 81 | return resultObject; 82 | } catch (Exception e) { 83 | 84 | resultObject = null; 85 | 86 | JSONObject result = new JSONObject(); 87 | 88 | try { 89 | result.put("status", "error"); 90 | result.put("errorMessage", e.getMessage()); 91 | } catch (JSONException jsonEx) { 92 | Log.e(TAG, jsonEx.getMessage(), jsonEx); 93 | } 94 | RecognitionResultObject errorResultObject = new RecognitionResultObject(); 95 | errorResultObject.setResult(result.toString()); 96 | return errorResultObject; 97 | } 98 | 99 | } 100 | 101 | public void clean(){ 102 | resultObject = null; 103 | } 104 | 105 | /** 106 | * 107 | * @param lang recognition language 108 | */ 109 | private void startListening(final String lang) { 110 | if (!recognitionActive) { 111 | 112 | final Intent sttIntent = new Intent(RecognizerIntent.ACTION_RECOGNIZE_SPEECH); 113 | sttIntent.putExtra(RecognizerIntent.EXTRA_LANGUAGE_MODEL, 114 | RecognizerIntent.LANGUAGE_MODEL_FREE_FORM); 115 | 116 | final String language = lang.replace('-', '_'); 117 | 118 | sttIntent.putExtra(RecognizerIntent.EXTRA_LANGUAGE, language); 119 | sttIntent.putExtra(RecognizerIntent.EXTRA_LANGUAGE_PREFERENCE, language); 120 | 121 | // WORKAROUND for https://code.google.com/p/android/issues/detail?id=75347 122 | // TODO Must be removed after fix in Android 123 | sttIntent.putExtra("android.speech.extra.EXTRA_ADDITIONAL_LANGUAGES", new String[]{}); 124 | 125 | runInUiThread(new Runnable() { 126 | @Override 127 | public void run() { 128 | initializeRecognizer(); 129 | 130 | speechRecognizer.startListening(sttIntent); 131 | recognitionActive = true; 132 | } 133 | }); 134 | 135 | } else { 136 | Log.w(TAG, "Trying to start recognition while another recognition active"); 137 | } 138 | } 139 | 140 | protected void onError(final String errorMessage) { 141 | JSONObject resultJson = new JSONObject(); 142 | 143 | try { 144 | resultJson.put("status", "error"); 145 | resultJson.put("errorMessage", errorMessage); 146 | } catch (JSONException je) { 147 | Log.e(TAG, je.getMessage(), je); 148 | } 149 | 150 | String resultJsonString = resultJson.toString(); 151 | if (resultObject != null) { 152 | resultObject.setResult(resultJsonString); 153 | } 154 | } 155 | 156 | protected void onResults(final Bundle results) { 157 | 158 | JSONObject resultJson = new JSONObject(); 159 | 160 | try { 161 | 162 | resultJson.put("status", "success"); 163 | 164 | final ArrayList recognitionResults = results 165 | .getStringArrayList(SpeechRecognizer.RESULTS_RECOGNITION); 166 | 167 | if (recognitionResults == null || recognitionResults.size() == 0) { 168 | resultJson.put("recognitionResults", new JSONArray()); 169 | } else { 170 | resultJson.put("recognitionResults", new JSONArray(recognitionResults)); 171 | 172 | float[] rates = null; 173 | 174 | if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.ICE_CREAM_SANDWICH) { 175 | rates = results.getFloatArray(SpeechRecognizer.CONFIDENCE_SCORES); 176 | if (rates != null && rates.length > 0) { 177 | final JSONArray ratesArray = new JSONArray(); 178 | for (int i = 0; i < rates.length; i++) { 179 | ratesArray.put(rates[i]); 180 | } 181 | resultJson.put("confidence", ratesArray); 182 | } 183 | } 184 | } 185 | 186 | 187 | } catch (JSONException je) { 188 | Log.e(TAG, je.getMessage(), je); 189 | } 190 | 191 | clearRecognizer(); 192 | String resultJsonString = resultJson.toString(); 193 | if (resultObject != null) { 194 | resultObject.setResult(resultJsonString); 195 | } 196 | } 197 | 198 | protected void initializeRecognizer() { 199 | synchronized (speechRecognizerLock) { 200 | if (speechRecognizer != null) { 201 | speechRecognizer.destroy(); 202 | speechRecognizer = null; 203 | } 204 | 205 | final ComponentName googleRecognizerComponent = RecognizerChecker.findGoogleRecognizer(context); 206 | 207 | if (googleRecognizerComponent == null) { 208 | speechRecognizer = SpeechRecognizer.createSpeechRecognizer(context); 209 | } else { 210 | speechRecognizer = SpeechRecognizer.createSpeechRecognizer(context, googleRecognizerComponent); 211 | } 212 | 213 | speechRecognizer.setRecognitionListener(new InternalRecognitionListener()); 214 | } 215 | } 216 | 217 | protected void clearRecognizer() { 218 | if (speechRecognizer != null) { 219 | synchronized (speechRecognizerLock) { 220 | if (speechRecognizer != null) { 221 | speechRecognizer.destroy(); 222 | speechRecognizer = null; 223 | } 224 | } 225 | } 226 | } 227 | 228 | private void runInUiThread(final Runnable runnable) { 229 | handler.post(runnable); 230 | } 231 | 232 | private class InternalRecognitionListener implements RecognitionListener { 233 | 234 | @Override 235 | public void onReadyForSpeech(final Bundle params) { 236 | 237 | } 238 | 239 | @Override 240 | public void onBeginningOfSpeech() { 241 | 242 | } 243 | 244 | @Override 245 | public void onRmsChanged(final float rmsdB) { 246 | 247 | } 248 | 249 | @Override 250 | public void onBufferReceived(final byte[] buffer) { 251 | 252 | } 253 | 254 | @Override 255 | public void onEndOfSpeech() { 256 | 257 | } 258 | 259 | @Override 260 | public void onError(final int error) { 261 | recognitionActive = false; 262 | 263 | String aiError; 264 | if (errorMessages.containsKey(error)) { 265 | final String description = errorMessages.get(error); 266 | aiError = "Speech recognition engine error: " + description; 267 | } else { 268 | aiError = "Speech recognition engine error: " + error; 269 | } 270 | RecognitionHelper.this.onError(aiError); 271 | } 272 | 273 | @TargetApi(14) 274 | @Override 275 | public void onResults(final Bundle results) { 276 | if (recognitionActive) { 277 | recognitionActive = false; 278 | 279 | RecognitionHelper.this.onResults(results); 280 | } 281 | } 282 | 283 | @Override 284 | public void onPartialResults(final Bundle partialResults) { 285 | 286 | } 287 | 288 | @Override 289 | public void onEvent(final int eventType, final Bundle params) { 290 | 291 | } 292 | } 293 | 294 | } 295 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | Apache License 2 | Version 2.0, January 2004 3 | http://www.apache.org/licenses/ 4 | 5 | TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION 6 | 7 | 1. Definitions. 8 | 9 | "License" shall mean the terms and conditions for use, reproduction, and 10 | distribution as defined by Sections 1 through 9 of this document. 11 | 12 | "Licensor" shall mean the copyright owner or entity authorized by the copyright 13 | owner that is granting the License. 14 | 15 | "Legal Entity" shall mean the union of the acting entity and all other entities 16 | that control, are controlled by, or are under common control with that entity. 17 | For the purposes of this definition, "control" means (i) the power, direct or 18 | indirect, to cause the direction or management of such entity, whether by 19 | contract or otherwise, or (ii) ownership of fifty percent (50%) or more of the 20 | outstanding shares, or (iii) beneficial ownership of such entity. 21 | 22 | "You" (or "Your") shall mean an individual or Legal Entity exercising 23 | permissions granted by this License. 24 | 25 | "Source" form shall mean the preferred form for making modifications, including 26 | but not limited to software source code, documentation source, and configuration 27 | files. 28 | 29 | "Object" form shall mean any form resulting from mechanical transformation or 30 | translation of a Source form, including but not limited to compiled object code, 31 | generated documentation, and conversions to other media types. 32 | 33 | "Work" shall mean the work of authorship, whether in Source or Object form, made 34 | available under the License, as indicated by a copyright notice that is included 35 | in or attached to the work (an example is provided in the Appendix below). 36 | 37 | "Derivative Works" shall mean any work, whether in Source or Object form, that 38 | is based on (or derived from) the Work and for which the editorial revisions, 39 | annotations, elaborations, or other modifications represent, as a whole, an 40 | original work of authorship. For the purposes of this License, Derivative Works 41 | shall not include works that remain separable from, or merely link (or bind by 42 | name) to the interfaces of, the Work and Derivative Works thereof. 43 | 44 | "Contribution" shall mean any work of authorship, including the original version 45 | of the Work and any modifications or additions to that Work or Derivative Works 46 | thereof, that is intentionally submitted to Licensor for inclusion in the Work 47 | by the copyright owner or by an individual or Legal Entity authorized to submit 48 | on behalf of the copyright owner. For the purposes of this definition, 49 | "submitted" means any form of electronic, verbal, or written communication sent 50 | to the Licensor or its representatives, including but not limited to 51 | communication on electronic mailing lists, source code control systems, and 52 | issue tracking systems that are managed by, or on behalf of, the Licensor for 53 | the purpose of discussing and improving the Work, but excluding communication 54 | that is conspicuously marked or otherwise designated in writing by the copyright 55 | owner as "Not a Contribution." 56 | 57 | "Contributor" shall mean Licensor and any individual or Legal Entity on behalf 58 | of whom a Contribution has been received by Licensor and subsequently 59 | incorporated within the Work. 60 | 61 | 2. Grant of Copyright License. 62 | 63 | Subject to the terms and conditions of this License, each Contributor hereby 64 | grants to You a perpetual, worldwide, non-exclusive, no-charge, royalty-free, 65 | irrevocable copyright license to reproduce, prepare Derivative Works of, 66 | publicly display, publicly perform, sublicense, and distribute the Work and such 67 | Derivative Works in Source or Object form. 68 | 69 | 3. Grant of Patent License. 70 | 71 | Subject to the terms and conditions of this License, each Contributor hereby 72 | grants to You a perpetual, worldwide, non-exclusive, no-charge, royalty-free, 73 | irrevocable (except as stated in this section) patent license to make, have 74 | made, use, offer to sell, sell, import, and otherwise transfer the Work, where 75 | such license applies only to those patent claims licensable by such Contributor 76 | that are necessarily infringed by their Contribution(s) alone or by combination 77 | of their Contribution(s) with the Work to which such Contribution(s) was 78 | submitted. If You institute patent litigation against any entity (including a 79 | cross-claim or counterclaim in a lawsuit) alleging that the Work or a 80 | Contribution incorporated within the Work constitutes direct or contributory 81 | patent infringement, then any patent licenses granted to You under this License 82 | for that Work shall terminate as of the date such litigation is filed. 83 | 84 | 4. Redistribution. 85 | 86 | You may reproduce and distribute copies of the Work or Derivative Works thereof 87 | in any medium, with or without modifications, and in Source or Object form, 88 | provided that You meet the following conditions: 89 | 90 | You must give any other recipients of the Work or Derivative Works a copy of 91 | this License; and 92 | You must cause any modified files to carry prominent notices stating that You 93 | changed the files; and 94 | You must retain, in the Source form of any Derivative Works that You distribute, 95 | all copyright, patent, trademark, and attribution notices from the Source form 96 | of the Work, excluding those notices that do not pertain to any part of the 97 | Derivative Works; and 98 | If the Work includes a "NOTICE" text file as part of its distribution, then any 99 | Derivative Works that You distribute must include a readable copy of the 100 | attribution notices contained within such NOTICE file, excluding those notices 101 | that do not pertain to any part of the Derivative Works, in at least one of the 102 | following places: within a NOTICE text file distributed as part of the 103 | Derivative Works; within the Source form or documentation, if provided along 104 | with the Derivative Works; or, within a display generated by the Derivative 105 | Works, if and wherever such third-party notices normally appear. The contents of 106 | the NOTICE file are for informational purposes only and do not modify the 107 | License. You may add Your own attribution notices within Derivative Works that 108 | You distribute, alongside or as an addendum to the NOTICE text from the Work, 109 | provided that such additional attribution notices cannot be construed as 110 | modifying the License. 111 | You may add Your own copyright statement to Your modifications and may provide 112 | additional or different license terms and conditions for use, reproduction, or 113 | distribution of Your modifications, or for any such Derivative Works as a whole, 114 | provided Your use, reproduction, and distribution of the Work otherwise complies 115 | with the conditions stated in this License. 116 | 117 | 5. Submission of Contributions. 118 | 119 | Unless You explicitly state otherwise, any Contribution intentionally submitted 120 | for inclusion in the Work by You to the Licensor shall be under the terms and 121 | conditions of this License, without any additional terms or conditions. 122 | Notwithstanding the above, nothing herein shall supersede or modify the terms of 123 | any separate license agreement you may have executed with Licensor regarding 124 | such Contributions. 125 | 126 | 6. Trademarks. 127 | 128 | This License does not grant permission to use the trade names, trademarks, 129 | service marks, or product names of the Licensor, except as required for 130 | reasonable and customary use in describing the origin of the Work and 131 | reproducing the content of the NOTICE file. 132 | 133 | 7. Disclaimer of Warranty. 134 | 135 | Unless required by applicable law or agreed to in writing, Licensor provides the 136 | Work (and each Contributor provides its Contributions) on an "AS IS" BASIS, 137 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied, 138 | including, without limitation, any warranties or conditions of TITLE, 139 | NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A PARTICULAR PURPOSE. You are 140 | solely responsible for determining the appropriateness of using or 141 | redistributing the Work and assume any risks associated with Your exercise of 142 | permissions under this License. 143 | 144 | 8. Limitation of Liability. 145 | 146 | In no event and under no legal theory, whether in tort (including negligence), 147 | contract, or otherwise, unless required by applicable law (such as deliberate 148 | and grossly negligent acts) or agreed to in writing, shall any Contributor be 149 | liable to You for damages, including any direct, indirect, special, incidental, 150 | or consequential damages of any character arising as a result of this License or 151 | out of the use or inability to use the Work (including but not limited to 152 | damages for loss of goodwill, work stoppage, computer failure or malfunction, or 153 | any and all other commercial damages or losses), even if such Contributor has 154 | been advised of the possibility of such damages. 155 | 156 | 9. Accepting Warranty or Additional Liability. 157 | 158 | While redistributing the Work or Derivative Works thereof, You may choose to 159 | offer, and charge a fee for, acceptance of support, warranty, indemnity, or 160 | other liability obligations and/or rights consistent with this License. However, 161 | in accepting such obligations, You may act only on Your own behalf and on Your 162 | sole responsibility, not on behalf of any other Contributor, and only if You 163 | agree to indemnify, defend, and hold each Contributor harmless for any liability 164 | incurred by, or claims asserted against, such Contributor by reason of your 165 | accepting any such warranty or additional liability. 166 | 167 | END OF TERMS AND CONDITIONS 168 | 169 | APPENDIX: How to apply the Apache License to your work 170 | 171 | To apply the Apache License to your work, attach the following boilerplate 172 | notice, with the fields enclosed by brackets "[]" replaced with your own 173 | identifying information. (Don't include the brackets!) The text should be 174 | enclosed in the appropriate comment syntax for the file format. We also 175 | recommend that a file or class name and description of purpose be included on 176 | the same "printed page" as the copyright notice for easier identification within 177 | third-party archives. 178 | 179 | Copyright [yyyy] [name of copyright owner] 180 | 181 | Licensed under the Apache License, Version 2.0 (the "License"); 182 | you may not use this file except in compliance with the License. 183 | You may obtain a copy of the License at 184 | 185 | http://www.apache.org/licenses/LICENSE-2.0 186 | 187 | Unless required by applicable law or agreed to in writing, software 188 | distributed under the License is distributed on an "AS IS" BASIS, 189 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 190 | See the License for the specific language governing permissions and 191 | limitations under the License. -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # DEPRECATED Api.ai: Unity Plugin 2 | 3 | | Deprecated | 4 | |-------| 5 | | This Dialogflow client library and Dialogflow API V1 [have been deprecated and will be shut down on October 23th, 2019](https://blog.dialogflow.com/post/migrate-to-dialogflow-api-v2/). Please [migrate to Dialogflow API V2](https://cloud.google.com/dialogflow-enterprise/docs/migrating). | 6 | 7 | The Api.ai Unity Plugin makes it easy to integrate the [Api.ai natural language processing API](http://api.ai) into your Unity project. Api.ai allows the use of voice commands and integration with dialog scenarios defined for a particular agent in Api.ai. 8 | 9 | The Library provides a simple programming interface for making text and voice requests to the Api.ai service. 10 | 11 | ## Getting started 12 | 13 | To use the Unity SDK you must have Unity installed on your computer. See [official website](http://unity3d.com) for details. 14 | 15 | ### Installation 16 | 17 | [Download](https://www.assetstore.unity3d.com/en/#!/content/31498) plugin bundle from the Unity Asset Store, and unpack it to the Assets folder in your project. 18 | 19 | ### Example 20 | 21 | First, load and watch the **ServiceSample** scene from the Api.ai bundle. 22 | 23 | ![Api.ai Bundle](docs/images/bundle.png) 24 | 25 | This sample demonstrates Api.ai SDK features. 26 | 27 | ![Running Sample](docs/images/runningSample.png) 28 | 29 | * Top buttons start and stop listening accordingly. 30 | * With the text field and **Send Text** button you can make text requests to the server. 31 | * **Android Recognizer** button demonstrates recognition options available only on Android devices. 32 | 33 | **ApiAiModule** file contains C# code for the sample scene. You can take a look at the methods in the module. 34 | 35 | #### Initialization 36 | 37 | In the ‘Start’ method, initialize the ‘ApiAiUnity’ object with access keys (use your access keys from [api.ai](https://api.ai) console). 38 | 39 | ```csharp 40 | const string ACCESS_TOKEN = "3485a96fb27744db83e78b8c4bc9e7b7"; 41 | var config = new AIConfiguration(ACCESS_TOKEN, SupportedLanguage.English); 42 | apiAiUnity = new ApiAiUnity(); 43 | apiAiUnity.Initialize(config); 44 | ``` 45 | 46 | and configure handlers for ‘OnResult’ and ‘OnError’ events 47 | 48 | ```csharp 49 | apiAiUnity.OnError += HandleOnError; 50 | apiAiUnity.OnResult += HandleOnResult; 51 | ``` 52 | 53 | #### Results processing 54 | 55 | In ‘HandleOnResult’ and ‘HandleOnError’ you need to process the server response. In the example, it will be printed to the text field. 56 | 57 | ```csharp 58 | void HandleOnResult(object sender, AIResponseEventArgs e) 59 | { 60 | var aiResponse = e.Response; 61 | if (aiResponse != null) 62 | { 63 | var outText = JsonConvert.SerializeObject(aiResponse, jsonSettings); 64 | Debug.Log(outText); 65 | answerTextField.text = outText; 66 | } 67 | else 68 | { 69 | Debug.LogError("Response is null"); 70 | } 71 | } 72 | ``` 73 | 74 | #### Start and stop listening 75 | 76 | The methods ‘StartListening’ and ‘StopListening’ are connected to particular buttons in the scene UI. 77 | 78 | ![OnClick](docs/images/buttonOnClick.png) 79 | 80 | In the ‘StartListening` method you need to pass the ‘AudioSource’ object to the ‘apiAi’ object. ‘AudioSource’ will be used for audio capturing. 81 | ``` csharp 82 | public void StartListening() 83 | { 84 | var aud = GetComponent(); 85 | apiAiUnity.StartListening(aud); 86 | } 87 | ``` 88 | 89 | The ‘StopListening’ method is quite simple. All the work is done in the ‘ApiAi’ module. 90 | 91 | ``` csharp 92 | public void StopListening() 93 | { 94 | try 95 | { 96 | apiAiUnity.StopListening(); 97 | } 98 | catch (Exception ex) 99 | { 100 | Debug.LogException(ex); 101 | } 102 | } 103 | ``` 104 | 105 | #### Text requests 106 | 107 | Another way to make requests is through **text requests**. In this case, results will not fire the ‘OnResult’ event. All work will be done simultaneously. 108 | 109 | ``` csharp 110 | public void SendText() 111 | { 112 | try 113 | { 114 | var text = inputTextField.text; 115 | var response = apiAiUnity.TextRequest(text); 116 | if (response != null) 117 | { 118 | var outText = JsonConvert.SerializeObject(response, jsonSettings); 119 | Debug.Log("Result: " + outText); 120 | answerTextField.text = outText; 121 | } 122 | else 123 | { 124 | Debug.LogError("Response is null"); 125 | } 126 | } 127 | catch (Exception ex) 128 | { 129 | Debug.LogException(ex); 130 | } 131 | } 132 | ``` 133 | 134 | #### Native Android recognition 135 | 136 | In some cases it will be useful to use the Google recognition engine built into the Android platform. This way has at least one advantage: using voice activity detection. This means you don't need to stop listening manually. 137 | 138 | To start native Android recognition, all you need is a call appropriate method: 139 | 140 | ``` csharp 141 | public void StartNativeRecognition() 142 | { 143 | try 144 | { 145 | apiAiUnity.StartNativeRecognition(); 146 | } catch (Exception ex) 147 | { 148 | Debug.LogException(ex); 149 | } 150 | } 151 | ``` 152 | 153 | But the Unity platform needs one more step to make the Unity<=>Android interop work. You need to call the Update method once per frame. To do this, enter the code below: 154 | 155 | ``` csharp 156 | // Update is called once per frame 157 | void Update() 158 | { 159 | if (apiAiUnity != null) 160 | { 161 | apiAiUnity.Update(); 162 | } 163 | } 164 | ``` 165 | 166 | ### Create helper module 167 | 168 | * Add a new script to the Assets folder (ApiAiModule, for example) ![Create script](docs/images/create_script.png) 169 | 170 | * Your new module should look like this: 171 | 172 | ``` csharp 173 | using UnityEngine; 174 | using System.Collections; 175 | 176 | public class ApiAiModule : MonoBehaviour { 177 | 178 | // Use this for initialization 179 | void Start () { 180 | 181 | } 182 | 183 | // Update is called once per frame 184 | void Update () { 185 | 186 | } 187 | } 188 | ``` 189 | 190 | * First add Api.ai using 191 | 192 | ``` csharp 193 | using fastJSON; 194 | using ApiAiSDK; 195 | using ApiAiSDK.Model; 196 | using ApiAiSDK.Unity; 197 | ``` 198 | 199 | * Add a private field to your module to keep the reference to the SDK object: 200 | 201 | ``` csharp 202 | private ApiAiUnity apiAiUnity; 203 | ``` 204 | 205 | * At the start of your module, the ApiAiUnity object must be initialized. Required data for initialization are the keys from your development console on [api.ai](http://api.ai) service and a supported language: 206 | 207 | ``` csharp 208 | // Use this for initialization 209 | void Start() 210 | { 211 | const string ACCESS_TOKEN = "your_access_token"; 212 | 213 | var config = new AIConfiguration(ACCESS_TOKEN, SupportedLanguage.English); 214 | 215 | apiAiUnity = new ApiAiUnity(); 216 | apiAiUnity.Initialize(config); 217 | 218 | apiAiUnity.OnResult += HandleOnResult; 219 | apiAiUnity.OnError += HandleOnError; 220 | } 221 | ``` 222 | 223 | * ‘OnError’ and ‘OnResult’ events are used for processing service results. Handling functions must look like this: 224 | 225 | ``` csharp 226 | void HandleOnResult(object sender, AIResponseEventArgs e) 227 | { 228 | var aiResponse = e.Response; 229 | if (aiResponse != null) { 230 | // get data from aiResponse 231 | } else { 232 | Debug.LogError("Response is null"); 233 | } 234 | } 235 | 236 | void HandleOnError(object sender, AIErrorEventArgs e) 237 | { 238 | Debug.LogException(e.Exception); 239 | } 240 | ``` 241 | 242 | ### Usage 243 | 244 | ApiAi Unity SDK lets you perform the following actions: 245 | 246 | 1. Start the listening process and then send voice data to the Api.ai service for recognition and processing 247 | 2. Send a simple text request to the Api.ai service 248 | 3. Use the integrated Android recognition engine to send recognized text to the Api.ai service for processing 249 | 250 | #### Using Api.ai recognition 251 | 252 | To use the Api.ai voice recognition service you need to provide the ApiAiUnity object with a valid ‘AudioSource’ object. This can usually be received by using the `GetComponent()` function. 253 | 254 | A temporary limitation of this situation is that if you are using Api.ai recognition, you need to stop listening manually. You can use these code snippets to start and stop listening: 255 | 256 | ``` csharp 257 | public void StartListening() 258 | { 259 | try { 260 | var aud = GetComponent(); 261 | apiAiUnity.StartListening(aud); 262 | } catch (Exception ex) { 263 | Debug.LogException(ex); 264 | } 265 | } 266 | 267 | public void StopListening() 268 | { 269 | try { 270 | apiAiUnity.StopListening(); 271 | } catch (Exception ex) { 272 | Debug.LogException(ex); 273 | } 274 | } 275 | ``` 276 | 277 | After you start or stop listening, you will receive the Api.ai result in the ‘OnResult’ handler. 278 | 279 | **Note**: In some cases the Unity application must get Sound Recording privileges in order to use the Microphone. To do so, change your helper module Start function like this: 280 | 281 | ``` csharp 282 | IEnumerator Start() 283 | { 284 | // check access to the Microphone 285 | yield return Application.RequestUserAuthorization (UserAuthorization.Microphone); 286 | if (!Application.HasUserAuthorization(UserAuthorization.Microphone)) { 287 | throw new NotSupportedException ("Microphone using not authorized"); 288 | } 289 | 290 | ... // apiAiUnity initialization... 291 | } 292 | ``` 293 | 294 | #### Simple text requests 295 | 296 | The use of text requests is very simple. All you need is a text query. 297 | 298 | ``` csharp 299 | public void SendText() 300 | { 301 | var text = "hello"; 302 | try { 303 | var response = apiAiUnity.TextRequest(text); 304 | if (response != null) { 305 | // process response 306 | } else { 307 | Debug.LogError("Response is null"); 308 | } 309 | } catch (Exception ex) { 310 | Debug.LogException(ex); 311 | } 312 | } 313 | ``` 314 | 315 | **Note**: You will receive the Api.ai result immediately, not in the ‘OnResult’ handler. 316 | 317 | #### Using native Android recognition 318 | 319 | This situation is only applicable for Android Unity applications. You can check if an application is running on the Android platform using this simple code snippet: 320 | 321 | ``` csharp 322 | if (Application.platform == RuntimePlatform.Android) { 323 | // you can use Android recognition here 324 | } 325 | ``` 326 | 327 | Because native Android recognition uses a Unity-to-Native bridge, you need to add the following code to the script ‘Update’ method. This code is used to check recognition results from the native layer, since callbacks are not supported in this case. 328 | 329 | ``` csharp 330 | if (apiAiUnity != null) { 331 | apiAiUnity.Update(); 332 | } 333 | ``` 334 | 335 | To start the recognition process, use the simple call of the ‘StartNativeRecognition’ method. 336 | 337 | ``` csharp 338 | public void StartNativeRecognition(){ 339 | try { 340 | apiAiUnity.StartNativeRecognition(); 341 | } catch (Exception ex) { 342 | Debug.LogException (ex); 343 | } 344 | } 345 | ``` 346 | 347 | ## How to make contributions? 348 | Please read and follow the steps in the [CONTRIBUTING.md](CONTRIBUTING.md). 349 | 350 | ## License 351 | See [LICENSE](LICENSE). 352 | 353 | ## Terms 354 | Your use of this sample is subject to, and by using or downloading the sample files you agree to comply with, the [Google APIs Terms of Service](https://developers.google.com/terms/). 355 | 356 | This is not an official Google product. 357 | --------------------------------------------------------------------------------