comparison Plugins/Input/console/Dual_Resampler.cpp @ 493:c04dff121e1d trunk

[svn] hostile merge, phase 2: reimport based on new plugin code
author nenolod
date Tue, 24 Jan 2006 20:19:01 -0800
parents
children f12d7e208b43
comparison
equal deleted inserted replaced
492:ccb68bad47b2 493:c04dff121e1d
1
2 // Game_Music_Emu 0.3.0. http://www.slack.net/~ant/
3
4 #include "Dual_Resampler.h"
5
6 #include <stdlib.h>
7 #include <string.h>
8
9 /* Copyright (C) 2003-2006 Shay Green. This module is free software; you
10 can redistribute it and/or modify it under the terms of the GNU Lesser
11 General Public License as published by the Free Software Foundation; either
12 version 2.1 of the License, or (at your option) any later version. This
13 module is distributed in the hope that it will be useful, but WITHOUT ANY
14 WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
15 FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for
16 more details. You should have received a copy of the GNU Lesser General
17 Public License along with this module; if not, write to the Free Software
18 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
19
20 #include BLARGG_SOURCE_BEGIN
21
22 int const resampler_extra = 256;
23
24 Dual_Resampler::Dual_Resampler()
25 {
26 }
27
28 Dual_Resampler::~Dual_Resampler()
29 {
30 }
31
32 blargg_err_t Dual_Resampler::resize( int pairs )
33 {
34 BLARGG_RETURN_ERR( sample_buf.resize( pairs * 2 ) );
35 buf_pos = sample_buf.size();
36 oversamples_per_frame = int (pairs * resampler.ratio()) * 2 + 2;
37 return resampler.buffer_size( oversamples_per_frame + resampler_extra );
38 }
39
40 void Dual_Resampler::play_frame_( Blip_Buffer& blip_buf, sample_t* out )
41 {
42 long pair_count = sample_buf.size() >> 1;
43 blip_time_t blip_time = blip_buf.count_clocks( pair_count );
44 int sample_count = oversamples_per_frame - resampler.written();
45
46 int new_count = play_frame( blip_time, sample_count, resampler.buffer() );
47 assert( unsigned (new_count - sample_count) < resampler_extra );
48
49 blip_buf.end_frame( blip_time );
50 assert( blip_buf.samples_avail() == pair_count );
51
52 resampler.write( new_count );
53
54 long count = resampler.read( sample_buf.begin(), sample_buf.size() );
55 assert( count == (long) sample_buf.size() );
56
57 mix_samples( blip_buf, out );
58 blip_buf.remove_samples( pair_count );
59 }
60
61 void Dual_Resampler::play( long count, sample_t* out, Blip_Buffer& blip_buf )
62 {
63 // empty extra buffer
64 long remain = sample_buf.size() - buf_pos;
65 if ( remain )
66 {
67 if ( remain > count )
68 remain = count;
69 count -= remain;
70 memcpy( out, &sample_buf [buf_pos], remain * sizeof *out );
71 out += remain;
72 buf_pos += remain;
73 }
74
75 // entire frames
76 while ( count >= (long) sample_buf.size() )
77 {
78 play_frame_( blip_buf, out );
79 out += sample_buf.size();
80 count -= sample_buf.size();
81 }
82
83 // extra
84 if ( count )
85 {
86 play_frame_( blip_buf, sample_buf.begin() );
87 buf_pos = count;
88 memcpy( out, sample_buf.begin(), count * sizeof *out );
89 out += count;
90 }
91 }
92
93 #include BLARGG_ENABLE_OPTIMIZER
94
95 void Dual_Resampler::mix_samples( Blip_Buffer& blip_buf, sample_t* out )
96 {
97 Blip_Reader sn;
98 int bass = sn.begin( blip_buf );
99 const sample_t* in = sample_buf.begin();
100
101 for ( int n = sample_buf.size() >> 1; n--; )
102 {
103 int s = sn.read();
104 long l = (long) in [0] * 2 + s;
105 sn.next( bass );
106 long r = in [1];
107 if ( (BOOST::int16_t) l != l )
108 l = 0x7FFF - (l >> 24);
109 r = r * 2 + s;
110 in += 2;
111 out [0] = l;
112 out [1] = r;
113 out += 2;
114 if ( (BOOST::int16_t) r != r )
115 out [-1] = 0x7FFF - (r >> 24);
116 }
117
118 sn.end( blip_buf );
119 }
120