Skip to content
GitLab
Menu
Projects
Groups
Snippets
Loading...
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Sign in
Toggle navigation
Menu
Open sidebar
Libretro
retro8
Commits
1b209238
Commit
1b209238
authored
Dec 17, 2019
by
Jack
Browse files
working on music structure in memory, in APU and loading from .p8 file
parent
53600f43
Changes
7
Hide whitespace changes
Inline
Side-by-side
src/io/loader.cpp
View file @
1b209238
...
...
@@ -65,7 +65,7 @@ void LoaderP8::load(const std::string& path, Machine& m)
//TODO: not efficient but for now it's fine
std
::
stringstream
code
;
coord_t
sy
=
0
,
my
=
0
,
fy
=
0
,
snd
=
0
;
coord_t
sy
=
0
,
my
=
0
,
fy
=
0
,
snd
=
0
,
msc
=
0
;
static
constexpr
size_t
DIGITS_PER_PIXEL_ROW
=
128
;
static
constexpr
size_t
BYTES_PER_GFX_ROW
=
DIGITS_PER_PIXEL_ROW
/
2
;
...
...
@@ -74,6 +74,7 @@ void LoaderP8::load(const std::string& path, Machine& m)
static
constexpr
size_t
DIGITS_PER_SPRITE_FLAGS_ROW
=
128
*
2
;
static
constexpr
size_t
DIGITS_PER_SOUND
=
168
;
static
constexpr
size_t
DIGITS_PER_MUSIC_PATTERN
=
2
+
1
+
8
;
for
(
auto
&
line
:
lines
)
...
...
@@ -167,7 +168,41 @@ void LoaderP8::load(const std::string& path, Machine& m)
break
;
}
case
State
::
MUSIC
:
{
const
char
*
p
=
line
.
c_str
();
if
(
!
line
.
empty
())
{
sfx
::
Music
*
music
=
m
.
memory
().
music
(
msc
);
/* XX AABBCCDD*/
constexpr
sfx
::
sound_index_t
UNUSED_CHANNEL
=
0x40
;
uint8_t
flags
=
valueForUint8
(
p
);
if
(
flags
&
0b1
)
music
->
markLoopBegin
();
else
if
(
flags
&
0b10
)
music
->
markLoopEnd
();
else
if
(
flags
&
0b100
)
music
->
markStop
();
for
(
sfx
::
channel_index_t
i
=
0
;
i
<
sfx
::
APU
::
CHANNEL_COUNT
;
++
i
)
{
sfx
::
sound_index_t
index
=
valueForUint8
(
p
+
3
+
2
*
i
);
if
(
index
<
UNUSED_CHANNEL
)
music
->
setSound
(
i
,
index
);
else
assert
(
index
==
UNUSED_CHANNEL
+
i
);
}
++
msc
;
}
break
;
}
}
}
}
...
...
src/sdl_helper.h
View file @
1b209238
...
...
@@ -23,6 +23,7 @@ protected:
bool
willQuit
;
u32
ticks
;
float
_lastFrameTicks
;
u32
frameRate
;
float
ticksPerFrame
;
...
...
@@ -41,6 +42,8 @@ public:
this
->
ticksPerFrame
=
1000
/
(
float
)
frameRate
;
}
float
lastFrameTicks
()
const
{
return
_lastFrameTicks
;
}
bool
init
();
void
deinit
();
void
capFPS
();
...
...
@@ -111,14 +114,12 @@ void SDL<EventHandler, Renderer>::capFPS()
u32
ticks
=
SDL_GetTicks
();
u32
elapsed
=
ticks
-
SDL
::
ticks
;
//printf("Ticks: %u, waiting %f ticks, aticks: %u\n", elapsed, TICKS_PER_FRAME - elapsed, Gfx::fticks);
u32
frameTime
=
elapsed
;
_lastFrameTicks
=
elapsed
;
if
(
elapsed
<
ticksPerFrame
)
{
SDL_Delay
(
ticksPerFrame
-
elapsed
);
f
rameTi
me
=
ticksPerFrame
;
_lastF
rameTi
cks
=
ticksPerFrame
;
}
SDL
::
ticks
=
SDL_GetTicks
();
...
...
src/views/game_view.cpp
View file @
1b209238
...
...
@@ -10,7 +10,8 @@ namespace r8 = retro8;
retro8
::
Machine
machine
;
GameView
::
GameView
(
ViewManager
*
manager
)
:
manager
(
manager
),
_paused
(
false
)
GameView
::
GameView
(
ViewManager
*
manager
)
:
manager
(
manager
),
_paused
(
false
),
_showFPS
(
false
),
_showCartridgeName
(
false
)
{
}
...
...
@@ -151,10 +152,6 @@ void GameView::render()
SDL_UpdateTexture
(
_outputTexture
,
nullptr
,
_output
->
pixels
,
_output
->
pitch
);
}
text
(
_path
,
2
,
2
);
SDL_Rect
dest
;
//SDL_Texture* texture = SDL_CreateTextureFromSurface(renderer, machine.screen());
#ifdef _WIN32
...
...
@@ -169,6 +166,11 @@ else
dest
=
{
0
,
0
,
320
,
240
};
#endif
text
(
_path
.
c_str
(),
10
,
10
);
char
buffer
[
16
];
sprintf
(
buffer
,
"%.0f"
,
1000.0
f
/
manager
->
lastFrameTicks
());
text
(
buffer
,
10
,
22
);
SDL_RenderCopy
(
renderer
,
_outputTexture
,
nullptr
,
&
dest
);
#if DEBUGGER
...
...
@@ -213,10 +215,8 @@ else
SDL_RenderCopy
(
renderer
,
texture
,
nullptr
,
&
destr
);
SDL_DestroyTexture
(
texture
);
SDL_FreeSurface
(
palettes
);
}
/* palette */
{
/*static SDL_Surface* tilemap = nullptr;
...
...
@@ -256,12 +256,13 @@ else
void
GameView
::
text
(
const
std
::
string
&
text
,
int32_t
x
,
int32_t
y
)
{
constexpr
float
scale
=
2.0
;
constexpr
int32_t
GLYPHS_PER_ROW
=
16
;
for
(
size_t
i
=
0
;
i
<
text
.
length
();
++
i
)
{
SDL_Rect
src
=
{
8
*
(
i
%
GLYPHS_PER_ROW
),
8
*
(
i
/
GLYPHS_PER_ROW
),
4
,
6
};
SDL_Rect
dest
=
{
x
+
4
*
i
,
y
,
4
,
6
};
SDL_Rect
src
=
{
8
*
(
text
[
i
]
%
GLYPHS_PER_ROW
),
8
*
(
text
[
i
]
/
GLYPHS_PER_ROW
),
4
,
6
};
SDL_Rect
dest
=
{
x
+
4
*
i
*
scale
,
y
,
4
*
scale
,
6
*
scale
};
SDL_RenderCopy
(
manager
->
renderer
(),
_font
,
&
src
,
&
dest
);
}
}
...
...
src/views/main_view.h
View file @
1b209238
...
...
@@ -35,7 +35,9 @@ namespace ui
bool
_paused
;
void
rasterize
();
bool
_showFPS
;
bool
_showCartridgeName
;
void
render
();
void
update
();
...
...
src/vm/memory.h
View file @
1b209238
...
...
@@ -68,6 +68,7 @@ namespace retro8
integral_t
*
cartData
(
index_t
idx
)
{
return
as
<
integral_t
>
(
address
::
CART_DATA
+
idx
*
sizeof
(
integral_t
));
}
//TODO: ENDIANNESS!!
sfx
::
Sound
*
sound
(
sfx
::
sound_index_t
i
)
{
return
as
<
sfx
::
Sound
>
(
address
::
SOUNDS
+
sizeof
(
sfx
::
Sound
)
*
i
);
}
sfx
::
Music
*
music
(
sfx
::
music_index_t
i
)
{
return
as
<
sfx
::
Music
>
(
address
::
MUSIC
+
sizeof
(
sfx
::
Music
)
*
i
);
}
sprite_flags_t
*
spriteFlagsFor
(
sprite_index_t
index
)
{
...
...
src/vm/sound.cpp
View file @
1b209238
...
...
@@ -274,6 +274,7 @@ void APU::handleCommands()
if
(
c
.
channel
>=
0
&&
c
.
channel
<
channels
.
size
()
&&
c
.
index
>=
0
&&
c
.
index
<=
SOUND_COUNT
)
{
/* overtaking channel */
auto
&
channel
=
channels
[
c
.
channel
];
channel
.
soundIndex
=
c
.
index
;
...
...
@@ -294,6 +295,22 @@ void APU::handleCommands()
/* stop sound on channel*/
}
void
APU
::
updateMusic
()
{
if
(
music
.
music
)
{
for
(
channel_index_t
i
=
0
;
i
<
CHANNEL_COUNT
;
++
i
)
{
/* will use channel if channel is forced or there's no sound currently playing there */
bool
willUseChannel
=
((
music
.
channelMask
&
(
1
<<
i
))
!=
0
)
||
!
channels
[
i
].
sound
;
}
}
}
void
APU
::
renderSounds
(
int16_t
*
dest
,
size_t
totalSamples
)
{
handleCommands
();
...
...
src/vm/sound.h
View file @
1b209238
...
...
@@ -21,6 +21,7 @@ namespace retro8
using
frequency_t
=
int32_t
;
using
channel_index_t
=
int32_t
;
using
sound_index_t
=
int32_t
;
using
music_index_t
=
int32_t
;
enum
class
Waveform
{
...
...
@@ -60,11 +61,11 @@ namespace retro8
//TODO: endianness is a fail here
uint16_t
value
;
bool
useSfx
()
const
{
return
value
&
0x8000
;
}
Effect
effect
()
const
{
return
Effect
((
value
&
EffectMask
)
>>
EffectShift
);
}
Waveform
waveform
()
const
{
return
Waveform
((
value
&
WaveformMask
)
>>
WaveformShift
);
}
volume_t
volume
()
const
{
return
(
value
&
VolumeMask
)
>>
VolumeShift
;
}
pitch_t
pitch
()
const
{
return
value
&
PitchMask
;
}
inline
bool
useSfx
()
const
{
return
value
&
0x8000
;
}
inline
Effect
effect
()
const
{
return
Effect
((
value
&
EffectMask
)
>>
EffectShift
);
}
inline
Waveform
waveform
()
const
{
return
Waveform
((
value
&
WaveformMask
)
>>
WaveformShift
);
}
inline
volume_t
volume
()
const
{
return
(
value
&
VolumeMask
)
>>
VolumeShift
;
}
inline
pitch_t
pitch
()
const
{
return
value
&
PitchMask
;
}
void
setPitch
(
pitch_t
pitch
)
{
value
=
(
value
&
~
PitchMask
)
|
pitch
;
}
void
setVolume
(
volume_t
volume
)
{
value
=
(
value
&
~
VolumeMask
)
|
(
volume
<<
VolumeShift
);
}
...
...
@@ -83,7 +84,27 @@ namespace retro8
struct
Music
{
uint8_t
dummy
[
4
];
private:
constexpr
static
uint8_t
SOUND_INDEX_MASK
=
0xb00111111
;
constexpr
static
uint8_t
CONFIG_MASK
=
0xb11000000
;
constexpr
static
uint8_t
SOUND_ON_FLAG
=
0b01000000
;
constexpr
static
uint8_t
LOOP_FLAG
=
0b10000000
;
std
::
array
<
uint8_t
,
4
>
indices
;
public:
void
setSound
(
channel_index_t
channel
,
sound_index_t
index
)
{
indices
[
channel
]
=
(
indices
[
channel
]
&
CONFIG_MASK
)
|
index
|
SOUND_ON_FLAG
;
}
void
markLoopBegin
()
{
indices
[
0
]
|=
LOOP_FLAG
;
}
void
markLoopEnd
()
{
indices
[
1
]
|=
LOOP_FLAG
;
}
void
markStop
()
{
indices
[
2
]
|=
LOOP_FLAG
;
}
inline
bool
isLoopBegin
()
const
{
return
(
indices
[
0
]
&
LOOP_FLAG
)
!=
0
;
}
inline
bool
isLoopEnd
()
const
{
return
(
indices
[
1
]
&
LOOP_FLAG
)
!=
0
;
}
inline
bool
isStop
()
const
{
return
(
indices
[
2
]
&
LOOP_FLAG
)
!=
0
;
}
inline
bool
isChannelEnabled
(
channel_index_t
channel
)
{
return
(
indices
[
channel
]
&
SOUND_ON_FLAG
)
!=
0
;
}
sound_index_t
sound
(
channel_index_t
channel
)
const
{
return
indices
[
channel
]
&
SOUND_INDEX_MASK
;
}
};
using
sound_t
=
Sound
;
...
...
@@ -101,6 +122,14 @@ namespace retro8
uint32_t
position
;
// absolute
uint32_t
end
;
};
struct
MusicState
{
std
::
array
<
SoundState
,
4
>
channels
;
Music
*
music
;
music_index_t
pattern
;
uint8_t
channelMask
;
};
class
DSP
{
...
...
@@ -125,6 +154,10 @@ namespace retro8
class
APU
{
public:
static
constexpr
size_t
CHANNEL_COUNT
=
4
;
private:
retro8
::
Memory
&
memory
;
struct
Command
...
...
@@ -135,17 +168,21 @@ namespace retro8
uint32_t
end
;
};
static
constexpr
size_t
CHANNEL_COUNT
=
4
;
SDL_AudioSpec
spec
;
SDL_AudioDeviceID
device
;
std
::
array
<
SoundState
,
CHANNEL_COUNT
>
channels
;
MusicState
music
;
std
::
mutex
queueMutex
;
std
::
vector
<
Command
>
queue
;
void
handleCommands
();
void
updateMusic
();
public:
APU
(
Memory
&
memory
)
:
memory
(
memory
)
{
}
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
.
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment