Text to Speech (TTS) part2 : Applying to IE11 vfp browser

Published on by Yousfi Benameur

           

this is the second part of the previous post "Working with Text to Speech (TTS)" :http://yousfi.over-blog.com/2018/01/working-with-text-to-speech-tts.html
this builds a vfp browser olecontrol and intercept some events.its the same modified code in my previous post:
http://yousfi.over-blog.com/2015/02/vfp-and-internet-explorer-eventhandler.html
i add some interactions with the com Object SAPI.SPVOICe (from sapi.dll).
i build a second  eventHandler hooked on the TTS object and modify the code in Browser to detect the selection start /selection end and give to the TTS the hand to speak the text selection.
infortubatly the HTMLSelectElementEvents class dont contains any procedure to detect a selectionChange event.it have only the event:HTMLSelectElementEvents_onselectstart()
i used the HTMLSelectElementEvents_onmouseDown() and HTMLSelectElementEvents_onmouseUp() events  to return the valid text selected and pass it to the TTS engine.
can select the voice (i have the french as item(0) and english as item(1) in my PC).
can make a selection by the mouse only  on the document(mouseDown...mouseUp).this is passed to TTS to be spoken.
the TTS at any start fires an animated gif to simulate the speaking activity .this is hidden when the TTS terminate speaking (using the TTS eventHandler).
the oEv1 eventhandler attached to TTS object return also the progress in the _ISpeechVoiceEvents_Word() event procedure.Can be used for other goals also.

[post 253]


Click on code to select [then copy] -click outside to deselect



*1*  created on wednesday 03 of january 2017

* this is the second part of the previous post "Working with Text to Speech (TTS)" :http://yousfi.over-blog.com/2018/01/working-with-text-to-speech-tts.html
*this builds a vfp browser olecontrol and intercept som events.ist the same modified code in my previous post:http://yousfi.over-blog.com/2015/02/vfp-and-internet-explorer-eventhandler.html
*i add some interactions with the com Object SAPI.SPVOICe (from sapi.dll).
*i build an  eventHandler hooked on the TTS object and modify the code in Browser to detect the selection start /selection end and give to the TTS the hand to speak the text selection.
*infortubatly the HTMLSelectElementEvents class dont contains any procedure to detect a selectionChange event.it have only the event:HTMLSelectElementEvents_onselectstart()
*i used the HTMLSelectElementEvents_onmouseDown() and HTMLSelectElementEvents_onmouseUp() events to return the text selected and pass it to the TTS engine.
*can select the voice (i have the french as item0 and english as item1 in my PC).
*can make a selection on the document(mouseDown...mouseUp).this is passed to TTS to be spoken.
*the TTS start fires an animated gif to simulate teh speaking .this is hidden when the TTS terminate speaking (using the TTS eventHandler)
*the oEv1 eventhandler attached to TTS object return also the progress in the _ISpeechVoiceEvents_Word() event.



Set Defa To Addbs(Justpath(Sys(16,1)))
Set Safe Off

with _Screen
.AddProperty("yselect",.F.)
.WindowState=1
Endwith

