2016-05-13 88 views
1

我想建立我自己的音频播放器(因为没有插件可用)。我用滑块来显示玩家的进度。当移动滑块时,我可以允许用户转到特定的位置,但我无法将其与正在播放的录像同步。定时器在Xamarin.forms

形式

int i = 1; 
Button btnPlay = new Button 
{ 
    Text = "Play/Pause", 
    Command = new Command(() => 
        { 
         DependencyService.Get<IAudio>().PlayMp3File(); 
         TimeSpan tmspan = new TimeSpan(00, 00, 00); 
         label.Text = String.Format("{0:hh\\:mm\\:ss}", tmspan.Add(TimeSpan.FromMilliseconds(i))); 
         i++; 
         return true; 
        }) 
}; 
Button btnStop = new Button { Text = "Stop" }; 
TimeSpan timeSpan = DependencyService.Get<IAudio>().GetInfo(); 
Label lblDuration = new Label { Text = String.Format("{0:hh\\:mm\\:ss}", timeSpan) }; 

var slider = new Slider { 
    Minimum = 0, 
    Maximum = timeSpan.TotalHours, 
}; 
var label = new Label { 
    Text = "Slider value is 0", 
    FontSize = 25, 
    HorizontalOptions = LayoutOptions.Start, 
}; 
slider.ValueChanged += 
    (sender, e) => 
    { 
     label.Text = String.Format("Slider value is {0:hh\\:mm\\:ss}", TimeSpan.FromMilliseconds(e.NewValue)); 
     DependencyService.Get<IAudio>().SeekTo(Convert.ToInt32(e.NewValue)); 

    }; 
MainPage = new ContentPage 
{ 
    Content = new StackLayout { 
     Children = { 
      btnPlay, 
      btnStop, 
      slider, 
      lblDuration, 
      label 
     } 
    }, 
    Padding = new Thickness (10, Device.OnPlatform (20, 0, 0), 10, 5) 
}; 

服务

using System; 
using System.Collections.Generic; 
using System.Linq; 
using System.Text; 

using Android.App; 
using Android.Content; 
using Android.OS; 
using Android.Runtime; 
using Android.Views; 
using Android.Widget; 
using AudioTest.Droid; 
using Xamarin.Forms; 
using Android.Media; 
using System.Threading.Tasks; 

[assembly: Dependency(typeof(AudioService))] 

namespace AudioTest.Droid 
{ 
    public class AudioService : IAudio 
    { 
     public AudioService() { } 

     MediaPlayer player = null; 

     public async Task StartPlayerAsync() 
     { 
      try 
      { 
       if (player == null) 
       { 
        player = new MediaPlayer(); 
        player = MediaPlayer.Create(global::Android.App.Application.Context, Resource.Raw.test); 
        player.Start(); 
       } 
       else 
       { 
        if (player.IsPlaying == true) 
        { 
         player.Pause(); 
        } 
        else 
        { 
         player.Start(); 
        } 
       } 
      } 
      catch (Exception ex) 
      { 
       Console.Out.WriteLine(ex.StackTrace); 
      } 
     } 

     public void StopPlayer() 
     { 
      if ((player != null)) 
      { 
       if (player.IsPlaying) 
       { 
        player.Stop(); 
       } 
       player.Release(); 
       player = null; 
      } 
     } 

     public async Task PlayMp3File() 
     { 
      await StartPlayerAsync(); 
     } 

     public void Stop() 
     { 
      this.StopPlayer(); 
     } 

     public async Task SeekTo(int s) 
     { 
      await seekTo(s); 
     } 

     public double CurrentPosition() 
     { 
      if ((player != null)) 
      { 
       return player.CurrentPosition; 
      } 
      else 
      { return 0; } 
     } 

     private async Task seekTo(int mseconds) 
     { 
      if (player == null) 
      { 
       player = new MediaPlayer(); 
       player = MediaPlayer.Create(global::Android.App.Application.Context, Resource.Raw.test); 

      } 

      player.SeekTo(mseconds); 
      player.Start(); 
     } 



     public TimeSpan GetInfo() 
     { 
      int arr; 
      if (player == null) 
      { 
       player = new MediaPlayer(); 
       player = MediaPlayer.Create(global::Android.App.Application.Context, Resource.Raw.test); 

      } 
      arr = player.Duration; 

      return TimeSpan.FromMilliseconds(arr);//TimeSpan.FromMilliseconds(arr).TotalMinutes; 
     } 
    } 
} 

任何人有如何去它的主意?

编辑 截图画面 enter image description here

上播放定时器应该开始,也是我的滑块值应该增加的。在暂停计时器和滑块应暂停和停止时,应停止。

回答

2

看看Device班的Xamarin.Forms,特别是StartTimer的方法。

鉴于这种情况,你可以设置你的计时器:

Device.StartTimer(new TimeSpan(0, 0, 0, 0, 300), TimerElapsed); 

private bool TimerElapsed() 
{ 
    Device.BeginInvokeOnMainThread(() => 
    { 
     //put here your code which updates the view 
    }); 
    //return true to keep timer reccuring 
    //return false to stop timer 
} 

这将触发大约每300毫秒(取决于设备功能)

关于你的代码,你可以用类似的东西入手:

1.增加以下到您的播放命令:

Device.StartTimer(new TimeSpan(0, 0, 0, 0, 1000), CheckPositionAndUpdateSlider); 

2.Add CheckPositionAndUpdateSlider方法:

private bool CheckPositionAndUpdateSlider() 
{ 
    var position = DependencyService.Get<IAudio>().GetCurrentPosition(); 
    Device.BeginInvokeOnMainThread(() => 
    { 
     slider.Value = position; 
    }); 
    return true; 
} 
+0

有没有办法暂停或停止计时器? – Arti

+0

只需从'TimerElapsed'方法返回'false'即可停止它。当你想暂停计时器时,你必须自己写这个逻辑。我的意思是停止计时器,然后再次启动计时器,当你想恢复它。 –

+0

我无法让滑块根据录制进度移动。任何想法呢? – Arti