source: extensions/charlies_content/getid3/getid3/module.audio-video.nsv.php @ 3318

Revision 3318, 8.0 KB checked in by vdigital, 11 years ago (diff)

+ Add Charlies' content to depository

  • Property svn:keywords set to Author Date Id Revision
Line 
1<?php
2// +----------------------------------------------------------------------+
3// | PHP version 5                                                        |
4// +----------------------------------------------------------------------+
5// | Copyright (c) 2002-2006 James Heinrich, Allan Hansen                 |
6// +----------------------------------------------------------------------+
7// | This source file is subject to version 2 of the GPL license,         |
8// | that is bundled with this package in the file license.txt and is     |
9// | available through the world-wide-web at the following url:           |
10// | http://www.gnu.org/copyleft/gpl.html                                 |
11// +----------------------------------------------------------------------+
12// | getID3() - http://getid3.sourceforge.net or http://www.getid3.org    |
13// +----------------------------------------------------------------------+
14// | Authors: James Heinrich <infoØgetid3*org>                            |
15// |          Allan Hansen <ahØartemis*dk>                                |
16// +----------------------------------------------------------------------+
17// | module.audio-video.nsv.php                                           |
18// | module for analyzing Nullsoft NSV files                              |
19// | dependencies: NONE                                                   |
20// +----------------------------------------------------------------------+
21//
22// $Id$
23
24       
25       
26class getid3_nsv extends getid3_handler
27{
28
29    public function Analyze() {
30
31        $getid3 = $this->getid3;
32
33        $getid3->info['fileformat']          = 'nsv';
34        $getid3->info['audio']['dataformat'] = 'nsv';
35        $getid3->info['video']['dataformat'] = 'nsv';
36        $getid3->info['audio']['lossless']   = false;
37        $getid3->info['video']['lossless']   = false;
38
39        fseek($getid3->fp, $getid3->info['avdataoffset'], SEEK_SET);
40        $nsv_header = fread($getid3->fp, 4);
41
42        switch ($nsv_header) {
43           
44            case 'NSVs':
45                $this->getNSVsHeader();
46                break;
47
48            case 'NSVf':
49                if ($this->getNSVfHeader()) {
50                        $this->getNSVsHeader($getid3->info['nsv']['NSVf']['header_length']);
51                }
52                break;
53
54            default:
55                throw new getid3_exception('Expecting "NSVs" or "NSVf" at offset '.$getid3->info['avdataoffset'].', found "'.$nsv_header.'"');
56                break;
57        }
58
59        if (!isset($getid3->info['nsv']['NSVf'])) {
60            $getid3->warning('NSVf header not present - cannot calculate playtime or bitrate');
61        }
62
63        return true;
64    }
65
66
67
68    private function getNSVsHeader($file_offset = 0) {
69       
70        $getid3 = $this->getid3;
71       
72        fseek($getid3->fp, $file_offset, SEEK_SET);
73        $nsvs_header = fread($getid3->fp, 28);
74       
75        $getid3->info['nsv']['NSVs'] = array ();
76        $info_nsv_NSVs = &$getid3->info['nsv']['NSVs'];
77
78        $info_nsv_NSVs['identifier'] = substr($nsvs_header, 0, 4);
79        if ($info_nsv_NSVs['identifier'] != 'NSVs') {
80            throw new getid3_exception('expected "NSVs" at offset ('.$file_offset.'), found "'.$info_nsv_NSVs['identifier'].'" instead');
81        }
82       
83        $info_nsv_NSVs['offset'] = $file_offset;
84       
85        getid3_lib::ReadSequence('LittleEndian2Int', $info_nsv_NSVs, $nsvs_header, 4,
86            array (
87                'video_codec'     => -4,    // string
88                'audio_codec'     => -4,    // string
89                'resolution_x'    => 2,
90                'resolution_y'    => 2,
91                'framerate_index' => 1,
92            )
93        );
94
95        if ($info_nsv_NSVs['audio_codec'] == 'PCM ') {
96       
97            getid3_lib::ReadSequence('LittleEndian2Int', $info_nsv_NSVs, $nsvs_header, 24,
98                array (
99                    'bits_channel' => 1,
100                    'channels'     => 1,
101                    'sample_rate'  => 2
102                )
103            );
104            $getid3->info['audio']['sample_rate'] = $info_nsv_NSVs['sample_rate'];
105           
106        }
107
108        $getid3->info['video']['resolution_x']       = $info_nsv_NSVs['resolution_x'];
109        $getid3->info['video']['resolution_y']       = $info_nsv_NSVs['resolution_y'];
110        $info_nsv_NSVs['frame_rate']                 = getid3_nsv::NSVframerateLookup($info_nsv_NSVs['framerate_index']);
111        $getid3->info['video']['frame_rate']         = $info_nsv_NSVs['frame_rate'];
112        $getid3->info['video']['bits_per_sample']    = 24;
113        $getid3->info['video']['pixel_aspect_ratio'] = (float)1;
114
115        return true;
116    }
117
118
119
120    private function getNSVfHeader($file_offset = 0, $get_toc_offsets=false) {
121       
122        $getid3 = $this->getid3;
123       
124        fseek($getid3->fp, $file_offset, SEEK_SET);
125        $nsvf_header = fread($getid3->fp, 28);
126       
127        $getid3->info['nsv']['NSVf'] = array ();
128        $info_nsv_NSVf = &$getid3->info['nsv']['NSVf'];
129       
130        $info_nsv_NSVf['identifier'] = substr($nsvf_header, 0, 4);
131        if ($info_nsv_NSVf['identifier'] != 'NSVf') {
132            throw new getid3_exception('expected "NSVf" at offset ('.$file_offset.'), found "'.$info_nsv_NSVf['identifier'].'" instead');
133        }
134
135        $getid3->info['nsv']['NSVs']['offset']        = $file_offset;
136
137        getid3_lib::ReadSequence('LittleEndian2Int', $info_nsv_NSVf, $nsvf_header, 4,
138            array (
139                'header_length' => 4,
140                'file_size'     => 4,
141                'playtime_ms'   => 4,
142                'meta_size'     => 4,
143                'TOC_entries_1' => 4,
144                'TOC_entries_2' => 4
145            )
146        );
147               
148        if ($info_nsv_NSVf['playtime_ms'] == 0) {
149            throw new getid3_exception('Corrupt NSV file: NSVf.playtime_ms == zero');
150        }
151       
152        if ($info_nsv_NSVf['file_size'] > $getid3->info['avdataend']) {
153            $getid3->warning('truncated file - NSVf header indicates '.$info_nsv_NSVf['file_size'].' bytes, file actually '.$getid3->info['avdataend'].' bytes');
154        }
155
156        $nsvf_header .= fread($getid3->fp, $info_nsv_NSVf['meta_size'] + (4 * $info_nsv_NSVf['TOC_entries_1']) + (4 * $info_nsv_NSVf['TOC_entries_2']));
157        $nsvf_headerlength = strlen($nsvf_header);
158        $info_nsv_NSVf['metadata'] = substr($nsvf_header, 28, $info_nsv_NSVf['meta_size']);
159
160        $offset = 28 + $info_nsv_NSVf['meta_size'];
161        if ($get_toc_offsets) {
162            $toc_counter = 0;
163            while ($toc_counter < $info_nsv_NSVf['TOC_entries_1']) {
164                if ($toc_counter < $info_nsv_NSVf['TOC_entries_1']) {
165                    $info_nsv_NSVf['TOC_1'][$toc_counter] = getid3_lib::LittleEndian2Int(substr($nsvf_header, $offset, 4));
166                    $offset += 4;
167                    $toc_counter++;
168                }
169            }
170        }
171
172        if (trim($info_nsv_NSVf['metadata']) != '') {
173            $info_nsv_NSVf['metadata'] = str_replace('`', "\x01", $info_nsv_NSVf['metadata']);
174            $comment_pair_array = explode("\x01".' ', $info_nsv_NSVf['metadata']);
175            foreach ($comment_pair_array as $comment_pair) {
176                if (strstr($comment_pair, '='."\x01")) {
177                    list($key, $value) = explode('='."\x01", $comment_pair, 2);
178                    $getid3->info['nsv']['comments'][strtolower($key)][] = trim(str_replace("\x01", '', $value));
179                }
180            }
181        }
182
183        $getid3->info['playtime_seconds'] = $info_nsv_NSVf['playtime_ms'] / 1000;
184        $getid3->info['bitrate']          = ($info_nsv_NSVf['file_size'] * 8) / $getid3->info['playtime_seconds'];
185
186        return true;
187    }
188
189
190
191    public static function NSVframerateLookup($frame_rate_index) {
192       
193        if ($frame_rate_index <= 127) {
194            return (float)$frame_rate_index;
195        }
196
197        static $lookup = array (
198            129 => 29.970,
199            131 => 23.976,
200            133 => 14.985,
201            197 => 59.940,
202            199 => 47.952
203        );
204        return (isset($lookup[$frame_rate_index]) ? $lookup[$frame_rate_index] : false);
205    }
206
207}
208
209
210?>
Note: See TracBrowser for help on using the repository browser.