*this creates a form with a activeX browser.
Publi yform
yform=Newobject("asup")
yform.Show
Read Events
Return
*
Define Class asup As Form
  Top = 24
  Left = 87
  Height = 500
  Width = 726
  ShowWindow = 2
  AutoCenter=.T.
  Caption = "Iexplore EventHandler-intercepting events..."
  Name = "form1"

  Add Object olecontrol1 As OleControl With ;
    oleclass="Shell.explorer.2",;
    anchor=15,;
    Top = 3, ;
    Left = 4, ;
    Height = 348, ;
    Width = 720, ;
    Name = "Olecontrol1"

  Add Object timer1 As Timer With ;
    Top = 312, ;
    Left = 696, ;
    Height = 23, ;
    Width = 23, ;
    Enabled = .F., ;
    Interval = 1000, ;
    Name = "Timer1"

  Add Object yhelp As Label With ;
    FontBold = .T., ;
    FontSize = 20, ;
    Anchor = 4, ;
    Caption = "?", ;
    autosize=.t., ;
    Left = 5, ;
    Top = 408, ;
    ForeColor = Rgb(64,128,0), ;
    Backstyle=0 , ;
    mousepointer=15,;
    Name = "yHelp"

  Add Object command1 As CommandButton With ;
    anchor=768,;
    Top = 408, ;
    Left = 20+10, ;
    Height = 27, ;
    Width = 120, ;
    Anchor = 4, ;
    backcolor=Rgb(0,255,0),;
    mousepointer=15,;
    Caption = "Navigate....", ;
    Name = "Command1"

  Add Object label1 As Label With ;
    anchor=80,;
    FontBold = .T., ;
    FontSize = 10, ;
    Anchor = 4, ;
    WordWrap = .T., ;
    Caption = "", ;
    Height = 108, ;
    Left = 180, ;
    Top = 358, ;
    Width = 540, ;
    ForeColor = Rgb(0,255,0), ;
    BackColor = Rgb(0,0,0), ;
    Name = "Label1"

  Add Object label2 As Label With ;
    FontBold = .T., ;
    FontSize = 10, ;
    Anchor = 4, ;
    WordWrap = .T., ;
    Caption = "", ;
    Height = 27, ;
    Left = 180, ;
    Top = 358+110, ;
    Width = 540, ;
    ForeColor = 255, ;
    BackColor = Rgb(0,0,0), ;
    Name = "Label2"

  Add Object combo1 As ComboBox With ;
    anchor=4,;
    Height = 27, ;
    Left = 20+10, ;
    Top =441, ;
    Width = 120, ;
    value=0, ;
    Name = "Combo1"

  Add Object img As Image With ;
    anchor=4,;
    left=20+10,;
    top=374-10,;
    stretch=2,;
    width=80,;
    height=40,;
    name="img"

  procedure yhelp.click
  local m.myvar
  text to m.myvar pretext 7 noshow
                  TTS Reading any selection on internet explorer navigator
 this is the second part of the previous post "Working with Text to Speech (TTS)" :http://yousfi.over-blog.com/2018/01/working-with-text-to-speech-tts.html
this builds a vfp browser olecontrol and intercept some events.its the same modified code in my previous post:
http://yousfi.over-blog.com/2015/02/vfp-and-internet-explorer-eventhandler.html
i add some interactions with the com Object SAPI.SPVOICe (from sapi.dll).
i build a second  eventHandler hooked on the TTS object and modify the code in Browser to detect the selection start /selection end and give to the TTS the hand to speak the text selection.
infortubatly the HTMLSelectElementEvents class dont contains any procedure to detect a selectionChange event.it have only the event:HTMLSelectElementEvents_onselectstart()
i used the HTMLSelectElementEvents_onmouseDown() and HTMLSelectElementEvents_onmouseUp() events  to return the valid text selected and pass it to the TTS engine.
can select the voice (i have the french as item(0) and english as item(1) in my PC)...to adapt.
can make a selection on the document(mouseDown...mouseUp).this is passed to TTS to be spoken.
the TTS at any start fires an animated gif to simulate the speaking activity .this is hidden when the TTS terminate speaking (using the TTS eventHandler).
the oEv1 eventhandler attached to TTS object return also the progress in the _ISpeechVoiceEvents_Word() event procedure.Can be used for other goals also.
 endtext
