播放歌曲文本文件时使用堆栈(钢琴应用程序) [英] Usage of stack while playing a song text file(Piano application)

查看:80
本文介绍了播放歌曲文本文件时使用堆栈(钢琴应用程序)的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

Hello Friends,



我正在开发一个钢琴应用程序,我正在阅读一个歌曲文本文件。在我的应用程序中,我试图实现一个功能在哪里我正在使用一个循环堆栈进行阅读,在堆栈前进通过歌曲文本文件时同时播放音符和显示歌曲文本文件的音符。



现在我在一个goto语句中使用了2个堆栈,一个堆栈用于显示注释,15个注释之后我启用了一个计数器,它启动另一个负责播放音符的堆栈。我在歌曲显示之间保持15个音符的偏移。歌曲播放,以便用户可以看到即将发行的音符。



但由于使用了两个叠加,歌曲播放没有顺畅,歌曲之间的间隔不规律地播放,任何人都可以纠正我或指导我另一种解决方案。

Hello Friends,

I am developing a piano application in which i am reading a song text file.In my app i am trying to achieve a functionality where in i am using a stack with in a loop for reading, playing notes On and displaying the notes of song text file simultaneously as the stack advances through the song text file.

Now i have used 2 stacks within a single goto statement, one stack perform for displaying notes,after 15 notes i enable a counter which starts another stack which is responsible for playing notes on.I am keeping an offset of 15 notes between song display and song play so that user can see the upcoming notes.

But due to usage of two stack there is no smoothness of song play,the intervals between songs are irregularly playing,can anybody correct me or guide me another solution.

