Reproductor de música en Actionscript 3, usando POO y patrón MVC

Una vez creada la instancia de Playlist, la clase Control muestra la lista en el componente List del reproductor mediante un bucle, como se ve a continuación:

private function mostrarLista():void {
     // Obtener referencia al List del reproductor
     var list:List = _reproductor.getChildByName("listaCanciones") as List;
     // Recorrer la playlist y obtener canción a canción, procesándolas
     // de forma que se puedan añadir a la lista
     var obj:Object;
     var cancion:Cancion;
     for (var i:uint = 0; i < _playlist.lista.length; i++) {
          cancion = _playlist.lista[i];
          obj = {data:cancion.id, label:cancion.artista + " - " + cancion.nombre};
          list.addItem(obj);
     }
     list.selectedIndex = 0;
}

Una vez la lista es visible al usuario, se inicializa la instancia de la clase Reproductor. Llegados a este paso, es hora de echar una ojeada de nuevo a la clase Reproductor, de la cual solo habíamos visto el constructor y los métodos para arrastrarlo. El método inicializar() aplicará un formato personalizado al texto del componente List, y creará el temporizador que llevará el control de la reproducción, así que de momento se crea, pero no se pone en marcha:

// Una vez disponible una playlist, se inicializa con ella el reproductor (su lista de canciones)
public function inicializar(playlist:Playlist):void {
      _list = this.getChildByName("listaCanciones") as List;
      formatear(_list);
      _playlist = playlist;
      _timer = new Timer(10, 0);
      _timer.addEventListener(TimerEvent.TIMER, onTimer);
 }

Ahora veremos los métodos formatear() y onTimer(). El primero es llamado directamente desde inicializar(), mientras que onTimer() se ejecutará cuando se dispare el evento timer del temporizador (cada 10 milisegundos durante una reproducción de música).

private function formatear(lista:List):void {
      var fuente:Font = new CenturyGothicRegular(); // Importar fuente incrustada en biblioteca
      var formatoTexto:TextFormat = new TextFormat();
      formatoTexto.color = 0x666688;
      formatoTexto.letterSpacing = .5;
      formatoTexto.font = fuente.fontName;
      StyleManager.setStyle("textFormat", formatoTexto);
}
private function onTimer(e:TimerEvent):void {
      // Actualizar display de tiempo dependiendo de posición del canal de audio
      var timer_txt:TextField = this.getChildByName("time_txt") as TextField;
      timer_txt.text = displayTime(_channel.position);
      _barraTiempo.actualizar(_channel.position, _sonido.length /_tiempocargado);
}

private function displayTime(pos:Number):String {
      var horas, minutos, segundos:uint;
      var output:String;
      var totalSec:uint = pos / 1000;
      var resto:uint;
      horas = Math.floor(totalSec / (60*60));
      resto = totalSec % (60*60);
      minutos = Math.floor(resto / 60);
      resto = resto % 60;
      segundos = Math.floor(resto);
      output = ((horas > 0) ? String(horas) + ":" : "") +
               ((minutos > 9) ? String(minutos) : "0" + String(minutos)) + ":" +
               ((segundos > 9) ? String(segundos) : "0" + String(segundos));
      return output;
}

Como se puede observar, formatear() crea una instancia de la clase Font a partir de la fuente importada en la biblioteca. Seguidamente crea un objeto TextFormat con varias propiedades de formato de texto, incluyendo la fuente anterior, y a continuación asigna ese formato como estilo global de componentes, usando el StyleManager.

El detector del temporizador onTimer(), cada vez que se ejecuta aplica, al display de tiempo, que es un campo de texto dinámico llamado time_txt, la cadena obtenida a partir de la hora, minuto y segundo de reproducción. Esto lo hace gracias a otro método llamado displayTime(). Finalmente llama al método actualizar() de la instancia de BarraTiempo que ya hemos visto anteriormente. A este método se le pasa la posición actual de reproducción, y el tiempo total actual dividido por una fracción o ratio llamado _tiempoCargado, de manera que, ya en el método actualizar() de BarraTiempo y tal y como hemos visto anteriormente en la descripción de esta clase, calcula un nuevo ratio para posicionar el puntero o cabezal de reproducción. La propiedad _tiempoCargado, como ya se verá más adelante, se trata de una división entre los bytes cargados de una canción, y los bytes totales. Dicha propiedad se calcula en el método datosRecibidos() cada vez que se reciben datos durante el proceso de carga de la canción. Este método ya lo veremos después, pero se hace necesario explicar este paso aquí. El resultado obtenido mediante la división (bytes cargados / bytes totales) podemos aplicarlo a su vez como divisor del valor de _sonido.length durante la carga, de modo que aplicará una estimación de la duración total de la canción. Una vez finalizada la carga la canción, dicha división será igual a 1 (bytes cargados == bytes totales) y ya no afectará al resultado de la duración total, puesto que ya no será necesaria la estimación.

Leave a Reply

Your email address will not be published. Required fields are marked *

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>