[MODULE] Text - Sprachausgabe

Hier könnt Ihr gute, von Euch geschriebene Codes posten. Sie müssen auf jeden Fall funktionieren und sollten möglichst effizient, elegant und beispielhaft oder einfach nur cool sein.
Benutzeravatar
Mijikai
Beiträge: 754
Registriert: 25.09.2016 01:42

[MODULE] Text - Sprachausgabe

Beitrag von Mijikai »

Die Veröffentlichung von PB.Ex Speech (RSBasic) -> http://www.purebasic.fr/german/viewtopi ... 11&t=30692
hat mein Interesse geweckt.

Ich wollte wissen wie TextToSpeaker() funktioniert aber da es keinen
Sourcecode gab habe ich beschlossen es selbst zu versuchen.

Hier mein VOICE Module:

Code: Alles auswählen

DeclareModule VOICE
  Declare.i Init()
  Declare.i Voices()
  Declare.s GetVoiceName(Index.i)
  Declare.i SetVoice(Index.i)
  Declare.i Speak(Text.s,Volume.l,Rate.l,Async.b)
  Declare.i SpeakXML(Text.s,Volume.l,Rate.l,Async.b)
  Declare.i SpeakFile(File.s,Volume.l,Rate.l,Async.b)
  Declare.i SpeakFileXML(File.s,Volume.l,Rate.l,Async.b)
  Declare.i Release()
EndDeclareModule

