Convertir texto a voz con Delphi en Android, IOS, Windows

 

 
En esta ocasión les presento un programa que sirve para leer en voz alta un texto cualquiera.
Al leer el texto el programa comprueba el lenguaje del dispositivo por lo que un texto en español leído desde un dispositivo en español lo leerá sin problemas.

En mi caso, hasta ahora utilizaba el componente AndroidTTS realizado por Jim McKeeth, muy fácil de usar y que me daba un resultado estupendo en mis apps.
 
Últimamente al actualizar a la última versión de Delphi, la 11.2 la cual orienta las apps compiladas hacia el sdk de versión 32, me encontré con el problema que al iniciarse las apps se quedaban con la pantalla en negro y eso era debido al componente anterior.
 
Para solucionarlo he encontrado en la red este programa TextToSpeech que forma parte de un conjunto de utilidades llamadas "JustAddCode" obtenidas de la página web de Grijjy
 
- Para todas las plataformas hay que hacer lo siguiente:
 
1) Añadir en el bloque uses de la unit principal
     Grijjy.TextToSpeech
 
2) Definir una nueva variable privada (p.ej. FTextToSpeech):
    
   public
          ....
   
   private
           ....
     FTextToSpeech: IgoTextToSpeech;
 
3) En el evento Oncreate añadir lo siguiente:
 
  FTextToSpeech := TgoTextToSpeech.Create;
 
 
- Cambios que hay que hacer en las apps orientadas a Android:
 
En el archivo AndroidManifestTemplate.xml hay que:
 
1) Añadir
         action android:name="android.intent.action.TTS_SERVICE
         en el bloque "queries" (antes del bloque application)
        Ya que en la última actualización de Android obliga a hacerlo en las apps que tengan como objetivo Android 11.
 
 


2) Añadir
         android:exported="true" 
         en el bloque "activity"
 
 

 

Si quieren hacer su propia app no olviden incluir los siguientes archivos en la ruta donde se encuentre su app.

-Grijjy.TextToSpeech.Android.pas
-Grijjy.TextoToSpeech.Base.pas
-Grijjy.TextoToSpeech.IOS.pas
-Grijjy.TextoToSpeech.macOS.pas
-Grijjy.TextoToSpeech.pas
-Grijjy.TextoToSpeech.Windows.pas
 
Al final el resultado es el siguiente:
 
 
Aquí tienen el código fuente que incluye las modificaciones anteriores:
 
 

Si les ha sido útil este post y quieren recibir un email cada vez que publique uno nuevo pueden suscríbirse desde aquí

 

 

 


 
 
 
 
 
 
 
 

Ejemplo de uso del componente tNetHttpClient

 

 


 

 

Les voy a comentar, según mi experiencia personal, por qué decidí usar este componente para acceder a páginas webs, descargar archivos, utilizarlo con módulos PHP para hacer un webservice, etc... en vez de usar el componente de Indy tIdHttp.

El principal motivo es que maneja de forma transparente el acceso a las páginas seguras, y es que antes con el componente Idhttp tenía que utilizarlo junto con el idSSLIOHandlerSocketOpenSSL, configurarlo y además añadir los archivos libcrypto.so y libssl.so (en el caso de software para Android), lo que implica que aumenta el tamaño de la app, por si fuera poco, a veces dan problemas y hay que dedicar tiempo a solucionarlos, ahora desde que descubrí que con tNetHttpClient ya no es necesario hacerlo, las apps ocupan menos tamaño al no incluir esos archivos lo cual es muy importante a la hora del posicionamiento en la tienda de Google.

Últimamente estoy convirtiendo todos mis desarrollos para poder usar este componente que me simplifica la vida como programador.

Les recuerdo que si pasan parámetros por POST en la propiedad "ContentType" hay que poner:

 'multipart/form-data'  si se envian ficheros
 'application/x-www-form-urlencoded'  si NO se envian ficheros

Les adjunto algunos ejemplos por si les pueden ser de utilidad.

- Descargar una página web guardándola como un string.

 

aURL:='www.paginaweb.com';
FUNCTION DownloadWeb(aURL: STRING): STRING;
BEGIN
  TRY
    Result := NetHttpClient1.Get(aURL).ContentAsString;
  EXCEPT
    ON E: Exception DO
    BEGIN
      Showmessage('Error al obtener datos');
    END;
  END;
END; 

==== 

- Envíar a un modulo PHP varios parámetros por POST y creando el componente NetHttpClient en tiempo de ejecución.


FUNCTION ObtenerWebPOST(progPHP: STRING): STRING;
VAR
  datos: STRING;
  Stream: TStringStream;
  Params: tstringlist;
  MiNetHttp: TNetHTTPClient;

