Obtenga información sobre la integración del SDK de HarmonyOS, parámetros, API, callbacks y código de ejemplo para la síntesis de voz en tiempo real.
NativeNui
El SDK de HarmonyOS proporciona conversión de texto a voz en streaming a través de NativeNui.
- Cree una instancia de conversión de texto a voz en streaming llamando a
new NativeNui(Constants.ModeType.MODE_STREAM_INPUT_TTS).NativeNui.GetInstance()devuelve un singletonMODE_DIALOGy no se puede utilizar para la conversión de texto a voz en streaming. - No llame a
initialize()en el modo de conversión de texto a voz en streaming. Pase las credenciales y los parámetros de síntesis directamente astartStreamInputTts(),playStreamInputTts()oasyncPlayStreamInputTts(). - Reciba eventos de síntesis y audio a través de
INativeStreamInputTtsCallback. - El SDK devuelve
STREAM_INPUT_TTS_EVENT_SYNTHESIS_STARTEDcuando comienza la tarea, audio a través deonStreamInputTtsDataCallback,STREAM_INPUT_TTS_EVENT_SYNTHESIS_COMPLETEcuando finaliza la tarea ySTREAM_INPUT_TTS_EVENT_TASK_FAILEDcuando falla la síntesis.
import { Constants, INativeStreamInputTtsCallback, NativeNui, StreamInputTtsEvent } from 'neonui';
const nuiInstance = new NativeNui(Constants.ModeType.MODE_STREAM_INPUT_TTS);
Flujos de llamadas
CosyVoice admite entrada única y entrada en streaming.
Entrada única es adecuada para textos cortos o escenarios que requieren SSML.
- Llame a
playStreamInputTtsoasyncPlayStreamInputTtspara pasar el texto completo e iniciar la síntesis. El primero bloquea hasta que finaliza la síntesis. El segundo devuelve el control inmediatamente y sintetiza en segundo plano. No llame primero astartStreamInputTtsni llame a un método de detención después. - Reciba el audio en
onStreamInputTtsDataCallback. - La síntesis finaliza cuando se recibe
STREAM_INPUT_TTS_EVENT_SYNTHESIS_COMPLETE.
Entrada en streaming es adecuada para conversaciones en tiempo real o síntesis incremental de textos largos. SSML no es compatible con este modo.
- Llame a
startStreamInputTtspara abrir la conexión y configurar el callback y los parámetros. - Llame a
sendStreamInputTtspara enviar fragmentos de texto. - Reciba el audio en
onStreamInputTtsDataCallback. - Después de enviar todo el texto, llame a
stopStreamInputTts. - La síntesis finaliza cuando se recibe
STREAM_INPUT_TTS_EVENT_SYNTHESIS_COMPLETE.
Cuando ya no se necesite la conversión de texto a voz, llame a releaseStreamInputTts para liberar recursos.
Tanto la longitud de una sola entrada de texto como la longitud acumulada de múltiples entradas están limitadas. Consulte la API WebSocket de CosyVoice.
startStreamInputTts
Inicia la síntesis en streaming bidireccional, abre la conexión y registra el callback. Este método puede bloquearse. No lo llame en el subproceso de la interfaz de usuario.
startStreamInputTts(
callback: INativeStreamInputTtsCallback,
ticket: string,
parameters: string,
session_id: string,
log_level: number,
save_log: boolean
): number
| Parámetro | Tipo | Descripción |
|---|---|---|
callback | INativeStreamInputTtsCallback | Callback de eventos y audio. |
ticket | string | Cadena JSON que contiene configuraciones de autenticación, conexión y depuración. |
parameters | string | Cadena JSON que contiene la configuración de síntesis. |
session_id | string | ID de sesión especificado por el cliente. Pase una cadena vacía para permitir que el servidor genere uno. |
log_level | number | Nivel de registro del SDK. Utilice un valor de Constants.LogLevel: 0 (VERBOSE), 1 (DEBUG), 2 (INFO), 3 (WARNING), 4 (ERROR) o 5 (NONE). |
save_log | boolean | Si se deben guardar registros localmente. Si se establece en true, configure debug_path en ticket. |
El método devuelve un código de error. Constants.NuiResultCode.SUCCESS (0) indica éxito.
campos de ticket
{
"url": "wss://dashscope.aliyuncs.com/api-ws/v1/inference",
"apikey": "st-****",
"device_id": "my_device_id"
}
| Campo | Tipo | Obligatorio | Descripción |
|---|---|---|---|
url | string | Sí | Endpoint de servicio. Utilice el endpoint público wss://dashscope.aliyuncs.com/api-ws/v1/inferenceo un endpoint específico del espacio de trabajo: wss://{WorkspaceId}.cn-beijing.maas.aliyuncs.com/api-ws/v1/inferencepara Beijing o wss://{WorkspaceId}.ap-southeast-1.maas.aliyuncs.com/api-ws/v1/inferencepara Singapur. Reemplace {WorkspaceId} con su ID de espacio de trabajo. |
apikey | string | Sí | Clave API. Utilice una clave API temporal para reducir el riesgo de exponer una clave de larga duración. |
device_id | string | Sí | Un identificador único de usuario final, como un ID de usuario dentro de la aplicación o un ID de dispositivo generado por el cliente. Se utiliza principalmente para el rastreo de registros y la solución de problemas. |
complete_waiting_ms | number | No | Tiempo en milisegundos para esperar el evento de síntesis completada después de stopStreamInputTts(false). Valor predeterminado: 10000. |
debug_path | string | No | Directorio de registros. Este campo es obligatorio cuando save_log es true. El SDK conserva como máximo dos archivos de registro. |
max_log_file_size | number | No | Tamaño máximo de un solo archivo de registro en bytes. Valor predeterminado: 104857600 (100 MiB). Este campo solo tiene efecto cuando save_log es true. |
log_track_level | number | No | Nivel de filtro de registro de seguimiento interno. Valor predeterminado: 2. Los valores válidos son los mismos que para log_level. La interfaz de callback de HarmonyOS actualmente no expone un callback de registro de TTS en streaming, por lo que los registros filtrados solo son escritos por el SDK. |
campos de parameters
{
"model": "cosyvoice-v3-plus",
"voice": "longanyang",
"format": "mp3",
"sample_rate": 24000,
"volume": 50,
"rate": 1.0,
"pitch": 1.0,
"enable_audio_decoder": true
}
| Campo | Tipo | Obligatorio | Descripción |
|---|---|---|---|
model | string | Sí | Nombre del modelo. Consulte Modelos de síntesis de voz. |
voice | string | Sí | Voz. Para voces del sistema, consulte voces de CosyVoice. También puede usar una voz creada mediante clonación de voz o Diseño de voz. |
format | string | No | Formato de codificación de audio: pcm, wav, mp3 (predeterminado) o opus. |
enable_audio_decoder | boolean | No | Si se debe habilitar el decodificador del SDK. Valor predeterminado: false. Para MP3 u Opus, establézcalo en true para decodificar el audio a PCM antes de devolverlo a través del callback de datos. |
volume | number | No | Volumen. Valor predeterminado: 50. Rango válido: [0, 100]. |
sample_rate | number | No | Frecuencia de muestreo en Hz. Valores válidos: 8000, 16000, 22050 (predeterminado), 24000, 44100 y 48000. |
rate | number | No | Velocidad de habla. Valor predeterminado: 1.0. Rango válido: [0.5, 2.0]. |
pitch | number | No | Tono. Valor predeterminado: 1.0. Rango válido: [0.5, 2.0]. |
bit_rate | number | No | Tasa de bits MP3 u Opus en kbps. Valor predeterminado: 32. Rango válido: [6, 510]. |
enable_ssml | boolean | No | Si se debe habilitar SSML. Valor predeterminado: false. Consulte Límites de SSML. |
word_timestamp_enabled | boolean | No | Indica si se deben devolver marcas de tiempo a nivel de palabra. Valor predeterminado: false. Este campo solo está disponible para la salida en streaming. Es compatible con voces clonadas de cosyvoice-v3.5-plus, cosyvoice-v3.5-flash, cosyvoice-v3-flash, cosyvoice-v3-plus, cosyvoice-v2 y voces del sistema marcadas como compatibles en la lista de voces de CosyVoice. Las voces clonadas de otros modelos no son compatibles. Los resultados de las marcas de tiempo se incluyen en all_response de INativeStreamInputTtsCallback. |
seed | number | No | Semilla aleatoria utilizada para variar el resultado sintetizado. Si la versión del modelo, el texto, la voz y todos los demás parámetros son iguales, la misma seed reproduce el mismo resultado. Valor predeterminado: 0. Rango válido: [0, 65535]. |
language_hints | string[] | No | Idioma objetivo de la síntesis. Esta configuración mejora la síntesis y es independiente del idioma del audio de muestra utilizado para la clonación de voz. Para establecer el idioma de origen de una tarea de clonación de voz, consulte la Referencia de la API de clonación de voz. La versión actual utiliza únicamente el primer elemento del arreglo, por lo que debe pasar un solo valor. Utilice este campo cuando la lectura de números, abreviaturas o símbolos no sea la esperada, o cuando la síntesis en un idioma menos común suene poco natural. Por ejemplo, puede hacer que "hello, this is 110" se lea como "one one zero" en inglés en lugar de la lectura en chino, o que @ se lea como "at".Valores válidos Valores admitidos: |
instruction | string | No | Instrucción que controla dialecto, emoción o rol. Consulte Control de instrucciones. |
enable_aigc_tag | boolean | No | Si se debe incrustar una etiqueta AIGC invisible. Valor predeterminado: false.NotaAdmitido por cosyvoice-v3-flash, cosyvoice-v3-plus, cosyvoice-v2. |
aigc_propagator | string | No | Campo |
aigc_propagate_id | string | No | Campo |
hot_fix | object | No | Configuración de corrección en caliente de texto para pronunciación personalizada y reemplazo de texto. Nota Para el esquema, consulte Eventos del cliente. |
sendStreamInputTts
sendStreamInputTts(text: string): number
Envía un fragmento de texto después de que startStreamInputTts tenga éxito. Este método no analiza etiquetas SSML. Después de enviar todo el texto, llame a stopStreamInputTts().
| Parámetro | Tipo | Descripción |
|---|---|---|
text | string | Texto a sintetizar. SSML no es compatible. Las etiquetas SSML se leen como texto normal. |
El método devuelve un código de error.
stopStreamInputTts
stopStreamInputTts(flag_async: boolean = true): number
Finaliza la entrada por streaming.
true(predeterminado): Finaliza de forma asíncrona y devuelve el control inmediatamente. Espere aSTREAM_INPUT_TTS_EVENT_SYNTHESIS_COMPLETEpara determinar que la síntesis ha finalizado.false: Bloquea hasta que se reciban todo el audio y el evento de síntesis completada. El tiempo de espera está controlado porcomplete_waiting_ms.
Llamar a un método de cancelación después de una detención síncrona puede bloquear el proceso. Recomendamos el modo asíncrono predeterminado.
| Parámetro | Tipo | Descripción |
|---|---|---|
flag_async | boolean | Si se debe finalizar de forma asíncrona. Valor predeterminado: true. true devuelve el control sin esperar una respuesta del servidor. false bloquea hasta que se complete la síntesis. |
El método devuelve un código de error.
cancelStreamInputTts
cancelStreamInputTts(): number
Cierra inmediatamente la conexión y termina la tarea actual. No se reciben más callbacks de audio después de esta llamada. El método devuelve un código de error.
cancelStreamInputTtsKeepConnection
cancelStreamInputTtsKeepConnection(): number
Envía un comando de cancelación a nivel de protocolo para terminar la tarea actual pero mantener abierta la conexión WebSocket. Utilice este método cuando deba iniciarse inmediatamente otra ronda de síntesis, evitando el costo de volver a abrir la conexión. El método devuelve un código de error.
playStreamInputTts
playStreamInputTts(
callback: INativeStreamInputTtsCallback,
ticket: string,
parameters: string,
text: string,
session_id: string,
log_level: number,
save_log: boolean
): number
Síntesis única síncrona. Este método inicializa la tarea, envía el texto, recibe todo el audio y luego devuelve el control. No llame primero a startStreamInputTts ni llame a un método de detención después. SSML está habilitado de forma predeterminada. Si enable_ssml se establece explícitamente, ese valor tiene prioridad. No llame a este método en el subproceso de la interfaz de usuario.
callback, ticket, parameters, session_id, log_level y save_log se definen en startStreamInputTts. text es el texto a sintetizar y admite SSML. El método devuelve un código de error.
asyncPlayStreamInputTts
asyncPlayStreamInputTts(
callback: INativeStreamInputTtsCallback,
ticket: string,
parameters: string,
text: string,
session_id: string,
log_level: number,
save_log: boolean
): number
Síntesis única asíncrona. Este método devuelve el control inmediatamente y entrega resultados a través de callbacks. No llame primero a startStreamInputTts ni llame a un método de detención después. SSML está habilitado de forma predeterminada. Si enable_ssml se establece explícitamente, ese valor tiene prioridad.
callback, ticket, parameters, session_id, log_level y save_log se definen en startStreamInputTts. text es el texto a sintetizar y admite SSML. El método devuelve un código de error.
releaseStreamInputTts
releaseStreamInputTts(): number
Libera la instancia de TTS en streaming y sus recursos. Llame a este método cuando se destruya la página o cuando ya no se necesite la conversión de texto a voz. El método devuelve un código de error.
INativeStreamInputTtsCallback
export interface INativeStreamInputTtsCallback {
onStreamInputTtsEventCallback(
event: StreamInputTtsEvent,
task_id: string,
session_id: string,
ret_code: number,
error_msg: string,
timestamp: string,
all_response: string
): void;
onStreamInputTtsDataCallback(data: ArrayBuffer | null): void;
}
onStreamInputTtsEventCallback
| Parámetro | Tipo | Descripción |
|---|---|---|
event | StreamInputTtsEvent | Evento de síntesis. |
task_id | string | ID de la tarea de síntesis. |
session_id | string | ID de sesión. Un valor especificado por el cliente se devuelve sin cambios. De lo contrario, el servidor genera uno. |
ret_code | number | Código de error. Válido solo para un evento de tarea fallida. |
error_msg | string | Mensaje de error. Válido solo para un evento de tarea fallida. |
timestamp | string | Resultado de marcas de tiempo. |
all_response | string | Respuesta completa del servidor como cadena JSON. Analícela para obtener detalles de uso, marcas de tiempo y errores. |
onStreamInputTtsDataCallback
onStreamInputTtsDataCallback(data: ArrayBuffer | null): void;
Devuelve fragmentos de audio de forma continua. Tenga en cuenta lo siguiente:
- Los datos MP3 y Opus requieren un decodificador en streaming. Alternativamente, establezca
enable_audio_decoderentruepara permitir que el SDK devuelva PCM. - Para ensamblar un archivo completo, añada los datos del callback en orden.
- Para WAV y MP3, solo el primer callback contiene el encabezado del archivo. Cada trama Opus es una página Ogg independiente y se pueden concatenar en orden.
StreamInputTtsEvent
| Evento | Descripción |
|---|---|
STREAM_INPUT_TTS_EVENT_SYNTHESIS_STARTED | El servidor ha aceptado la solicitud y ha comenzado a procesarla. Los primeros datos de audio suelen llegar a través de onStreamInputTtsDataCallback poco después de este evento. |
STREAM_INPUT_TTS_EVENT_SENTENCE_BEGIN | El servidor ha comenzado a sintetizar una utterance. |
STREAM_INPUT_TTS_EVENT_SENTENCE_SYNTHESIS | Información sobre el progreso de la síntesis, incluida información de facturación y marcas de tiempo. |
STREAM_INPUT_TTS_EVENT_SENTENCE_END | El servidor ha completado la síntesis de una utterance. |
STREAM_INPUT_TTS_EVENT_SYNTHESIS_COMPLETE | El servidor ha devuelto todos los datos de audio. onStreamInputTtsEventCallback no se llama después de este evento, que es la señal explícita de fin de flujo. Este evento no indica que la reproducción local haya terminado. |
STREAM_INPUT_TTS_EVENT_TASK_FAILED | Error de síntesis. Obtenga task_id, error_code y error_message de all_response, o utilice los argumentos de callback ret_code y error_msg. |
Ejemplo de respuesta de tarea fallida:
{
"header": {
"task_id": "2bf83b9a-baeb-4fda-8d9a-xxxxxxxxxxxx",
"event": "task-failed",
"error_code": "InvalidParameter",
"error_message": "[tts:]Engine return error code: 418",
"attributes": {}
},
"payload": {}
}
Código de ejemplo
- Obtenga una clave API. No codifique de forma rígida una clave API de larga duración en una aplicación cliente. Recomendamos que el servidor de su aplicación obtenga una clave API temporal y la envíe al cliente.
- Descargue el paquete SDK más reciente. Extraiga el paquete, copie
entry/libs/neonui.haren el directorioentry/libsde su aplicación y agregue la dependencia aentry/oh-package.json5:
{
"dependencies": {
"neonui": "file:libs/neonui.har"
}
}
- Abra el proyecto de ejemplo del paquete SDK en DevEco Studio. La página de ejemplo es
entry/src/main/ets/pages/dashscope/DashCosyVoiceStreamTtsPage.ets. Configure una clave API y ejecute el proyecto.
El siguiente código muestra el flujo principal de entrada en streaming. Para la reproducción completa de audio, selección de parámetros y gestión del estado de la tarea, consulte DashCosyVoiceStreamTtsPage.ets en el paquete del SDK.
import { Constants, INativeStreamInputTtsCallback, NativeNui, StreamInputTtsEvent } from 'neonui';
const callback: INativeStreamInputTtsCallback = {
onStreamInputTtsEventCallback: (event: StreamInputTtsEvent, taskId: string,
sessionId: string, retCode: number, errorMsg: string,
timestamp: string, allResponse: string): void => {
if (event == StreamInputTtsEvent.STREAM_INPUT_TTS_EVENT_SYNTHESIS_COMPLETE) {
// Synthesis is complete.
} else if (event == StreamInputTtsEvent.STREAM_INPUT_TTS_EVENT_TASK_FAILED) {
// Handle the error based on retCode, errorMsg, or allResponse.
}
},
onStreamInputTtsDataCallback: (data: ArrayBuffer | null): void => {
if (data != null) {
// Write PCM to AudioRenderer, or append encoded audio data in order.
}
}
};
const nuiInstance = new NativeNui(Constants.ModeType.MODE_STREAM_INPUT_TTS);
const ticket: Record<string, Object> = {
'url': 'wss://dashscope.aliyuncs.com/api-ws/v1/inference',
'apikey': 'st-****',
'device_id': 'my_device_id'
};
const parameters: Record<string, Object> = {
'model': 'cosyvoice-v3-plus',
'voice': 'longanyang',
'format': 'mp3',
'sample_rate': 24000,
'enable_audio_decoder': true
};
const result = nuiInstance.startStreamInputTts(
callback,
JSON.stringify(ticket),
JSON.stringify(parameters),
'',
Constants.LogLevel.LOG_LEVEL_INFO,
false
);
if (result == Constants.NuiResultCode.SUCCESS) {
nuiInstance.sendStreamInputTts('Hello, ');
nuiInstance.sendStreamInputTts('welcome to real-time speech synthesis.');
nuiInstance.stopStreamInputTts(true);
}
// Call nuiInstance.releaseStreamInputTts() from the SYNTHESIS_COMPLETE handler.
Para entrada única, llame directamente a playStreamInputTts o asyncPlayStreamInputTts:
const oneShotInstance = new NativeNui(Constants.ModeType.MODE_STREAM_INPUT_TTS);
oneShotInstance.asyncPlayStreamInputTts(
callback,
JSON.stringify(ticket),
JSON.stringify(parameters),
'Hello, welcome to real-time speech synthesis.',
'',
Constants.LogLevel.LOG_LEVEL_INFO,
false
);
// Call oneShotInstance.releaseStreamInputTts() from the SYNTHESIS_COMPLETE handler.
Funciones avanzadas
SSML
Propósito: Incrustar etiquetas XML en el texto para controlar la pronunciación, la velocidad de habla, las pausas y otros detalles de la síntesis.
Límites: Solo las API de entrada única playStreamInputTts y asyncPlayStreamInputTts admiten SSML. La API de entrada en streaming sendStreamInputTts no lo admite.
Uso: El SDK habilita SSML de forma predeterminada para playStreamInputTts y asyncPlayStreamInputTts. Pase texto SSML en text. Para obtener más información, consulte SSML y LaTeX.
Expresiones matemáticas
Propósito: Hacer que el modelo lea correctamente fórmulas y expresiones matemáticas comunes.
Uso: Pase texto que contenga una expresión matemática con formato LaTeX en text. Para consultar la sintaxis admitida, vea Conversión de texto a voz LaTeX.