Skip to content

Commit ab94dbb

Browse files
committed
[[ Bug 12885 ]] Initial API for PlatformSoundRecorder - TODO-RECORDER marks the places in the engine where they need to be used.
1 parent c6eb5ad commit ab94dbb

File tree

10 files changed

+124
-1
lines changed

10 files changed

+124
-1
lines changed

engine/src/answer.cpp

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -425,8 +425,13 @@ Exec_errors MCAnswer::exec_effect(MCExecPoint& ep, const char *p_title)
425425
Exec_errors MCAnswer::exec_record(MCExecPoint& ep, const char *p_title)
426426
{
427427
MCresult -> clear(False);
428+
429+
#ifdef FEATURE_PLATFORM_RECORDER
430+
// TODO-RECORDER: Implement using MCPlatformSoundRecorder.
431+
#else
428432
extern void MCQTRecordDialog(MCExecPoint& ep, const char *p_title, Boolean sheet);
429433
MCQTRecordDialog(ep, p_title, sheet);
434+
#endif
430435
return EE_UNDEFINED;
431436
}
432437
#endif /* MCAnswer::exec_record */

engine/src/cmdsc.cpp

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1925,8 +1925,13 @@ Exec_stat MCRecord::exec(MCExecPoint &ep)
19251925
}
19261926
char *soundfile = MCS_get_canonical_path(ep.getcstring());
19271927

1928+
#ifdef FEATURE_PLATFORM_RECORDER
1929+
// TODO-RECORD: Implement using MCPlatformSoundRecorder.
1930+
#else
19281931
extern void MCQTRecordSound(char *soundfile);
19291932
MCQTRecordSound(soundfile);
1933+
#endif
1934+
19301935
return ES_NORMAL;
19311936
#endif /* MCRecord */
19321937
}

engine/src/cmdse.cpp

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2265,8 +2265,12 @@ Exec_stat MCStop::exec(MCExecPoint &ep)
22652265
MCU_play_stop();
22662266
break;
22672267
case SC_RECORDING:
2268-
extern void MCQTStopRecording(void);
2268+
#ifdef FEATURE_PLATFORM_RECORDER
2269+
// TODO-RECORDER: Implement using MCPlatformSoundRecorder
2270+
#else
2271+
extern void MCQTStopRecording(void);
22692272
MCQTStopRecording();
2273+
#endif
22702274
break;
22712275
case SC_USING:
22722276
{

engine/src/desktop-dc.cpp

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -831,6 +831,7 @@ Boolean MCScreenDC::wait(real8 duration, Boolean dispatch, Boolean anyevent)
831831
else if (!done && eventtime > curtime)
832832
t_sleep = MCMin(eventtime - curtime, exittime - curtime);
833833

834+
#ifndef FEATURE_PLATFORM_RECORDER
834835
#ifdef FEATURE_QUICKTIME_EFFECTS
835836
// If we are recording, then poke QT (if enabled) and reduce sleep.
836837
if (MCrecording)
@@ -839,6 +840,7 @@ Boolean MCScreenDC::wait(real8 duration, Boolean dispatch, Boolean anyevent)
839840
MCQTHandleRecord();
840841
t_sleep = MCMin(0.1, t_sleep);
841842
}
843+
#endif
842844
#endif
843845

844846
// IM-2014-06-25: [[ Bug 12671 ]] If there are runloop actions then set a timeout instead of waiting for the next event

engine/src/funcs.cpp

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1909,17 +1909,29 @@ Exec_stat MCQTEffects::eval(MCExecPoint &ep)
19091909
Exec_stat MCRecordCompressionTypes::eval(MCExecPoint &ep)
19101910
{
19111911
#ifdef /* MCRecordCompressionTypes */ LEGACY_EXEC
1912+
1913+
#ifdef FEATURE_PLATFORM_RECORDER
1914+
// TODO-RECORDER: Implement using MCPlatformSoundRecorder - the format is list of 'label,id'.
1915+
#else
19121916
extern void MCQTGetRecordCompressionList(MCExecPoint& ep);
19131917
MCQTGetRecordCompressionList(ep);
1918+
#endif
1919+
19141920
return ES_NORMAL;
19151921
#endif /* MCRecordCompressionTypes */
19161922
}
19171923

