it-swarm.com.de

PHP Funktion, um MP3-Dauer zu erhalten

Gibt es eine PHP Funktion, die mir die MP3-Dauer geben wird? Ich habe mir die ID 3-Funktion angesehen, aber ich sehe dort für die Dauer nichts und abgesehen davon ist ID3 eine Art Tag, das nicht in allen MP3-Dateien vorhanden ist.

25
ram

Dies sollte für Sie funktionieren, beachten Sie die getduration-Funktion: http://www.zedwood.com/article/127/php-calculate-duration-of-mp3

29
Richard Askew

Installiere getid3, aber wenn du nur Dauer brauchst, kannst du alle außer diesen Modulen löschen:

  • module.audio.mp3.php
  • module.tag.id3v1.php
  • module.tag.apetag.php
  • module.tag.id3v2.php

Zugriff auf die Dauer mit Code wie folgt:

$getID3 = new getID3;
$ThisFileInfo = $getID3->analyze($pathName);
$len= @$ThisFileInfo['playtime_string']; // playtime in minutes:seconds, formatted string

Erhalten Sie es bei Sourceforge

25
TecBrat

Sie können die Dauer eines MP3- oder vieler anderer Audio-/Videodateien mithilfe von ffmpeg abrufen.

  1. Installieren Sie ffmpeg auf Ihrem Server.
  2. Stellen Sie sicher, dass PHP Shell_exec in Ihrem PHP nicht eingeschränkt ist.

        // Discriminate only the audio/video files you want
        if(preg_match('/[^?#]+\.(?:wma|mp3|wav|mp4)/', strtolower($file))){
            $filepath = /* your file path */;
            // execute ffmpeg form linux Shell and grab duration from output
            $result = Shell_exec("ffmpeg -i ".$filepath.' 2>&1 | grep -o \'Duration: [0-9:.]*\'');
            $duration = str_replace('Duration: ', '', $result); // 00:05:03.25
    
            //get the duration in seconds
            $timeArr = preg_split('/:/', str_replace('s', '', $duration[0]));
            $t = $this->_times[$file] = (($timeArr[3])? $timeArr[3]*1 + $timeArr[2] * 60 + $timeArr[1] * 60 * 60 : $timeArr[2] + $timeArr[1] * 60)*1000;
    
        }
    
7
awavi

Ich habe schon so viele Zeit bestanden, aber ohne getID3 ( http://getid3.sourceforge.net/ ), um die Dauer der Audiodatei nicht zu erhalten.

1) Erste Download-Bibliothek von getID3 über folgenden Link:

 https://github.com/JamesHeinrich/getID3/archive/master.Zip

2) Probieren Sie den folgenden Code aus:

    <?php
       include("getid3/getid3.php");
       $filename = 'bcd4ecc6bf521da9b9a2d8b9616d1505.wav';
       $getID3 = new getID3;
       $file = $getID3->analyze($filename);
       $playtime_seconds = $file['playtime_seconds'];
       echo gmdate("H:i:s", $playtime_seconds);
    ?>
