<?php

/**
 * @file
 * Defines a field formatter and theming for the wavesurfer plugin.
 */
/**
 * Implements hook_libraries_info().
 *
 * Declare the wavesurfer library and files.
 */
function wavesurfer_libraries_info(){
  $libraries['wavesurfer'] = array(
    'name' => 'Wavesurfer',
    'vendor url' => 'http://waveform.fm',
    'download url' => 'http://www.wavesurfer.fm',
    'version callback' => 'wavesurfer_bypass_version_control',
    'files' => array(
      'js' => array(
        'dist/wavesurfer.min.js',
        'dist/plugin/wavesurfer.regions.min.js',
        'dist/plugin/wavesurfer.spectrogram.min.js'
      )
    )
  );
  return $libraries;
}

/**
 * Callback function to bypass the library version check.
 */
function wavesurfer_bypass_version_control(){
  return TRUE;
}

/**
 * Implements hook_field_formatter_info().
 */
function wavesurfer_field_formatter_info(){
  $info = array(
    'wavesurfer_waveform' => array(
      'label' => 'Wavesurfer waveform player',
      'field types' => array(
        'file'
      ),
      'description' => t('Displays a waveform player generated from an audio file'),
      'settings' => array(
        'wavecolor' => '000000',
        'progress_colour' => '000000'
      )
    )
  );
  return $info;
}

/**
 * Implements hook_field_formatter_view().
 */
function wavesurfer_field_formatter_view($entity_type, $entity, $field, $instance, $langcode, $items, $display){
  $elements = array();
  $settings = $display['settings'];
  switch($display['type']){
    case 'wavesurfer_waveform':
      foreach($items as $delta => $item){
        $elements[] = array(
          '#markup' => theme('wavesurfer_waveform', array(
            'file' => (object)$item,
            'settings' => $settings
          ))
        );
      }
      break;
  }
  return $elements;
}

/**
 * Implements hook_field_formatter_settings_summary().
 *
 * Displays the field formatter settings for the Wavesurfer field.
 */
function wavesurfer_field_formatter_settings_summary($field, $instance, $view_mode){
  $display = $instance['display'][$view_mode];
  $settings = $display['settings'];
  $summary = array();
  switch($display['type']){
    case 'wavesurfer_waveform':
      $summary[] = t('Wave Colour: %wavecolor', array(
        '%wavecolor' => $settings['wavecolor']
      ));
      $summary[] = t('Progress Colour: %progress_colour', array(
        '%progress_colour' => $settings['progress_colour']
      ));
      break;
  }
  return implode('<br />', $summary);
}

/**
 * Implements hook_field_formatter_settings_form().
 *
 * Adds colour settings to the field settings for Wavesurfer field.
 */
function wavesurfer_field_formatter_settings_form($field, $instance, $view_mode, $form, &$form_state){
  $display = $instance['display'][$view_mode];
  $settings = $display['settings'];
  $element = array();
  switch($display['type']){
    case 'wavesurfer_waveform':
      $element['wavecolor'] = array(
        '#type' => 'jquery_colorpicker',
        '#title' => t('Background Waveform Colour'),
        '#required' => TRUE,
        '#default_value' => $settings['wavecolor']
      );
      $element['progress_colour'] = array(
        '#type' => 'jquery_colorpicker',
        '#title' => t('Progress Waveform Colour'),
        '#required' => TRUE,
        '#default_value' => $settings['progress_colour']
      );
      break;
  }
  return $element;
}

/**
 * Implements hook_theme().
 */
function wavesurfer_theme(){
  $theme = array();
  $theme['wavesurfer_waveform'] = array(
    'variables' => array(
      'file' => NULL
    ),
    'settings' => array()
  );
  return $theme;
}

/**
 * Theme function for the Wavesurfer Audio field.
 */
function theme_wavesurfer_waveform($variables){
  $file = $variables['file'];
  // Exit if no valid file.
  if(!$file){return '';}
  // Check mime type supported.
  $allowed_mimetypes = array(
    'audio/mpeg',
    'audio/ogg',
    'audio/x-wav'
  );
  if(!in_array($file->filemime, $allowed_mimetypes)){return '<div class="messages error"><p>Mime type not supported by Wavesurfer</p></div>';}
  $settings = $variables['settings'];
  // Extract settings variables; $wavecolor, $progress_colour.
  //^^ Why two spellings of colo(u)r?
  extract($settings);
  // Set up JavaScript call.
  $container_id = 'waveform_' . $file->fid;
  $wavesurfer_id = 'wavesurfer_' . $file->fid;
  libraries_load('wavesurfer');
  $audiofile = file_create_url($file->uri);
  $parts = explode("/", current_path());
  if ($parts[0] == "node") {
    $cloud_url = "https://ams3.digitaloceanspaces.com/bioacoustica-analysis/flac/".$parts[1].".flac";
  }
  if (false  === file_get_contents($cloud_url,0,null,0,1)) {
    $cloud_url = NULL;
  } else {
    $audiofile = $cloud_url;
  }
  $onready = array();
  foreach(module_implements('wavesurfer_onready') as $module){
    $onready[] = module_invoke($module, 'wavesurfer_onready');
  }
  $pixels_second = 25;
  drupal_add_js(array(
    'wavesurfer' => array(
      'onready' => $onready
    )
  ), 'setting');
  $data_array = array(
    'container_id' => $container_id,
    'wavesurfer_id' => $wavesurfer_id,
    'fileid' => $file->fid,
    'audiofile' => $audiofile,
    'wavecolor' => $wavecolor,
    'progresscolor' => $progress_colour,
    'pixelrate' => $pixels_second
  );
  drupal_add_js(drupal_get_path('module', 'wavesurfer') . '/js/wavesurfer_module.js', 'file');
  drupal_add_css(drupal_get_path('module', 'wavesurfer') . '/css/wavesurfer.css', 'file');
  // Container html.
  $output = '<span id="wavesurfer_position"></span>
  		     <div id="' . $container_id . '" class="wavesurfer-container" ';
  foreach($data_array as $key => $value){
    $output .= " data-$key='$value'";
  }
  $output .= '>
               <div id="progress-bar-' . $file->fid . '" class="progress progress-striped active" style="display: none;">
           <div class="progress-bar-' . $file->fid . ' progress-bar progress-bar-info" style="width: 100%;">
         </div>
               </div>
</div>
<div class="spectrogram-container" id="spectrogram-'.$file->fid.'"></div>';
  // Controls HTML
  // @TODO Could probably add more in here and make it optional in settings.
  $output .= '<div class="controls">
                <button id="play_' . $file->fid . '" class="btn btn-primary" onclick="wavesurfer_playsurfer(' . $file->fid . ')">
                    <i class="play"></i>
                    Play
                    /
                    <i class="pause"></i>
                    Pause
                </button>
              </div>';
  $output .= '<div class="wavesurfer-file-download">';
  $output .= l('Download', $audiofile);
  $output .= '</div>';
  return $output;
}

function wavesurfer_duration_wav($file){
  $fp = fopen($file, 'r');
  if(fread($fp, 4) == "RIFF"){
    fseek($fp, 20);
    $rawheader = fread($fp, 16);
    $header = unpack('vtype/vchannels/Vsamplerate/Vbytespersec/valignment/vbits', $rawheader);
    $pos = ftell($fp);
    while(fread($fp, 4) != "data" && !feof($fp)){
      $pos++;
      fseek($fp, $pos);
    }
    $rawheader = fread($fp, 4);
    $data = unpack('Vdatasize', $rawheader);
    $sec = $data['datasize'] / $header['bytespersec'];
    return $sec;
  }
}