19181924
Exec_stat MCRecordLoudness::eval(MCExecPoint &ep)
19191925
{
19201926
#ifdef /* MCRecordLoudness */ LEGACY_EXEC
1927+
1928+
#ifdef FEATURE_PLATFORM_RECORDER
1929+
// TODO-RECORDER: Implement using MCPlatformSoundRecorder.
1930+
#else
19211931
extern void MCQTGetRecordLoudness(MCExecPoint& ep);
19221932
MCQTGetRecordLoudness(ep);
1933+
#endif
1934+
19231935
return ES_NORMAL;
19241936
#endif /* MCRecordLoudness */
19251937
}

engine/src/globals.cpp

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1025,11 +1025,15 @@ int X_close(void)
10251025
MCselected->clear(False);
10261026

10271027
MCU_play_stop();
1028+
#ifdef FEATURE_PLATFORM_RECORDER
1029+
// TODO-RECORDER: Implement using MCPlatformSoundRecorder
1030+
#else
10281031
if (MCrecording)
10291032
{
10301033
extern void MCQTStopRecording(void);
10311034
MCQTStopRecording();
10321035
}
1036+
#endif
10331037
MClockmessages = True;
10341038
MCS_killall();
10351039

engine/src/platform.h

Lines changed: 84 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1103,6 +1103,90 @@ void MCPlatformSoundGetProperty(MCPlatformSoundRef sound, MCPlatformSoundPropert
11031103

11041104
////////////////////////////////////////////////////////////////////////////////
11051105

1106+
// Implementation guidence:
1107+
//
1108+
// This is basic abstraction of the sound recording functionality which the
1109+
// engine currently has.
1110+
//
1111+
// The platform sound recorder opaque type should be a procedural wrapper around
1112+
// a class which implements an abstract interface (just like the PlatformPlayer).
1113+
//
1114+
// Initially we need an implementation using the QT Sequence Grabber which needs
1115+
// to use the SGAudioMediaType (essentially this means that the code in the engine
1116+
// already for this is not usable - its heavily tied to SoundMediaType which
1117+
// crashes on modern Mac's).
1118+
//
1119+
// There is a sample code project 'WhackedTV' which should be useful to base the
1120+
// implementation on. This project goes a bit further than we need though - our
1121+
// dialog only needs to be the QT one provided by SCRequestImageSettings so that
1122+
// should hopefully simplify things.
1123+
//
1124+
// The SoundRecorder object should hold all the necessary system state to operate
1125+
// and whilst recording should ensure that things are idled appropriately using
1126+
// a Cocoa timer rather than requiring the engine to call an idle-proc (which is
1127+
// what is currently required).
1128+
//
1129+
1130+
typedef struct MCPlatformSoundRecorder *MCPlatformSoundRecorderRef;
1131+
1132+
struct MCPlatformSoundRecorderConfiguration
1133+
{
1134+
// The input to use for sound recording - this should be an id as returned by ListInputs.
1135+
unsigned int input;
1136+
// The sample rate for recording.
1137+
double sample_rate;
1138+
// The number of bits per sample.
1139+
unsigned int sample_bit_count;
1140+
// The number of channels.
1141+
unsigned int channel_count;
1142+
// The compressor to use - this should be an id as returned by ListCompressors.
1143+
unsigned int compression_type;
1144+
// Any extra info specific to a compressor - this is an opaque sequence of bytes. If nil
1145+
// when setting configuration, per-compressor defaults should be used.
1146+
uint8_t *extra_info;
1147+
size_t extra_info_size;
1148+
};
1149+
1150+
typedef bool (*MCPlatformSoundRecorderListInputsCallback)(void *context, unsigned int input_id, const char *label);
1151+
typedef bool (*MCPlatformSoundRecorderListCompressorsCallback)(void *context, unsigned int compressor_id, const char *label);
1152+
1153+
void MCPlatformSoundRecorderCreate(MCPlatformSoundRecorderRef& r_recorder);
1154+
1155+
void MCPlatformSoundRecorderRetain(MCPlatformSoundRecorderRef recorder);
1156+
void MCPlatformSoundRecorderRelease(MCPlatformSoundRecorderRef recorder);
1157+
1158+
// Return true if the recorder is recording.
1159+
bool MCPlatformSoundRecorderIsRecording(MCPlatformSoundRecorderRef recorder);
1160+
1161+
// Return the current volume of the recorded input - if not recording, return 0.
1162+
double MCPlatformSoundRecorderGetLoudness(MCPlatformSoundRecorderRef recorder);
1163+
1164+
// Start sound recording to the given file. If the sound recorder is already recording then
1165+
// the existing recording should be cancelled (stop and delete output file).
1166+
bool MCPlatformSoundRecorderStart(MCPlatformSoundRecorderRef recorder, const char *filename);
1167+
// Stop the sound recording.
1168+
void MCPlatformSoundRecorderStop(MCPlatformSoundRecorderRef recorder);
1169+
1170+
// Call callback for each possible input device available - if the callback returns 'false' at any point
1171+
// enumeration is cancelled, and the false will be returned.
1172+
bool MCPlatformSoundRecorderListInputs(MCPlatformSoundRecorderRef recorder, MCPlatformSoundRecorderListInputsCallback callback, void *context);
1173+
// Call callback for each possible compressor available - if the callback returns 'false' at any point
1174+
// enumeration is cancelled, and the false will be returned.
1175+
bool MCPlatformSoundRecorderListCompressors(MCPlatformSoundRecorderRef recorder, MCPlatformSoundRecorderListCompressorsCallback callback, void *context);
1176+
1177+
// Get the current sound recording configuration. The caller is responsible for freeing 'extra_info'.
1178+
void MCPlatformSoundRecorderGetConfiguration(MCPlatformSoundRecorderRef recorder, MCPlatformSoundRecorderConfiguration& r_config);
1179+
// Set the current sound recording configuration.
1180+
void MCPlatformSoundRecorderSetConfiguration(MCPlatformSoundRecorderRef recorder, const MCPlatformSoundRecorderConfiguration& config);
1181+
1182+
// Popup a configuration dialog for the compressors. If the dialog is not cancelled the
1183+
// sound recorders config will have been updated.
1184+
void MCPlatformSoundRecorderBeginConfigurationDialog(MCPlatformSoundRecorderRef recorder);
1185+
// End the configuration dialog.
1186+
MCPlatformDialogResult MCPlatformSoundRecorderEndConfigurationDialog(MCPlatformSoundRecorderRef recorder);
1187+
1188+
////////////////////////////////////////////////////////////////////////////////
1189+
11061190
void MCPlatformSwitchFocusToView(MCPlatformWindowRef window, uint32_t id);
11071191

11081192
////////////////////////////////////////////////////////////////////////////////

engine/src/property.cpp

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2240,8 +2240,12 @@ Exec_stat MCProperty::set(MCExecPoint &ep)
22402240
return ES_ERROR;
22412241
if (!trecording)
22422242
{
2243+
#ifdef FEATURE_PLATFORM_RECORDER
2244+
// TODO-RECORDER: Implement using MCPlatformSoundRecorder
2245+
#else
22432246
extern void MCQTStopRecording(void);
22442247
MCQTStopRecording();
2248+
#endif
22452249
}
22462250
}
22472251
break;

engine/src/quicktime.cpp

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -172,6 +172,7 @@ void MCQTGetVersion(MCExecPoint& ep)
172172

173173
////////////////////////////////////////////////////////////////////////////////
174174

175+
#ifndef FEATURE_PLATFORM_RECORDER
175176
// Related class variables
176177
static void *sgSoundComp = NULL;
177178
static long sgSndDriver = 0;
@@ -554,6 +555,7 @@ void MCQTRecordDialog(MCExecPoint& ep, const char *p_title, Boolean sheet)
554555
}
555556
CloseComponent(ci);
556557
}
558+
#endif
557559

558560
////////////////////////////////////////////////////////////////////////////////
559561

engine/src/sysdefs.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -52,6 +52,7 @@ along with LiveCode. If not see <http://www.gnu.org/licenses/>. */
5252
#define FEATURE_TASKBAR_ICON
5353
#define FEATURE_QUICKTIME_EFFECTS
5454
#define FEATURE_PLATFORM_PLAYER
55+
#define FEATURE_PLATFORM_RECORDER
5556
#define FEATURE_PLATFORM_AUDIO
5657

5758
#elif defined(_LINUX_DESKTOP)

0 commit comments

Comments
 (0)