7
Mohin Mathakia
<?php
class MP3File
{
protected $filename;
public function __construct($filename)
{
    $this->filename = $filename;
}

public static function formatTime($duration) //as hh:mm:ss
{
    //return sprintf("%d:%02d", $duration/60, $duration%60);
    $hours = floor($duration / 3600);
    $minutes = floor( ($duration - ($hours * 3600)) / 60);
    $seconds = $duration - ($hours * 3600) - ($minutes * 60);
    return sprintf("%02d:%02d:%02d", $hours, $minutes, $seconds);
}

//Read first mp3 frame only...  use for CBR constant bit rate MP3s
public function getDurationEstimate()
{
    return $this->getDuration($use_cbr_estimate=true);
}

//Read entire file, frame by frame... ie: Variable Bit Rate (VBR)
public function getDuration($use_cbr_estimate=false)
{
    $fd = fopen($this->filename, "rb");

    $duration=0;
    $block = fread($fd, 100);
    $offset = $this->skipID3v2Tag($block);
    fseek($fd, $offset, SEEK_SET);
    while (!feof($fd))
    {
        $block = fread($fd, 10);
        if (strlen($block)<10) { break; }
        //looking for 1111 1111 111 (frame synchronization bits)
        else if ($block[0]=="\xff" && (ord($block[1])&0xe0) )
        {
            $info = self::parseFrameHeader(substr($block, 0, 4));
            if (empty($info['Framesize'])) { return $duration; } //some corrupt mp3 files
            fseek($fd, $info['Framesize']-10, SEEK_CUR);
            $duration += ( $info['Samples'] / $info['Sampling Rate'] );
        }
        else if (substr($block, 0, 3)=='TAG')
        {
            fseek($fd, 128-10, SEEK_CUR);//skip over id3v1 tag size
        }
        else
        {
            fseek($fd, -9, SEEK_CUR);
        }
        if ($use_cbr_estimate && !empty($info))
        { 
            return $this->estimateDuration($info['Bitrate'],$offset); 
        }
    }
    return round($duration);
}

private function estimateDuration($bitrate,$offset)
{
    $kbps = ($bitrate*1000)/8;
    $datasize = filesize($this->filename) - $offset;
    return round($datasize / $kbps);
}

private function skipID3v2Tag(&$block)
{
    if (substr($block, 0,3)=="ID3")
    {
        $id3v2_major_version = ord($block[3]);
        $id3v2_minor_version = ord($block[4]);
        $id3v2_flags = ord($block[5]);
        $flag_unsynchronisation  = $id3v2_flags & 0x80 ? 1 : 0;
        $flag_extended_header    = $id3v2_flags & 0x40 ? 1 : 0;
        $flag_experimental_ind   = $id3v2_flags & 0x20 ? 1 : 0;
        $flag_footer_present     = $id3v2_flags & 0x10 ? 1 : 0;
        $z0 = ord($block[6]);
        $z1 = ord($block[7]);
        $z2 = ord($block[8]);
        $z3 = ord($block[9]);
        if ( (($z0&0x80)==0) && (($z1&0x80)==0) && (($z2&0x80)==0) && (($z3&0x80)==0) )
        {
            $header_size = 10;
            $tag_size = (($z0&0x7f) * 2097152) + (($z1&0x7f) * 16384) + (($z2&0x7f) * 128) + ($z3&0x7f);
            $footer_size = $flag_footer_present ? 10 : 0;
            return $header_size + $tag_size + $footer_size;//bytes to skip
        }
    }
    return 0;
}

public static function parseFrameHeader($fourbytes)
{
    static $versions = array(
        0x0=>'2.5',0x1=>'x',0x2=>'2',0x3=>'1', // x=>'reserved'
    );
    static $layers = array(
        0x0=>'x',0x1=>'3',0x2=>'2',0x3=>'1', // x=>'reserved'
    );
    static $bitrates = array(
        'V1L1'=>array(0,32,64,96,128,160,192,224,256,288,320,352,384,416,448),
        'V1L2'=>array(0,32,48,56, 64, 80, 96,112,128,160,192,224,256,320,384),
        'V1L3'=>array(0,32,40,48, 56, 64, 80, 96,112,128,160,192,224,256,320),
        'V2L1'=>array(0,32,48,56, 64, 80, 96,112,128,144,160,176,192,224,256),
        'V2L2'=>array(0, 8,16,24, 32, 40, 48, 56, 64, 80, 96,112,128,144,160),
        'V2L3'=>array(0, 8,16,24, 32, 40, 48, 56, 64, 80, 96,112,128,144,160),
    );
    static $sample_rates = array(
        '1'   => array(44100,48000,32000),
        '2'   => array(22050,24000,16000),
        '2.5' => array(11025,12000, 8000),
    );
    static $samples = array(
        1 => array( 1 => 384, 2 =>1152, 3 =>1152, ), //MPEGv1,     Layers 1,2,3
        2 => array( 1 => 384, 2 =>1152, 3 => 576, ), //MPEGv2/2.5, Layers 1,2,3
    );
    //$b0=ord($fourbytes[0]);//will always be 0xff
    $b1=ord($fourbytes[1]);
    $b2=ord($fourbytes[2]);
    $b3=ord($fourbytes[3]);

    $version_bits = ($b1 & 0x18) >> 3;
    $version = $versions[$version_bits];
    $simple_version =  ($version=='2.5' ? 2 : $version);

    $layer_bits = ($b1 & 0x06) >> 1;
    $layer = $layers[$layer_bits];

    $protection_bit = ($b1 & 0x01);
    $bitrate_key = sprintf('V%dL%d', $simple_version , $layer);
    $bitrate_idx = ($b2 & 0xf0) >> 4;
    $bitrate = isset($bitrates[$bitrate_key][$bitrate_idx]) ? $bitrates[$bitrate_key][$bitrate_idx] : 0;

    $sample_rate_idx = ($b2 & 0x0c) >> 2;//0xc => b1100
    $sample_rate = isset($sample_rates[$version][$sample_rate_idx]) ? $sample_rates[$version][$sample_rate_idx] : 0;
    $padding_bit = ($b2 & 0x02) >> 1;
    $private_bit = ($b2 & 0x01);
    $channel_mode_bits = ($b3 & 0xc0) >> 6;
    $mode_extension_bits = ($b3 & 0x30) >> 4;
    $copyright_bit = ($b3 & 0x08) >> 3;
    $original_bit = ($b3 & 0x04) >> 2;
    $emphasis = ($b3 & 0x03);

    $info = array();
    $info['Version'] = $version;//MPEGVersion
    $info['Layer'] = $layer;
    //$info['Protection Bit'] = $protection_bit; //0=> protected by 2 byte CRC, 1=>not protected
    $info['Bitrate'] = $bitrate;
    $info['Sampling Rate'] = $sample_rate;
    $info['Framesize'] = self::framesize($layer, $bitrate, $sample_rate, $padding_bit);
    $info['Samples'] = $samples[$simple_version][$layer];
    return $info;
}

private static function framesize($layer, $bitrate,$sample_rate,$padding_bit)
{
    if ($layer==1)
        return intval(((12 * $bitrate*1000 /$sample_rate) + $padding_bit) * 4);
    else //layer 2, 3
        return intval(((144 * $bitrate*1000)/$sample_rate) + $padding_bit);
}
}
?>
<?php
$mp3file = new MP3File("Chal_Halke.mp3");//http://www.npr.org/rss/podcast.php?id=510282
$duration1 = $mp3file->getDurationEstimate();//(faster) for CBR only
$duration2 = $mp3file->getDuration();//(slower) for VBR (or CBR)
echo "duration: $duration1 seconds"."\n";

