3

我创建了一个 WinForm 应用程序,其中包含一个 AxWMPLib.AxMediaPlayer,我在其中播放一些视频。我还必须在不同的线程中播放一些其他自定义声音。为此,我使用了 System.Media.SoundPlayer.PlaySync()。该线程循环播放几个声音文件。问题是当我暂停/停止视频时,按钮事件的声音播放得很好。但是当视频运行时,有时会跳过一些声音文件。它是随机发生的。任何人都可以对这个问题以及如何解决它给出一些解释。我的意思是我怎么能同时播放声音和视频。

视频在 UI 线程中播放,其他声音在不同线程中播放。请查看以下代码:

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.Threading;
using ElectroQ;
using ElectroQServer1.Entities;
using WMPLib;
using System.Media;
using System.Windows.Media;

namespace ElectroQServer1
{
    public partial class Form1 : Form
    {
        Thread dbListenerThread;
        IWMPPlaylist playlist;

        //string[] tokenNumber = { "A001", "B002", "C003", "D004","E005", "F006", "G007","HAMB" };
        //string[] counterNumber = { "01", "02", "03", "04", "05", "06", "07", "MB" };
        public Form1()
        {
            InitializeComponent();
            //ResizeRedraw = true;
            this.SetStyle(System.Windows.Forms.ControlStyles.DoubleBuffer, true);
            this.WindowState = FormWindowState.Maximized;
            //this.FormBorderStyle = FormBorderStyle.None;
            //this.TopMost = true;


            dbListenerThread = new Thread(RefreshQueueBoard);
            dbListenerThread.Start();

        }
        /// <summary>
        /// This method is used to prevent the flickering of the window.
        /// </summary>
        protected override CreateParams CreateParams
        {
            get
            {
                CreateParams cp = base.CreateParams;
                cp.ExStyle |= 0x02000000;  // Turn on WS_EX_COMPOSITED
                return cp;
            }
        } 
        public void RefreshQueueBoard()
        {
            //Thread.Sleep(000);
            while (true)
            {
                List<QueueData> lstQData = DA.GetAllQueueData(" where service_status_id = 2 ");
                printToken(lstQData);
                printCounter(lstQData);

                playSound(lstQData);
                Thread.Sleep(1000);
            }
        }

        public void playSound(List<QueueData> lstQData)
        {
            foreach (QueueData qData in lstQData)
            {
                if (!qData.SoundPlayed)
                {
                    string strSoundFile;
                    PlaySoundFIle(@"Sounds/TN.WAV");
                    foreach (char c in qData.ServiceQueueSerial)
                    {
                        strSoundFile = string.Format(@"Sounds/{0}.WAV", c);
                        PlaySoundFIle(strSoundFile);
                    }
                    PlaySoundFIle(@"Sounds/CN.WAV");
                    foreach (char c in qData.ServiceCounterID)
                    {
                        strSoundFile = string.Format(@"Sounds/{0}.WAV", c);
                        PlaySoundFIle(strSoundFile);
                    }
                    string strUpdateQuery = string.Format("UPDATE electro_queue SET sound_played = 1 WHERE service_queue_serial = '{0}'", qData.ServiceQueueSerial);
                    DA.UpdateQueueData(strUpdateQuery);

                }
            }
        }

        public void PlaySoundFIle(string strFile)
        {
            //string[] files = new string[4] { @"Sounds/TN.WAV", @"Sounds/CN.WAV", @"Sounds/TN.WAV", @"Sounds/CN.WAV"};

            //WaveIO wa = new WaveIO();
            //wa.Merge(files, @"tempfile.wav");
            //MediaPlayer wowSound = new MediaPlayer(); //Initialize a new instance of MediaPlayer of name wowSound
            //wowSound.Open(new Uri(@"tempfile.wav", UriKind.Relative)); //Open the file for a media playback
            //wowSound.Play();
            using (var soundPlayer = new SoundPlayer(strFile))
            {
                soundPlayer.PlaySync(); // can also use soundPlayer.Play() but it misses some sound file.
            }
        }

