ScummVM API documentation
pcspk.h
1 /* ScummVM - Graphic Adventure Engine
2  *
3  * ScummVM is the legal property of its developers, whose names
4  * are too numerous to list here. Please refer to the COPYRIGHT
5  * file distributed with this source distribution.
6  *
7  * This program is free software: you can redistribute it and/or modify
8  * it under the terms of the GNU General Public License as published by
9  * the Free Software Foundation, either version 3 of the License, or
10  * (at your option) any later version.
11  *
12  * This program is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15  * GNU General Public License for more details.
16  *
17  * You should have received a copy of the GNU General Public License
18  * along with this program. If not, see <http://www.gnu.org/licenses/>.
19  *
20  */
21 
22 #ifndef SCUMM_IMUSE_PCSPK_H
23 #define SCUMM_IMUSE_PCSPK_H
24 
25 #include "audio/softsynth/emumidi.h"
26 #include "audio/softsynth/pcspk.h"
27 
28 namespace Scumm {
29 
31 public:
33  ~IMuseDriver_PCSpk() override;
34 
35  int open() override;
36  void close() override;
37 
38  void send(uint32 d) override;
39 
40  MidiChannel *allocateChannel() override;
41  MidiChannel *getPercussionChannel() override { return nullptr; }
42 
43  bool isStereo() const override { return _pcSpk.isStereo(); }
44  int getRate() const override { return _pcSpk.getRate(); }
45 protected:
46  void generateSamples(int16 *buf, int len) override;
47  void onTimer() override;
48 
49 private:
50  Audio::PCSpeaker _pcSpk;
51  int _effectTimer;
52  uint8 _randBase;
53 
54  void updateNote();
55  void output(uint16 out);
56 
57  static uint8 getEffectModifier(uint16 level);
58  int16 getEffectModLevel(int16 level, int8 mod);
59  int16 getRandScale(int16 input);
60 
61  struct EffectEnvelope {
62  uint8 state;
63  int16 currentLevel;
64  int16 duration;
65  int16 maxLevel;
66  int16 startLevel;
67  uint8 loop;
68  uint8 stateTargetLevels[4];
69  uint8 stateModWheelLevels[4];
70  uint8 modWheelSensitivity;
71  uint8 modWheelState;
72  uint8 modWheelLast;
73  int16 stateNumSteps;
74  int16 stateStepCounter;
75  int16 changePerStep;
76  int8 dir;
77  int16 changePerStepRem;
78  int16 changeCountRem;
79  };
80 
81  struct EffectDefinition {
82  int16 phase;
83  uint8 type;
84  uint8 useModWheel;
85  EffectEnvelope *envelope;
86  };
87 
88  struct OutputChannel {
89  uint8 active;
90  uint8 note;
91  uint8 sustainNoteOff;
92  uint8 length;
93  const uint8 *instrument;
94  uint8 unkA;
95  uint8 unkB;
96  uint8 unkC;
97  int16 unkE;
98  EffectEnvelope effectEnvelopeA;
99  EffectDefinition effectDefA;
100  EffectEnvelope effectEnvelopeB;
101  EffectDefinition effectDefB;
102  int16 unk60;
103  };
104 
105  class MidiChannel_PcSpk: public MidiChannel {
106  public:
107  MidiChannel_PcSpk(IMuseDriver_PCSpk *owner, byte number);
108  MidiDriver *device() override { return _owner; }
109  byte getNumber() override { return _number; }
110  void release() override;
111 
112  void send(uint32 b) override;
113  void noteOff(byte note) override;
114  void noteOn(byte note, byte velocity) override;
115  void programChange(byte program) override;
116  void pitchBend(int16 bend) override;
117  void controlChange(byte control, byte value) override;
118  void pitchBendFactor(byte value) override;
119  void transpose(int8 value) override;
120  void detune(int16 value) override;
121  void priority(byte value) override;
122  void sysEx_customInstrument(uint32 type, const byte *instr, uint32 dataSize) override;
123 
124  bool allocate();
125 
126  bool _allocated;
127  OutputChannel _out;
128  uint8 _instrument[23];
129  uint8 _priority;
130  uint8 _tl;
131  uint8 _modWheel;
132  int16 _pitchBend;
133 
134  private:
135  IMuseDriver_PCSpk *_owner;
136  const byte _number;
137  //uint8 _programNr;
138  uint8 _sustain;
139  uint8 _pitchBendFactor;
140  int16 _pitchBendTmp;
141  int8 _transpose;
142  int8 _detune;
143  };
144 
145  void setupEffects(MidiChannel_PcSpk &chan, EffectEnvelope &env, EffectDefinition &def, byte flags, const byte *data);
146  void startEffect(EffectEnvelope &env, const byte *data);
147  void initNextEnvelopeState(EffectEnvelope &env);
148  void updateEffectGenerator(MidiChannel_PcSpk &chan, EffectEnvelope &env, EffectDefinition &def);
149  uint8 advanceEffectEnvelope(EffectEnvelope &env, EffectDefinition &def);
150 
151  MidiChannel_PcSpk *_channels[6];
152  MidiChannel_PcSpk *_activeChannel;
153 
154  MidiChannel_PcSpk *_lastActiveChannel;
155  uint16 _lastActiveOut;
156 
157  static const byte _outInstrumentData[1024];
158  static const byte _outputTable1[];
159  static const byte _outputTable2[];
160  static const uint16 _effectEnvStepTable[];
161  static const uint16 _frequencyTable[];
162 };
163 
164 } // End of namespace Scumm
165 
166 #endif
void send(uint32 d) override
Definition: pcspk.h:30
void close() override
bool isStereo() const override
Definition: pcspk.h:43
int getRate() const override
Definition: pcspk.h:44
Definition: mididrv.h:309
Definition: mixer.h:59
Definition: mididrv.h:537
Definition: emumidi.h:29
bool isStereo() const
Definition: pcspk.h:90
int getRate() const
Definition: pcspk.h:93
Definition: actor.h:30
Definition: pcspk.h:31