Module VOICE
  
  ;VOICE MODULE by Mijikai
  ;PB v.5.62 x64 (Windows 10)
  ;v.alpha

  Interface ISpeechObjectToken Extends IDispatch
    Get_Id(*Output)
    Get_DataKey(*ISpeechDataKey)
    Get_Category(*ISpeechObjectTokenCategory)
    GetDescription(Locale.l,*Output)
    Set_Id(Id.s,CategoryID.s,CreateIfNotExist.i)
    GetAttribute(AttributeName.s,*Output)
    CreateInstance(*pUnkOuter,ClsContext.l,*IUnknown)
    Remove(ObjectStorageCLSID.s)
    GetStorageFileName(ObjectStorageCLSID.s,KeyName.s,FileName.s,Folder.l,*Output)
    RemoveStorageFileName(ObjectStorageCLSID.s,KeyName.s,DeleteFile.i)
    IsUISupported(TypeOfUI.s,*ExtraData,*IUnknown,*Output)
    DisplayUI(hWnd.l,Title.s,TypeOfUI.s,*ExtraData,*IUnknown)
    MatchesAttributes(Attributes.s,*Output)
  EndInterface
  
  Interface ISpeechObjectTokens Extends IDispatch
    Get_Count(*Output)
    Item(Index.l,*ISpeechObjectToken)
    Get_PropGet()
  EndInterface
  
  Interface ISpeechVoice Extends IDispatch
    Get_Status(*ISpeechVoiceStatus)
    Get_Voice(*ISpeechObjectToken)
    Set_Voice(*ISpeechObjectToken)
    Get_AudioOutput(*ISpeechObjectToken)
    Set_AudioOutput(*ISpeechObjectToken)
    Get_AudioOutputStream(*ISpeechBaseStream)
    Set_AudioOutputStream(*ISpeechBaseStream)
    Get_Rate(*Output)
    Set_Rate(Rate.l)
    Get_Volume(*Output)
    Set_Volume(Volume.l)
    Set_AllowAudioOutputFormatChangesOnNextSet(Allow.i)
    Get_AllowAudioOutputFormatChangesOnNextSet(*Output)
    Get_EventInterests()
    Set_EventInterests(EventInterestFlags.l)
    Set_Priority(Priority.l)
    Get_Priority(*Output)
    Set_AlertBoundary(Boundary.l)
    Get_AlertBoundary(*Output)
    Set_SynchronousSpeakTimeout(msTimeout.l)
    Get_SynchronousSpeakTimeout()
    Speak(Text.s,Flags.l,*Output)
    SpeakStream(*ISpeechBaseStream,Flags.l,*Output)
    Pause()
    Resume()
    Skip(Type.s,NumItems.l,*Output)
    GetVoices(RequiredAttributes.s,OptionalAttributes.s,*ISpeechObjectTokens)
    GetAudioOutputs(RequiredAttributes.s,OptionalAttributes.s,*ISpeechObjectTokens)
    WaitUntilDone(msTimeout.l,*Output)
    SpeakCompleteEvent(*Output)
    IsUISupported(TypeOfUI.s,*ExtraData,*Output)
    DisplayUI(hWndParent.l,Title.s,TypeOfUI.s,*ExtraData)
  EndInterface
  
  #SPF_ASYNC            = 1
  #SPF_IS_FILENAME      = 4
  #SPF_IS_XML           = 8
  #SPF_IS_NOT_XML       = 16
  
  Global *Speech.ISpeechVoice
  
  Procedure.i Init()
    Protected rclsid.CLSID
    Protected riid.CLSID
    Protected VirtualTable.i
    If Not *Speech
      If CoInitializeEx_(#Null,#Null) = #S_OK
        If CLSIDFromString_("{96749377-3391-11D2-9EE3-00C04F797396}",@rclsid) = #S_OK;CLSID_SpVoice  
          If IIDFromString_("{269316D8-57BD-11D2-9EEE-00C04F797396}",@riid) = #S_OK;IID_ISpeechVoice
            If CoCreateInstance_(@rclsid,#Null,#CLSCTX_INPROC_SERVER,@riid,@VirtualTable) = #S_OK
              *Speech = VirtualTable
              ProcedureReturn #True
            EndIf
          EndIf
        EndIf
        CoUninitialize_()
      EndIf
    Else
      ProcedureReturn #True
    EndIf
  EndProcedure
    
  Procedure.i Voices()
    Protected *Tokens.ISpeechObjectTokens
    Protected Count.i
    If *Speech
      If *Speech\GetVoices(#Null$,#Null$,@*Tokens) = #S_OK
        If *Tokens\Get_Count(@Count) = #S_OK 
          ProcedureReturn Count
        EndIf
        *Tokens\Release()
      EndIf
    EndIf
  EndProcedure
  
  Procedure.s GetVoiceName(Index.i)
    Protected *Tokens.ISpeechObjectTokens
    Protected Count.i
    Protected *Token.ISpeechObjectToken
    Protected Buffer.i
    Protected Name.s
    If *Speech
      If *Speech\GetVoices(#Null$,#Null$,@*Tokens) = #S_OK
        If *Tokens\Get_Count(@Count) = #S_OK 
          If Not Index > Count
            If *Tokens\Item(Index,@*Token) = #S_OK
              If *Token\GetDescription(#Null,@Buffer) = #S_OK
                Name = PeekS(Buffer)
                SysFreeString_(Buffer)
              EndIf
              *Token\Release()
            EndIf
          EndIf
        EndIf
        *Tokens\Release()
      EndIf
    EndIf
    ProcedureReturn Name
  EndProcedure
  
  Procedure.i SetVoice(Index.i)
    Protected *Tokens.ISpeechObjectTokens
    Protected Count.i
    Protected *Token.ISpeechObjectToken
    Protected Result.i
    If *Speech
      If *Speech\GetVoices(#Null$,#Null$,@*Tokens) = #S_OK
        If *Tokens\Get_Count(@Count) = #S_OK 
          If Not Index > Count
            If *Tokens\Item(Index,@*Token) = #S_OK
              If *Speech\Set_Voice(*Token) = #S_OK
                Result = #True
              EndIf
              *Token\Release()
            EndIf
          EndIf
        EndIf
        *Tokens\Release()
      EndIf
    EndIf
    ProcedureReturn Result
  EndProcedure
  
  Procedure.i Speak(Text.s,Volume.l,Rate.l,Async.b)
    Protected Result.i
    If *Speech
      *Speech\Set_Volume(Volume)
      *Speech\Set_Rate(Rate)
      If Async
        Result = *Speech\Speak(Text,#SPF_IS_NOT_XML|#SPF_ASYNC,#Null)
      Else
        Result = *Speech\Speak(Text,#SPF_IS_NOT_XML,#Null)
      EndIf
    EndIf
    ProcedureReturn Bool(Result = #S_OK)
  EndProcedure
  
  Procedure.i SpeakXML(Text.s,Volume.l,Rate.l,Async.b)
    Protected Result.i
    If *Speech
      *Speech\Set_Volume(Volume)
      *Speech\Set_Rate(Rate)
      If Async
        Result = *Speech\Speak(Text,#SPF_IS_XML|#SPF_ASYNC,#Null)
      Else
        Result = *Speech\Speak(Text,#SPF_IS_XML,#Null)
      EndIf
    EndIf
    ProcedureReturn Bool(Result = #S_OK)
  EndProcedure
  
  Procedure.i SpeakFile(File.s,Volume.l,Rate.l,Async.b)
    Protected Result.i
    If *Speech
      *Speech\Set_Volume(Volume)
      *Speech\Set_Rate(Rate)
      If Async
        Result = *Speech\Speak(File,#SPF_IS_NOT_XML|#SPF_IS_FILENAME|#SPF_ASYNC,#Null)
      Else
        Result = *Speech\Speak(File,#SPF_IS_NOT_XML|#SPF_IS_FILENAME,#Null)
      EndIf
    EndIf
    ProcedureReturn Bool(Result = #S_OK)
  EndProcedure
  
  Procedure.i SpeakFileXML(File.s,Volume.l,Rate.l,Async.b)
    Protected Result.i
    If *Speech
      *Speech\Set_Volume(Volume)
      *Speech\Set_Rate(Rate)
      If Async
        Result = *Speech\Speak(File,#SPF_IS_XML|#SPF_IS_FILENAME|#SPF_ASYNC,#Null)
      Else
        Result = *Speech\Speak(File,#SPF_IS_XML|#SPF_IS_FILENAME,#Null)
      EndIf
    EndIf
    ProcedureReturn Bool(Result = #S_OK)
  EndProcedure
  
  Procedure.i Release()
    If *Speech
      *Speech\Release()
      *Speech = #Null
      CoUninitialize_()
    EndIf
  EndProcedure
  
EndModule

Global Index.i

If VOICE::Init()
  
  For Index = 0 To VOICE::Voices() - 1
    Debug VOICE::GetVoiceName(Index)
    If Index = 1
      VOICE::SetVoice(Index)
    EndIf
  Next
    
  Debug VOICE::SpeakXML("This sounds normal <pitch middle = '-80'/> but the pitch drops half way through",100,0,#True)
  Debug VOICE::Speak("take some notice here i speak",100,0,#False)
  
  VOICE::Release()
EndIf
Viel Spass :)
Benutzeravatar
Bisonte
Beiträge: 2427
Registriert: 01.04.2007 20:18

Re: [MODULE] Text - Sprachausgabe

Beitrag von Bisonte »

:allright:

Klingt lustig, wenn die deutsche Stimme den englischen Text vorliest :mrgreen:
PureBasic 6.04 LTS (Windows x86/x64) | Windows10 Pro x64 | Asus TUF X570 Gaming Plus | R9 5900X | 64GB RAM | GeForce RTX 3080 TI iChill X4 | HAF XF Evo | build by vannicom​​
Benutzeravatar
RSBasic
Admin
Beiträge: 8022
Registriert: 05.10.2006 18:55
Wohnort: Gernsbach
Kontaktdaten:

Re: [MODULE] Text - Sprachausgabe

Beitrag von RSBasic »

:allright:
Aus privaten Gründen habe ich leider nicht mehr so viel Zeit wie früher. Bitte habt Verständnis dafür.
Bild
Bild
Benutzeravatar
mk-soft
Beiträge: 3695
Registriert: 24.11.2004 13:12
Wohnort: Germany

Re: [MODULE] Text - Sprachausgabe

Beitrag von mk-soft »

Geht es nicht für alles OS?

Code: Alles auswählen

Global SpeechSynthesizer = CocoaMessage(0, CocoaMessage(0, 0, "NSSpeechSynthesizer alloc"), "initWithVoice:", #nil)
Global voice.s = "com.apple.speech.synthesis.voice.anna"

CocoaMessage(0, SpeechSynthesizer, "setVoice:$", @voice)
CocoaMessage(0, SpeechSynthesizer, "startSpeakingString:$", @"Es muss nicht immer nur für windows sein")
If OpenWindow(0, 0, 0, 200, 30, "Hallo", #PB_Window_SystemMenu | #PB_Window_Minimize | #PB_Window_NoActivate)
  Repeat : Until WaitWindowEvent() = #PB_Event_CloseWindow
EndIf
Alles ist möglich, fragt sich nur wie...
Projekte ThreadToGUI / EventDesigner V3 / OOP-BaseClass-Modul
Downloads auf MyWebspace / OneDrive
Benutzeravatar
RSBasic
Admin
Beiträge: 8022
Registriert: 05.10.2006 18:55
Wohnort: Gernsbach
Kontaktdaten:

Re: [MODULE] Text - Sprachausgabe

Beitrag von RSBasic »

Jetzt nur noch Linux. :mrgreen:
ccode_new hat geschrieben:

Code: Alles auswählen

;Sprachausgabe unter Linux (Test)

text.s = Chr(34)+"Ich bin eine Computerstimme."+Chr(34)
prog = RunProgram("espeak", "-v de -a 120 -p 20 -s 120 "+text , GetCurrentDirectory(), #PB_Program_Wait)
Es gibt bestimmt dort auch ne API-Schnittstelle.
Aus privaten Gründen habe ich leider nicht mehr so viel Zeit wie früher. Bitte habt Verständnis dafür.
Bild
Bild
ccode_new
Beiträge: 1214
Registriert: 27.11.2016 18:13
Wohnort: Erzgebirge

Re: [MODULE] Text - Sprachausgabe

Beitrag von ccode_new »

Hallo!

Plattformunabhängig über SpiderBasic:

Code: Alles auswählen

EnableJS
var hallo = new SpeechSynthesisUtterance("Ich bin eine Computerstimme");
hallo.lang = "de-DE";
hallo.rate = 0.5;
hallo.pitch = 3;
window.speechSynthesis.speak(hallo);
DisableJS
;Es kommt halt auf dem verwendeten Browser an.

Sprachausgabe ist die einfachere Sache, aber Spracheingabe wird (vor allem unter Linux) recht komplex und kompliziert.

->Die beste Lösung für Spracheingabe könnte sein:

Ein Hinweis das sie bitte Google Chrome installieren sollen und ihre Internetverbindung aktivieren. (Verwendung von Google Chrome)
Oder Verwendung einer (Android-)App (mit Spracherkennungsdienst) auf einem Smartphone das als Vermittlungsprogramm dient.
Zuletzt geändert von ccode_new am 02.04.2018 17:00, insgesamt 2-mal geändert.
Betriebssysteme: div. Windows, Linux, Unix - Systeme

no Keyboard, press any key
no mouse, you need a cat
Benutzeravatar
RSBasic
Admin
Beiträge: 8022
Registriert: 05.10.2006 18:55
Wohnort: Gernsbach
Kontaktdaten:

Re: [MODULE] Text - Sprachausgabe

Beitrag von RSBasic »

ccode_new hat geschrieben:Platformunabhängig
Naja, nicht ganz: https://caniuse.com/#search=speechsynthesisutterance
IE 11 wird nicht unterstützt.
Und Edge gibts erst ab Windows 10.
Aus privaten Gründen habe ich leider nicht mehr so viel Zeit wie früher. Bitte habt Verständnis dafür.
Bild
Bild
ccode_new
Beiträge: 1214
Registriert: 27.11.2016 18:13
Wohnort: Erzgebirge

Re: [MODULE] Text - Sprachausgabe

Beitrag von ccode_new »

Es gibt bestimmt dort auch ne API-Schnittstelle.
Wer möchte kann sich damit gerne auseinandersetzen:

http://espeak.sourceforge.net/speak_lib.h.
Betriebssysteme: div. Windows, Linux, Unix - Systeme

no Keyboard, press any key
no mouse, you need a cat
Antworten