I'm working on a speech synthesis project, and I decided to try and use the Microsoft.Speech namespace instead of the built-in System.Speech namespace because Microsoft isn't fixing the memory leak here and recommends using Microsoft.Speech as a workaround.
When I run the program below, I get a NullReferenceException when it calls GetInstalledVoices.
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using Microsoft.Speech.Synthesis;
namespace ConsoleApplication1
{
class Program
{
static void Main(string[] args)
{
SpeechSynthesizer synth = new SpeechSynthesizer();
synth.GetInstalledVoices();
}
}
}
And when I run this next program, I get a UnauthorizedAccessException (I am running as an administrator) when it calls Speak.
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using Microsoft.Speech.Synthesis;
namespace ConsoleApplication1
{
class Program
{
static void Main(string[] args)
{
SpeechSynthesizer synth = new SpeechSynthesizer();
synth.Speak("exception");
}
}
}
I'm running VS Express 2012 on Windows 8 x64, and the project is configured for x64. I installed the x64 runtime and SDK for Microsoft speech, and installed the en-us language pack from http://www.microsoft.com/en-us/download/details.aspx?id=27224. I even tried downloading the x86 runtime and SDK and changing my project to x86, but that results in a PlatformNotSupportedException.
Is there some other install I'm missing, or is the Microsoft.Speech namespace just not supported on my platform? If I change using Microsoft.Speech.Synthesis to using System.Speech.Synthesis, it's fine except for the memory leak that I mentioned, and I can probably get away with that for now, since this is a hobby application, not for work.
It takes me some time but i realized that i installed only MSSpeech_SR_en-US_TELE.msi which means SpeechRecognition. You need to scroll down in installer and install also text to speech e.g. "MSSpeech_TTS_en-US_Helen.msi".
I'm using eSpeak instead, and just shelling out to their command line program from my .Net program. This is a better solution for me because eSpeak and it's associated voice are easy to install on multiple computers - if I used the Microsoft Speech solutions, I would be stuck with whatever the default voices on that computer are, unless we bought voices for each computer. It also happens that the robotic-sounding eSpeak voice is a better fit for my project, because guess what, it's a talking robot head!
I was having the same problem and noticed that it was a first-time-run problem. So what I did to solve this, is I have a List<InstalledVoice> InstalledVoices; declared as a global property.
Then in the Form.Load(), I have this:
while (InstalledVoices == null)
{
InstalledVoices = SpeechSynth.GetInstalledVoices().ToList();
}
When I ran the debug output on that, it failed once, then succeeded the second time.
That guarantees that you have a collection of the Installed Voices and no null reference. SpeechSynth is my instance of the SpeechSynthesizer class. I store each InstalledVoice in a Dictionary<string, VoiceInfo> for later reference.
Make sure you that Windows updates have been installed.
I tried to get away with a Windows 7 installation without any updates, and something like SpeechSynthesizer.SelectVoice(SomeVoiceName) would fail.
The only solution was to get the automatic Windows updates. Not sure which update exactely resolved the issue.
But I stumble over this problem again and again when I test my app in a VM with Windows 7 without updates.
Related
In the last few days, I tried to access regedit using c#.
The class RegistryKey is not defined after I added using Microsoft.Win32.
Can you help me?
Code:
using System;
using Microsoft.Win32;
using System.Security.Permissions;
namespace TMREAddons
{
public class RegEdit
{
RegistryKey key = Registry.LocalMachine.OpenSubKey("Software\\Wow6432Node\\MySQL AB\\MySQL Connector\\Net")
}
}
This is a basic class library, nothing more than that.
The targetFramework is:
<TargetFramework>netstandard2.1</TargetFramework>
You're targeting netstandard2.1 - which basically means "I want this to be able to run on any platform that's compatible with .NET Standard 2.1". Given that the Windows Registry doesn't exist on every .NET Standard 2.1 compatible platform, I'm not surprised at the error you're getting. (In general, I wouldn't expect anything from Microsoft.Win32 to be supported in .NET Standard.)
You can add the Microsoft.Win32.Registry NuGet package as a dependency, and that should solve the compilation issue - although it will still fail if you run on a non-Windows platform, of course.
I'm trying to play a wav file from a .NET Core console application (No, I'm not using the console beep. Weird requirements, I know.). I figured I could do that using OpenAL. I'm able to read the file in fine, but then when I try to play it, it fails on the first line:
int handle = AL.GenBuffer();
I get the exception: InvalidOperationException: Could not load openal32.dll. I'm using the OpenTK.NETCore NuGet package. Am I missing something?
I figured it out. It turns out the OpenTK.NETCore package doesn't come with OpenAL, just the SDK. Instead, it looks for it already installed on the machine. I used the installer, and imagine I'll need to install it on every machine that uses my application
Not using OpenAL, but an alternative solution to play wav files in a console application can be found here:
Playing sounds on Console - C#
After adding the sound file to your solution the suggested code in the link is:
using System.Reflection;
using System.IO;
using System.Resources;
using System.Media;
using System.Diagnostics;
namespace Yournamespace
{
public partial class Form2 : Form
{
public Form2()
{
InitializeComponent();
}
private void Form2_Load(object sender, EventArgs e)
{
Assembly assembly;
Stream soundStream;
SoundPlayer sp;
assembly = Assembly.GetExecutingAssembly();
sp = new SoundPlayer(assembly.GetManifestResourceStream
("Yournamespace.Dreamer.wav"));
sp.Play();
}
}
}
This problem has been causing me a headache for a few days, and I cannot find a reason for it. I'm pretty sure this is an environmental issue particular to my machine, but still its causing me problems with testing.
I'm creating a DLL in C# using Visual Studio 2010 Professional. Version one is below;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.Runtime.InteropServices;
namespace TestCOM
{
[ClassInterface(ClassInterfaceType.AutoDual)]
[System.Runtime.InteropServices.ComVisible(true)]
[System.Runtime.InteropServices.ProgId("TestCOM.Class1")]
[System.Runtime.InteropServices.Guid("803A1B2F-1CDA-4571-9084-87500388693B")]
public class Class1
{
public void showMessage()
{
MessageBox.Show("Hello from TextCom");
}
}
}
This assembly compiles fine, and everything is good. I run the following script to register it as a COM object (first for 32-bit, then for 64-bit);
C:\Windows\Microsoft.NET\Framework\v4.0.30319\regasm.exe TestCOM.dll /codebase /nologo /tlb:TestCOM32.tlb
C:\Windows\Microsoft.NET\Framework64\v4.0.30319\regasm.exe TestCOM.dll /codebase /nologo /tlb:TestCOM64.tlb
And then use the following script to test it;
dim tc
set tc = CreateObject("TestCOM.Class1")
tc.showMessage()
I use csript to test the script, so I can control which bit depth it uses - I test it once with 32-bit and once with 64-bit. So far everything is good.
Now, when I modify the original assembly to add a function, as follows
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.Runtime.InteropServices;
namespace TestCOM
{
[ClassInterface(ClassInterfaceType.AutoDual)]
[System.Runtime.InteropServices.ComVisible(true)]
[System.Runtime.InteropServices.ProgId("TestCOM.Class1")]
[System.Runtime.InteropServices.Guid("803A1B2F-1CDA-4571-9084-87500388693B")]
public class Class1
{
public void showMessage()
{
MessageBox.Show("Hello from TextCom");
}
public void HelloWorld()
{
MessageBox.Show("Hello World!!");
}
}
}
Before the modification, I unregistered the library using "regasm /unregister" and it reported all types unregistered successfully.
When i register the library, now with changes, the original test script works perfectly. If I extend the test script to call the new HelloWorld function;
In 32-bit scripts, it works perfectly.
In 64-bit scripts, it complains that no such function exists for the TestCOM.Class1 object
I've tried this every which way I can, but I cannot identify why the new function is available to the 32-bit callers, but not the 64-bit calls.
What am I doing wrong ? is there a cache somewhere for the 64-bit stuff I'm not aware of, or a registry setting that needs changed?
To be clear;
1. Build assembly
2. Register using regasm, once for 32 and once for 64
3. Test using script - everything works
4. Unregister library
5. Make modifications, rebuild
6. Register as per Step 2
7. Tests work in 32-bit, but not 64. Wtf ?
Clearly you are suffering from DLL Hell, always around with COM, it is loading an old version of your DLL. Your GAC could have gotten polluted by earlier experiments, it will always find the GACed version first. You are making it worse by specifying the [Guid], making your new class look the same as the old one, even though it is not identical. Preventing COM from telling you that it cannot find the new version of the class.
The most reliable, although noisy, way to see where the DLL came from is by using SysInterals' ProcMon utility. You'll see it reading the registry key and loading the DLL. You can see what directory it came from. Make sure it is not the GAC, remove it with gacutil /u if that's the case, and make sure that you got it rebuilt by checking the timestamp on the file.
I'm doing some exercises with C# in the trial version of VS 2012. I want to execute a cmd command from a CS file. For this, I've tried Process.Start as well as System.Diagnostics.Process that are mentioned in these posts:
Run Command Prompt Commands
Execute CMD command from code
However, despite I added "using System.Diagnostics" and "using System.ComponentModel", I'm still getting "The type or namespace name 'Process' does not exist in the namespace 'System.Diagnostics', missing assembly reference" error. ¿Any suggestion so I can i get rid of this error? Thanks in advance.
This usually happens when you have Target framework = .NET Framework Client Profile, but DLL you reference is from .NET Framework (full). Make sure you have System.dll in your references from valid framework.
I just did the same - created empty console application with the following code:
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.ComponentModel;
using System.Linq;
using System.Text;
namespace ConsoleApplication1
{
class Program
{
static void Main(string[] args)
{
var prc = Process.Start("explorer.exe");
}
}
}
Works perfectly fine for me.
Additional thing to check is Intellisense - when you start typing "System.Diagnostics.Proc"... - does it show you dropdown with "Process" there?
UPDATE:
Windows Store projects are based on different version of target .NET Framework - .NET for Windows Store apps, which does not support functionality you need.
For more details do web search:".NET for Windows Store apps". Helpful links:
http://msdn.microsoft.com/en-us/library/windows/apps/br230302.aspx
http://msdn.microsoft.com/en-us/library/windows/apps/br230232.aspx
I am struggling with the following error when compiling my C# code with CSC - "error CS0234: The type or namespace name 'Core' does not exits in the namespace 'Microsoft.Office' (are you missing an assembly)"
I've had zero experience with object oriented programming before tackling this project. It involves automation of a couple devices through serial commands. Parameters are read from a native Excel file and data is written to Excel files that the code creates.
Here's what think maybe pertinent:
my compiling command: CSC /r:"C:\Data\Code\Microsoft.Office.Interop.Excel.dll" compiled.cs
I have the file Microsoft.Office.Interop.Excel.dll in the directory above. I found the file on my computer from something else that installed it. It is dated 2007.
I am using Office 2010
I installed Microsoft Office 2010: Primary Interop Assemblies Redistributable but can't tell what that did
I am referencing CSC from Framework (not Framework64) revision 4.0.30319
Here is the header to my code
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.IO.Ports;
using System.Threading;
using Microsoft.Office.Core;
using Excel = Microsoft.Office.Interop.Excel;
using Microsoft.Office.Interop.Excel;
namespace ConsoleApplication1
{
class Program
{
static void Main(string[] args)
Follow-up question (if I get this working) what things do I need to worry about to make this run on another computer? My thoughts was that all I needed was the .excel.dll and the .exe file in the same directory structure? (At this time I don't know what version of .NET or Office is being run on the target computer - my guess would be at least it would be Office 2010.)
Any guidance would be greatly appreciated. I've been wearing out google on this one for the past week+
Regards,
Keith
I know this is not the exact answer you're looking for, but I'm posting it because I think it would be more helpful than directly answering your question.
You would save yourself a LOT of time by downloading Visual C# 2010 Express and letting the IDE do the heavy lifting for you.
It sounds like you need to add a reference, which means referencing an existing .dll file somewhere. I know if can be done via the command line, but it's a LOT easier to use the IDE.
It's free, and can be found here: http://www.microsoft.com/visualstudio/en-us/products/2010-editions/visual-csharp-express
There's a How-To guide for Office Interop here: http://msdn.microsoft.com/en-us/library/dd264733.aspx