软件课程设计个人报告-音乐播放器软件.doc_第1页
软件课程设计个人报告-音乐播放器软件.doc_第2页
软件课程设计个人报告-音乐播放器软件.doc_第3页
软件课程设计个人报告-音乐播放器软件.doc_第4页
软件课程设计个人报告-音乐播放器软件.doc_第5页
已阅读5页,还剩32页未读 继续免费阅读

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

软件课程设计个人报告课 题: 音乐播放器软件班 级:通信工程1202班作 者: 学 号: 指导老师: 课设评价:课设成绩:1、 需求分析1、课题描述描述:基于WINDOWS的音乐播放器软件,实现音乐库的管理和播放功能。 2、软件基本要求有图形界面;提供基本播放功能:播放、暂停、快进、快退、停止;支持播放模式:单曲播放、单曲循环、顺序播放和随机播放;支持播放信息显示:歌曲名、播放时间;支持播放列表管理:歌曲增加、歌曲删除、歌曲播放次序调整。3、拓展要求支持歌词显示和同步播放;支持本地歌曲搜索和管理;均衡器管理:支持不同风格的音乐模式播放;自动记忆播放功能(程序关闭时能记忆当前播放的歌曲,重启后继续播放);提供更良好的操作界面;其他功能。4、 设计目标使用JAVA语言设计开发一个基于JMF的音乐播放器,有基本的图形界面,尽量做到美观,提供基本的播放功能如播放、暂停、快进、快退、停止,能借助拖动进度条来控制播放,支持4种播放模式,即单曲播放、单曲循环、顺序播放和随机播放。支持播放信息显示,将窗口名显示为当前正在播放的歌曲的名称,显示播放时间。支持播放列表的管理,添加歌曲,删除歌曲,删除列表。预期添加功能:能够同步显示歌词,并且能够让用户根据个人喜好来改变歌词显示字体。能够联网搜索下载歌曲及歌词,能够分享自己的歌单给QQ好友。能够依靠麦克风提供歌曲录制保存功能。能够更换播放器皮肤。2、 总体方案设计说明1、 系统框图JAVA音乐播放器歌曲播放、控制模块图形模块歌词模块播放列表模块2、 软件各模块说明歌曲播放控制模块:歌曲的播放、暂停、下一曲、上一曲等功能。图形模块:主界面,进度条、音量条、各控制按钮,图片背景,皮肤变换。歌词模块:歌词显示,歌词同步,歌词字体设置。播放列表模块:添加歌曲、删除歌曲、删除列表,将播放列表生成TXT文件存储。 其中图形模块中各个按钮调用了播放控制模块所写的函数,播放歌曲时播放模块根据播放列表模块中选中歌曲的序号来播放,歌词模块根据播放模块中播放的歌曲名称来匹配歌词,通过歌曲播放的时间参数来实现歌词同步。3、 开发平台及工具JDK,JAVA Media Framework(JMF),Eclipse编译器。选择依据:由于Java是一个纯的面向对象的程序设计语言,它继承了 C+语言面向对象技术的核心。Java舍弃了C +语言中容易引起错误的指针(以引用取代)、运算符重载(operator overloading)、多重继承(以接口取代)等特性,增加了垃圾回收器功能用于回收不再被引用的对象所占据的内存空间,使得程序员不用再为内存管理而担忧。所以选用JAVA语言来编写音乐播放器。 JMF实际上是Java的一个类包。JMF 2.1.1技术提供了先进的媒体处理能力,从而扩展了Java平台的功能。这些功能包括:媒体捕获、压缩、流转、回放,以及对各种主要媒体形式和编码的支 持,如M-JPEG、H.263、MP3、RTP/RTSP (实时传送协议和实时流转协议)、Macromedias Flash、IBM的HotMedia和Beatniks的Rich Media Format (RMF)等。JMF 2.1.1还支持广受欢迎的媒体类型,如Quicktime、Microsofts AVI和MPEG-1等。此外,JMF 2.1.1软件中包括了一个开放的媒体架构,可使开发人员灵活采用各种媒体回放、捕获组件,或采用他们自己的定制的内插组件。 Eclipse 是一个开放源代码的、基于Java的可扩展开发平台。就其本身而言,它只是一个框架和一组服务,用于通过插件组件构建开发环境。Eclipse 附带了一个标准的插件集,包括Java开发工具(Java Development Kit,JDK)。3、 详细设计说明邵康:负责播放模块、控制模块、播放列表、歌词字体改变等其他模块的开发,各模块的拼装以及后期测试、优化,小组报告的编写。1、播放列表模块该模块通过在data文件夹创建一个songlist.txt文件来存储添加的歌曲名称,文件路径。下次播放时直接读取songlist.txt文件来获取播放列表。通过addList、deleteList、deleteAll三个参数来添加、删除歌曲。每次添加的歌曲都有一个编号下标,以后的顺序播放和随机播放以及对播放列表的操作都与这个下标有关。列表控制前面在图形界面模块已经添加了3个按钮来控制添加、删除歌曲,并添加了对3个按钮的监听。public void actionPerformed(ActionEvent e) if (e.getSource() = addList) open();if (e.getSource() = deleteList) removeFile(MusicPlayer.playerList.getSelectedIndex(), false);if (e.getSource() = deleteAll) if (JOptionPane.showConfirmDialog(null, 确认要删除所有的歌曲吗?)=0)removeFile(MusicPlayer.playerList.getSelectedIndex(), true);根据监听哪个按钮被单击来执行相应的操作。其中open为定义的打开文件的方法,removeFile为定义的删除文件的方法。打开文件public static File open() JFileChooser fileChooser = new JFileChooser();/ 文件过滤器FileNameExtensionFilter filter = new FileNameExtensionFilter(mp3,MP3, wav, mpg, mpeg, wav, avi, gif, GIF, PNG,png, jpg, JPG);fileChooser.setFileFilter(filter);fileChooser.setFileSelectionMode(JFileChooser.FILES_ONLY);/ 仅限显示文件fileChooser.setMultiSelectionEnabled(true);/ 允许多选int result = fileChooser.showOpenDialog(fileChooser);if (result = JFileChooser.CANCEL_OPTION) return null; else files = fileChooser.getSelectedFiles();addList(files);saveListToFile(files);return files;其中saveListToFile为定义的写播放列表信息到songlist.txt文件的方法。addList为定义的添加文件到播放列表的方法。添加播放列表private static void addList(File file) for (int i = 0; i file.length; i+) mp3.getSongNameList().addElement(1 + mp3.getSongNameList().size() + . + filei.getName();mp3.getSongPathList().addElement(filei);MusicPlayer.playerList.setListData(mp3.getSongNameList();mp3.getSongNameList().trimToSize();mp3.getSongPathList().trimToSize();从文件中读取歌曲名称并编号添加到播放列表中写songlist.txt文件private static void saveListToFile(File files) BufferedWriter bf = null;try bf = new BufferedWriter(new FileWriter(datasonglist.txt, true);for (int i = 0; i files.length; i+) bf.write(filesi + n); 保存的songlist.txt文件如图删除歌曲public void removeFile(int fileIndex, boolean ifAll) if (fileIndex ct) int i = 1;double pt = 0;int of = 0; /of为每一行歌词偏移量if (ls.size() 1) continue; else String cs = ls.removeLast(); /cs为当前播放的歌词pt = 60 * Integer.parseInt(cs.substring(1, 3)+ Integer.parseInt(cs.substring(4, 6)+ Integer.parseInt(cs.substring(7, 9) / 100.0;of = (int) (-(ct - pt) / (nt - pt) * 20); /of控制每行偏移量if (ls.size() 0) g.setColor(Color.GRAY); /播放过的歌词为灰色g.setFont(f);g.drawString(ls.poll().substring(10), 30, 20 * i + of); /播放过的行+i;g.setColor(Color.YELLOW); /当前播放的歌词为黄色g.setFont(f);g.drawString(cs.substring(10), 50, 20 * i + of); /当前播放行g.setColor(Color.GREEN); /下一行歌词为绿色+i;g.drawString(s.substring(10), 10, 20 * i + of); / 下一个未播放的行for (+i; i 8)ls.poll();ls 链表中存歌词行字符串,当取到的当前行时间刚大于播放时间时,立刻取表中最后一行,即刚读到的一行到cs中,并从ls表中移除该行,用removeLast方法实现。然后将ls中所有行用灰色字体显示出来,cs行用黄色字体显示出来。当前行显示过以后再添加到表中(每当表中元素大于8时用poll方法移除最早存入的行),然后显示下一行为绿色,最后用一个for循环来用黑色字体显示以后未播放的几行歌词。这样就实现了当前播放行为黄色,播放过的行为灰色,未播放的行为黑色。of = (int) (-(ct - pt) / (nt - pt) * 20); nt-pt计算本行歌词播放总时间,ct-pt表示本行已经播放的时间,(ct-pt)/(nt-pt)表示本行已经播放的比例,乘以20,用of来存储这个值。g.drawString(s.substring(10), 10, 20 * i + of); 以后每次显示歌词时,都加上了of,of即为歌词行垂直方向上向上的偏移,由于播放时间一直在变化,所以of 的值一直改变,从而实现了歌词向上滚动。 歌词字体设置 private JList fontSizeList;private JList fontStyleList;private JList fontNameList;private JTextField fontSizeText;private JTextField fontStyleText;private JTextField fontNameText;首先用JList定义3个列表,分别为字体大小,字形和字体。用JTextField将当前设置的字体大小,字形和字体显示出来。private void actionForward(ListSelectionEvent arg0) fontNameText.setText(String.valueOf(fontNameList.getSelectedValue();fontSizeText.setText(String.valueOf(fontSizeList.getSelectedValue();fontStyleText.setText(String.valueOf(fontStyleList.getSelectedValue();String name = fontNameText.getText();String size = fontSizeText.getText();String style = fontStyleText.getText();通过fontSizeText.setText处理选择的值。if (!size.equals(null) int intSize = Integer.parseInt(size);if (style.equals(常规)newFont = new Font(name, Font.PLAIN, intSize);if (style.equals(加粗)newFont = new Font(name, Font.BOLD, intSize);if (style.equals(倾斜)newFont = new Font(name, Font.ITALIC, intSize);if (style.equals(加粗_倾斜)newFont = new Font(name, Font.BOLD + Font.ITALIC, intSize);prve_label.setFont(newFont);通过4个if语句判断来设置字体的风格为常规、加粗、倾斜、加粗_倾斜。public DialogFont(Frame frame, String string) super(frame, string, true);setResizable(false);setBounds(100, 100, 386, 375);定义弹出字体设置窗口final JPanel panel = new JPanel();panel.setLayout(null);getContentPane().add(panel, BorderLayout.CENTER);final JLabel label = new JLabel();label.setText(字体:);label.setBounds(10, 11, 35, 20);panel.add(label);fontNameText = new JTextField();fontNameText.setBackground(new Color(255, 255, 255);fontNameText.setEditable(false);fontNameText.setBounds(10, 32, 120, 21);panel.add(fontNameText);设置字体设置的位置final JLabel label_1 = new JLabel();label_1.setText(字形:);label_1.setBounds(151, 11, 35, 20);panel.add(label_1);fontStyleText = new JTextField();fontStyleText.setBackground(new Color(255, 255, 255);fontStyleText.setEditable(false);fontStyleText.setBounds(151, 32, 120, 21);panel.add(fontStyleText);设置字形设置的位置final JLabel label_2 = new JLabel();label_2.setText(大小:);label_2.setBounds(285, 12, 35, 20);panel.add(label_2);fontSizeText = new JTextField();fontSizeText.setBackground(new Color(255, 255, 255);fontSizeText.setEditable(false);fontSizeText.setBounds(285, 32, 73, 21);panel.add(fontSizeText);设置字体大小设置的位置final JLabel label_3 = new JLabel();label_3.setText(预览:);label_3.setBounds(151, 192, 35, 20);panel.add(label_3);设置预览final JButton button = new JButton();button.addActionListener(new ActionListener() public void actionPerformed(ActionEvent arg0) if (g != null)g.setFont(getFont();setVisible(false););button.setText(确定);button.setBounds(154, 296, 100, 25);panel.add(button);final JButton button_1 = new JButton();button_1.addActionListener(new ActionListener() public void actionPerformed(ActionEvent arg0) setVisible(false););button_1.setText(取消);button_1.setBounds(258, 296, 100, 25);panel.add(button_1);添加“确定”“取消”两个按钮prve_label = new JLabel();prve_label.setHorizontalAlignment(SwingConstants.CENTER);prve_label.setOpaque(true);prve_label.setBackground(new Color(255, 255, 255);prve_label.setBorder(new EtchedBorder(EtchedBorder.LOWERED);prve_label.setText(字体样式 WordPad);prve_label.setBounds(151, 218, 207, 63);panel.add(prve_label);将当前设置的字体生成预览字体样式 WordPad显示出来final JScrollPane scrollPane = new JScrollPane();scrollPane.setBounds(10, 59, 120, 262);panel.add(scrollPane);fontNameList = new JList();fontNameList.addListSelectionListener(new ListSelectionListener() public void valueChanged(ListSelectionEvent arg0) actionForward(arg0););fontNameList.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);fontNameList.setModel(new DefaultComboBoxModel(getFontList();scrollPane.setViewportView(fontNameList);fontStyleList = new JList();fontStyleList.addListSelectionListener(new ListSelectionListener() public void valueChanged(ListSelectionEvent arg0) actionForward(arg0););fontStyleList.setBounds(151, 59, 120, 124);fontStyleList.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);fontStyleList.setModel(new DefaultComboBoxModel(getFontStyleList();panel.add(fontStyleList);final JScrollPane scrollPane_1 = new JScrollPane();scrollPane_1.setBounds(285, 59, 73, 124);panel.add(scrollPane_1);fontSizeList = new JList();fontSizeList.addListSelectionListener(new ListSelectionListener() public void valueChanged(ListSelectionEvent arg0) actionForward(arg0););fontSizeList.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);fontSizeList.setModel(new DefaultComboBoxModel(getFontSizeList();scrollPane_1.setViewportView(fontSizeList);/以上语句为显示3个列表,并添加监听,监听鼠标左键选定的是三个列表中的哪一项。最后定义三个列表中的元素。private String getFontStyleList() return new String 常规, 倾斜, 加粗, 加粗_倾斜 ;字形private String getFontSizeList() return new String 6, 8, 9, 10, 11, 12, 14, 16,18, 20, 22, 24, 26, 28, 36, 48, 72 ;大小private String getFontList() java.awt.GraphicsEnvironment eq = java.awt.GraphicsEnvironment.getLocalGraphicsEnvironment(); /获取系统当前字体String fontNames = eq.getAvailableFontFamilyNames();return fontNames;3、 歌曲播放、控制模块本模块主要实现歌曲的播放、暂停、停止、下一曲、上一曲、播放进度控制、播放模式的控制、音量调节、皮肤变换等功能。主要函数:public Vector getSongPathList() return songPathList;获取歌曲路径列表public void setTriggerStart(boolean state) triggerStart = state; 设置歌曲状态为播放public boolean getTriggerStart() return triggerStart;查询歌曲状态是否为播放public void setCurrentIndex(int index) currentIndex = index;设置当前播放的序号public int getCurrentIndex() return currentIndex;获取当前播放的序号public void setPlayer(Player player) this.player = player;设置对象public Player getPlayer() return player;获取对象public void setIsStarted(boolean state) isStarted = state; 设置歌曲状态为开始播放public boolean getIsStarted() return isStarted;查询歌曲状态是否为开始播放public void setIsPaused(boolean state) isPaused = state;设置歌曲状态为暂停public boolean getIsPaused() return isPaused;查询歌曲状态是否为暂停public void setPauseTime(Time time) pauseTime = time;设置暂停时间public Time getPauseTime() return pauseTime;获取暂停时间public Vector getSongNameList() return songNameList;定义歌曲名称列表播放共分3个状态,播放中,暂停,停止。暂停时记录当前播放时间,下次点击播放时读取记录的时间来继续播放。而停止以后下次播放时从0开始继续播放。播放进度的调整调用了JMF以后可以直接拖动进度条来控制,不需编写代码控制。播放播放时直接调用Manager.createRealizedPlayer(currentSong.toURL()来创建一个Player对象,使用了JMF。从播放列表中取currentIndex的值进一步获取当前要播放歌曲的名称、文件路径,然后打开文件并播放。String song = songlist.get(mp3.getCurrentIndex().toString();File currentSong = new File(song); player.start();/开始播放当判断到是在暂停状态点击播放时,读取暂停时间,从暂停时间继续播放。用if语句实现if (mp3.getIsPaused() player.setMediaTime(mp3.getPauseTime(); 如果是在停止状态点击播放,则从头开始播放。暂停暂停时获取当前播放时间,记录为暂停时间。然后将Isstarted变量设置为false,IsPaused设置为true,TriggerStart设置为false。将CurrentIndex设置为mp3.getCurrentIndex() - 1,以便下次播放时继续播放本歌曲。并且将暂停按钮替换为播放按钮。if (mp3.getIsStarted() Player player = mp3.getPlayer();mp3.setPauseTime(player.getMediaTime();player.stop();player.deallocate();player.close();mp3.setIsStarted(false);mp3.setIsPaused(true);mp3.setTriggerStart(false);mp3.setCurrentIndex(mp3.getCurrentIndex() - 1); PlayerToolBar.start.setIcon(new ImageIcon(resourceDir+ start0.jpg);停止停止时不需要记录时间,直接将Isstarted变量设置为false,TriggerStart设置为false。将CurrentIndex设置为mp3.getCurrentIndex() - 1,以便下次播放时继续播放本歌曲。if (mp3.getIsStarted() Player player = mp3.getPlayer();player.stop();player.deallocate();player.close();mp3.setIsStarted(false);mp3.setTriggerStart(false);mp3.setCurrentIndex(mp3.getCurrentIndex() - 1);需注意的是,无论是暂停还是停止时,都要先判断是否处于播放状态,否则可能会出BUG。上、下一曲当切换下一曲时,先判断当前的状态,若为暂停状态,则需要先设置为停止,并将PauseTime清零,否则下一首歌曲会继续从上首歌曲暂停处播放。若为播放状态,则先停止。然后判断当前歌曲是否为播放列表最后一首,若不为最后一首歌,则将CurrentIndex加1后继续播放。if (mp3.getIsStarted() this.mp3Stop();if (mp3.getIsPaused() mp3.setPauseTime(null);mp3.setIsPaused(false);int currentIndex = mp3.getCurrentIndex();if (currentIndex (mp3.getSongPathList().size() - 1) mp3.setCurrentIndex(currentIndex + 1);this.mp3Start(); 上一曲的切换与此类此,不同的是将currentIndex -1.判断时判断的是当前歌曲是否为播放列表第一首。 皮肤变换通过传递设置的numSkin的值,编写5个case,以此来设置各按钮,插入的图片以及字体颜色。switch (numSkin) case 0: snext=next0.jpg; sprevious=previous0.jpg; sstart=start0.jpg; sstop=stop00.jpg; sstop1=stop10.jpg; sstop2=stop20.jpg; saddp=addp0.jpg; sdelete=delete0.jpg; sdeletel=deletel0.jpg; ssound=sound.png; MusicPlayer.playerList.setForeground(Color.BLUE); backgroundImage = new ImageIcon(PlayerToolBar.resourceDir+ sss0.jpg).getImage(); break;在此只列举一个case,其他case与此类似。播放模式通过对currentIndex的设置来控制下一首歌曲的播放。若为单曲循环,则每次播放完一首歌曲以后将currentIndex设置为当前的currentIndex。若为列表播放,则播放完一首歌曲以后将currentIndex加一,当播放到列表最后一首歌时判断到currentIndex+1=songlistLength,停止播放。若为列表循环,则播放到列表最后一首歌时将currentIndex设置为零。若为随机播放,则通过random函数生成一个取值范围为0到songlistLength的随机数,将currentIndex设置为该随机数。switch (PlayerMenuBar.list) case 1:mp3.setCurrentIndex(currentIndex);break;case 2:mp3.setCurrentIndex(currentIndex + 1);break;case 3:if (currentIndex + 1 = songlistLength)mp3.setCurrentIndex(0);elsemp3.setCurrentIndex(currentIndex + 1);break;case 4:int i=(int)(Math.random()*songlistLength);mp3.setCurrentIndex(i);菜单栏设置菜单栏分5项:文件、播放控制、播放模式、皮肤变换、关于。其中“文件”中分“打开”和“退出”,分别实现打开文件添加歌曲功能和退出功能。“播放控制”中分“开始”“暂停”“上一曲”“下一曲”。“播放模式”中4个选项控制歌曲播放模式的选择。“皮肤变换”中5个选项控制播放器的皮肤选择。“关于”中的帮助选项控制打开帮助窗口,其中存放了帮助信息。定义5个主选项 private JMenu file=new JMenu(文件);private JMenu player=new JMenu(播放控制);priva

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

评论

0/150

提交评论