|
新的.NET类库中加入了SystemSound类来解决音频播放的问题。
这个类在使用的过程中非常简单,就是不能知道什么时候播放结束,想要知道什么时候结束可以使用PlaySound函数反复监视
使用方法是
while (!PlaySound("",new IntPtr(), PlaySoundFlags.SND_NOSTOP))
函数导入
[DllImport("winmm.DLL", EntryPoint = "PlaySound", SetLastError = true)]
private static extern bool PlaySound(string szSound, System.IntPtr hMod, PlaySoundFlags flags);
但是这个SystemSound类在WINDOWS7的WINSERVICE环境下使用不能,具体原因可能是DLL权限的问题,在运行的过程中不会发生错误,可是音乐无法播放。
解决方法1:使用DirectX
下载微软的DirectX SDK 使用方法很多地方都有写我就不再赘述了。
2: mciSendString函数播放
具体方法如下
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Runtime.InteropServices;
using System.IO;
using System.Threading;
namespace SoundControl
{
public class MciPlaySound
{
#region 変数
private StructMCI m_MciInfo = new StructMCI();
private StringBuilder m_sbCommand = new StringBuilder();
[MarshalAs(UnmanagedType.ByValTStr, SizeConst = 260)]
private string m_strShortName = "";
[MarshalAs(UnmanagedType.LPTStr, SizeConst = 128)]
private string m_strCommandResult = "";
private long m_lReturn = 0;
private string m_strDeviceName = "";
#endregion
#region
public enum State
{
// 準備中
Ready = 0,
// 再生中
Playing = 1,
// 再生完了
Stop = 2
};
public struct StructMCI
{
public string FileName;
public State State;
};
#endregion
#region 再生部品
[DllImport("kernel32.dll", CharSet = CharSet.Auto)]
public static extern int GetShortPathName(
string lpszLongPath,
string shortFile,
int cchBuffer);
// WAVE再生部品
[DllImport("winmm.dll", EntryPoint = "mciSendString", CharSet = CharSet.Auto)]
private static extern int mciSendString(
string lpstrCommand,
string lpstrReturnString,
int uReturnLength,
IntPtr hwndCallback);
#endregion
#region
public string DeviceName
{
get
{
return m_strDeviceName;
}
}
public string FileName
{
get
{
return m_MciInfo.FileName;
}
set
{
lock (m_sbCommand)
{
if (!File.Exists(value))
{
m_MciInfo.FileName = "";
throw new Exception("文件不存在。");
}
m_MciInfo.FileName = value;
m_lReturn =
mciSendString("close all",
m_strCommandResult,
m_strCommandResult.Length,
IntPtr.Zero);
if (m_lReturn != 0)
{
throw new Exception("初期化失敗。");
}
ClearCommand();
m_strShortName = "";
m_strShortName = m_strShortName.PadLeft(260, Convert.ToChar(" "));
m_lReturn = GetShortPathName(m_MciInfo.FileName,
m_strShortName,
m_strShortName.Length);
m_sbCommand.Append("open \"");
m_sbCommand.Append(GetPath(m_strShortName));
m_sbCommand.Append("\" type WaveAudio alias micmediaplay");
m_lReturn =
mciSendString(m_sbCommand.ToString(),
m_strCommandResult,
m_strCommandResult.Length,
IntPtr.Zero);
if (m_lReturn != 0)
{
throw new Exception("初期化失敗。");
}
m_strDeviceName = "micmediaplay";
m_lReturn =
mciSendString("set micmediaplay time format milliseconds",
m_strCommandResult,
m_strCommandResult.Length,
IntPtr.Zero);
if (m_lReturn != 0)
{
throw new Exception("初期化失敗。");
}
m_MciInfo.State = State.Ready;
}
}
}
#endregion
#region
public void Play()
{
lock (m_sbCommand)
{
m_strCommandResult = "";
m_strCommandResult =
m_strCommandResult.PadLeft(128, Convert.ToChar(" "));
if (String.IsNullOrEmpty(m_MciInfo.FileName))
{
throw new Exception("音声文件不存在。");
}
if (m_MciInfo.State != State.Ready)
{
return;
}
m_lReturn = mciSendString("play micmediaplay from 0",
m_strCommandResult,
m_strCommandResult.Length,
IntPtr.Zero);
if (m_lReturn != 0)
{
throw new Exception("再生失敗。");
}
m_MciInfo.State = State.Playing;
}
}
public void StopPlay()
{
lock (m_sbCommand)
{
m_MciInfo.State = State.Stop;
}
}
public void Close()
{
m_lReturn = mciSendString("close all",
m_strCommandResult,
m_strCommandResult.Length,
IntPtr.Zero);
if (m_lReturn != 0)
{
throw new Exception("釈放失敗。");
}
}
public bool IsStop()
{
lock (m_sbCommand)
{
m_strCommandResult = "";
m_strCommandResult =
m_strCommandResult.PadLeft(128, Convert.ToChar(" "));
if (m_MciInfo.State == State.Stop)
{
if (String.IsNullOrEmpty(m_strDeviceName))
{
m_lReturn = mciSendString("close micmediaplay",
m_strCommandResult,
m_strCommandResult.Length,
IntPtr.Zero);
if (m_lReturn != 0)
{
throw new Exception("停止失敗。");
}
m_strDeviceName = "";
}
m_lReturn = mciSendString("close all",
m_strCommandResult,
m_strCommandResult.Length,
IntPtr.Zero);
if (m_lReturn != 0)
{
throw new Exception("停止失敗。");
}
return true;
}
m_lReturn = mciSendString("status micmediaplay mode",
m_strCommandResult,
m_strCommandResult.Length,
IntPtr.Zero);
if (m_lReturn != 0)
{
throw new Exception("状態取得失敗");
}
if (m_strCommandResult.IndexOf("stopped") >= 0)
{
// 状態を変更する
m_MciInfo.State = State.Ready;
return true;
}
return false;
}
}
private string GetPath(string strPath)
{
if (strPath.Length < 1)
{
return "";
}
strPath = strPath.Trim();
strPath = strPath.Substring(0, strPath.Length - 1);
return strPath;
}
private void ClearCommand()
{
if (m_sbCommand.Length != 0)
{
m_sbCommand.Remove(0, m_sbCommand.Length);
}
}
#endregion
}
}
第二个方法的好处是不用去下SDK应该所有机器上都能使用 |
|