thisform.combo1.value=2   &&english
oEv.yspeak(m.myvar)
local oshell
oShell = Createobject('WScript.Shell')
oShell.Popup(m.myvar,0, 'Text to Speech (TTS) on IE11', 0+32+4096)  &&4,16,48,64...
oshell=null

 endproc


  Procedure combo1.Init
    With This
      .AddItem("french as item0")
      .AddItem("English as Item1")
      .Style=2
      .Value=1
      .ListIndex=1
    Endwith
  Endproc

  Procedure img.Init
    With This
      Local loRequest,m.lcURL
      m.lcURL="http://img.over-blog-kiwi.com/1/43/54/07/20171019/ob_20b74f_gif017small.gif"
      m.loRequest = Createobject('MsXml2.XmlHttp')
      m.loRequest.Open("GET",lcURL,.F.)
      m.loRequest.Send()
      .PictureVal=m.loRequest.ResponseBody
      m.loRequest=Null
      .Visible=.F.
    Endwith
  Endproc

  Procedure Destroy
    *clean refrences public variables
    oDoc=Null
    Release oDoc
    Try
      oSapi=Null
      Release oSapi
    Catch
    Endtry
    oEv=Null
    Release oEv
    oEv1=Null
    Release oEv1
    yform=Null
    Release yform

    Clea Events
  Endproc

  Procedure Load
    _Screen.WindowState=1
  Endproc

  Procedure Init
    Thisform.Width=800
    Thisform.Height=600
    Thisform.AutoCenter=.T.
    Thisform.timer1.Enabled=.T.
  Endproc

  Procedure olecontrol1.Init
    This.Anchor=15
    This.Navigate("about:blank")

    Do While This.busy Or This.readystate#4
    Enddo
    Inkey(1)

    Publi oDoc,oEv
    oDoc=This.Document
    &&set the events hook
    oEv = Newobject("HTMLSelectElementEvents")
    Eventhandler(oDoc,oEv)
  Endproc

  Procedure timer1.Timer
    TEXT to myvar0 noshow
       *!* original post with first evenHandler
        *!*--Author Yousfi Benameur El Bayadh Algeria<BR>
        *!*--Time stamp samedi 14 août 2010; 09:40:58<BR>
        *!*--Subject :Focus with activeX on VFP forms<BR>
        *!*--Version Vfp9Sp2  WINDOWS XP SP2  WIN8.1 <BR>
    ENDTEXT

    TEXT to myvar textmerge  noshow
        <p>
        <center><h3 style="align:center;color:navy ;background-color:yellow;"> HOW TO INTERCEPT KEYSTROKES OU MOUSE EVENTS ON IEXPLORE ACTIVEX</H3>
         <h3 style="align:center;color:red ;background-color:lime;"> Make any selection then PC start speaking</H3></center>
        This is a browser internet explorer activeX on a form.<br>
        When any activeX is placed on a form it receive the focus and make <br>
        the intercepting keys (keypreview=.t.) unavailbale on the form <br>
        All the keystrokes go to the activeX and dont be seen with the form event(keypress).<br>
        To intercept the keystrokes intercepted by the activeX , we must build an eventHandler<br>
        on it.
        The activeX seen from the object explorer have interface,methods,.... we can drag the <br>
        interface class code fromthe vfp object Browser  on the command window or a prg open file <br>
        and then have the class code to do that.<br><br>

        Can build the class as prg and in the form make the relation "eventHandler".<br>
        Try to stroke any key ,left mouse, rightmouse,key copy selection  CTRL+C and see<br>
        the interactive interceptions in the form.label<br
        you can add the code you want to the yeventHandler.prg  procedures to make some actions<br>
        when a key is pressed, click,dblclick,rightclick....<BR><BR>
       </p>
        <p style ="color :maroon;font-bold:bold;font-size:20px;">
        -for TTS sapi.spvoice object<BR>
            -Make a selection with mouse .the TTSstarts immediatly to speak it.<BR>
            -An animated image is fired at speak start and hidden at speak end (see the seconf hook oEv1 for oSAPI)<BR>
            -can dblClick at any time on Document stop the TTS.<BR>
         </p>
        <<myvar0>>
        </p>
    ENDTEXT
    oDoc.body.innerhtml=myvar
    This.Enabled=.F.
  Endproc

  Procedure command1.Click
    Y=Inputbox("url to navigate to","")
    If Not Empty(Y)
      Thisform.olecontrol1.Navigate(m.y)
    Endi
  Endproc
Enddefine
*
*!- End COde

