📄 unamsacmclasses.pas
字号:
f_srcFormat: pWAVEFORMATEX;
f_dstFormat: pWAVEFORMATEX;
//
f_event: unaEvent;
f_openCloseEvent: unaEvent;
f_dataInEvent: unaEvent;
f_dataOutEvent: unaEvent;
f_gate: unaInProcessGate;
//
f_inStream: unaAbstractStream;
f_outStream: unaAbstractStream;
f_headers: unaObjectList;
f_consumers: unaList;
f_notifyDevices: unaList;
//
// -- silence detection
f_minAT: unsigned;
f_minVL: unsigned;
f_timeActive: unsigned;
//
f_isSilence: bool;
f_isSilencePrev: bool;
f_isSilenceFirstTime: bool;
f_passThrough: bool;
//
{$IFDEF UNA_VC_ACMCLASSES_USE_DSP }
f_dspl: unaDspDLibRoot;
f_dsplAutoLD: unaDSPLibAutomat;
f_dsplAutoND: unaDSPLibAutomat;
f_dsplObjLD: dspl_handle;
f_dsplObjND: dspl_handle;
//
f_dsplOutBufLD: unaDspSignalData;
f_dsplOutBufND: unaDspSignalData;
f_dsplOutBufLDSize: unaDspSignalDataSize;
f_dsplOutBufNDSize: unaDspSignalDataSize;
f_outBufValid: bool;
{$ENDIF }
//
f_sdm: unaWaveInSDMehtods;
//
f_onThreshold: unaWaveInOnThresholdEvent;
//
procedure setMinVL(value: unsigned);
// silence detection --
//
function internalWrite(buf: pointer; size: unsigned): unsigned;
{DP:METHOD
Reads size bytes from internal buffer into buf. Returns number of bytes actually read.
}
function internalRead(buf: pointer; size: unsigned): unsigned;
procedure destroyStream(isInStream: bool);
procedure notifyRemove();
procedure addNotification(device: unaMsAcmStreamDevice);
procedure removeNotification(device: unaMsAcmStreamDevice);
//
function getNextHeaderNum(): unsigned;
function adjustLastDoneHeaderNum(num: unsigned): bool;
function locateHeaderTry(header: unaMsAcmDeviceHeader; locateUnused: bool = false; locateNotInQuery: bool = false): bool;
function locateHeader(locateUnused: bool = false; locateNotInQuery: bool = false): unaMsAcmDeviceHeader;
procedure clearHeaders();
procedure setCalcVolume(const Value: bool);
function formatChoose(var format: pWAVEFORMATEX; const title: string; style: unsigned; enumFlag: unsigned; enumFormat: pWAVEFORMATEX = nil): MMRESULT;
//
procedure setInOverCN(value: unsigned);
procedure setOutOverCN(value: unsigned);
//
function checkSilence(data: pointer; len: uint): bool;
protected
{DP:METHOD
Sets the source or destination PCM format for device. Format is given in string representation using base64 encoding.
}
function setFormat(isSrc: bool; const format: string): bool;
{DP:METHOD
Sets the source or destination PCM format for device. Format is given as WAVEFORMATEX structure.
}
function setFormatEx(isSrc: bool; const format: WAVEFORMATEX): bool; virtual;
//
{DP:METHOD
Opens device. This method is usually overrided by descendant classes to perform the actual job.
}
function doOpen(flags: unsigned): MMRESULT; virtual;
function open2(query: bool = false; timeout: unsigned = 10000; flags: unsigned = 0): MMRESULT; virtual;
{DP:METHOD
Closes device. This method is usually overrided by descendant classes to perform the actual job.
}
function doClose(timeout: unsigned = 1): MMRESULT; virtual;
{DP:METHOD
Uses mmGetErrorCodeText2() to produce the error message.
Other devices could have own doGetErrorText() implementation.
}
function doGetErrorText(errorCode: MMRESULT): string; virtual;
{}
function doGetPosition(): int64; virtual;
{DP:METHOD
Performs initial actions for new chunk of data, such as volume level calculation.
}
function beforeNewChunk(data: pointer; size: unsigned): bool; virtual;
//
{DP:METHOD
Prepares the buffer header before first use. Descendant classes must override this method.
}
function prepareHeader(header: unaMsAcmDeviceHeader): MMRESULT; virtual; abstract;
{DP:METHOD
Unprepares the buffer header after last use. Descendant classes must override this method.
}
function unprepareHeader(header: unaMsAcmDeviceHeader): MMRESULT; virtual; abstract;
//
{DP:METHOD
Called after the device was opened. Descendant classes may override this method to perform additional actions required by hardware/software.
}
function afterOpen(): MMRESULT; virtual;
procedure afterClose(closeResult: MMRESULT); virtual;
function close2(timeout: unsigned = 10000): MMRESULT; virtual;
//
procedure startIn(); override;
procedure startOut(); override;
//
function flush2(waitForComplete: bool = true): bool; virtual;
//
function getMasterIsSrc2(): bool; virtual; abstract;
function formatChooseDef2(var format: pWAVEFORMATEX): MMRESULT; dynamic;
//
procedure setRealTime(value: bool); virtual;
//
property dstChunkSize: unsigned read f_dstChunkSize;
//
public
{DP:METHOD
Initializates class instance.
}
constructor create(createInStream: bool = true; createOutStream: bool = true; inOverNum: unsigned = 0; outOverNum: unsigned = 0; calcVolume: bool = false);
destructor Destroy(); override;
procedure AfterConstruction(); override;
procedure BeforeDestruction(); override;
{DP:METHOD
Opens the device.
}
function open(query: bool = false; timeout: unsigned = 10000; flags: unsigned = 0): MMRESULT;
{DP:METHOD
Closes the device.
}
function close(timeout: unsigned = 10000): MMRESULT;
{DP:METHOD
Returns true if device was opened successfully.
}
function isOpen(): bool;
//
{DP:METHOD
Returns current volume level for open device.
Volume range is from 0 to 32768.
}
function getVolume(channel: unsigned = 0): unsigned;
{DP:METHOD
Returns previous volume level for open device.
}
function getPrevVolume(channel: unsigned = 0): unsigned;
//
procedure setDspProperty(isLD: bool; propID: uint; value: int); overload;
procedure setDspProperty(isLD: bool; propID: uint; const value: float); overload;
function getDspProperty(isLD: bool; propID: uint; def: int = 0): int; overload;
function getDspProperty(isLD: bool; propID: uint; const def: float = 0.0): float; overload;
//
{DP:METHOD
Use this method to check if you can read new data from device.
}
function okToRead(): bool;
{DP:METHOD
Returns current position in samples.
}
function getPosition(): int64;
//
{DP:METHOD
Reads data from device.
Returns size of actual returned data.
Specify 0 as size parameter value when reading from ACM codec device.
}
function read(buf: pointer; size: unsigned = 0): unsigned;
{DP:METHOD
Sends data to device.
}
function write(buf: pointer; size: unsigned): unsigned;
//
function flush(waitForComplete: bool = true): bool;
{DP:METHOD
Returns number of bytes available to read from the device.
}
function getDataAvailable(isIn: bool): unsigned;
{DP:METHOD
Returns true if device is output device (playback or codec).
Returns false if device is input device (recording).
}
function getMasterIsSrc(): bool;
//
{DP:METHOD
Assigns input or output stream for device.
You can specify nil as stream to disable the input/output.
If you wish the device to destroy the stream in own destructor - specify true in careDestroy parameter.
}
function assignStream(isInStream: bool; stream: unaAbstractStream; careDestroy: bool = false): unaAbstractStream; overload;
{DP:METHOD
Assigns input or output stream for device.
Stream will be created using the provided stream class.
If you wish the device to destroy the stream in own destructor - specify true in careDestroy parameter.
}
function assignStream(streamClass: unaAbstractStreamClass; isInStream: bool; careDestroy: bool = true): unaAbstractStream; overload;
{DP:METHOD
Adds a new consumer for device output.
All data produced by device will be passed to all consumers added by this method.
If you wish to destroy the output stream leave the default true value for removeOutStream parameter.
(Stream will be destroyed only if it was not a stream assigned by assignStream() with careDestroy = false).
}
function addConsumer(device: unaMsAcmStreamDevice; removeOutStream: bool = true): unsigned;
{DP:METHOD
Removes consumer from consumers list.
}
function removeConsumer(device: unaMsAcmStreamDevice): bool;
//
{DP:METHOD
Default implementation of format choosing routine.
}
function formatChooseDef(var format: pWAVEFORMATEX): MMRESULT;
{DP:METHOD
Returns error message text corresponding to given errorCode parameter.
}
function getErrorText(errorCode: MMRESULT): string;
//
{DP:METHOD
Size in bytes of internal buffer used to handle the audio stream data.
}
property chunkSize: unsigned read f_chunkSize;
{DP:METHOD
Specifies number of chunks produced by component per second.
Note, that not all components are working in real time, in which case this property has no meaning.
Readonly property, change the global c_defChunksPerSecond variable if you wish to change this number.
}
property chunkPerSecond: unsigned read f_chunkPerSecond;
{DP:METHOD
Specifies whether volume level calculation should be performed.
Set to true if planning to use silence detection when silenceDetectionMode is set to unasdm_VC.
}
property calcVolume: bool read f_calcVolume write setCalcVolume;
//
{DP:METHOD
Number of bytes passed to device (as input). Playback and codec devices increase this value.
}
property inBytes: int64 read f_inBytes;
{DP:METHOD
Number of bytes produced by device (as output). Recording and codec devices increase this value.
}
property outBytes: int64 read f_outBytes;
{DP:METHOD
Returns source format for device.
}
property srcFormat: pWAVEFORMATEX read f_srcFormat;
{DP:METHOD
Returns destination format for device.
}
property dstFormat: pWAVEFORMATEX read f_dstFormat;
//
{DP:METHOD
Returns string representation of source format.
}
property srcFormatInfo: string read f_srcFormatInfo;
{DP:METHOD
Returns string representation of destination wave format.
}
property dstFormatInfo: string read f_dstFormatInfo;
//
{DP:METHOD
This event is set to signaled state every time new data was produced by device.
}
property dataEvent: unaEvent read f_dataOutEvent;
{DP:METHOD
Number of chunks passed to Windows ACM or wave device.
}
property inProgress: unsigned read f_inProgress;
//
{DP:METHOD
}
property realTime: bool read f_realTime write setRealTime;
property dataInEvent: unaEvent read f_dataInEvent;
{DP:METHOD
}
property overNumIn: unsigned read f_inOverCN write setInOverCN;
property inOverloadTotal: int64 read f_inOverloadTotal; // total amount of in-data skipped due to overload
{DP:METHOD
}
property overNumOut: unsigned read f_outOverCN write setOutOverCN;
property outOverloadTotal: int64 read f_outOverloadTotal; // total amount of out-data skipped due to overload
{DP:METHOD
Specifies whether component will flush unfinished data before closing.
}
property flushBeforeClose: bool read f_flushBeforeClose write f_flushBeforeClose;
{DP:METHOD
Specifies the minimum value of volume level for silence detection.
Has meaning only when silenceDetectionMode is set to unasdm_VC.
<BR />Set this property to 0 to disable the volume detection feature.
}
property minVolumeLevel: unsigned read f_minVL write setMinVL;
{DP:METHOD
Specifies the minimum amount of time (in milliseconds) for silence detection to be active once activated.
Has meaning only when silenceDetectionMode is set to unasdm_VC.
}
property minActiveTime: unsigned read f_minAT write f_minAT;
{DP:METHOD
Returns true if components is currently not producing any audio chunks due to low signal level.
}
property isSilence: bool read f_isSilence;
{DP:METHOD
Specifies which method will be used to detect silence.
<UL>
<LI>unasdm_none - no silence detection</LI>
<LI>unasdm_VC - "old" method, which uses minVolumeLevel and minActiveTime</LI>
<LI>unasdm_DSP</LI>
<UL>
}
property silenceDetectionMode: unaWaveInSDMehtods read f_sdm write f_sdm;
//
//-- events --
//
{DP:METHOD
This event is fired when current level of a signal is crossing specified threshold.
}
property onThreshold: unaWaveInOnThresholdEvent read f_onThreshold write f_onThreshold;
{DP:METHOD
This event is called when new data is available.
}
property onDataAvailable: unaWaveDataEvent read f_onDA write f_onDA;
end;
//
// -- unaMsAcmCodecHeader --
//
unaMsAcmCodec = class;
{DP:CLASS
This class stores the data used by MS ACM codec.
}
unaMsAcmCodecHeader = class(unaMsAcmDeviceHeader)
private
f_header: ACMSTREAMHEADER;
f_drvHeader: ACMDRVSTREAMHEADER;
//
{$IFDEF UNA_VC_USE_GLOBAL_MEM }
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -