此项目需求是针对.wav格式音频进行操作,转换成相应的.mp3格式的音频文件,对音频进行切割,最后以需求的形式输出,此篇会回顾运用到的一些知识点。

1.MDI子窗口的建立:

首先一个窗体能够创建多个MDI窗体,应当将IsMDIContainer属性设为true;以下为效果图:

控制窗体切换的是一个DotNetBar.TabStrip控件,style属性为Office2007Document,TabLayOutType:FixedWithNavigationBox

创建窗体的代码如下:

01 /// <summary> 
02  /// 创建MDI子窗体类 
03  /// </summary> 
04  classCreateMDIWindow 
05  
06       /// <summary> 
07      /// 当前程序的主窗体对象 
08      /// </summary> 
09      public staticForm MainForm { getset; } 
10       
11      /// <summary> 
12      /// 创建子窗口 
13      /// </summary> 
14      ///
15 <typeparam name="T">     窗口类型
16 </typeparam>      
17      public static void CreateChildWindow
18 <t>     () where T : Form, new() 
19      // where 子句还可以包括构造函数约束。 可以使用 new 运算符创建类型参数的实例;但类型参数为此必须受构造函数约束  
20      // new() 的约束。 new() 约束可以让编译器知道:提供的任何类型参数都必须具有可访问的无参数(或默认)构造函数。            
21      
22          T form = null
23     
24          var childForms = MainForm.MdiChildren; 
25          //遍历窗体 
26          foreach (Form f inchildForms) 
27          
28              if (f isT) 
29              
30                  form = f asT; 
31                  break
32              
33          
34          //如果没有,则创建 
35          if(form == null
36          
37              //新建窗体 
38              form = newT(); 
39              //设定窗体的图标 
40              form.Icon = System.Drawing.Icon.FromHandle(Properties.Resources.MainIcon.GetHicon()); 
41              //设定窗体的主图标 
42              form.MdiParent = MainForm; 
43              //设定窗体的边框类型 
44              form.FormBorderStyle = FormBorderStyle.FixedToolWindow; 
45          
46          //窗口如何显示 
47          form.WindowState = FormWindowState.Maximized; 
48          form.Show(); 
49      
50  
51 </t>

前台点击按钮调用代码:CreateMDIWindow.CreateChildWindow ();  <>里为窗体的名称。

2.序列化与反序列化:

当一个系统你有默认的工作目录,默认的文件保存路径,且这些数据时唯一的,你希望每次打开软件都会显示这些数据,也可以更新这些数据,可以使用序列化与反序列化。

我们以项目存储根目录和选择项目为例:

代码如下:

01 [Serializable] 
02 public  classUserSetting 
03
04     /// <summary> 
05     /// 序列化存储路径 
06     /// </summary> 
07     private string FilePath{ get returnPath.Combine(Environment.CurrentDirectory, "User.data"); } } 
08    
09     /// <summary> 
10     /// 音频资源存储目录 
11     /// </summary> 
12     public  stringAudioResourceFolder { getset; } 
13    
14     /// <summary> 
15     /// 项目名称 
16     /// </summary> 
17     public stringSolution { getset; } 
18    
19     /// <summary> 
20     /// 构造函数,创建序列化存储文件 
21     /// </summary> 
22     publicUserSetting() 
23     
24         if(!File.Exists(FilePath)) 
25         
26             FileStream fs = File.Create(FilePath); 
27             fs.Close();//不关闭文件流,首次创建该文件后不能被使用买现成会被占用 
28         }       
29     
30    
31     /// <summary> 
32     /// 通过反序列化方法,获得保存的数据 
33     /// </summary>       
34     publicUserSetting ReadUserSetting()        
35     
36         using (FileStream fs = newFileStream(FilePath, FileMode.Open,FileAccess.Read)) 
37         
38             objectob = null
39             if(fs.Length > 0) 
40             
41                 SoapFormatter sf = newSoapFormatter(); 
42                 ob = sf.Deserialize(fs);                   
43             
44             return ob asUserSetting; 
45         
46     
47    
48     /// <summary> 
49     /// 通过序列化方式,保存数据 
50     /// </summary>       
51     public void SaveUserSetting(objectobj) 
52     
53         using (FileStream fs = newFileStream(FilePath, FileMode.OpenOrCreate, FileAccess.Write)) 
54         
55             SoapFormatter sf = newSoapFormatter(); 
56             sf.Serialize(fs,obj); 
57         
58     
59        
60 }

3.Datagridview动态生成:

根据设置的楼层生成相应楼层带button按钮的datagridview,并且每层按钮为每层选定选择音乐,代码如下:

01 /// <summary> 
02 /// 绑定楼层音乐属性 
03 /// </summary> 
04 private void BindData(int elevatorLow,intnumber) 
05
06     try 
07     
08         DataTable list = newDataTable(); 
09         list.Columns.Clear(); 
10         list.Columns.Add(newDataColumn("name"typeof(string))); 
11         list.Columns.Add(newDataColumn("musicPath"typeof(string)));              
12         for (inti =0; i < number; i++) 
13         
14             //不包括楼层0层 
15             if(elevatorLow != 0) 
16             
17                 list.Rows.Add(list.NewRow()); 
18                 list.Rows[i][0] = elevatorLow; 
19             
20             else{ i--; } 
21             elevatorLow++; 
22         
23         dataGridViewX1.DataSource = list; 
24     
25     catch(Exception ex) 
26     { MessageBox.Show(ex.ToString()); } 
27 }

选择音乐按钮事件:

01 private void dataGridViewX1_CellContentClick(objectsender, DataGridViewCellEventArgs e) 
02
03     try 
04     {          
05         //点击选择按钮触发的事件 
06         if(e.RowIndex >= 0) 
07         
08             DataGridViewColumn column = dataGridViewX1.Columns[e.ColumnIndex]; 
09             if (column isDataGridViewButtonColumn) 
10             
11                 OpenFileDialog openMusic = newOpenFileDialog(); 
12                 openMusic.AddExtension = true
13                 openMusic.Multiselect = true
14                 openMusic.Filter = "MP3文件(*.mp3)|*mp3";                    
15                 if(openMusic.ShowDialog() == DialogResult.OK) 
16                 
17                     dataGridViewX1.Rows[e.RowIndex].Cells[2].Value = Path.GetFileName(openMusic.FileName);                        
18                 
19             
20         
21     
22     catch(Exception ex) 
23     { MessageBox.Show(ex.ToString()); } 
24 }

4.获得音乐文件属性:

使用Shellclass获得文件属性可以参考  点击打开链接

代码如下:

01 /// <summary> 
02 /// 获得音乐长度 
03 /// </summary> 
04 /// <param name="filePath">文件的完整路径 
05 public static string[] GetMP3Time(stringfilePath) 
06
07     stringdirName = Path.GetDirectoryName(filePath); 
08     stringSongName = Path.GetFileName(filePath);//获得歌曲名称            
09     ShellClass sh = newShellClass(); 
10     Folder dir = sh.NameSpace(dirName); 
11     FolderItem item = dir.ParseName(SongName); 
12     stringSongTime = dir.GetDetailsOf(item, 27);//27为获得歌曲持续时间 ,28为获得音乐速率,1为获得音乐文件大小     
13     string[] time = Regex.Split(SongTime, ":"); 
14     returntime; 
15 }

5.音频操作:

音频的操作用的fmpeg.exe ,下载地址

fmpeg放在bin目录下,代码如下:

01 /// <summary> 
02 /// 转换函数 
03 /// </summary> 
04 /// <param name="exe">ffmpeg程序 
05 /// <param name="arg">执行参数      
06 public static void ExcuteProcess(string exe, stringarg) 
07
08     using (var p = newProcess()) 
09     {              
10             p.StartInfo.FileName = exe; 
11             p.StartInfo.Arguments = arg; 
12             p.StartInfo.UseShellExecute = false;    //输出信息重定向 
13             p.StartInfo.CreateNoWindow = true
14             p.StartInfo.RedirectStandardError = true
15             p.StartInfo.RedirectStandardOutput = true
16             p.Start();                    //启动线程 
17             p.BeginOutputReadLine(); 
18             p.BeginErrorReadLine(); 
19             p.WaitForExit();//等待进程结束                                       
20     
21 }

音频转换的代码如下:

