porcupine/demo/java/src/ai/picovoice/porcupinedemo/FileDemo.java
Go to the documentation of this file.
1 /*
2  Copyright 2018-2021 Picovoice Inc.
3 
4  You may not use this file except in compliance with the license. A copy of the license is
5  located in the "LICENSE" file accompanying this source.
6 
7  Unless required by applicable law or agreed to in writing, software distributed under the
8  License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either
9  express or implied. See the License for the specific language governing permissions and
10  limitations under the License.
11 */
12 
13 package ai.picovoice.porcupinedemo;
14 
16 import org.apache.commons.cli.*;
17 
18 import javax.sound.sampled.AudioFormat;
19 import javax.sound.sampled.AudioInputStream;
20 import javax.sound.sampled.AudioSystem;
21 import javax.sound.sampled.UnsupportedAudioFileException;
22 import java.io.File;
23 import java.io.IOException;
24 import java.nio.ByteBuffer;
25 import java.nio.ByteOrder;
26 import java.util.Arrays;
27 
28 public class FileDemo {
29 
30  public static void runDemo(String accessKey, File inputAudioFile, String libPath,
31  String modelPath, String[] keywordPaths, float[] sensitivities) {
32 
33  // create keywords from keyword_paths
34  String[] keywords = new String[keywordPaths.length];
35  for (int i = 0; i < keywordPaths.length; i++) {
36  File keywordFile = new File(keywordPaths[i]);
37  if (!keywordFile.exists())
38  throw new IllegalArgumentException(String.format("Keyword file at '%s' " +
39  "does not exist", keywordPaths[i]));
40  keywords[i] = keywordFile.getName().split("_")[0];
41  }
42 
43  AudioInputStream audioInputStream;
44  try {
45  audioInputStream = AudioSystem.getAudioInputStream(inputAudioFile);
46  } catch (UnsupportedAudioFileException e) {
47  System.err.println("Audio format not supported. Please provide an input file of .au, .aiff or .wav format");
48  return;
49  } catch (IOException e) {
50  System.err.println("Could not find input audio file at " + inputAudioFile);
51  return;
52  }
53 
54  Porcupine porcupine = null;
55  try {
56  porcupine = new Porcupine.Builder()
57  .setAccessKey(accessKey)
58  .setLibraryPath(libPath)
59  .setModelPath(modelPath)
60  .setKeywordPaths(keywordPaths)
61  .setSensitivities(sensitivities)
62  .build();
63 
64  AudioFormat audioFormat = audioInputStream.getFormat();
65 
66  if (audioFormat.getSampleRate() != 16000.0f || audioFormat.getSampleSizeInBits() != 16) {
67  throw new IllegalArgumentException(String.format("Invalid input audio file format. " +
68  "Input file must be a %dkHz, 16-bit audio file.", porcupine.getSampleRate()));
69  }
70 
71  if (audioFormat.getChannels() > 1) {
72  System.out.println("Picovoice processes single-channel audio, but a multi-channel file was provided. " +
73  "Processing leftmost channel only.");
74  }
75 
76  int frameIndex = 0;
77  long totalSamplesRead = 0;
78  short[] porcupineFrame = new short[porcupine.getFrameLength()];
79 
80  ByteBuffer sampleBuffer = ByteBuffer.allocate(audioFormat.getFrameSize());
81  sampleBuffer.order(ByteOrder.LITTLE_ENDIAN);
82  while (audioInputStream.available() != 0) {
83  totalSamplesRead++;
84 
85  int numBytesRead = audioInputStream.read(sampleBuffer.array());
86  if (numBytesRead < 2) {
87  break;
88  }
89 
90  porcupineFrame[frameIndex++] = sampleBuffer.getShort(0);
91 
92  if (frameIndex == porcupineFrame.length) {
93  int result = porcupine.process(porcupineFrame);
94  if (result >= 0) {
95  System.out.printf("Detected '%s' at %.02f sec\n", keywords[result],
96  totalSamplesRead / (float) porcupine.getSampleRate());
97  }
98 
99  frameIndex = 0;
100  }
101  }
102  } catch (Exception e) {
103  System.out.println(e.toString());
104  } finally {
105  if (porcupine != null) {
106  porcupine.delete();
107  }
108  }
109  }
110 
111  public static void main(String[] args) {
112 
113  Options options = BuildCommandLineOptions();
114  CommandLineParser parser = new DefaultParser();
115  HelpFormatter formatter = new HelpFormatter();
116 
117  CommandLine cmd;
118  try {
119  cmd = parser.parse(options, args);
120  } catch (ParseException e) {
121  System.out.println(e.getMessage());
122  formatter.printHelp("porcupinefiledemo", options);
123  System.exit(1);
124  return;
125  }
126 
127  if (cmd.hasOption("help")) {
128  formatter.printHelp("porcupinefiledemo", options);
129  return;
130  }
131 
132  String accessKey = cmd.getOptionValue("access_key");
133  String inputAudioPath = cmd.getOptionValue("input_audio_path");
134  String libraryPath = cmd.getOptionValue("library_path");
135  String modelPath = cmd.getOptionValue("model_path");
136  String[] keywords = cmd.getOptionValues("keywords");
137  String[] keywordPaths = cmd.getOptionValues("keyword_paths");
138  String[] sensitivitiesStr = cmd.getOptionValues("sensitivities");
139 
140  // parse sensitivity array
141  float[] sensitivities = null;
142  if (sensitivitiesStr != null) {
143  sensitivities = new float[sensitivitiesStr.length];
144 
145  for (int i = 0; i < sensitivitiesStr.length; i++) {
146  float sensitivity;
147  try {
148  sensitivity = Float.parseFloat(sensitivitiesStr[i]);
149  } catch (Exception e) {
150  throw new IllegalArgumentException("Failed to parse sensitivity value. " +
151  "Must be a floating-point number between [0,1].");
152  }
153 
154  if (sensitivity < 0 || sensitivity > 1) {
155  throw new IllegalArgumentException(String.format("Failed to parse sensitivity value (%s). " +
156  "Must be a floating-point number between [0,1].", sensitivitiesStr[i]));
157  }
158  sensitivities[i] = sensitivity;
159  }
160  }
161 
162  if (accessKey == null || accessKey.length() == 0) {
163  throw new IllegalArgumentException("AccessKey is required for Porcupine.");
164  }
165 
166  if (inputAudioPath == null){
167  throw new IllegalArgumentException("No input audio file provided. This is a required argument.");
168  }
169  File inputAudioFile = new File(inputAudioPath);
170  if (!inputAudioFile.exists()) {
171  throw new IllegalArgumentException(String.format("Audio file at path %s does not exits.", inputAudioPath));
172  }
173 
174  if (libraryPath == null) {
175  libraryPath = Porcupine.LIBRARY_PATH;
176  }
177 
178  if (modelPath == null) {
179  modelPath = Porcupine.MODEL_PATH;
180  }
181 
182  if (keywordPaths == null || keywordPaths.length == 0) {
183  if (keywords == null || keywords.length == 0) {
184  throw new IllegalArgumentException("Either '--keywords' or '--keyword_paths' must be set.");
185  }
186 
187  keywordPaths = new String[keywords.length];
188  for (int i = 0; i < keywords.length; i++) {
189  final String keyword = keywords[i].toUpperCase().replace(" ", "_");
190  try {
191  final Porcupine.BuiltInKeyword builtInKeyword = Porcupine.BuiltInKeyword.valueOf(keyword);
192  keywordPaths[i] = Porcupine.BUILT_IN_KEYWORD_PATHS.get(builtInKeyword);
193  } catch (Exception e) {
194  throw new IllegalArgumentException(String.format("'%s' not a built-in keyword", keyword));
195  }
196  }
197  }
198 
199  if (sensitivities == null) {
200  sensitivities = new float[keywordPaths.length];
201  Arrays.fill(sensitivities, 0.5f);
202  }
203 
204  if (sensitivities.length != keywordPaths.length) {
205  throw new IllegalArgumentException(String.format("Number of keywords (%d) does " +
206  "not match number of sensitivities (%d)", keywordPaths.length, sensitivities.length));
207  }
208 
209  runDemo(accessKey, inputAudioFile, libraryPath, modelPath, keywordPaths, sensitivities);
210  }
211 
212  private static Options BuildCommandLineOptions() {
213  Options options = new Options();
214 
215  options.addOption(Option.builder("a")
216  .longOpt("access_key")
217  .hasArg(true)
218  .desc("AccessKey obtained from Picovoice Console (https://picovoice.ai/console/).")
219  .build());
220 
221  options.addOption(Option.builder("i")
222  .longOpt("input_audio_path")
223  .hasArg(true)
224  .desc("Absolute path to input audio file.")
225  .build());
226 
227  options.addOption(Option.builder("l")
228  .longOpt("library_path")
229  .hasArg(true)
230  .desc("Absolute path to the Porcupine native runtime library.")
231  .build());
232 
233  options.addOption(Option.builder("m")
234  .longOpt("model_path")
235  .hasArg(true)
236  .desc("Absolute path to the file containing model parameters.")
237  .build());
238 
239  options.addOption(Option.builder("k")
240  .longOpt("keywords")
241  .hasArgs()
242  .desc(String.format("List of built-in keywords for detection. Available keywords: %s", Porcupine.BuiltInKeyword.options()))
243  .build());
244 
245  options.addOption(Option.builder("kp")
246  .longOpt("keyword_paths")
247  .hasArgs()
248  .desc("Absolute paths to keyword model files.")
249  .build());
250 
251  options.addOption(Option.builder("s")
252  .longOpt("sensitivities")
253  .hasArgs()
254  .desc("Sensitivities for detecting keywords. Each value should be a number within [0, 1]. A higher " +
255  "sensitivity results in fewer misses at the cost of increasing the false alarm rate. " +
256  "If not set 0.5 will be used.")
257  .build());
258  options.addOption(new Option("h", "help", false, ""));
259 
260  return options;
261  }
262 }
ai.picovoice.porcupine
Definition: android/Porcupine/porcupine/src/main/java/ai/picovoice/porcupine/exception/PorcupineActivationException.java:11
ai.picovoice.porcupinedemo.FileDemo.runDemo
static void runDemo(String accessKey, File inputAudioFile, String libPath, String modelPath, String[] keywordPaths, float[] sensitivities)
Definition: porcupine/demo/java/src/ai/picovoice/porcupinedemo/FileDemo.java:30
ai.picovoice.porcupine.Porcupine.Builder
Definition: android/Porcupine/porcupine/src/main/java/ai/picovoice/porcupine/Porcupine.java:165
ai.picovoice.porcupine.Porcupine.Builder.setKeywordPaths
Builder setKeywordPaths(String[] keywordPaths)
Definition: android/Porcupine/porcupine/src/main/java/ai/picovoice/porcupine/Porcupine.java:183
ai.picovoice.porcupine.Porcupine.delete
void delete()
Definition: android/Porcupine/porcupine/src/main/java/ai/picovoice/porcupine/Porcupine.java:75
ai.picovoice.porcupinedemo.FileDemo.main
static void main(String[] args)
Definition: porcupine/demo/java/src/ai/picovoice/porcupinedemo/FileDemo.java:111
ai.picovoice.porcupine.Porcupine.LIBRARY_PATH
static final String LIBRARY_PATH
Definition: java/src/ai/picovoice/porcupine/Porcupine.java:33
ai.picovoice.porcupine.Porcupine.Builder.build
Porcupine build(Context context)
Definition: android/Porcupine/porcupine/src/main/java/ai/picovoice/porcupine/Porcupine.java:256
f
f
ai.picovoice.porcupine.Porcupine.getFrameLength
native int getFrameLength()
ai.picovoice.porcupine.Porcupine.Builder.setSensitivities
Builder setSensitivities(float[] sensitivities)
Definition: android/Porcupine/porcupine/src/main/java/ai/picovoice/porcupine/Porcupine.java:203
ai.picovoice.porcupine.Porcupine.MODEL_PATH
static final String MODEL_PATH
Definition: java/src/ai/picovoice/porcupine/Porcupine.java:34
ai.picovoice.porcupine.Porcupine.BUILT_IN_KEYWORD_PATHS
static final HashMap< BuiltInKeyword, String > BUILT_IN_KEYWORD_PATHS
Definition: android/Porcupine/porcupine/src/main/java/ai/picovoice/porcupine/Porcupine.java:42
ai
ai.picovoice
python.setup.keywords
keywords
Definition: porcupine/binding/python/setup.py:88
ai.picovoice.porcupine.Porcupine.process
int process(short[] pcm)
Definition: android/Porcupine/porcupine/src/main/java/ai/picovoice/porcupine/Porcupine.java:94
ai.picovoice.porcupine.Porcupine.Builder.setLibraryPath
Builder setLibraryPath(String libraryPath)
Definition: java/src/ai/picovoice/porcupine/Porcupine.java:156
ai.picovoice.porcupine.Porcupine.getSampleRate
native int getSampleRate()
ai.picovoice.porcupine.Porcupine.BuiltInKeyword.options
static String options()
Definition: java/src/ai/picovoice/porcupine/Porcupine.java:134
ai.picovoice.porcupine.Porcupine.Builder.setAccessKey
Builder setAccessKey(String accessKey)
Definition: android/Porcupine/porcupine/src/main/java/ai/picovoice/porcupine/Porcupine.java:173
ai.picovoice.porcupine.Porcupine
Definition: android/Porcupine/porcupine/src/main/java/ai/picovoice/porcupine/Porcupine.java:35
args
cmd
string cmd
ai.picovoice.porcupinedemo.FileDemo
Definition: porcupine/demo/java/src/ai/picovoice/porcupinedemo/FileDemo.java:28
ai.picovoice.porcupine.Porcupine.Builder.setModelPath
Builder setModelPath(String modelPath)
Definition: android/Porcupine/porcupine/src/main/java/ai/picovoice/porcupine/Porcupine.java:178
ai.picovoice.porcupine.Porcupine.BuiltInKeyword
Definition: android/Porcupine/porcupine/src/main/java/ai/picovoice/porcupine/Porcupine.java:145
ai.picovoice.porcupinedemo.FileDemo.BuildCommandLineOptions
static Options BuildCommandLineOptions()
Definition: porcupine/demo/java/src/ai/picovoice/porcupinedemo/FileDemo.java:212


picovoice_driver
Author(s):
autogenerated on Fri Apr 1 2022 02:13:55