        private void printToken(List<QueueData> lstQData)
        {
            if (InvokeRequired)
            {
                this.Invoke(new MethodInvoker(delegate
                {
                    pnlQStat.Controls.Clear(); 
                    string dir;
                    //int xpos = 55;
                    //int ypos = 207;
                    int xpos = 10;
                    int ypos = 00;
                    //int k=0;
                    for (int i = 0; i < lstQData.Count; i++)
                    {
                       /* if (i == 4 || i == 8)
                        {
                            ypos = ypos - 360;
                            xpos = 675;
                        }*/

                        foreach (char c in lstQData[i].ServiceQueueSerial)
                        {
                            if (i == 0)
                            {
                                dir = "Resources/_" + c + ".bmp";
                            }
                            else
                            {
                                dir = "Resources/" + c + ".bmp";
                            }
                            createPicBox(dir, "pBox" + i, xpos, ypos);
                            xpos = xpos + 43;

                        }

                        ypos = ypos + 50;
                        xpos = 10;


                    }
                }));
                return;
            }
        }

        private void printCounter(List<QueueData> lstQData)
        {
            if (InvokeRequired)
            {
                this.Invoke(new MethodInvoker(delegate
                {

                    //int xpos = 415;
                    //int ypos = 207;
                    //int xpos = 292;
                    int xpos = 220;
                    int ypos = 00;
                    //int k=0;
                    for (int i = 0; i < lstQData.Count; i++)
                    {
                        /*if (i == 4 || i == 8)
                        {
                            ypos = ypos - 360;
                            xpos = 1035;
                        }
                        */
                        foreach (char c in lstQData[i].ServiceCounterID)
                        {
                            string dir;
                            if (i == 0)
                            {
                                dir = "Resources/_" + c + ".bmp";
                            }
                            else
                            {
                                dir = "Resources/" + c + ".bmp";
                            }
                            //string dir = "Resources/" + c + ".bmp";
                            createPicBox(dir, "pBox" + i, xpos, ypos);
                            xpos = xpos + 63;

                        }

                        ypos = ypos + 50;
                        xpos = xpos - 63;


                    }
                }));
                return;
            }
        }
        private void createPicBox(string directory, string name, int xposition, int yposition)
        {
            PictureBox picBox = new System.Windows.Forms.PictureBox();
            picBox.Name = name;

            picBox.Location = new System.Drawing.Point(xposition, yposition);
            picBox.Size = new System.Drawing.Size(40, 50);

            picBox.BackgroundImage = Image.FromFile(directory);
            picBox.BackgroundImageLayout = ImageLayout.Stretch;
            pnlQStat.Controls.Add(picBox);
        }

        private void Form1_Load(object sender, EventArgs e)
        {
            createPlayList();
            //dbListenerThread.Abort(); // this line of code should be placed in onClosing Event.
        }

        private void Form1_FormClosing(object sender, FormClosingEventArgs e)
        {
            dbListenerThread.Abort();
            player.playlistCollection.remove(playlist);
        }

        private void createPlayList()
        {
            playlist = player.playlistCollection.newPlaylist("mpl");
            playlist.appendItem(player.newMedia(@"E:\SONGS\teri-meri-promo-Muskurahat.Com.wmv"));
            playlist.appendItem(player.newMedia(@"E:\MOVZZZ\English\The Kid\THE KID FILM_1_0001.avi"));
            player.currentPlaylist = playlist;
        }

        private void btnPlay_Click(object sender, EventArgs e)
        {
           // player.URL = @"E:\MOVZZZ\English\The Kid\THE KID FILM_1_0001.avi";
            player.Ctlcontrols.play();
        }

        private void btnStop_Click(object sender, EventArgs e)
        {
            player.Ctlcontrols.stop();
        }


    }

}

我的目标是按顺序播放循环播放的声音文件,同时并行播放视频。

4

1 回答 1

2

您不应将SoundPlayer其用于此目的;SoundPlayer是一个轻量级、方便的类,用于在应用程序中播放偶尔的附带声音。如果音频子系统中发生其他事情(如视频播放),它偶尔会跳过声音。这是一个很好的示例,展示了如何使用低级 waveOutOpen API 播放声音

于 2013-04-17T11:45:54.967 回答