01 private void btnConvert_Click(objectsender, EventArgs e) 
02
03     //转换MP3 
04     if(txtMp3Music.Text != ""
05     
06         string fromMusic = Statics.Setting.AudioResourceFolder + "\\"+ Statics.Setting.Solution+"\\" + cobFolders.Text + "\\" + txtMusic.Text;//转换音乐路径 
07         string toMusic = Statics.Setting.AudioResourceFolder + "\\"+ Statics.Setting.Solution+"\\" + cobFolders.Text + "\\"+ txtMp3Music.Text;//转换后音乐路径 
08         intbitrate = Convert.ToInt32(cobBitRate.Text) * 1000;//恒定码率 
09         stringHz = cobHz.Text;//采样频率 
10    
11         try 
12         
13             MP3Convertion.ExcuteProcess("ffmpeg.exe""-y -ab " + bitrate + " -ar "+ Hz + " -i \"" + fromMusic + "\" \"" + toMusic + "\""); 
14             if(cbRetain.Checked == false
15             
16                 File.Delete(fromMusic); 
17                 BindList(); 
18             
19             else 
20             
21                 foreach (ListViewItem lt inlistMusics.Items) 
22                 
23                     if(lt.Text == txtMusic.Text) 
24                     
25                         listMusics.Items.Remove(lt); 
26                     
27                 
28             
29    
30             //转换完成 
31             MessageBox.Show("转换完成"); 
32             txtMusic.Text = ""
33             txtMp3Music.Text = ""
34         
35         catch(Exception ex) 
36         { MessageBox.Show(ex.ToString()); } 
37     
38     else 
39     
40         MessageBox.Show("请选择你要转换的音乐");  
41     
42 }

音频切割的代码如下:

01 private void btnCut_Click(objectsender, EventArgs e) 
02
03     SaveFileDialog saveMusic = newSaveFileDialog(); 
04     saveMusic.Title = "选择音乐文件存放的位置"
05     saveMusic.DefaultExt = ".mp3"
06     saveMusic.InitialDirectory = Statics.Setting.AudioResourceFolder +"\\" + Statics.Setting.Solution+"\\" + cobFolders.Text; 
07     string fromPath = Statics.Setting.AudioResourceFolder + "\\"+ Statics.Setting.Solution +"\\"+ cobFolders.Text + "\\"+ txtMusic.Text;//要切割音乐的物理路径 
08     stringstartTime = string.Format("0:{0}:{1}", txtBeginM.Text, txtBeginS.Text).Trim();//歌曲起始时间 
09     intduration = (Convert.ToInt32(this.txtEndM.Text) * 60 + Convert.ToInt32(this.txtEndS.Text)) - (Convert.ToInt32(this.txtBeginM.Text) * 60 + Convert.ToInt32(this.txtBeginS.Text)); 
10     stringendTime = string.Format("0:{0}:{1}", duration / 60, duration % 60);//endTime是持续的时间,不是歌曲结束的时间 
11     if(saveMusic.ShowDialog() == DialogResult.OK) 
12     
13         stringsavePath = saveMusic.FileName;//切割后音乐保存的物理路径 
14         try 
15         
16             MP3Convertion.ExcuteProcess("ffmpeg.exe""-y -i \"" + fromPath + "\" -ss "+ startTime + " -t " + endTime + " -acodec copy \""+ savePath+"\"");//-acodec copy表示歌曲的码率和采样频率均与前者相同 
17             MessageBox.Show("已切割完成"); 
18         
19         catch(Exception ex) 
20         
21             MessageBox.Show(ex.ToString()); 
22         }                
23     
24 }

切割音频操作系统的知识点就总结道这了,就是fmpeg的应用。