while ((stopSong==true )&&readFile.ReadString(strLine))
{
//there is a for loop for starting the file index
for (int n=readStartIndex, m=readStartIndex; n < size && m < size; n++, m++)
     {
//there is a while loop for inserting the notes until the dot(.) and end of file 'T'is reached.
//inside while loop notes is pushed
//-------------------------------------------------------------------------
while((s[n]!='.')&&s[n]!='T'&&stopSong==true)
    {
     notesChar.push_back(s[n]);
     c++;
     n++;
    }
//-------------------------------------------------------------------------
//notes are popped according to identification of

//d-notes ON for right hand press
//u-notes OFF for right hand release
//e-notes ON for left hand press
//v-notes OFF for left hand release
//s- for timer delay between notes
//-------------------------------------------------------------------------
      if(s[n]=='.')
       {
           if((s[n-1]=='d')&&stopSong==true) 
	  {
	   c--;
	   notesChar.pop_back();
	   std::string NotesStr(notesChar.begin(),notesChar.end());
	   int Noteid=atoi(NotesStr.c_str());
	  
	    
	    m_Keys.findchords(Noteid);
	    StaticColor=RGB(250,250,100);  		   
            m_Keys1.dischords=m_Keys1.dischords+m_Keys.dischords;
	     
	    displaychords(m_Keys1.dischords);//<-------------displaying chords
	    m_Keys.dischords.Empty();
          }

//Similalry for 'e'.
//---------------------------------------------------------------------------------
        else if(s[n-1]=='u'&&stopSong==true)
	 {
	  c--;
	  notesChar.pop_back();
	  std::string NotesStr(notesChar.begin(),notesChar.end());
	  int Noteid=atoi(NotesStr.c_str());
	  m_Keys.NoteOff(Noteid);
	  ucount++;
	  }
//Similarly for 'v'.
//----------------------------------------------------------------------------------
else if(s[n-1]=='s'&&stopSong==true)
	  {
           
            c--;
	    notesChar.pop_back();
	    std::string NotesStr(notesChar.begin(),notesChar.end());
	    int Noteid=atoi(NotesStr.c_str());  
	    XSleep(Noteid);
	  }
//------------------------------------------------------------------------------------
//for poping out remaining notes.

          for(int p=0;p<c&&stopSong==true;p++)
	  {
	    notesChar.pop_back();
	  }
	  c=0;
	  n++;
//------------------------------------------------------------------------------------        
//Counter is getting incremented, at 'u' after 15 counts.
       if(ucount>15)
       {
/there is a while loop for inserting the notes until the dot(.) and end of file 'T'is reached.
//inside while loop notes is pushed

         while((q[m]!='.')&&q[m]!='T'&&stopSong==true)
	 {
	  //MessageBox("while loop");
	  QueueChar.push_back(q[m]);	 
          m++;
	  h++;
         }
//--------------------------------------------------------------------------------------
//notes are popped according to identification of

//d-notes ON for right hand press
//u-notes OFF for right hand release
//e-notes ON for left hand press
//v-notes OFF for left hand release
//s- for timer delay between notes
         if(q[m]=='.')
	 {
	  if((q[m-1]=='d')&&stopSong==true)
	  {
	   h--;
	   QueueChar.pop_back();
	   std::string NotesStr1(QueueChar.begin(),QueueChar.end());
	   int Noteid=atoi(NotesStr1.c_str());
	   m_Keys.NoteOn(Noteid,RGB(0,250,0));//<---------------------Playing note on
	   m_Keys.dischords.Empty();
	 }

//Similarly for 'e'.
//----------------------------------------------------------------------
	  
	else if((q[m-1]=='u')&&stopSong==true)
	 {
           h--;
	   QueueChar.pop_back();
	   std::string NotesStr1(QueueChar.begin(),QueueChar.end());
	   int Noteid=atoi(NotesStr1.c_str());
           m_Keys.NoteOff(Noteid);//<-------------------------------Playing notes off
	 }
//Similarly for 'v'.
//----------------------------------------------------------------------
	 
        else if((q[m-1]=='s')&&stopSong==true)
	{
          h--;
	  QueueChar.pop_back();
	  std::string NotesStr1(QueueChar.begin(),QueueChar.end());
	  int Noteid=atoi(NotesStr1.c_str());
	  XSleep(Noteid);
        }
//-----------------------------------------------------------------------
//for poping out remaining notes
	 
	for(int p=0; p < m && stopSong==true; p++)							      
         {
	  QueueChar.pop_back();
         }
         h=0;
         m++;
       } 
      goto L1;
     }
    else if(s[n]=='T')
     {
        break;
      }
   }
  if(closed==false)
	{
		readFile.Close();

		closed=true;
		m_Recording.EnableWindow(true);
		m_PlayRecord.EnableWindow(true);
		stopSong=false;
	         
	}
}
and song notes are like this-
60d.250s.60u.65d.250s.65u.65d.5u.67d.150s.67u.T 

推荐答案

在您的代码中肯定有很多需要改进的地方,我愿意帮助您逐步完成这项工作。但首先要解决你最紧迫的问题:为什么你的笔记回放如此不规则?



从猜测,你的代码如何工作,我会说问题是显示循环中的's'部分。 s命令负责笔记的正确计时。但是,当您只是显示接下来的15个音符时,您绝对不希望等待中间音符,而是尽可能快地进行显示。所以在第一节中:

There are certainly many things to improve in your code and I would be willing to help you step-by-step to do that. But first to your most pressing problem: Why is the playback of your notes so irregular?

From guessing, how your code might work, I would say that the problem is the 's' section in your display loop. The s-commands are responsible for the correct timing of the notes. But when you are just displaying the next 15 notes you definitely do not want wait in-between notes, but do the display as quickly as possible. So in the first s-section:
    else if(s[n-1]=='s'&&stopSong==true)
{

      c--;
  notesChar.pop_back();
  std::string NotesStr(notesChar.begin(),notesChar.end());
  int Noteid=atoi(NotesStr.c_str());
  XSleep(Noteid);
}



您要删除XSleep语句。实际上你也可以删除它上面的两行。



试试并告诉我们,如果这带来了你正在寻找的改进。然后我们开始关注可以对您的代码进行的许多其他改进。


you want to remove the XSleep statement. Actually you could also remove the two lines above it.

Try that and tell us, if that brings the improvement your are looking for. Then we start to attend to the many other improvements that could be made to your code.


为什么不使用队列。播放第一个对象后,它将被删除。以下元素排在最后。
why arent you using a queue for that. After playing the first object it gets removed. And following elements are enqueued at the end.


这篇关于播放歌曲文本文件时使用堆栈(钢琴应用程序)的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