月舞芸袖音画论坛

 找回密码
 中文注册
搜索
热搜: 音画 签名 教程
查看: 609|回复: 19

[播放器制作] MP3播放器制作[连载07]

[复制链接]
  • TA的每日心情
    奋斗
    2019-3-24 10:02
  • 签到天数: 486 天

    [LV.9]以坛为家II

    5864

    金币

    44

    主题

    23

    精华

    贵宾

    积分
    7957

    活跃会员优秀会员最佳新人五一劳动勋章月舞居民贵宾

    UID
    1586
    发表于 2017-4-23 19:34 | 显示全部楼层 |阅读模式
    本帖最后由 疯子 于 2017-4-24 00:09 编辑

    这节继续声音播放控制制作:
    前面我们把声音播放进度控制代码写在帧上,这节我们把这些代码也写成一个声音播放进度控制类(PlayControl);
    首先新建一个AS3.0类PlayControl保存到文件夹 com.ui 里;
    打开库,选择元件control-属性-高级-ActionSpcript 链接-勾选为ActionSpcript 导出-类(c)com.ui.PlayControl-确定,元件control就受PlayControl控制了


    PlayControl类:
    1. package com.ui
    2. {
    3.         /*导入声音类*/
    4.         import com.media.SoundDispatcher;
    5.        
    6.         import flash.display.MovieClip;
    7.         import flash.events.Event;
    8.         import flash.events.MouseEvent;
    9.         import flash.utils.setInterval;
    10.         import flash.utils.clearInterval;
    11.         import flash.geom.Rectangle;

    12.         public class PlayControl extends MovieClip
    13.         {
    14.                 /*创建一个新对象player控制SoundDispatcher*/
    15.                 private var player:SoundDispatcher;

    16.                 /*定义声音文件地址*/
    17.                 private var url:String = "http://www.lxeblog.cn/UploadFiles/2017-4/81831561037.mp3";


    18.                 /*声音播放的当前位置*/
    19.                 private var seekpoint:Number = 0;

    20.                 /*用来记录声音加载进度*/
    21.                 private var percent:Number = 0;

    22.                 /*记录声音的总长度*/
    23.                 private var duration:Number = 0;

    24.                 /*记录播放进度*/
    25.                 private var playheadPercentage:Number = 0;

    26.                 /*播放滑块 按下、拖动 拖动记时器*/
    27.                 private var scrubbInterval:Number;

    28.                 /*拖动布尔值*/
    29.                 private var scrubbing:Boolean;


    30.                 /*构造函数*/
    31.                 public function PlayControl()
    32.                 {
    33.                         /*初始方法*/
    34.                         init();
    35.                 }

    36.                 private function init():void
    37.                 {
    38.                         /*把player对象NEW出来*/
    39.                         player=new SoundDispatcher();

    40.                         /*执行SoundDispatcher类中的play()方法 播放声音 */
    41.                         player.play(url);

    42.                         /*播放、暂停按钮的显示状态*/
    43.                         status = false;

    44.                         /*把player对象传给音量控制类里的_player对象*/
    45.                         volControl.player = player;

    46.                         /*把player对象传给声音平衡控制类里的_player对象*/
    47.                         panControl.player = player;

    48.                         /*播放进度滑块鼠标事件呈现手型*/
    49.                         seekBar.buttonMode = true;

    50.                         /*播放进度条对象不接收鼠标事件,意思是鼠标才能越过进度条点击进度条下面层的加载进度条*/
    51.                         playheadBar.mouseEnabled = false;

    52.                         /*================声音加载过程=================*/
    53.                         /*侦听声音加载进度*/
    54.                         player.addEventListener("progress",progressHandler);
    55.                         /*侦听声音加载错误*/
    56.                         player.addEventListener("ioerror",ioErrorHandler);
    57.                         /*侦听声音加载完成*/
    58.                         player.addEventListener(Event.COMPLETE,completeHandler);

    59.                         /*==============鼠标侦听事件=================*/

    60.                         /*暂停按钮侦听*/
    61.                         pauseButton.addEventListener(MouseEvent.CLICK, pauseButtonClickHandler);
    62.                         /*停止按钮侦听*/
    63.                         stopButton.addEventListener(MouseEvent.CLICK,stopButtonClickHandler);
    64.                         /*播放按钮侦听*/
    65.                         playButton.addEventListener(MouseEvent.CLICK,playButtonClickHandler);

    66.                         /*播放滑块按下*/
    67.                         seekBar.addEventListener(MouseEvent.MOUSE_DOWN,seekBarDownHandler);
    68.                         /*加载进度条按下*/
    69.                         loadBar.addEventListener(MouseEvent.MOUSE_DOWN,loadBarDownHandler);


    70.                         /**********帧频事件(重复执行)*************/
    71.                         addEventListener(Event.ENTER_FRAME,enterFrameHandler);

    72.                 }


    73.                 /*加载进度事件,声音没加载完成前一直在执行*/
    74.                 function progressHandler(event:Event):void
    75.                 {
    76.                         /*加载进度的宽度 Infinity-不限制*/
    77.                         if (player.loadPercentage > 0 && player.loadPercentage != Infinity)
    78.                         {
    79.                                 loadBar.width = seekControlBar.width * player.loadPercentage;
    80.                         }
    81.                         else
    82.                         {
    83.                                 loadBar.width = 1;
    84.                         }
    85.                         //bytesTxt.text=millToBytes(player.bytesLoaded)+"M - "+millToBytes(player.bytesTotal)+"M"+"  KBPS:"+Math.round(player.bytesTotal/player.length * 1000 * 8 / 1024 / 32)*32

    86.                         bytesTxt.text = millToBytes(player.bytesLoaded) + "M - " + millToBytes(player.bytesTotal) + "M" + "   KBPS:" + Math.round(player.bytesTotal * 8 / player.duration);

    87.                         //trace("总字节:"+player.bytesTotal+"  总长度"+player.length)
    88.                 }

    89.                 /*声音加载错误事件*/
    90.                 function ioErrorHandler(event:Event):void
    91.                 {
    92.                         trace("加载错误");
    93.                 }

    94.                 /*加载完成事件*/
    95.                 function completeHandler(event:Event):void
    96.                 {
    97.                         trace("加载完成");
    98.                 }

    99.                 /*================ 声音播放过程 =================*/

    100.                 function enterFrameHandler(event:Event):void
    101.                 {
    102.                         /*侦听声音播放完成*/
    103.                         player.addEventListener(Event.SOUND_COMPLETE,soundCompleteHandler);

    104.                         if (scrubbing)
    105.                         {
    106.                                 /*鼠标在播放滑块(加载进度条)按下时
    107.                                 播放显示的时间是拖动的位置seekpoint,总时间不变*/
    108.                                 playtime.txt.htmlText = "<font FACE=\"Verdana\" SIZE=\"10\">" + millToTime(seekpoint) + "|" + millToTime(player.duration) + "</font>";
    109.                         }
    110.                         else
    111.                         {
    112.                                 if (player.position > 0 && player.duration > 0)
    113.                                 {
    114.                                         /* 没有鼠标按下动作的时候,播放滑块的X坐标
    115.                                         播放滑块的X坐标=播放进度*播放条宽度 */
    116.                                         seekBar.x = player.position / player.duration * seekControlBar.width;
    117.                                 }
    118.                                 else
    119.                                 {
    120.                                         /*如果当前播放头位置 和 总长度为0*/
    121.                                         seekBar.x = seekControlBar.x;
    122.                                         seekpoint = 0;
    123.                                 }
    124.                                 /*没有鼠标动作的时候,播放显示的时间是声音当前播放头的位置player.position,总时间不变*/
    125.                                 playtime.txt.htmlText = "<font FACE=\"Verdana\" SIZE=\"10\">" + millToTime(player.position) + "|" + millToTime(player.duration) + "</font>";

    126.                         }
    127.                         /*计算playtime的X坐标 = 播放滑块X坐标与播放条宽度的比值 * playtime要移动的总长度(距离)*/
    128.                         playtime.x=int(seekBar.x/seekControlBar.width*(seekControlBar.width-72));

    129.                         /*播放进度条的宽度*/
    130.                         playheadBar.width = seekBar.x;
    131.                 }

    132.                 /*播放完成事件*/
    133.                 function soundCompleteHandler(event:Event):void
    134.                 {
    135.                         trace("播放完成");
    136.                         /*清除声音*/
    137.                         player.close();
    138.                         /*声音从新播放*/
    139.                         player.play(url);
    140.                 }



    141.                 /*========== 播放控制、拖动进度事件 =============*/
    142.                 /*滑块按下事件*/
    143.                 function seekBarDownHandler(event:MouseEvent=null):void
    144.                 {
    145.                         if (player.playing)
    146.                         {
    147.                                 /*拖动的布尔值这时候为true(真)*/
    148.                                 scrubbing = true;

    149.                                 /*SoundDispatcher类里的_scrubbing为true(真)*/
    150.                                 player.scrubbing = true;

    151.                                 /* setInterval 开启拖动记时器,没关闭前一直在执行;
    152.                                 setInterval(执行的事件,执行的间隔时间);*/
    153.                                 scrubbInterval = setInterval(scrubbUpdate,30);

    154.                                 /*拖动范围 Rectangle(左边,上边,右边,下边)
    155.                                 滑块的拖动范围*/
    156.                                 var rectangle:Rectangle = new Rectangle(seekControlBar.x,seekBar.y,Math.round(loadBar.width));

    157.                                 /*开始拖动 startDrag */
    158.                                 seekBar.startDrag(false,rectangle);

    159.                                 /*侦听鼠标弹起事件*/
    160.                                 stage.addEventListener(MouseEvent.MOUSE_UP,seekBarUpHandler);
    161.                         }
    162.                 }

    163.                 /*鼠标弹起事件*/
    164.                 function seekBarUpHandler(event:MouseEvent=null):void
    165.                 {
    166.                         /*移除鼠标弹起侦听*/
    167.                         stage.removeEventListener(MouseEvent.MOUSE_UP,seekBarUpHandler);
    168.                         /*滑块停止拖动*/
    169.                         seekBar.stopDrag();
    170.                         /*关闭拖动记时器*/
    171.                         clearInterval(scrubbInterval);
    172.                         /*声音开始播放*/
    173.                         player.resume();
    174.                         /*把seekpoint的值传给SoundDispatcher类里seek()方法*/
    175.                         player.seek(seekpoint);

    176.                         /*按钮的显示状态*/
    177.                         status = false;
    178.                         /*拖动的布尔值这时候为false(假)*/
    179.                         scrubbing = false;
    180.                         /*SoundDispatcher类里的_scrubbing为false(假)*/
    181.                         player.scrubbing = false;
    182.                 }

    183.                 function scrubbUpdate():void
    184.                 {
    185.                         /*滑块按下、拖动的时候记录下seekpoint的值,用来改变声音播放的位置*/
    186.                         seekpoint=(seekBar.x-seekControlBar.x)/seekControlBar.width*player.duration;
    187.                 }

    188.                 /*加载进度条按下事件*/
    189.                 function loadBarDownHandler(event:MouseEvent):void
    190.                 {
    191.                         /*加载进度条按下的时候,滑块X坐标等于鼠标的X坐标;
    192.                         SoundDispatcher类里的声音播放事件;
    193.                         执行滑块按下、拖动事件seekBarDownHandler*/
    194.                         seekBar.x = mouseX;
    195.                         player.resume();
    196.                         seekBarDownHandler();
    197.                 }



    198.                 /*暂停事件*/
    199.                 function pauseButtonClickHandler(event:MouseEvent):void
    200.                 {
    201.                         /*SoundDispatcher类里的暂停事件*/
    202.                         player.pause();

    203.                         /*播放、暂停按钮的显示状态*/
    204.                         status = true;
    205.                 }

    206.                 /*停止事件*/
    207.                 function stopButtonClickHandler(event:MouseEvent):void
    208.                 {
    209.                         /*SoundDispatcher类里的声音停止事件*/
    210.                         player.stop();

    211.                         /*播放、暂停按钮的显示状态*/
    212.                         status = true;
    213.                 }

    214.                 /*播放事件*/
    215.                 function playButtonClickHandler(event:MouseEvent):void
    216.                 {
    217.                         /*SoundDispatcher类里的声音播放事件*/
    218.                         player.resume();
    219.                         /*播放、暂停按钮的显示状态*/
    220.                         status = false;
    221.                 }

    222.                 /*播放、暂停按钮的显示状态*/
    223.                 function set status(value:Boolean):void
    224.                 {
    225.                         if (value)
    226.                         {
    227.                                 pauseButton.visible = false;
    228.                                 playButton.visible = true;
    229.                         }
    230.                         else
    231.                         {
    232.                                 pauseButton.visible = true;
    233.                                 playButton.visible = false;
    234.                         }
    235.                 }

    236.                 /*返回一个字符串方法,显示时间格式
    237.                 mill传入的参数,比如播放时间、总时间等*/
    238.                 function millToTime(mill:Number):String
    239.                 {
    240.                         /*声音的播放时间、总长度也毫秒为单位,所以要除以1000
    241.                         这里就是一个分秒的换算方法*/
    242.                         mill = mill / 1000;
    243.                         var minutes = int(mill / 60);
    244.                         var seconds = int(mill % 60);
    245.                         minutes < 10 ? minutes = "0" + minutes:null;
    246.                         seconds < 10 ? seconds = "0" + seconds:null;

    247.                         /*minutes < 10 ? minutes = "0" + minutes:null
    248.                         是
    249.                         if(minutes < 10){
    250.                         minutes="0"+minutes
    251.                         }else{
    252.                         minutes=minutes
    253.                         }
    254.                         这样的简单写法
    255.                         ?: 定向运算符*/
    256.                         return minutes+ ":" + seconds;
    257.                 }

    258.                 function millToBytes(mill:Number):String
    259.                 {
    260.                         /*和上面的millToTime方法一样,用来计算声音文件的大小
    261.                         1MB=1024KB
    262.                         1KB=1024字节*/
    263.                         mill = mill / 1024 / 1024 * 100;
    264.                         var minutes = int(mill /100);
    265.                         var seconds = int(mill %100);
    266.                         minutes < 10 ? minutes = "0" + minutes:null;
    267.                         seconds < 10 ? seconds = "0" + seconds:null;
    268.                         return minutes+ "." + seconds;
    269.                 }








    270.         }

    271. }
    复制代码



    原文件下载
    游客,如果您要查看本帖隐藏内容请回复

    评分

    参与人数 7金币 +108 收起 理由
    AMOS很费解 + 12 精美作品!
    青树 + 20 月舞芸袖因你更精彩!
    走过岁月 + 12 月舞芸袖因你更精彩!
    豪情云天 + 12 很给力!
    自由飞翔 + 20 月舞芸袖因你更精彩!
    花仙子 + 12 精美作品!
    月舞精灵 + 20 优秀作品!

    查看全部评分

    回复

    使用道具 举报

  • TA的每日心情
    奋斗
    2019-3-23 21:42
  • 签到天数: 519 天

    [LV.9]以坛为家II

    4万

    金币

    202

    主题

    3

    精华

    管理员

    Rank: 14Rank: 14Rank: 14Rank: 14

    积分
    60991

    活跃会员优秀会员最佳新人活动参与勋章2016年灌水天才音乐达人月舞1周年庆典月舞居民论坛管理组

    UID
    1483
    发表于 2017-4-23 19:56 | 显示全部楼层
    问候疯帅 继续学习 支持佳作 感谢分享 精彩制作
    gift5904.gif
    回复 支持 反对

    使用道具 举报

  • TA的每日心情
    奋斗
    2019-3-23 21:42
  • 签到天数: 519 天

    [LV.9]以坛为家II

    4万

    金币

    202

    主题

    3

    精华

    管理员

    Rank: 14Rank: 14Rank: 14Rank: 14

    积分
    60991

    活跃会员优秀会员最佳新人活动参与勋章2016年灌水天才音乐达人月舞1周年庆典月舞居民论坛管理组

    UID
    1483
    发表于 2017-4-23 19:57 | 显示全部楼层
    祝疯帅 身体健康 事事顺心 周末快乐!
    回复 支持 反对

    使用道具 举报

  • TA的每日心情
    开心
    2017-5-22 21:59
  • 签到天数: 106 天

    [LV.6]常住居民II

    8340

    金币

    94

    主题

    1

    精华

    贵宾

    积分
    9458

    活跃会员优秀会员最佳新人五一劳动勋章月舞居民贵宾

    UID
    1226
    发表于 2017-4-23 20:04 | 显示全部楼层
    继续学习,慢慢体会
    回复 支持 反对

    使用道具 举报

  • TA的每日心情
    开心
    2017-5-22 21:59
  • 签到天数: 106 天

    [LV.6]常住居民II

    8340

    金币

    94

    主题

    1

    精华

    贵宾

    积分
    9458

    活跃会员优秀会员最佳新人五一劳动勋章月舞居民贵宾

    UID
    1226
    发表于 2017-4-23 20:05 | 显示全部楼层
    这些类得好好的记住
    回复 支持 反对

    使用道具 举报

  • TA的每日心情
    奋斗
    2019-3-25 00:00
  • 签到天数: 965 天

    [LV.10]以坛为家III

    9万

    金币

    493

    主题

    36

    精华

    管理员

    Rank: 14Rank: 14Rank: 14Rank: 14

    积分
    129681

    月舞探花月舞1周年庆典鸡祥如意月舞功臣月舞居民论坛管理组月舞创始人

    UID
    947
    发表于 2017-4-23 20:18 | 显示全部楼层
    刚才疯帅分享好教程,真的辛苦了,非常感谢!
    回复 支持 反对

    使用道具 举报

  • TA的每日心情
    奋斗
    2019-3-25 00:00
  • 签到天数: 965 天

    [LV.10]以坛为家III

    9万

    金币

    493

    主题

    36

    精华

    管理员

    Rank: 14Rank: 14Rank: 14Rank: 14

    积分
    129681

    月舞探花月舞1周年庆典鸡祥如意月舞功臣月舞居民论坛管理组月舞创始人

    UID
    947
    发表于 2017-4-23 20:20 | 显示全部楼层
    继续学习,大家记得交作业哦
    回复 支持 反对

    使用道具 举报

  • TA的每日心情
    奋斗
    2018-1-11 19:17
  • 签到天数: 321 天

    [LV.8]以坛为家I

    3万

    金币

    306

    主题

    62

    精华

    贵宾

    积分
    38274

    活跃会员优秀会员最佳新人音乐达人五一劳动勋章月舞居民贵宾

    UID
    977
    发表于 2017-4-23 20:21 | 显示全部楼层
    问候疯帅 继续学习 支持佳作 感谢分享 精彩制作
    回复 支持 反对

    使用道具 举报

  • TA的每日心情
    奋斗
    2018-1-11 19:17
  • 签到天数: 321 天

    [LV.8]以坛为家I

    3万

    金币

    306

    主题

    62

    精华

    贵宾

    积分
    38274

    活跃会员优秀会员最佳新人音乐达人五一劳动勋章月舞居民贵宾

    UID
    977
    发表于 2017-4-23 20:22 | 显示全部楼层
    谢谢疯帅分享好教程,辛苦了,非常感谢!
    回复 支持 反对

    使用道具 举报

  • TA的每日心情
    开心
    2018-2-7 23:36
  • 签到天数: 333 天

    [LV.8]以坛为家I

    6万

    金币

    443

    主题

    61

    精华

    贵宾

    积分
    64797

    活跃会员优秀会员月舞同图活动勋章最佳新人月舞1周年庆典鸡祥如意五一劳动勋章月舞居民贵宾

    UID
    1384
    发表于 2017-4-23 22:01 | 显示全部楼层
    继续学习
    回复

    使用道具 举报

  • TA的每日心情
    开心
    2019-2-7 22:45
  • 签到天数: 253 天

    [LV.8]以坛为家I

    3万

    金币

    133

    主题

    6

    精华

    贵宾

    积分
    38436

    活跃会员优秀会员最佳新人月舞1周年庆典五一劳动勋章月舞居民贵宾

    UID
    1593
    发表于 2017-4-23 22:08 | 显示全部楼层
    哇,,精华在这里,,我看着都是天书一样的符号,,这个教学意义重大,学习了,非常感谢您的分享,点赞!!
    回复 支持 反对

    使用道具 举报

  • TA的每日心情
    奋斗
    2019-3-25 10:39
  • 签到天数: 917 天

    [LV.10]以坛为家III

    7万

    金币

    211

    主题

    19

    精华

    管理员

    Rank: 14Rank: 14Rank: 14Rank: 14

    积分
    102712

    活跃会员月舞2周年庆典优秀会员月舞同图活动勋章最佳新人月舞1周年庆典鸡祥如意五一劳动勋章月舞居民论坛管理组

    UID
    966
    发表于 2017-4-23 22:15 | 显示全部楼层
    不愧为精华!大大的赞!
    回复 支持 反对

    使用道具 举报

  • TA的每日心情
    奋斗
    2019-3-25 10:39
  • 签到天数: 917 天

    [LV.10]以坛为家III

    7万

    金币

    211

    主题

    19

    精华

    管理员

    Rank: 14Rank: 14Rank: 14Rank: 14

    积分
    102712

    活跃会员月舞2周年庆典优秀会员月舞同图活动勋章最佳新人月舞1周年庆典鸡祥如意五一劳动勋章月舞居民论坛管理组

    UID
    966
    发表于 2017-4-23 22:16 | 显示全部楼层
    问好疯帅老师,分享辛苦了
    回复 支持 反对

    使用道具 举报

  • TA的每日心情
    奋斗
    2017-10-4 21:21
  • 签到天数: 298 天

    [LV.8]以坛为家I

    7811

    金币

    76

    主题

    5

    精华

    贵宾

    积分
    10608

    活跃会员漂亮MM优秀会员最佳新人音乐达人五一劳动勋章月舞居民贵宾

    UID
    1201
    发表于 2017-4-23 23:28 | 显示全部楼层
    问好,欣賞老师的精彩分享!
    回复 支持 反对

    使用道具 举报

  • TA的每日心情
    奋斗
    2018-12-8 19:52
  • 签到天数: 38 天

    [LV.5]常住居民I

    2183

    金币

    23

    主题

    0

    精华

    高级会员

    Rank: 4

    积分
    2352

    五一劳动勋章月舞居民

    UID
    1385
    发表于 2017-4-27 12:16 | 显示全部楼层
    又继续教程了,继续保存学习资料
    回复 支持 反对

    使用道具 举报

  • TA的每日心情
    奋斗
    2017-6-16 11:22
  • 签到天数: 6 天

    [LV.2]偶尔看看I

    88

    金币

    1

    主题

    0

    精华

    新手上路

    Rank: 1

    积分
    120

    五一劳动勋章月舞居民

    UID
    1604
    发表于 2017-4-29 20:18 | 显示全部楼层
    不知道能不能学会
    回复 支持 反对

    使用道具 举报

  • TA的每日心情
    开心
    2017-6-10 22:50
  • 签到天数: 30 天

    [LV.5]常住居民I

    357

    金币

    1

    主题

    0

    精华

    贵宾

    积分
    594

    五一劳动勋章月舞居民贵宾

    UID
    1594
    发表于 2017-4-29 21:27 | 显示全部楼层
    学习来了,问好老师~~~
    回复 支持 反对

    使用道具 举报

  • TA的每日心情
    奋斗
    2019-3-24 22:52
  • 签到天数: 253 天

    [LV.8]以坛为家I

    7811

    金币

    93

    主题

    8

    精华

    贵宾

    积分
    8789

    月舞居民贵宾

    UID
    1755
    发表于 2018-3-13 20:38 | 显示全部楼层
    学习
    回复

    使用道具 举报

  • TA的每日心情
    开心
    2019-1-15 20:00
  • 签到天数: 26 天

    [LV.4]偶尔看看III

    278

    金币

    4

    主题

    0

    精华

    贵宾

    积分
    398

    活跃会员月舞2周年庆典优秀会员月舞居民贵宾

    QQ
    UID
    1443
    发表于 2018-11-15 22:37 | 显示全部楼层
    谢谢老师分享好教程
    心很脆弱,你得学会哄它,不管碰到多大的困难,告诉你的心“ALL is Well”
    回复 支持 反对

    使用道具 举报

  • TA的每日心情
    开心
    2019-1-16 08:51
  • 签到天数: 8 天

    [LV.3]偶尔看看II

    133

    金币

    1

    主题

    0

    精华

    新手上路

    Rank: 1

    积分
    173
    UID
    1964
    发表于 2019-1-12 23:25 | 显示全部楼层

    继续学习,慢慢体会
    回复 支持 反对

    使用道具 举报

    您需要登录后才可以回帖 登录 | 中文注册

    本版积分规则

    Archiver|手机版|小黑屋|月舞芸袖音画论坛 My title page contents

    GMT+8, 2019-3-25 15:27 , Processed in 0.489520 second(s), 34 queries .

    Powered by Discuz! X3.2

    © 2001-2013 Comsenz Inc.

    快速回复 返回顶部 返回列表