?>
3
debasish

Dafür gibt es keine native PHP-Funktion.

Abhängig von Ihrer Serverumgebung können Sie ein Tool wie MP3Info verwenden.

$length = Shell_exec('mp3info -p "%S" sample.mp3');   // total time in seconds
3
Ragnar123

Die MP3-Länge wird nirgendwo gespeichert (im "einfachen" MP3-Format), da MP3 in Frames "aufgeteilt" werden soll und diese Frames abspielbar bleiben.

http://mpgedit.org/mpgedit/mpeg_format/mpeghdr.htm

Wenn Sie kein ID-Tag haben, auf das Sie sich verlassen können, müssen Sie die gesamte MP3-Datei lesen und die Dauer jedes Frames summieren. Dazu benötigen Sie Tools und PHP -Klassen, die dies tun.

1
LSerni

Wie zuvor habe ich eine Lösung für beide mp3 - undWAV-Dateien bereitgestellt. Nun ist diese Lösung speziell für die einzigeWAV- Datei mit mehr Genauigkeit aber mit längerer Länge Bewertung Zeit als die frühere Lösung.

function calculateWavDuration( $file ) {

    $fp = fopen($file, 'r');

    if (fread($fp, 4) == "RIFF") {

        fseek($fp, 20);
        $raw_header = fread($fp, 16);
        $header = unpack('vtype/vchannels/Vsamplerate/Vbytespersec/valignment/vbits', $raw_header);
        $pos = ftell($fp);

        while (fread($fp, 4) != "data" && !feof($fp)) {

            $pos++;
            fseek($fp, $pos);

        }

        $raw_header = fread($fp, 4);
        $data = unpack('Vdatasize', $raw_header);
        $sec = $data[datasize] / $header[bytespersec];
        $minutes = intval(($sec / 60) % 60);
        $seconds = intval($sec % 60);

        return str_pad($minutes, 2, "0", STR_PAD_LEFT) . ":" . str_pad($seconds, 2, "0", STR_PAD_LEFT);

    }

}

$file = '1.wav'; //Enter File wav
calculateWavDuration($file);

Schließlich entwickelte ich eine Lösung mit meinen eigenen Berechnungen. Diese Lösung funktioniert am besten für die Dateiformate mp3 und WAV. Es werden jedoch geringfügige Präzisionsabweichungen erwartet. Die Lösung ist in PHP. Ich nehme ein wenig Ahnung von WAV

function calculateFileSize($file){

    $ratio = 16000; //bytespersec

    if (!$file) {

        exit("Verify file name and it's path");

    }

    $file_size = filesize($file);

    if (!$file_size)
        exit("Verify file, something wrong with your file");

    $duration = ($file_size / $ratio);
    $minutes = floor($duration / 60);
    $seconds = $duration - ($minutes * 60);
    $seconds = round($seconds);
    echo "$minutes:$seconds minutes";

}

$file = 'Apple-classic.mp3'; //Enter File Name mp3/wav
calculateFileSize($file);
$getID3 = new getID3;
$ThisFileInfo = $getID3->analyze($pathName);

// playtime in minutes:seconds, formatted string
$len = @$ThisFileInfo['playtime_string']; 

//don't get playtime_string, but get playtime_seconds
$len = @$ThisFileInfo['playtime_seconds']*1000; //*1000 as calculate millisecond

Ich hoffe das hilft dir.

1
Andi Kur

Wenn Sie FFMpeg installiert haben, ist das Abrufen der Dauer mit FFProbe ganz einfach

$filepath = 'example.mp3';
$ffprobe = \FFMpeg\FFProbe::create();
$duration = $ffprobe->format($filepath)->get('duration');

echo gmdate('H:i:s', $duration);
0
user1214684