*the class code belaw was dragged from vfp object browse and adapted to context  -  interface:HTMLSelectElementEvents
Define Class HTMLSelectElementEvents As Session OlePublic
  oSapi=Null  &&new class property
  Implements HTMLSelectElementEvents In "C:\WINDOWS\SYSTEM32\MSHTML.TLB"

  Procedure HTMLSelectElementEvents_onhelp() As LOGICAL
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onclick() As LOGICAL
    * add user code here
    This.ylog("Element clicked!"+Chr(13)+"called from:"+Program() )
  Endproc

  Procedure HTMLSelectElementEvents_ondblclick() As LOGICAL   &&Sto the oSAPI (TTS)
    * add user code here
    This.ylog("Element dblclicked! this stops the oSAPI TTS engine."+Chr(13)+"called from:"+Program() )
    Try  && if oSAPi exists
      This.oSapi.speak("",2)   &&purge oSapi
    Catch
    Endtry
  Endproc

  Procedure HTMLSelectElementEvents_onkeypress() As LOGICAL
    * add user code here)
  Endproc

  Procedure HTMLSelectElementEvents_onkeydown() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onkeyup() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onmouseout() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onmouseover() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onmousemove() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onmousedown() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onmouseup() As VOID
    * add user code here
    If _Screen.yselect=.T.
      Local m.y
      m.y=oDoc.Selection.createRange.Text
      If ! Empty(m.y)
        Messagebox(m.y,0+32+4096,'Text selection',1500)
        This.ySpeak(m.y)
      Endi
    Endi
    _Screen.yselect=.F.
  Endproc

  Procedure HTMLSelectElementEvents_onselectstart() As LOGICAL
    * add user code here

    This.ylog("on selectStart event"+Chr(13)+"called from:"+Program() )
    _Screen.yselect=.T.
  Endproc

  Procedure HTMLSelectElementEvents_onfilterchange() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_ondragstart() As LOGICAL
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onbeforeupdate() As LOGICAL
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onafterupdate() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onerrorupdate() As LOGICAL
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onrowexit() As LOGICAL
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onrowenter() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_ondatasetchanged() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_ondataavailable() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_ondatasetcomplete() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onlosecapture() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onpropertychange() As VOID
    * add user code here

  Endproc

  Procedure HTMLSelectElementEvents_onscroll() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onfocus() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onblur() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onresize() As VOID
    * add user code here
    This.ylog("Element resized!"+Chr(13)+"called from:"+Program() )
  Endproc

  Procedure HTMLSelectElementEvents_ondrag() As LOGICAL
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_ondragend() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_ondragenter() As LOGICAL
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_ondragover() As LOGICAL
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_ondragleave() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_ondrop() As LOGICAL
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onbeforecut() As LOGICAL
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_oncut() As LOGICAL
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onbeforecopy() As LOGICAL
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_oncopy() As LOGICAL
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onbeforepaste() As LOGICAL
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onpaste() As LOGICAL
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_oncontextmenu() As LOGICAL
    * add user code here
    This.ylog("Sorry rightclic is disabled by me ! you can skip this message and make it silent."+Chr(13)+"called from:"+Program() )
    Return .F.
  Endproc

  Procedure HTMLSelectElementEvents_onrowsdelete() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onrowsinserted() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_oncellchange() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onreadystatechange() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onbeforeeditfocus() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onlayoutcomplete() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onpage() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onbeforedeactivate() As LOGICAL
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onbeforeactivate() As LOGICAL
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onmove() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_oncontrolselect() As LOGICAL
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onmovestart() As LOGICAL
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onmoveend() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onresizestart() As LOGICAL
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onresizeend() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onmouseenter() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onmouseleave() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onmousewheel() As LOGICAL
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onactivate() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_ondeactivate() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onfocusin() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onfocusout() As VOID
    * add user code here
  Endproc

  Procedure HTMLSelectElementEvents_onchange() As VOID
    * add user code here
    This.ylog("Element onchange event!"+Chr(13)+"called from:"+Program() )
  Endproc

  Procedure ylog(ystr)
    _vfp.Forms(1).label1.Caption=ystr
    Try
      Local lcBell
      lcBell = Set("Bell")
      Set Bell To (Addbs(Getenv('windir')))+"MEDIA\notify.WAV"
      ?? Chr(7)
      Set Bell To (lcBell)
    Catch
    Endtry
  Endproc

  Procedure ySpeak
    Lparameters ytext

    If !Pcount()=1
      Return .F.
    Endi

    If  !Vartype(This.oSapi)='O'
      This.oSapi=Createobject("SAPI.spVoice")
   ***************************
      *build another  eventHandler for TTS oSAPI( set the events hook)
      Publi oEv1
      oEv1 = Newobject("yISpeechVoiceEvents")
      Eventhandler(This.oSapi,oEv1)
   ****************************
    Endi
    Local m.x
    m.x=_Screen.ActiveForm.combo1.Value-1
    This.oSapi.Voice=This.oSapi.GetVoices().Item(m.x)   &&_Screen.xitem)  &&0 french  1 englich to adapt
    Inke(1)
    This.oSapi.speak(ytext,1+2)
    * This.oSapi.waitUntilDone(-1)  &&war,inbg: block process until oSAPi finishes speaking
  Endproc