BEGIN
  Result := '';
  // usar  en el ContentType 'multipart/form-data'  si se envian ficheros
  // usar  en el ContentType application/x-www-form-urlencoded  si NO se envian ficheros
  MiNetHttp := TNetHTTPClient.Create(NIL);
  MiNetHttp.ContentType := 'application/x-www-form-urlencoded';
  Stream := TStringStream.Create('');
  Params := tstringlist.Create;
  TRY
    Params.Add('CP=08232';
    Params.Add('Poblacion=Barcelona');
    Stream.Position := 0;
    MiNetHttp.Post('https://www.paginaweb.com/datos.php', Params, Stream);
    datos := Stream.DataString;

  FINALLY
    Stream.Free;
    Params.Free;
    MiNetHttp.Free;
  END;
  Result := datos;

END;

======= 

- Descargar desde la web un archivo utilizando un tFileStream para guardar el archivo descargado.


URL:='www.paginaweb.com/archivo.txt'; Fichero:='c:\miCarpeta\Miarchivo.txt';
PROCEDURE DownloadFile(URL, Fichero: STRING);
VAR
  Stream: TFileStream;
  MiNetHttp: TNetHTTPClient;
BEGIN


  MiNetHttp := TNetHTTPClient.Create(NIL);
  // Stream := TmemoryStream.Create; (si queremos guardar el archivo en memoria)
  Stream := TFileStream.Create(Fichero, fmCreate);
  TRY
    MiNetHttp.Connection := 'keep-alive';
    TRY
      MiNetHttp.Get(URL, Stream);
    EXCEPT
      ON E: Exception DO
      BEGIN
        Showmessage('Error al descargar archivo '+e.message);
      END;
    END;
    // Stream.SaveToFile(Tpath.Combine(Directorio, FileName)); (si se usa un tMemoryStream)

  FINALLY
    MiNetHttp.Free;
    Stream.Free;
  END;
END; 
 
 
 
==========

- Bajar archivo pasado como parámetro de una función indicando la ruta donde se almacenará y el nombre del fichero de destino.

URL:='https://www.paginaweb.com/archivo.txt';
Directorio:='c:\carpeta';
Archivo:='ArchivoDescargado.txt';


PROCEDURE BajarArchivoDeInternet(NetHttp: TNetHTTPClient; URL, Directorio, FileName: STRING);
VAR
  Stream: TFileStream;
BEGIN
  // Stream := TmemoryStream.Create; (si usamos un TmemoryStream)
  Stream := TFileStream.Create(Tpath.Combine(Directorio, FileName), fmCreate);
  TRY
    MiNetHttp.Connection := 'keep-alive';
    TRY
      NetHttp.Get(URL, Stream);
    EXCEPT
      ON E: Exception DO
      BEGIN
        Showmessage('Error al descargar archivo '+e.message);
      END;
    END;
    // Stream.SaveToFile(Tpath.Combine(Directorio, FileName)); (si usamos un tMemoryStream)

  FINALLY
    Stream.Free;
  END;
END;

===== 

- Enviar ficheros por POST con varios parámetros que se tratarán dentro de un módulo PHP.

 

FUNCTION EnviarFicherosALaNubeConNetHttpClient: STRING;
CONST
  Codificacion = 'ISO-8859-1'; 

VAR
  ResponseStream: TStringStream;

  // esta en la uses System.Net.Mime
  Params: TMultipartFormData;
  Fichero: STRING;
  Path, Texto: STRING;
  MiNetHttp: TNetHTTPClient;

BEGIN
  MiNetHttp := TNetHTTPClient.Create(NIL);
  Result := '0';
  MiNetHttp.ContentType := 'multipart/form-data';
  MiNetHttp.acceptencoding := Codificacion; // 'ISO-8859-1' 


  // usar  en el ContentType 'multipart/form-data'  si se envian ficheros
  // usar  en el ContentType application/x-www-form-urlencoded  si NO se envian ficheros

  ResponseStream := TStringStream.Create('');
  TRY
    Params := TMultipartFormData.Create;
    TRY
      Params.AddField('calle', NombreCalle, Codificacion);
      Params.AddField('poblacion', Poblacion, Codificacion);
      Path := 'c:\carpeta';
      Fichero := Tpath.Combine(Path, 'foto1.jpg');
      IF tfile.Exists(Fichero) THEN
      BEGIN
        Params.AddFile('fich1', Fichero);
      END;
      Fichero := Tpath.Combine(Path, 'foto2.jpg');
      IF tfile.Exists(Fichero) THEN
      BEGIN
        Params.AddFile('fich2', Fichero);
      END;
      Fichero := Tpath.Combine(Path, 'index.html');
      IF tfile.Exists(Fichero) THEN
      BEGIN
        Params.AddFile('fich3', Fichero);
      END;

      TRY
        MiNetHttp.Post('https://www.paginaweb.com/datos.php', Params, ResponseStream);
      EXCEPT
        ON E: Exception DO
        BEGIN
         showmessage('Error al enviar el archivo: ' + E.Message');
        END;
      END;
      Result := ResponseStream.DataString;

    FINALLY
      Params.Free;
    END;
  FINALLY
    ResponseStream.Free;
    MiNetHttp.Free;
  END;

END;

===== 

- Enviar por POST varios parámetros a un módulo PHP.

 

FUNCTION ObtenerDatos: STRING;
VAR
  datos: STRING;
  Stream: TStringStream;
  Params: tstringlist;
  MiNetHttp: TNetHTTPClient;

BEGIN
  MiNetHttp := TNetHTTPClient.Create(NIL);
  Result := '';

  MiNetHttp.ContentType := 'application/x-www-form-urlencoded';
  Stream := TStringStream.Create('');
  Params := tstringlist.Create;
  TRY
    Params.Add('Producto1=3509');
    Params.Add('Producto2=9713');
    Stream.Position := 0; 
    MiNetHttp.Post('https://www.mipaginaweb.php/datos.php', Params, Stream);
    datos := Stream.DataString;

  FINALLY
    Stream.Free;
    Params.Free;
    MiNetHttp.Free;
  END;

END;

===== 

- Comprobar si un archivo existe en el servidor
(Si devuelve un código 200 es que existe)


//Añadir en el uses System.net.HTTPClient, System.Net.HTTPClientComponent

FUNCTION ArchivoExisteEnServidor(CONST URL: STRING): Boolean;
VAR
  Client: TNetHTTPClient;
  Response: IHTTPResponse;
BEGIN
  Client := TNetHTTPClient.Create(nil);
  TRY
    Response := Client.Head(URL);
    Result := (Response.StatusCode = 200);
  FINALLY
    Client.Free;
  END;
END;

 

Si les ha sido útil este post y quieren recibir un email cada vez que publique uno nuevo pueden suscríbirse desde aquí

 

Quizás te puede interesar...