C# 音频操作系统项目总结的更多相关文章

  1. EasyDarwin开源音频解码项目EasyAudioDecoder:EasyPlayer Android音频解码库(第二部分,封装解码器接口)

    上一节我们讲了如何基于ffmpeg-Android工程编译安卓上的支持音频的ffmpeg静态库:http://blog.csdn.net/xiejiashu/article/details/52524 ...

  2. EasyDarwin开源音频解码项目EasyAudioDecoder:基于ffmpeg的安卓音频(AAC、G726)解码库(第一部分,ffmpeg-android的编译)

    ffmpeg是一套开源的,完整的流媒体解决方案.基于它可以很轻松构建一些强大的应用程序.对于流媒体这个行业,ffmpeg就像圣经一样的存在.为了表达敬意,在这里把ffmpeg官网的一段简介搬过来,ff ...

  3. Ucan23操作系统项目地址

    期间耽误了近半年的时间.在昨天最终完毕了Ucan23OS, 项目托管在GitHub上,地址为: https://github.com/howardking/UCAN23OS 以下为操作系统的执行截图 ...

  4. 操作系统项目:向Linux内核添加一个系统调用

    内容: 向Linux增加一个系统调用 撰写一个应用测试程序调用该系统调用 使用ptrace或类似的工具对该测试程序进行跟踪调 环境: 1.vmware workstation 15.0.0 2.ubu ...

  5. 我发起了一个 操作系统 GUI 和 Tcp / IP 包 的 开源项目 DeviceOS

    操作系统 如果 不需要 处理 复杂多样 的 硬件 兼容性, 其实 并不算 大项目, 可以算 毕业设计 . 但是, GUI 和 Tcp / IP  这两个 部分 的 实现逻辑 很多 很复杂,  这  2 ...

  6. 物联网操作系统HelloX V1.79发布公告

    经过HelloX开发团队近半年的努力,在HelloX V1.78版本基础上,增加许多功能特性,并对V1.78版本的一些特性进行了进一步优化之后,正式形成HelloX V1.79测试版本.经相对充分的测 ...

  7. Cookiecutter: 更好的项目模板工具:(1)简介及可用资源汇总

    原文档地址:https://cookiecutter.readthedocs.io/en/latest/ 本系列只介绍cookiecutter的基础使用,而且会删除与功能使用无关的部分.深度使用及了解 ...

  8. EasyDarwin开源流媒体项目

    本文转自EasyDarwin CSDN官方博客:http://blog.csdn.net/easydarwin EasyDarwin是由国内开源流媒体团队维护和迭代的一整套开源流媒体视频平台框架,从2 ...

  9. [转帖](整理)GNU Hurd项目详解

    (整理)GNU Hurd项目详解 http://www.ha97.com/3188.html 发表于: 开源世界 | 作者: 博客教主 标签: GNU,Hurd,详解,项目 Hurd原本是要成为GNU ...

随机推荐

  1. Python 学习经历分享

    如果说 Java 是亲儿子的话,那么 Python 应该就是干儿子了.看了一下所有关于 Python 的笔记,我发现原来我在 4 月份的时候就已经涉足 Python 了,但是到目前为止才真正算做出了一 ...

  2. List元素为泛型时的注意事项

    最近的项目赶得非常紧,这节奏跟最近的天气一点也不搭调. 编码的过程,遇到一个关于List的小问题. 在调用List.add(E e)的时候范了一个小毛病,很自然地认为list中存储的是 E  对象的另 ...

  3. Error after SQL Server 2012 installation: Login Failure for "SQL Server Integration Services 11.0" SSIS service

    When you install SQL Server 2012 and you try to connect to SSIS services, you cannot due to that the ...

  4. 深入理解ajax系列第六篇

    前面的话 每个HTTP请求和响应都会带有相应的头部信息,其中有的对开发人员有用.XHR对象提供了操作头部信息的方法.本文将详细介绍HTTP的头部信息 默认信息 默认情况下,在发送XHR请求的同时,还会 ...

  5. hdu1242Rescue

     STL容器之优先队列 优先级队列,以前刷题的时候用的比较熟,现在竟然我只能记得它的关键字是priority_queue(太伤了).在一些定义了权重的地方这个数据结构是很有用的. 先回顾队列的定义 ...

  6. android view surfaceView GLSurfaceView

    韩梦飞沙  韩亚飞  313134555@qq.com  yue31313  han_meng_fei_sha 表面视图 SurfaceView 是 视图 的子类, 刷新界面速度比 视图 块, 因为它 ...

  7. [BZOJ5303][HAOI2018]反色游戏(Tarjan)

    暴力做法是列异或方程组后高斯消元,答案为2^自由元个数,可以得60分.但这个算法已经到此为止了. 从图论的角度考虑这个问题,当原图是一棵树时,可以从叶子开始唯一确定每条边的选择情况,所以答案为1. 于 ...

  8. 洛谷.4238.[模板]多项式求逆(NTT)

    题目链接 设多项式\(f(x)\)在模\(x^n\)下的逆元为\(g(x)\) \[f(x)g(x)\equiv 1\ (mod\ x^n)\] \[f(x)g(x)-1\equiv 0\ (mod\ ...

  9. 聊聊用CSS3来玩立方体

    声明:本文为原创文章,如需转载,请注明来源WAxes,谢谢! 虽然现在很多浏览器都还不支持css3的3D转换,不过估计也已经有很多人都有玩css3的3D了......所以我这篇也就相当于水一下了,哈哈 ...

  10. python开发_tkinter_小球完全弹性碰撞游戏_源码下载

    完成这个小球的完全弹性碰撞游戏灵感来自于: 下面是我花了一周下班时间所编写的一个小球完全弹性碰撞游戏: 游戏初始化状态: 最下面的游标和修改小球的移动速度 ====================== ...