Enddefine
*EndDefine HTMLSelectElementEvents
*
**the class code belaw was dragged from vfp object browse and adapted to context - interface  _ISpeechVoiceEvents
Define Class yISpeechVoiceEvents As Session OlePublic
  Implements _ISpeechVoiceEvents In "C:\WINDOWS\SYSTEM32\SPEECH\COMMON\SAPI.DLL"

  Procedure _ISpeechVoiceEvents_StartStream(StreamNumber As Number, StreamPosition As VARIANT) As VOID;
      HELPSTRING "StartStream"
    * add user code here
    With _Screen.ActiveForm
      .label2.Caption="Start of stream "+Trans(StreamNumber)+"  Streamposition:"+Trans(StreamPosition)
      .img.Visible=.T.
    Endwith
  Endproc

  Procedure _ISpeechVoiceEvents_EndStream(StreamNumber As Number, StreamPosition As VARIANT) As VOID;
      HELPSTRING "EndStream"
    * add user code here
    With _Screen.ActiveForm
      .label2.Caption="End of stream "+Trans(StreamNumber)+"  Streamposition:"+Trans(StreamPosition)
      .img.Visible=.F.
    Endwith
  Endproc

  Procedure _ISpeechVoiceEvents_VoiceChange(StreamNumber As Number, StreamPosition As VARIANT, VoiceObjectToken As VARIANT) As VOID;
      HELPSTRING "VoiceChange"
    * add user code here
  Endproc

  Procedure _ISpeechVoiceEvents_Bookmark(StreamNumber As Number, StreamPosition As VARIANT, Bookmark As String, BookmarkId As Number) As VOID;
      HELPSTRING "Bookmark"
    * add user code here
  Endproc

  Procedure _ISpeechVoiceEvents_Word(StreamNumber As Number, StreamPosition As VARIANT,CharacterPosition  As Number, Length As Number) As VOID;
      HELPSTRING "Word"
    * add user code here
    _Screen.ActiveForm.label2.Caption="Word: stream "+Trans(StreamNumber)+"  Streamposition:"+Trans(StreamPosition)+" CharacterPosition"+Trans(CharacterPosition)+" Length:"+Trans(Length)

  Endproc

  Procedure _ISpeechVoiceEvents_Sentence(StreamNumber As Number, StreamPosition As VARIANT, CharacterPosition As Number, Length As Number) As VOID;
      HELPSTRING "Sentence"
    * add user code here
  Endproc

  Procedure _ISpeechVoiceEvents_Phoneme(StreamNumber As Number, StreamPosition As VARIANT, Duration As Number, NextPhoneId As Integer, Feature As VARIANT, CurrentPhoneId As Integer) As VOID;
      HELPSTRING "Phoneme"
    * add user code here
  Endproc

  Procedure _ISpeechVoiceEvents_Viseme(StreamNumber As Number, StreamPosition As VARIANT, Duration As Number, NextVisemeId As VARIANT, Feature As VARIANT, CurrentVisemeId As VARIANT) As VOID;
      HELPSTRING "Viseme"
    * add user code here
  Endproc

  Procedure _ISpeechVoiceEvents_AudioLevel(StreamNumber As Number, StreamPosition As VARIANT, AudioLevel As Number) As VOID;
      HELPSTRING "AudioLevel"
    * add user code here
  Endproc

  Procedure _ISpeechVoiceEvents_EnginePrivate(StreamNumber As Number, StreamPosition As Number, EngineData As VARIANT) As VOID;
      HELPSTRING "EnginePrivate"
    * add user code here
  Endproc

Enddefine


of course can export text spoken to wav  (see the first part in previous post)-Dragged procedures must stay as it,dont erase procedures even if they are empty otherwise the code fires errors and fails.
of course can export text spoken to wav  (see the first part in previous post)-Dragged procedures must stay as it,dont erase procedures even if they are empty otherwise the code fires errors and fails.
of course can export text spoken to wav  (see the first part in previous post)-Dragged procedures must stay as it,dont erase procedures even if they are empty otherwise the code fires errors and fails.
of course can export text spoken to wav  (see the first part in previous post)-Dragged procedures must stay as it,dont erase procedures even if they are empty otherwise the code fires errors and fails.

of course can export text spoken to wav (see the first part in previous post)-Dragged procedures must stay as it,dont erase procedures even if they are empty otherwise the code fires errors and fails.


                     

Yousfi Benameur


Important:All Codes above are tested on VFP9SP2 & windows 10 pro 64 bits version 1709(fall creator) & IE11 emulation.

To be informed of the latest articles, subscribe:
Comment on this post