Solidworks VBA speech

Hi all

Here is my macro, the difficulty here is to read the message aloud instead of an msgbox but asynchronously (non-modal for msgbox)

these 2 codes work in the VBE editor with the F8 execute key but not directly with an action button in Solidworks, if anyone has an idea

sp. Speak " Select a Sketch ", 1
or
sp. Speak, SVSFlagsAsync  

'Select a sketch without going into it
'where
'Entering a sketch

Sub Piece_suppr_bancales()
Dim swApp     As SldWorks.SldWorks
Dim swDoc     As SldWorks.ModelDoc2
Dim swRelMgr  As SldWorks.SketchRelationManager
Dim swSketch  As SldWorks.Sketch
Dim vRels     As Variant
Dim swRel     As SldWorks.SketchRelation
Dim i         As Long
Dim sp        As Object

Set swApp = Application.SldWorks
Set swDoc = swApp.ActiveDoc
Set swSkMgr = swDoc.SketchManager
Set swSketch = swDoc.GetActiveSketch2
Set sp = CreateObject("SAPI.SpVoice")

If swDoc.SelectionManager.GetSelectedObjectType3(1, -1) = swSelSKETCHES Then
Set swSketch = swDoc.SelectionManager.GetSelectedObject6(1, -1).GetSpecificFeature
Else
sp.Speak "Sélectionner une esquisse"
'sp.Speak "Sélectionner une esquisse", 1 / sp.Speak "Sélectionner une esquisse", SVSFlagsAsync
'asynchrone pour effectuer d'autres tâches en même temps, ne fct que dans VBE pas avec bouton macro
Exit Sub
End If

Set swRelMgr = swSketch.RelationManager
If swRelMgr.GetRelationsCount(swDangling) > 0 Then
vRels = swRelMgr.GetRelations(swDangling)
    For i = 0 To UBound(vRels)
    Set swRel = vRels(i)
    swRelMgr.DeleteRelation swRel
    Next i
'MsgBox "Esquisse : " & swSketch.Name & Chr(10) & "Relations bancales supprimées : " & UBound(vRels) + 1
Else
sp.Speak "Esquisse : " & swSketch.Name & Chr(10) & "Pas de relation bancales trouvée"

End If
End Sub

I found this link (to be tested):

Hello
for me it has nothing to do with a text read asynchronously

Hello;

Have you tried replacing msgBoxes with " sendmsgtoUser2 "?

https://help.solidworks.com/2022/English/api/sldworksapi/SolidWorks.Interop.sldworks~SolidWorks.Interop.sldworks.ISldWorks~SendMsgToUser2.html?verRedirect=1

Kind regards.

… In the meantime I found this:

and this:

if it can help...

Hello
I don't want msgbox or sendmsgtoUser2 which is the same thing

I just tried the following macro, which doesn't work asynchronously weirdly

Function RobotSpeaking(sText As String) As Boolean
    On Error Resume Next
    Err.Clear
    With CreateObject("SAPI.SpVoice")
        .SVSFlagsAsync
        .Volume = 100
        .Speak sText
    End With
    RobotSpeaking = (Err.Number = 0)
End Function

And does it work without the asynchronous part or not?

.SVSFlagsAsync

with or without . SVSFlagsAsync is the same in Solidworks, the text is read synchronously

From what I understand it is well read, but not asynchronously and it doesn't matter if . SVSFlagsAsync is present or not.
Is that right?

yes that's it and when I put this macro, the message is read in VBE only (F8 key) but not with the macro button

Function RobotSpeaking(sText As String) As Boolean
    On Error Resume Next
    Err.Clear
    With CreateObject("SAPI.SpVoice")
        '.SVSFlagsAsync
        .Volume = 100
        .Speak sText, 1 'ou SVSFlagsAsync
    End With
    RobotSpeaking = (Err.Number = 0)
End Function

I try too
. Speak sText, SVSFlagsAsync = True, or false and it is read synchronously in both cases

I have the impression that this is the normal operation, if I replace:

  .Speak sText, 1 

by:

  .Speak sText, 0

The text is well read.
With the 1 no reading because it seems that as soon as it moves to the next line of code the text is interrupted (before it has started)

This macro under SW or excel has the same operation under the 2 software so for me it doesn't come from SW


Sub speech()

Set swApp = Application.SldWorks 'Ligne à mettre ne commentaire sous excel

 
RobotSpeaking "Ceci est un essai, de texte lu par windows 10, si vous entendez le message tout en affichant le msgbox, c'est que cela fonctione"
MsgBox "Fonctionne si le message s'affiche avant la fin du texte lu"
  
End Sub

Function RobotSpeaking(sText As String) As Boolean
    On Error Resume Next
    Err.Clear
    With CreateObject("SAPI.SpVoice")
        .SVSFlagsAsync
        .Volume = 100
        .Speak sText, 1 'ou SVSFlagsAsync
    End With
    RobotSpeaking = (Err.Number = 0)
End Function

yet in the VBE editor with the F8 key the text is read asynchronously with ,1 or SVSFlagsAsync

Yes but if you quickly click on F8 as soon as you arrive on msgbox it cuts the text.
In excel these 2 codes work. One asynchronously and the other not.

Sub TalkToMe3()
Application.Speech.Speak "Excel me parle tout en affichant le message", SpeakAsync:=True
MsgBox "test"
End Sub
Sub TalkToMe4()
Application.Speech.Speak "Excel me parle puis affichele message" ', SpeakAsync:=True
MsgBox "test"
End Sub

So I guess it comes from the function used.
We will have to find an equivalent method under SW.

If anyone has a code idea

By not creating a function (code of the function directly in the sub) it reads the text well, while displaying the msgbox:

Dim swApp As Object
Sub speech()
Dim sText As String
sText = "Ceci est un essai, de texte lu par windows 10, si vous entendez le message tout en affichant le msgbox, c'est que cela fonctione"

Set swApp = Application.SldWorks
With CreateObject("SAPI.SpVoice")
        '.SVSFlagsAsync
        .Volume = 100
        .speak sText, 1 ', 1 ', 0 'ou SVSFlagsAsync
    End With
 
MsgBox "Fonctionne si le message s'affiche avant la fin du texte lu"
  
End Sub

I just realized something

The asynchronous read code works fine but is cut off automatically because the macro closes with end sub

So to summarize my macro should ideally read the text and let me work on solidworks

In fact, the macro doesn't have time to read the text before it closes since I don't have any other actions afterwards

So the playback would have to continue while letting me manipulate solidworks and I don't know if it's possible to export the voice command out of vba (batch...)

I think we should ask him to wait with WaitUntilDone

The problem is that it comes down to the same as if it's synchronous, which I don't want

I don't have the impression that it's possible.

  • Either asynchronous and at the end of the sub whether the text is finished or not it cuts. (even including the text in a function or other sub called by call or other procedure)

  • Either not asynchronous and we wait for the end of the text to move on to the next instruction.

I don't know in what frame and why exactly you want to put voice text, but personally I'm not a fan of it at all, and I much prefer the msgbox or text box that allows you to continue the instructions while displaying the text.
On macros that we launch very often, it would very quickly take my head.
And for a design office shared by 20 colleagues like us, I'm not even talking about it, the sound is cut off on all the workstations.

1 Like

In asynchronous programming, on .NET for example, we are obliged to give an Await statement. Otherwise, you don't wait for an asynchronous instruction to finish, and that's what makes this type of programming so meaningful.

So you need to call your SpVoice method, then run a set of tasks if you want to and then call WaitUntilDone

Thank you for your answers
For the moment I don't see a solution, I'm leaving it on standby