annotate src/adplug/core/emuopl.cxx @ 166:a118245b88c7 trunk

[svn] - use a quantized variance instead of a fast fft sum for beat detection with thresholding
author nenolod
date Tue, 31 Oct 2006 22:09:04 -0800
parents 3da1b8942b8b
children 4709ce4e209e
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
0
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
1 /*
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
2 * AdPlug - Replayer for many OPL2/OPL3 audio file formats.
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
3 * Copyright (C) 1999 - 2005 Simon Peter <dn.tlp@gmx.net>, et al.
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
4 *
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
5 * This library is free software; you can redistribute it and/or
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
6 * modify it under the terms of the GNU Lesser General Public
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
7 * License as published by the Free Software Foundation; either
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
8 * version 2.1 of the License, or (at your option) any later version.
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
9 *
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
10 * This library is distributed in the hope that it will be useful,
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
13 * Lesser General Public License for more details.
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
14 *
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
15 * You should have received a copy of the GNU Lesser General Public
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
16 * License along with this library; if not, write to the Free Software
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
17 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
18 *
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
19 * emuopl.cpp - Emulated OPL, by Simon Peter <dn.tlp@gmx.net>
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
20 */
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
21
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
22 #include "emuopl.h"
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
23
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
24 CEmuopl::CEmuopl(int rate, bool bit16, bool usestereo)
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
25 : use16bit(bit16), stereo(usestereo), mixbufSamples(0)
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
26 {
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
27 opl[0] = OPLCreate(OPL_TYPE_YM3812, 3579545, rate);
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
28 opl[1] = OPLCreate(OPL_TYPE_YM3812, 3579545, rate);
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
29
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
30 currType = TYPE_DUAL_OPL2;
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
31
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
32 init();
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
33 }
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
34
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
35 CEmuopl::~CEmuopl()
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
36 {
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
37 OPLDestroy(opl[0]); OPLDestroy(opl[1]);
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
38
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
39 if(mixbufSamples) {
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
40 delete [] mixbuf0;
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
41 delete [] mixbuf1;
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
42 }
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
43 }
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
44
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
45 void CEmuopl::update(short *buf, int samples)
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
46 {
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
47 int i;
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
48
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
49 //ensure that our mix buffers are adequately sized
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
50 if(mixbufSamples < samples) {
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
51 if(mixbufSamples) { delete[] mixbuf0; delete[] mixbuf1; }
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
52 mixbufSamples = samples;
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
53
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
54 //*2 = make room for stereo, if we need it
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
55 mixbuf0 = new short[samples*2];
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
56 mixbuf1 = new short[samples*2];
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
57 }
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
58
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
59 //data should be rendered to outbuf
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
60 //tempbuf should be used as a temporary buffer
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
61 //if we are supposed to generate 16bit output,
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
62 //then outbuf may point directly to the actual waveform output "buf"
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
63 //if we are supposed to generate 8bit output,
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
64 //then outbuf cannot point to "buf" (because there will not be enough room)
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
65 //and so it must point to a mixbuf instead--
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
66 //it will be reduced to 8bit and put in "buf" later
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
67 short *outbuf;
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
68 short *tempbuf=mixbuf0;
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
69 short *tempbuf2=mixbuf1;
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
70 if(use16bit) outbuf = buf;
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
71 else outbuf = mixbuf1;
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
72 //...there is a potentially confusing situation where mixbuf1 can be aliased.
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
73 //beware. it is a little loony.
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
74
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
75 //all of the following rendering code produces 16bit output
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
76
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
77 switch(currType) {
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
78 case TYPE_OPL2:
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
79 //for opl2 mode:
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
80 //render chip0 to the output buffer
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
81 YM3812UpdateOne(opl[0],outbuf,samples);
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
82
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
83 //if we are supposed to output stereo,
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
84 //then we need to dup the mono channel
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
85 if(stereo)
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
86 for(i=samples-1;i>=0;i--) {
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
87 outbuf[i*2] = outbuf[i];
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
88 outbuf[i*2+1] = outbuf[i];
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
89 }
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
90 break;
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
91
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
92 case TYPE_OPL3: // unsupported
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
93 break;
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
94
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
95 case TYPE_DUAL_OPL2:
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
96 //for dual opl2 mode:
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
97 //render each chip to a different tempbuffer
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
98 YM3812UpdateOne(opl[0],tempbuf2,samples);
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
99 YM3812UpdateOne(opl[1],tempbuf,samples);
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
100
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
101 //output stereo:
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
102 //then we need to interleave the two buffers
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
103 if(stereo){
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
104 //first, spread tempbuf's samples across left channel
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
105 //left channel
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
106 for(i=0;i<samples;i++)
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
107 outbuf[i*2] = tempbuf2[i];
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
108 //next, insert the samples from tempbuf2 into right channel
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
109 for(i=0;i<samples;i++)
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
110 outbuf[i*2+1] = tempbuf[i];
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
111 } else
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
112 //output mono:
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
113 //then we need to mix the two buffers into buf
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
114 for(i=0;i<samples;i++)
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
115 outbuf[i] = (tempbuf[i]>>1) + (tempbuf2[i]>>1);
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
116 break;
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
117 }
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
118
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
119 //now reduce to 8bit if we need to
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
120 if(!use16bit)
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
121 for(i=0;i<(stereo ? samples*2 : samples);i++)
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
122 ((char *)buf)[i] = (outbuf[i] >> 8) ^ 0x80;
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
123 }
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
124
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
125 void CEmuopl::write(int reg, int val)
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
126 {
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
127 switch(currType){
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
128 case TYPE_OPL2:
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
129 case TYPE_DUAL_OPL2:
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
130 OPLWrite(opl[currChip], 0, reg);
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
131 OPLWrite(opl[currChip], 1, val);
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
132 break;
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
133 case TYPE_OPL3: // unsupported
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
134 break;
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
135 }
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
136 }
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
137
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
138 void CEmuopl::init()
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
139 {
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
140 OPLResetChip(opl[0]); OPLResetChip(opl[1]);
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
141 currChip = 0;
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
142 }
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
143
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
144 void CEmuopl::settype(ChipType type)
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
145 {
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
146 currType = type;
13389e613d67 [svn] - initial import of audacious-plugins tree (lots to do)
nenolod
parents:
diff changeset
147 }