2 * Copyright 2001-2012 Haiku, Inc. All Rights Reserved.
3 * Distributed under the terms of the MIT License.
6 * Christopher ML Zumwalt May (zummy@users.sf.net)
10 #include <SimpleGameSound.h>
13 #include <MediaFile.h>
14 #include <MediaTrack.h>
18 #include "GameSoundBuffer.h"
19 #include "GameSoundDefs.h"
20 #include "GameSoundDevice.h"
21 #include "GSUtility.h"
24 BSimpleGameSound::BSimpleGameSound(const entry_ref
*inFile
,
25 BGameSoundDevice
*device
)
29 if (InitCheck() == B_OK
)
30 SetInitError(Init(inFile
));
34 BSimpleGameSound::BSimpleGameSound(const char *inFile
, BGameSoundDevice
*device
)
38 if (InitCheck() == B_OK
) {
41 if (get_ref_for_path(inFile
, &file
) != B_OK
)
42 SetInitError(B_ENTRY_NOT_FOUND
);
44 SetInitError(Init(&file
));
49 BSimpleGameSound::BSimpleGameSound(const void *inData
, size_t inFrameCount
,
50 const gs_audio_format
*format
, BGameSoundDevice
*device
)
54 if (InitCheck() != B_OK
)
57 gs_audio_format actual
= *format
;
58 if (actual
.byte_order
== 0)
59 actual
.byte_order
= B_MEDIA_HOST_ENDIAN
;
62 = get_sample_size(format
->format
) * format
->channel_count
;
63 uchar
* data
= new uchar
[inFrameCount
* frameSize
];
64 memcpy(data
, inData
, inFrameCount
* frameSize
);
66 SetInitError(Init(data
, inFrameCount
, &actual
));
70 BSimpleGameSound::BSimpleGameSound(const BSimpleGameSound
&other
)
74 gs_audio_format format
;
77 status_t error
= other
.Device()->Buffer(other
.ID(), &format
, data
);
81 Init(data
, 0, &format
);
86 BSimpleGameSound::~BSimpleGameSound()
92 BSimpleGameSound::Clone() const
94 gs_audio_format format
;
97 status_t error
= Device()->Buffer(ID(), &format
, data
);
101 BSimpleGameSound
*clone
= new BSimpleGameSound(data
, 0, &format
, Device());
108 /* virtual */ status_t
109 BSimpleGameSound::Perform(int32 selector
, void * data
)
116 BSimpleGameSound::SetIsLooping(bool looping
)
118 gs_attribute attribute
;
120 attribute
.attribute
= B_GS_LOOPING
;
121 attribute
.value
= (looping
) ? -1.0 : 0.0;
122 attribute
.duration
= bigtime_t(0);
125 return Device()->SetAttributes(ID(), &attribute
, 1);
130 BSimpleGameSound::IsLooping() const
132 gs_attribute attribute
;
134 attribute
.attribute
= B_GS_LOOPING
;
137 if (Device()->GetAttributes(ID(), &attribute
, 1) != B_OK
)
140 return bool(attribute
.value
);
145 BSimpleGameSound::Init(const entry_ref
* inFile
)
147 BMediaFile
file(inFile
);
148 gs_audio_format gsformat
;
149 media_format mformat
;
150 int64 framesRead
, framesTotal
= 0;
152 if (file
.InitCheck() != B_OK
)
153 return file
.InitCheck();
155 BMediaTrack
* audioStream
= file
.TrackAt(0);
156 audioStream
->EncodedFormat(&mformat
);
157 if (!mformat
.IsAudio())
160 int64 frames
= audioStream
->CountFrames();
162 memset(&mformat
, 0, sizeof(media_format
));
163 mformat
.type
= B_MEDIA_RAW_AUDIO
;
164 // mformat.u.raw_audio.byte_order
165 // = (B_HOST_IS_BENDIAN) ? B_MEDIA_BIG_ENDIAN : B_MEDIA_LITTLE_ENDIAN;
166 status_t error
= audioStream
->DecodedFormat(&mformat
);
170 memset(&gsformat
, 0, sizeof(gs_audio_format
));
171 media_to_gs_format(&gsformat
, &mformat
.u
.raw_audio
);
173 if (mformat
.u
.raw_audio
.format
== media_raw_audio_format::B_AUDIO_CHAR
) {
174 // The GameKit doesnt support this format so we will have to reformat
175 // the data into something the GameKit does support.
176 char * buffer
= new char[gsformat
.buffer_size
];
177 uchar
* data
= new uchar
[frames
* gsformat
.channel_count
];
179 while (framesTotal
< frames
) {
180 // read the next chunck from the stream
181 memset(buffer
, 0, gsformat
.buffer_size
);
182 audioStream
->ReadFrames(buffer
, &framesRead
);
184 // refomat the buffer from
185 int64 position
= framesTotal
* gsformat
.channel_count
;
186 for (int32 i
= 0; i
< (int32
)gsformat
.buffer_size
; i
++)
187 data
[i
+ position
] = buffer
[i
] + 128;
189 framesTotal
+= framesRead
;
193 gsformat
.format
= gs_audio_format::B_GS_U8
;
195 error
= Init(data
, frames
, &gsformat
);
197 // free the buffers we no longer need
199 // We need to determine the size, in bytes, of a single sample.
200 // At the same time, we will store the format of the audio buffer
202 = get_sample_size(gsformat
.format
) * gsformat
.channel_count
;
203 char * data
= new char[frames
* frameSize
];
204 gsformat
.buffer_size
= frames
* frameSize
;
206 while (framesTotal
< frames
) {
207 char * position
= &data
[framesTotal
* frameSize
];
208 audioStream
->ReadFrames(position
, &framesRead
);
210 framesTotal
+= framesRead
;
213 error
= Init(data
, frames
, &gsformat
);
216 file
.ReleaseTrack(audioStream
);
222 BSimpleGameSound::Init(const void* inData
, int64 inFrameCount
,
223 const gs_audio_format
* format
)
228 = Device()->CreateBuffer(&sound
, format
, inData
, inFrameCount
);
232 BGameSound::Init(sound
);
238 /* unimplemented for protection of the user:
240 * BSimpleGameSound::BSimpleGameSound()
241 * BSimpleGameSound &BSimpleGameSound::operator=(const BSimpleGameSound &)
246 BSimpleGameSound::_Reserved_BSimpleGameSound_0(int32 arg
, ...)
253 BSimpleGameSound::_Reserved_BSimpleGameSound_1(int32 arg
, ...)
260 BSimpleGameSound::_Reserved_BSimpleGameSound_2(int32 arg
, ...)
267 BSimpleGameSound::_Reserved_BSimpleGameSound_3(int32 arg
, ...)
274 BSimpleGameSound::_Reserved_BSimpleGameSound_4(int32 arg
, ...)
281 BSimpleGameSound::_Reserved_BSimpleGameSound_5(int32 arg
, ...)
288 BSimpleGameSound::_Reserved_BSimpleGameSound_6(int32 arg
, ...)
295 BSimpleGameSound::_Reserved_BSimpleGameSound_7(int32 arg
, ...)
302 BSimpleGameSound::_Reserved_BSimpleGameSound_8(int32 arg
, ...)
309 BSimpleGameSound::_Reserved_BSimpleGameSound_9(int32 arg
, ...)
316 BSimpleGameSound::_Reserved_BSimpleGameSound_10(int32 arg
, ...)
323 BSimpleGameSound::_Reserved_BSimpleGameSound_11(int32 arg
, ...)
330 BSimpleGameSound::_Reserved_BSimpleGameSound_12(int32 arg
, ...)
337 BSimpleGameSound::_Reserved_BSimpleGameSound_13(int32 arg
, ...)
344 BSimpleGameSound::_Reserved_BSimpleGameSound_14(int32 arg
, ...)
351 BSimpleGameSound::_Reserved_BSimpleGameSound_15(int32 arg
, ...)
358 BSimpleGameSound::_Reserved_BSimpleGameSound_16(int32 arg
, ...)
365 BSimpleGameSound::_Reserved_BSimpleGameSound_17(int32 arg
, ...)
372 BSimpleGameSound::_Reserved_BSimpleGameSound_18(int32 arg
, ...)
379 BSimpleGameSound::_Reserved_BSimpleGameSound_19(int32 arg
, ...)
386 BSimpleGameSound::_Reserved_BSimpleGameSound_20(int32 arg
, ...)
393 BSimpleGameSound::_Reserved_BSimpleGameSound_21(int32 arg
, ...)
400 BSimpleGameSound::_Reserved_BSimpleGameSound_22(int32 arg
, ...)
407 BSimpleGameSound::_Reserved_BSimpleGameSound_23(int32 arg
, ...)