Cisco IP电话软件的WINRTP
?
縱覽Overview of this Document
介紹Introduction
更新What's New
功能Features
組件及安裝Components and Installation
源碼發布Source Code Distribution
二進制發布Binary Distribution
安裝Installation
測試程序Test Program
接口描述/程序員指南Interface Description/Programmer’s Guide
WINRTP COM?接口WINRTP COM Interface
WINRTP接口詳解(ICCNMedia)Details of WINRTP Interface (Interface ICCNMediaTerm)
COM的GUID?COM GUIDs, etc
可選參數?Configurable Parameters
靜態/動態 抖動緩沖器?Static/Dynamic Jitter Buffer
抖動緩沖區大小Jitter Buffer Length
接收的RTP音頻流放大等級?Level of Auto-Amplification of incoming RTP audio streams
發送的RTP包的TOS值Type of Service Value (DiffServ Byte) of Outgoing RTP Packets
指定UDP傳輸端口Fixed Transmit Port for UDP Packets
發送音頻的預加重Pre-emphasis of transmitted audio
接受音頻的后加重Post-emphasis of received audio
音量限制Volume Limiting
示例代碼Sample Code
未來的改進Future Improvements
?
This document describes the?WinRTP?for the Cisco IP?SoftPhone?from a programmer’s point of view. It discusses the COM interface it provides, installation, and configuration of the component.
?此文檔以程序員的視角描述了用于Cisco IP電話軟件的WINRTP。它論述了WINRTP的COM接口、安裝以及各組件的配置。
介紹
The?WinRTP?(WINRTP) was developed as part of the Cisco IP?SoftPhone?product. Cisco IP?SoftPhone?is a PC based telephone integrated with AVVID, and works with the Cisco Call Manager. The primary focus of the WINRTP is to ensure that it works well with other products in AVVID including desktop IP Phones,?gateways,?etc.It?can also be used as an independent component.
·????????It?is written in C++
·????????It?is a COM component. (Not an ActiveX control). This makes it easy to use using any programming language like C/C++/Java (using J/Direct) etc.???
?開發WinRTP是作為Cisco IP?SoftPhone產品的一部分。Cisco IP?SoftPhone是基于個人電腦的集成AVVID的電話,它和Cisco Call Manager一起工作。WINRTP的主要目的是確保此產品同AVVID(語音、視頻和集成數據體系架構)良好的工作,包括桌面IP電話、網關等等。當然,它也可以作為單獨組件使用。
The basic job of the WINRTP is to source and sink audio streams to/from the network.?So if an application needs the ability to do audio?endpointing?for real time voice (especially one that is integrated with Cisco’s AVVID), it can use this component.
?WINRTP最基礎的工作是發起和接收網絡上的音頻流。如果一個應用軟件需要實時語音的支持(特別是當它集成了Cisco的AVVID),它可以使用WINRTP組件。
?更新
Here are the improvements since the last version
這里是新版本的改進:
- Completely standalone package – Compatible with all flavors of desktop Windows starting from Windows 95. Uses standard .DLL files that come with all Windows flavors?完全獨立的包—兼容所有從windows95以來的版本,使用標準DLL適用所有windows。
- Simple distribution: just two DLL's, no more .ax files. Also, the whole software is less than 300 Kbytes?簡單的發布:只有兩個DLL,再無.ax文件,整個軟件小于300K字節
- Support for multiple sound cards?支持多聲卡
- Dynamic jitter buffer algorithm option: it is very simple, but it works most of the time?動態抖動緩沖設置:簡單而有效
- Audio quality enhancements: including pre-emphasis and post-emphasis of audio to make it sound sharper, automatic amplification of the incoming RTP audio stream?聲音質量改善:添加音頻預增強和后增強,使聲音清晰?。自動增大RTP音頻流。
- Others: Volume limiter algorithm in case you want to use it.?其它:需要時可以音量限制
- Comes with pre-built binaries for your convenience??帶有預先編譯好的二進制文件,便于用戶使用
- Ability to play any wav file. Previous format restrictions removed. Also, now you can play as many files at the same time as you want??取消先前格式限制支持播放任何wav?文件。并且,可以同時播放多個文件。
?功能
WINRTP consists of two independent parts. One part has the ability to capture the user’s voice (using the system’s microphone), encode it, and send the voice as an RTP (Real Time Protocol) stream to a configurable destination. The other part listens for an RTP stream from the network, extracts the audio from it, and plays it using the PC’s speaker. When both parts are used together, then WINRTP acts like an IP based voice endpoint. Here are the features in short
WINRTP?包含獨立的兩部分。其一提供捕捉用戶聲音、編碼及以RTP流形式發送語音的功能,另一部分在網絡上監聽RTP流,從中解出音頻并播放。當這兩者在一起使用的時候,可以扮演一個基于IP的語音終端,下面是簡要的功能介紹:
- Support for multiple sound devices:?This version of?WinRTP?supports multiple sound devices. This means you can independently choose which audio device to use for transmit and receive if there are multiple audio devices in your PC (for e.g. you have a sound card as well as an USB headset)?????????????
支持多個音頻設備:?此版本WinRTP支持多音頻設備。這樣,如果你的PC上有多個音頻設備,你可以自由地選擇使用那個設備去發送和接收。
- Number of streams:?currently, only one incoming audio stream and one outgoing audio stream are supported. This is because WINRTP uses the sound card, and only one application can use the system’s speaker or microphone at a time.
流數量:現在只支持一個輸入音頻流和一個輸出音頻流。這是因為WINRTP聲卡,同時只有一個應用程序可以使用系統揚聲器或麥克風。
- Codec Support:?G.711 64kbps (both?ALaw?and?ULaw). The version used in Cisco IP?SoftPhone?comes with support for G.723 and G.729. However, due to licensing restrictions, that support has been removed from the open source version of?WinRTP. This explains some of the parameters (like G723BitRate) in some of the calls in the interface
Codec支持:G.711 64kbps(ALaw及ULaw)。在Cisco IP?SoftPhone中使用的版本支持G.723?和?G.729。然而,由于許可限制,這些支持從開源版本的Winrtp中移除了。這說明了在接口調用中存在某些像G723BitRate這樣參數的原因。
- Support for Audio Mixing:?WINRTP allows the mixing of other audio streams (from WAV files) to be mixed with the incoming and outgoing audio streams.
混音支持:?WINRTP允許輸入或輸出音頻流混合其它來自WAV文件的音頻流。
- Volume Control Support:?WINRTP supports setting the volume level for the Microphone, Speaker, and each file that is being mixed in the audio streams.
音量調節支持:WINRTP支持設置麥克風、揚聲器以及被混音的音頻流的音量。
- Silence Suppression:?WINRTP supports silence suppression (Voice Activity Detection - VAD) of the outgoing streams. This means that if it detects silence (user is not speaking) then it stops sending outgoing RTP packets to conserve network bandwidth.
靜音抑制:WINRTP支持輸出流的靜音抑制(聲音活動性檢查VAD)。這就是說,如果發現靜音(用戶沒說話),它可以停止輸出RTP包,以節省網絡帶寬。
- QoS?Support:?WINRTP supports?DiffServ?(IP Type of Service-TOS) packet tagging for outgoing RTP packets.
Qos支持:WINRTP支持在輸出RTP包中標示DiffServ?。
- RTP Implementation:?Encoding and decoding of RTP packets.
- WINRTP does not support RTCP, but it does sink RTCP packets sent by the other end to prevent ICMP messages due to discarded packets.
RTP?實現:編碼和解碼RTP包。
????????????WINRTP不支持RTCP,但是它可以接收其它端發來的RTCP包,以免ICMP消息導致的丟包。
- Independence?of transmit/receive sides:?The transmit and receive sides are independent, and that means
- Different?codecs?may be used for transmit and receive
- User can choose to do only one of the two operations
發送和接收端的獨立性:發送和接收端是獨立的,這就是說:
??????發送和接收可以使用不同的codecs(多媒體數字信號編解碼器)。
??????用戶可以選擇只做其中某項操作。
- Operating Systems Supported:?All flavors of windows Windows95 and later, including Windows NT (Service Pack 3 onwards), Windows ME and Windows 2000/XP
操作系統支持:支持Windows95以后的版本,包括WindowsNT,WindowsME?及Windows2000/XP
- Configurable/Dynamic Jitter Buffer:?The depth of the jitter buffer can be specified, or a dynamic jitter buffer can also be used
可配置動態的抖動緩沖:可以設置抖動緩沖的深度值,也可以使用動態抖動。
- DSP algorithms:?like pre-emphasis and post-emphasis to make the audio sound sharper. Volume limiting to control the max volume, and auto-amplification of incoming RTP audio streams
DSP算法:?如預加重及后加重使聲音更清晰,音量限制控制最大音量,自動放大輸入的RTP音頻流。
?組件及安裝
The distribution comes with both source code and binaries. Extract the ZIP file to obtain everything. It will create a directory calledWinRTP, which will contain everything.
發行版同時包含了源代碼及二進制文件。解開ZIP文件,可以得到所有文件。
?源代碼發布
Build Order?編譯?順序
This will create TraceServer.dll and CCNSMT.dll. Build these projects either in Debug or Release mode.
?這將建立TraceServer.dll?和CCNSMT.dll?兩個文件,請在Debug和Release兩個模式下都編譯。
?二進制發布
WINRTP binary distribution consists of two DLL files under the?WinRTP?directory. The main COM DLL (CCNSMT.dll) that exposes the WINRTP interface is about 200Kbytes while the other (TraceServer.dll) DLL (used for tracing) is 28Kbytes
WINRTP的二進制發布在WinRTP目錄下包含了兩個DLL文件。主要的COM?動態鏈接庫(CCNSMT.dll)提供給我們WINRTOP的接口,大概200K字節大小。TraceServer.dll?28K字節。
安裝
Third Party Dependencies?第三方依賴
????????????None?無
Location of Distributed Files?文件位置:
- TraceServer.dll: Put TraceServer.dll in the SYSTEM directory of windows (i.e. /WINDOWS/SYSTEM of win95/98/ME or /WINNT/SYSTEM32 on win nt/2000??
TraceServer.dll:?將TraceServer.dll?放到windows的系統目錄(如?win95/98/ME??下的/WINDOWS/SYSTEM??或winNT/200下的?/WINNT/SYSTEM32?)
- CCNSMT.dll: This is a COM component, so its location is not important as long as it is registered with the system. It is recommended that it be kept all together in a separate directory or in the directory of the application that is using the?WinRTP.
CCNSMT.dll:?這是一個COM組件,當它被系統注冊以后它的位置已經不重要。推薦將它保存在一個單獨的目錄中或使用WINRTP的應用程序目錄。
Final Install Steps?最后一步:
????????????All COM objects must be registered before WINRTP can be used. For this, use the regsvr32 program that comes with windows (it may be found in the system directory)
????????????所有COM對象在使用前必須進行注冊,對于WINRTP,我們可以使用windows自帶的regsvr32程序完成,命令如下:
- Regsvr32 CCNSMT.dll
?
?測試程序
There is also a test program (both source code and binary) that is available. It is a simple program that does not exercise all the features. It just connects your default microphone to your default speaker for 5 seconds so that you can hear yourself, and then exits. The source code is in the “WinRTP/TestWinRTP” folder and the binary is WinRTP/TestWinRTP.exe
?
這里還包含一個供測試用的程序(源代碼及二進制)。它是一個簡單的程序,并沒有調用所有的功能,它只是連接你默認的麥克風到你默認的揚聲器5秒鐘時間,這期間,你可以從揚聲器中聽到你自己的聲音。源代碼在“WinRTP/TestWinRTP”目錄下,二進制文件為“TestWinRTP.exe”。
’s Guide?接口描述及程序員指南
The?WinRTP?main DLL is CCNSMT.dll which exposes a COM interface that can be used to make calls to the WINRTP.
WinRTP主要的DLL是CCNSMT.dll,它提供了我們一個COM接口用于調用WINRTP。
?WINRTP COM?接口
The interface of WINRTP (ICCNMediaTerm) consists of the following functions
WINRTP接口包含下面的函數:
- HRESULT Initialize()
- HRESULT?UnInitialize()
- HRESULT?StartMicrophone() - not implemented/needed in this version.?
- HRESULT?StopMicrophone() - not implemented/needed in this version.?
- HRESULT?StartAudioReceive() - not implemented/needed in this version.?
- HRESULT?StopAudioReceive() - not implemented/needed in this version.?
- HRESULT?SetAudioCodecRX(
?????????????????????????????????????????????????[in] long?CompressionType,
?????????????????????????????????????????????????[in] long?MillisecPacketSize,?
?????????????????????????????????????????????????[in] long?EchoCancellationValue,
?????????????????????????????????????????????????[in] long G723BitRate
?????????????????????????????????????????????????) - HRESULT?SetAudioCodecTX(
????????????????????????????????????????????????[in] long?CompressionType,
????????????????????????????????????????????????[in] long?MillisecPacketSize,
????????????????????????????????????????????????[in] long?PrecedenceValue,
????????????????????????????????????????????????[in] long?SilenceSuppression,
????????????????????????????????????????????????[in] unsigned short?MaxFramesPerPacket,
????????????????????????????????????????????????[in] long G723BitRate
????????????????????????????????????????????????) - HRESULT?SetAudioDestination(
?????????????????????????????????????????????????[in] BSTR?strHostName,
?????????????????????????????????????????????????[in] long?nUDPortNumber
?????????????????????????????????????????????????) - HRESULT?SetAudioReceivePort(
???????????????????????????????????????????????????[in] long?nUDPPortNumber
???????????????????????????????????????????????????) - HRESULT?StartPlayingFileTX(
???????????????????????????????????????????????[in] BSTR Filename,
???????????????????????????????????????????????[in] unsigned long Mode,
???????????????????????????????????????????????[in] unsigned long?StartPosition,
???????????????????????????????????????????????[in] unsigned long?StopPosition,
???????????????????????????????????????????????[in, out] long * Cookie
???????????????????????????????????????????????) - HRESULT?StartPlayingFileRX(
???????????????????????????????????????????????[in] BSTR Filename,
???????????????????????????????????????????????[in] unsigned long Mode,
???????????????????????????????????????????????[in] unsigned long?StartPosition,
???????????????????????????????????????????????[in] unsigned long?StopPosition,
?????????????????????????????????????????????? [in] unsigned long?waveoutDeviceID,
???????????????????????????????????????????????[in, out] long * Cookie
???????????????????????????????????????????????) - HRESULT?StopPlayingFileTX(
???????????????????????????????????????????????[in] unsigned long Cookie
???????????????????????????????????????????????) - HRESULT?StopPlayingFileRX(
???????????????????????????????????????????????[in] unsigned long Cookie
???????????????????????????????????????????????) - HRESULT?StartTX(unsigned long?waveinDeviceID)
- HRESULT?StopTX()
- HRESULT?StartRX(unsigned long?waveoutDeviceID)
- HRESULT?StopRX()
- HRESULT?SetSpeakerVolume(
????????????????????????????????????????????????[in] unsigned long volume
????????????????????????????????????????????????) - HRESULT?SetMicrophoneVolume(
?????????????????????????????????????????????????????[in] unsigned long volume
?????????????????????????????????????????????????????) - HRESULT?SetFilePlayVolume(
???????????????????????????????????????????????[in] unsigned long cookie,
???????????????????????????????????????????????[in] unsigned long volume
???????????????????????????????????????????????)
Events?From?WINRTP
WINRTP not only exposes a COM interface, it also has the ability to fire events to the component that using WINRTP. This is done through the standard Connection Point mechanism. For information on connection points read a book on COM and ATL (Active Template Library). The basic idea is that WINRTP describes a COM interface for receiving events. If a component implements that COM interface, then it can subscribe itself as a listener of events generated by the WINRTP.
?WINRTP?不只提供給我們一個COM接口,它還具有發送事件給組件的功能。它從頭至尾完成了標準的連接點機制(要了解關于connection points的信息,請查看關于COM和ATL的書籍)?;镜南敕ㄊ?span lang="EN-US">WINRTP?給出一個COM?接口用于接收事件。如果一個組件實現了這個接口,則它可以把自己作為WINRTP事件的監聽者。?PS:不太懂COM,瞎翻譯的
?
The events interface (ICCNMediaTermEvents) is as follows
·????????HRESULT?EndOfFileEventRX(
????????????????????????????????????????????????[in] long Cookie
????????????????????????????????????????????????)
·????????HRESULT?EndOfFileEventTX(
????????????????????????????????????????????????[in] long Cookie
????????????????????????????????????????????????)
?
ICCNMediaTerm)??WINRTP接口詳解
All methods in the interface return an HRESULT value. If the method succeeds, they return 0, otherwise a negative number for failure. The return values are changing?L?so the recommended way to debug any?function??failures?is to use the trace mechanism (i.e. turn on tracing for the WINRTP, and look at the trace file which includes a description of the error that caused the negative return value. If problems persist, contact the developer of WINRTP for details/help.In?some cases, some of the important return values may be discussed for a function, but not for all functions
?所有的方法都返回一個HRESULT值。如果方法成功,返回0,否則,返回一個負數表示失敗。返回值是變化的,所以推薦的調試函數返回失敗的方法是使用trace機制。(如,打開WINRTP的tracting,查看包含負值返回的錯誤描述的trace文件。如果問題無法解決請聯系WINRTP開發者得到詳細資料或幫助。有些情況下,函數的一些重要返回值可能需要討論,但不是所有都這樣)
?
HRESULT?Initialize()
?
Description:
Initializes the WINRTP.?Instantiates all components.?Also sets up default?codecs?using the following calls
初始化WINRTP,初始化所有組件,并且使用下面調用設置默認codecs:
- SetAudioCodecTX(Codec = G711 Ulaw 64kbps, 20, 0, 0, 1, 0)
- SetAudioCodecRX(Codec = G711 Ulaw 64kbps, 20, 0, 0)
This function must be called before any other calls to WINRTP
調用所有其它WINRTP函數前必須調用該函數。
?
Parameters:
None?無參數
?
?
HRESULT?UnInitialize()
?
Description:
Uninitializes?the WINRTP and releases all allocated resources. This must be the last call made to the WINRTP
銷毀WINRTP,釋放所有分配的資源。這必須是WINRTP的最后一個調用。
?
Parameters:
None?無參數
?
?
HRESULT?StartMicrophone()
?
Description:
No implemented/needed in this version
沒有在此版本中實現
?
Parameters:
None
?
?
?
HRESULT?StopMicrophone()
?
Description:
No implemented/needed in this version
沒有在此版本中實現
?
Parameters:
None
?
?
HRESULT?StartAudioReceive()
?
Description:
No implemented/needed in this version
沒有在此版本中實現
?
Parameters:
None
?
HRESULT?StopAudioReceive()
?
Description:
No implemented/needed in this version
沒有在此版本中實現
?
Parameters:
None
?
?
HRESULT?SetAudioCodecRX
?
Description:
Call this function to inform WINRTP of the audio codec used to encode the incoming RTP stream. This function may be called before?StartRX?is called. (so?you may need to call?StopRX?before making this call). If called before?StartRX?is called, it sets the codec for the next invocation of?StartRX. If it is called while receiving audio (i.e. after?StartRX) it may return an error.
調用這個函數通知WINRTP對輸入RTP流使用那個編碼。此函數可能在StartRX之前調用(所以,你可能需要此函數前調用StopRX)。如果StartRX已經調用了,它將設置下一個StartRX,如果調用時正在接收數據,它返回一個錯誤。
?
Parameters:
[in] long?CompressionType:?The following values are supported
·????????2 :?G.711?Alaw?64kbps
·????????4 :?G.711?Ulaw?64kbps
[in] long?MillisecPacketSize:?Specifies the length of audio in each incoming RTP audio packets
[in] long?EchoCancellationValue:?Ignored. Put any value here. Echo cancellation is not supported in the WINRTP
[in] long G723BitRate:?Ignored
?
?
HRESULT?SetAudioCodecTX
?
Description:
Sets the audio codec for the transmit stream (outgoing stream). Should be called while NOT streaming (i.e. before?StartTX/after?StopTX)
設置輸出流的codecs,需要在沒有流傳輸時調用(如,StartTX之前,StopTX之后)
?
Parameters:
[in] long?CompressionType:?See?SetAudioCodecRX
?
[in] long?MillisecPacketSize:?See?SetAudioCodecRX
?
[in] long?PrecedenceValue:?Ignored
[in] long?SilenceSuppression:?Specifies whether to do silence suppression in the transmit stream
0 :?Silence suppression is turned OFF
1 :?Silence suppression is turned ON
?
[in] unsigned short?MaxFramesPerPacket:?Ignored
?
[in] long G723BitRate:?See?SetAudioCodecRX
?
HRESULT?SetAudioDestination
?
Description:
Sets the destination [IP Address,?UDP?Port] where the send side audio stream should be transmitted.?Must be called while not streaming (i.e. Before?StartTX/after?StopTX).
設置發送端傳輸音頻流的目的地[IP地址,UDP端口]?。必須在無流傳輸時調用(如,StartTX之前,StopTX之后)。
?
Parameters:
[in] BSTR?strHostName:?IP address of the destination. E.g. “171.69.12.34”
[in] long?nUDPortNumber:?UDP port number where to send the stream
?
?
HRESULT?SetAudioReceivePort
?
Description:
Informs the WINRTP of the UDP port number where it should listen for the incoming RTP audio stream. Note:?StartAudioReceive?must be called before any audio from the incoming stream is played to the speaker.
告知WINRTP用于監聽輸入RTP音頻流的UDP地址。注:StartAudioReceive必須在輸入流已經播放之前。
?
Parameters:
[in] long?nUDPPortNumber:?UDP port number
?
?
HRESULT?StartPlayingFileTX
?
Description:
This method should be used when a WAV file needs to be transmitted. The audio from the file is mixed in with the outgoing audio stream (user’s voice). The WINRTP fires an event to let the caller know when the file has finished playing, so that another file may be played. If the file finished playing, the WINRTP automatically calls?StopPlayingFileTX?so the caller need not call it. Only one file may be playing at a time. If this function is called while another file is playing already, an error is returned and the original file keeps playing. The function returns?an?unique identifier (cookie) that may be used in later calls related to this file play (to set the volume, or stop it from playing any more). This method can also play the file in a loop continuously without stopping. By default, files start playing at 25% volume.
此方法用于WAV文件需要傳輸時。文件的音頻將同輸出流混音。WINRTP發送一個事件讓調用者知道文件已經播放完畢,這時其它文件可以播放。當文件播放完畢,WINRTP自動調用StopPlayingFileTX?,調用者不必再調用。同一時刻只能播放一個文件。如果此函數調用時已經有文件在播放,此調用將返回一個錯誤,原來的文件將繼續播放。函數返回一個唯一標示,可以被用于之后的函數調用(設置音量、停止播放等)。此方法也可以無間斷地重復播放一個文件。默認情況下,文件以25%的音量大小播放。
?
Parameters:
[in] BSTR Filename:?the location (path) of the file to be played??待播放文件的位置(路徑)
[in] unsigned long Mode:?specifies whether to play the file once or in a loop?制定播放一次或循環
·????????0 :?play the file continuously in a loop
·????????1 :?play the file once
?
[in] unsigned long?StartPosition:?unimplemented/ignored
[in] unsigned long?StopPosition:?unimplemented/ignored
[in, out] long * Cookie:?WINRTP returns a unique ID for this instance of the file being played. This cookie should be used in later calls pertaining to the instance of the file playing
?
HRESULT?StartPlayingFileRX
?
Description:
This function starts mixing audio from the specified file to the received audio stream, so that the user hears audio from both the incoming audio stream and the file. The only difference is that we can have two files playing simultaneously in the receive side instead of one. By default, files start playing at 25% volume.
此函數開始對接收音頻流和制定的文件進行混音。用戶將同時聽到輸入音頻流和文件音頻,唯一的不同點是我們可以在接收端同時播放兩個文件。默認音量為25%。
?
Parameters:
Exactly the same as?StartPlayingFileTX, but with another extra parameter
[in] unsigned long?waveoutDeviceID:?specifies which speaker device to play the file to.?WinRTP?now allows you to play the file using the wave/speaker device opened for audio (with?StartRX) or to another wave/speaker device. sometimes it may be useful to play a file locally to another audio device (for e.g. if you are using a USB headset for speech, you may want to play ring tones for incoming calls through? the speakers connected to the sound card so that it is heard loudly). See?StartRX?for a discussion on?waveoutDeviceID
?
?
HRESULT?StartTX
?
Description:
Starts streaming on the transmit side. This method must be called before?StartPlayingFileTX?is called. Calling this method starts transmitting the user’s voice
在傳輸端開始流。此函數必須在StartPlayingFileTX函數調用前。調用此方法開發傳輸用戶語音。
?
Parameters:
unsigned?long?waveinDeviceID:?specifies which audio device to use for audio capture/recording.?device?ID's are numbered 0...(#of recording audio devices-1), and -1 means use default audio device for windows. Check out?waveInOpen() and?waveInGetDevCaps() in the windows API. If you are confused, -1 actually means (unsigned long) –1.
?
?
HRESULT?StartRX
?
Description:
Sets up WINRTP to start the receive side. It also starts playing the received audio to the speaker.
設置接收端開始WINRTP,它也開始播放接收到的音頻。
?
Parameters:
unsigned?long?waveoutDeviceID:?specifies which audio device to use for playback/speaker. These device ID's are numbered 0 ... (# of playback devices - 1), and -1 means use the default playback device. Check out?waveOutOpen() and?waveOutGetDevCaps() functions in the windows API.. If you are confused, -1 actually means (unsigned long) –1.
?
?
HRESULT?StopTX
?
Description:
Stops transmitting audio.?Stops transmitting the user’s voice and files.
停止傳輸語音。停止傳輸用戶語音及文件。
?
Parameters:
None
?
?
HRESULT?StopRX
?
Description:
Stops receiving and playing audio.?Stops playing the received audio stream and the files
停止接收和播放音頻。停止播放接收的音頻流及文件。
?
Parameters:
None
?
?
HRESULT?SetSpeakerVolume
?
Description:
Sets the speaker volume on the PC.?This setting sets the WAVEOUT volume of the system (not the master volume).
設置PC揚聲器音量。此調用設置系統的WAVEOUT音量(不是主音量)。
?
Parameters:
[in] unsigned long volume:?value between 0 and 100 where 0 = silence, and 100 = max volume. The scale is linear, so 50 = half volume
?
HRESULT?SetMicrophoneVolume
?
Description:
Sets the microphone volume.?This setting changes the PC’s microphone volume or audio capture volume.
設置麥克風音量。此調用改變麥克風音量或音頻捕捉音量。
?
Parameters:
[in] unsigned long volume:?value between 0 and 100 where 0 = silence, and 100 = max volume. The scale is linear, so 50 = half volume
?
?
?
?
HRESULT?SetFilePlayVolume
?
Description:
Sets the volume of a file being played by the WINRTP.
設置WINRTP正在播放的文件的音量
?
Parameters:
[in] unsigned long cookie:?the cookie that pertains to this instance of the file play. The cookie is obtained when?StartPlayingFileTX(or RX) is called
[in] unsigned long volume:?Volume setting. Starts from 0 (silence) to 100 (max volume)
?
HRESULT?StopPlayingFileTX
?
Description:
Stops a file being played in the transmit side
在傳輸端停止當前文件播放
?
Parameters:
[in] unsigned long Cookie:?Cookie that was returned when the file started playing.
?
?
HRESULT?StopPlayingFileRX
?
Description:
Stops a file being played in the receive side
在接收端停止當前文件播放。
?
Parameters:
[in] unsigned long Cookie:?Cookie that was returned when the file started playing.
?
?
GUIDs, etc
The important?GUIDs?are??最主要的GUID為:
- WinRTP?COM object (CCNMediaTerm?class) :?94221C4E-00F1-11D4-9D59-0060B0FC246C
- WinRTP?COM?Inteface?(ICCNMediaTerm) :?94221C4D-00F1-11D4-9D59-0060B0FC246C
- WinRTP?Events Interface (_ICCNMediaTermEvents) :?94221C4F-00F1-11D4-9D59-0060B0FC246C
?
The following code snippet may be useful for more information?下面的小代碼斷可能會提供更多信息:
?
WINRTP Interface
//?CCNSMT.idl?:?IDL source for CCNSMT.dll
//
// This file will be processed by the MIDL tool to
// produce the type library (CCNSMT.tlb) and marshalling code.
import "oaidl.idl";
import "ocidl.idl";
[
object,
uuid(94221C4D-00F1-11D4-9D59-0060B0FC246C),
helpstring("ICCNMediaTerm?Interface"),
pointer_default(unique)
]
interface?ICCNMediaTerm?:?IUnknown
{
[helpstring("method Initialize")]
HRESULT Initialize();
[helpstring("method?UnInitialize")]
HRESULT?UnInitialize();
[helpstring("method?StartMicrophone")]?
HRESULT?StartMicrophone();
[helpstring("method?StopMicrophone")]?
HRESULT?StopMicrophone();
[helpstring("method?StartAudioReceive")]?
HRESULT?StartAudioReceive();
[helpstring("method?StopAudioReceive")]?
HRESULT?StopAudioReceive();
[helpstring("method?StopDtmfTone")]?
HRESULT?StopDtmfTone();
[helpstring("method?SetAudioCodecRX")]?
HRESULT?SetAudioCodecRX([in] long?CompressionType, [in] long?MillisecPacketSize, [in] long?EchoCancellationValue, [in] long G723BitRate);
[helpstring("method?SetAudioCodecTX")]?
HRESULT?SetAudioCodecTX([in] long?CompressionType, [in] long?MillisecPacketSize, [in] long?PrecedenceValue, [in] long?SilenceSuppression, [in] unsigned short?MaxFramesPerPacket, [in] long G723BitRate);
[helpstring("method?SetAudioDestination")]?
HRESULT?SetAudioDestination([in] BSTR?strHostName, [in] long?nUDPortNumber);
[helpstring("method?SetAudioReceivePort")]?
HRESULT?SetAudioReceivePort([in] long?nUDPPortNumber);
[helpstring("method?StartDtmfTone")]?
HRESULT?StartDtmfTone([in] long?cToneAsChar, [in] long?OnTime, [in] long?OffTime);
[helpstring("method?StartPlayingFileTX")]?
HRESULT?StartPlayingFileTX([in] BSTR Filename, [in] unsigned long Mode, [in, out] long * Cookie);
[helpstring("method?StartPlayingFileRX")]?
HRESULT?StartPlayingFileRX([in] BSTR Filename, [in] unsigned long Mode, [in] unsigned long?waveoutDeviceID, [in, out] long * Cookie);
[helpstring("method?StopPlayingFileTX")]?
HRESULT?StopPlayingFileTX([in] unsigned long Cookie);
[helpstring("method?StopPlayingFileRX")]?
HRESULT?StopPlayingFileRX([in] unsigned long Cookie);
[helpstring("method?StartTX")]?
HRESULT?StartTX([in] unsigned long?waveinDeviceID);
[helpstring("method?StopTX")]?
HRESULT?StopTX();
[helpstring("method?StartRX")]?
HRESULT?StartRX([in] unsigned long?waveoutDeviceID);
[helpstring("method?StopRX")]?
HRESULT?StopRX();
[helpstring("method?SetSpeakerVolume")]?
HRESULT?SetSpeakerVolume([in] unsigned long?deviceID, [in] unsigned long volume);
[helpstring("method?SetMicrophoneVolume")]?
HRESULT?SetMicrophoneVolume([in] unsigned long?deviceID, [in] unsigned long volume);
[helpstring("method?SetFilePlayVolume")]?
HRESULT?SetFilePlayVolume([in] unsigned long cookie, [in] unsigned long volume);
[helpstring("method?NetworkMonitor")]?
HRESULT?NetworkMonitor([in] unsigned long Enable, [in] unsigned long?DurationMillisec);
};
[
uuid(94221C4F-00F1-11D4-9D59-0060B0FC246C),
helpstring("_ICCNMediaTermEvents?Interface")
]
interface _ICCNMediaTermEvents?:?IUnknown
{
[helpstring("method?EndOfFileEventRX")]?
HRESULT?EndOfFileEventRX([in] long Cookie);
[helpstring("method?EndOfFileEventTX")]?
HRESULT?EndOfFileEventTX([in] long Cookie);
[helpstring("method?NetworkMonitorEventRX")]?
HRESULT?NetworkMonitorEventRX([in] double?RXMean, [in] double?RXVariance);
[helpstring("method?NetworkMonitorEventTX")]?
HRESULT?NetworkMonitorEventTX([in] double?TXMean, [in] double?TXVariance);
};
[
uuid(94221C40-00F1-11D4-9D59-0060B0FC246C),
version(1.0),
helpstring("CCNSMT 1.0 Type Library")
]
library?CCNSMTLib
{
importlib("stdole32.tlb");
importlib("stdole2.tlb");
[
uuid(94221C4E-00F1-11D4-9D59-0060B0FC246C),
helpstring("CCNMediaTerm?Class")
]
coclass?CCNMediaTerm
{
[default] interface?ICCNMediaTerm;
[default, source] interface _ICCNMediaTermEvents;
};
};
?
Type Library
[
????????????uuid(94221C40-00F1-11D4-9D59-0060B0FC246C),
????????????version(1.0),
????????????helpstring("CCNSMT 1.0 Type Library")
]
library?CCNSMTLib
{
????????????importlib("stdole32.tlb");
????????????importlib("stdole2.tlb");
?
????????????[
????????????????????????uuid(94221C4E-00F1-11D4-9D59-0060B0FC246C),
????????????????????????helpstring("CCNMediaTerm?Class")
????????????]
????????????coclass?CCNMediaTerm
????????????{
????????????????????????[default] interface?ICCNMediaTerm;
????????????????????????[default, source] interface _ICCNMediaTermEvents;
????????????};
};
Sample C++ Code?示例C++代碼:
Using the type library generated while compiling?WinRTP?(CCNSMT.tlb) one can easily?use?WinRTP?in code. Visual C++ 6.0 allows importing a type library in the #import command, as the following sample code shows. Note that you cannot import?WinRTP?as a COM object into your project because it is NOT and ActiveX control nor does it support?IDispatch.
使用編譯WINRTP時得到的類型庫文件,可以在編碼時很容易的使用WinRTP。就像下面代碼顯示的那樣,VC 6.0?允許使用#import?命令導入一個類型庫。注意,你不可以把WINRTP當作一個COM?對象導入你的工程,因為它不是。而且ActiveX?控件也不支持IDispatch。
?
#import "../CCNMediaTerm/CCNSMT/CCNSMT.tlb"?no_namespace,?raw_interfaces_only
int?main()
{
HRESULT hr;
// Initialize COM
hr =?CoInitialize(NULL);
// Get Interface?ICCNMediaTerm?from the?WinRTP?COM Object using smart pointer defined by the #import command above.?
// Automatically calls?IUnknown::AddRef();
ICCNMediaTermPtr?pICCNMediaTerm(__uuidof(CCNMediaTerm));
// Initialize?WinRTP. Must be the first call
pICCNMediaTerm->Initialize();
// Set parameters for receive side
pICCNMediaTerm->SetAudioCodecRX(4, 20, 0, 0);
pICCNMediaTerm->SetAudioReceivePort(8500);
// Set parameters for transmit side
pICCNMediaTerm->SetAudioCodecTX(4, 20, 0, 0, 0, 0);
pICCNMediaTerm->SetAudioDestination(L"127.0.0.1", 8500);
// Start reception side.?we?will use the default (-1) playback device
pICCNMediaTerm->StartRX(-1);
// Start transmit side. we will use the default (-1) recording device
pICCNMediaTerm->StartTX(-1);
// Set the speaker volume to 50%
pICCNMediaTerm->SetSpeakerVolume(-1, 50);
// Set the microphone volume to 50%
pICCNMediaTerm->SetMicrophoneVolume(-1, 50);
// Hear yourself for 5 seconds
Sleep(5000);
// Stop reception & transmission
pICCNMediaTerm->StopRX();
pICCNMediaTerm->StopTX();
//?Unitialize?WinRTP. Must be the last call
pICCNMediaTerm->UnInitialize();
// Let go of the reference to the?ICCNMediaTerm?interface. Automatically calls?IUnknown::Release()
pICCNMediaTerm?= 0;
//?Uninitialize?COM
CoUninitialize();
return 0;
}
?可選參數
The configurable parameters of WINRTP are mostly set using the registry. The registry key for these settings is HKEY_CURRENT_USER/Software/Cisco Systems/CCNMediaTerm/1.0. If these entries do not exist in the registry, then the WINRTP creates them automatically with the default values the first time it needs to use them.
大部分WINRTP的可選參數使用注冊表。這些設置的鍵值為HKEY_CURRENT_USER/Software/Cisco Systems/CCNMediaTerm/1.0?。如果這個鍵值不存在,WINRTP將在第一次需要使用它們時建立它。
?靜態/動態?抖動緩沖
Set the?UseDynamicJitterBuffer?registry entry to “true” to use dynamic jitter buffer algorithm for audio reception. Set it to “false” to use static jitter buffer (like the old version of?winrtp)
設置?UseDynamicJitterBuffer?條目為?“true”?則在音頻接收時使用動態抖動緩沖算法。設置為“false”?則使用靜態抖動緩沖(就像上的版本一樣)
?抖動緩沖長度
This value is relevant only if static jitter buffer is being used. The length of the jitter buffer can be specified using the?JitterBufferTime?registry setting. This setting is in milliseconds. The default value is 180, but lower values work on most computers. At the beginning of each talk spurt, the WINRTP fills x milliseconds of audio in the jitter buffer (where x is the value of the?JitterBufferTime?registry setting) before it starts playing it to the speaker. Higher jitter buffer length provides smoother audio and immunity to network problems, but increases the latency in a two-way conversation. But lowering this value too much can lead to bad quality audio (stuttering or jittery audio) in which case the user should try to increase this setting. The optimal value is very dependent on the configuration of the PC (sound card and drivers, operating system, etc.), so it should be set on a per-computer basis. The default value of 180 works on majority of computers (lower values may work too).
此值只有在使用靜態抖動緩沖時才有效。使用JitterBufferTime?鍵值來設置抖動緩沖的長度。此設置單位為毫秒。默認值為180,但是大多數計算機使用更低的值。話音突發(talk spurt)開始時,WINRTP在播放之前填充?x?毫秒到抖動緩沖(x?為JitterBufferTime?鍵值)。更高的抖動緩沖長度提供了更平滑的音頻及更好的網絡故障免疫性,但是增加了雙向交談的反應時間。降低太多此值,會帶來劣質的語音(間斷的,抖動的聲音),這時就需要增加這個值。最佳的值依賴于PC的配置(聲卡、驅動及操作系統等),所以它對于每個電腦是不同的。默認的180,可以適用于大部分電腦。
Try the following (Windows 2000/XP :?60ms, WinNT 4.0 : 120ms, Win 95/98/ME : 180ms
按照操作系統不同,可嘗試下面的設置:Windows 2000/XP :?60ms, WinNT 4.0 : 120ms, Win 95/98/ME : 180ms
?接收的RTP音頻流自動放大等級
WinRTP?can automatically amplify the volume of the incoming audio streams. It is needed because frequently the volume level in the incoming packets is pretty low, so they sound much faint compared to other sounds on the PC. We could increase the volume sliders on the PC, but that would make every other sound extremely loud so it is not a satisfactory solution. The real fix is to amplify the incoming audio to a level that is comparable to other system sounds.?WinRTP?2.1 onwards has that ability. Note that increasing the level of the incoming signal can cause distortion (due to clipping) so?WinRTP?employs a novel technique that gives the user complete control. It has amplification that is governed by two parameters, a max-gain (the maximum gain that will be applied if possible), and a distortion-free-percentile (percentage of audio samples that should not be distorted due to this amplification). It is best explained with an example. Say max gain is 5, and distortion-free-percentile is 95%. Then given an RTP packet with audio samples,?WinRTP?will calculate how much gain it can apply so the samples so that 95% of the samples will NOT be distorted. If this value (say x) is less than max-gain, then the packet will be amplified x times. If x is more that max-gain, then the packet will be amplified max-gain times. To ensure that no distortion occurs, set the percentile to 100% and max-gain to a high value. That way,?WinRTP?will always amplify the packet without distorting any sample. However, during quiet periods, x might be large which will increase the loudness of the background noise. This is where setting max-gain to?a?optimal value helps, because it is the max amplification that will ever be applied. I have seen that?max-gain values between 5-10 and percentile of 95% produces?a good balance. To turn off this feature altogether, set max-gain to 1, so that no amplification will be done. The following registry keys control this feature
WINRTP可以自動放大輸入的音頻流音量。這是很必要的,因為輸入包的音量常常都很小,于PC的其它聲音比起來很微弱。我們可以去增加PC的音量調節,但是它也將其它聲音放的很大,這不是令人滿意的解決辦法。真正的解決辦法是放大輸入音頻的等級和系統的其它聲音相當。WINRTP2.1首先具有這個功能。注意,增大輸入信號的等級可能會導致失真(由于clipping)?,所以WINRTP給用戶完全的控制權。我們通過兩個參數來進行設置,一個max-gain(可能的最大限度的增大)和一個distortion-free-percentile(最小保真率)。最好的闡述是通過一個例子:說,max gain設置為5?,distortion-free-percentile設置為95%?。這時,給出一個RTP包,WINRTP將計算多大的增加可以保證原始包中95%的語音沒有失真。如果這個值(x)小于?max-gain(5)?,這個包將放大x倍。如果這個值大于?max-gain(5),它將放大max-gain倍。要保證沒有失真出現,設置百分點為100%,?max-gain為一個很大值,這樣,WINRTP將在不失真的情況下放大音頻包。當靜音階段,x?可能會很大,這將導致環境雜音被放大。這就是為什么要設置max-gain為一個最佳值,因為這將是可以接收的最大放大倍數。我認為max-gain?在5到10之間,distortion-free-percentile為95%?,可以達到一個比較好的平衡。關閉此功能,設置max-gain?為1?,這樣不會有任何放大。下面的鍵值控制此功能:
VolumeMaximizeMaxGain?(floating point number >= 1.0 e.g.?8.0 )
VolumeMaximizePercentile?(floating point number between 0.0 and?100.0 )
?
DiffServ?Byte) of Outgoing RTP Packets?輸出RTP包的TOS
The WINRTP can stamp outgoing RTP packets with an IP TOS (type of service) value in the IP header. This is important for?QoS?purposes where packets of a certain TOS may be given priority in the network to reduce delay. To do this, you need to change the value in the?RtpOut?filter project (RtpOut.cpp)
?WINRTP可以為輸出RTP包在IP頭標示IP TOS?值,對于Qos來說這很重要,不同的TOS將給與不同的優先級來減少延遲。你需要修改這個值在RtpOut?filter?項目中(RtpOut.cpp)
?指定UDP?傳輸端口
If you want to use a particular local UDP port to transmit RTP streams, set the?UseFixedTransmitPort?to “true” and set the?TransmitPort?registry entry to the port number you want to use. Otherwise, set?UseFixedTransmitPort?to “false”. Note?the receive?and transmit port cannot be the same. Make sure transmit?port != receive port, and transmit port != (receive port + 1)
?如果你想使用一個確定的本地UDP端口在傳輸RTP流,可以設置?UseFixedTransmitPort?鍵值為?“true”?并?設置?TransmitPort?鍵值為你想使用的端口。否則,設置UseFixedTransmitPort?為?“false”?。注意:接收和發送端口不能為一個,請確保transmit port != receive port,?并且?transmit port != (receive port + 1)
?發送音頻的預加重
To do pre-emphasis of transmitted audio to make it sound sharper, set the?MicrophonePreprocess?registry entry to “true” (“false” otherwise) and then set the?TxFIRFilter?registry entry to either “1”?or “2”. This chooses between a set of parameters to set up an FIR filter to do pre-emphasis of the audio. Experiment to see which setting sounds best
預加重使聲音?sharper。設置?MicrophonePreprocess?鍵值為“true”?,并設置?TxFIRFilter?鍵值為??“1”?或?“2”?。這些參數被FIR過濾器用來進行預加重(pre-emphasis),你可以自己實驗得到最好的效果。
?
?接收音頻的后加重
To do post-emphasis of received audio to make it sound sharper, set the?SpeakerPostprocess?registry entry to “true” (“false” otherwise) and then set the?RxFIRFilter?registry entry to either “1”?or “2”. This chooses between a set of parameters to set up an FIR filter to do post-emphasis of the audio. Experiment to see which setting sounds best
?后加重使接收到的聲音sharper。設置?SpeakerPostprocess?鍵值為“true”?,并設置?鍵值?RxFIRFilter?為“1”?或?“2”?。這些參數將傳給FIR過濾器用來后加重(post-emphasis),你可以自己實驗得到最好的效果。
?音量限制
Sometimes the received audio may be too loud and you may want to do volume limiting to reduce the max volume. In that case, set the?LimitVolume?registry entry to “true” (“false” otherwise). This will turn on the volume limiting feature. To control the behavior of the limiter, there are three registry settings:?LimiterThreshold?(default –8.0),?LimiterLossIncrement?(default 0.075),?LimiterLossDecrement?(default –0.00075). Setting the threshold lower (for e.g. to –25.0 instead of –8.0) will limit audio to a lower volume. I recommend against playing around with the other parameters.
?某些接收到的音頻可能聲音太大,你想限制音量的最大值。這時候,設置?LimitVolume?鍵值為??“true”?。這將打開音量限制功能,控制限制器的行為,有三個鍵值:LimiterThreshold?(默認-8.0),LimiterLossIncrement?(默認0.075),?LimiterLossDecrement?(默認–0.00075)。降低threshold?的值將會限制聲音,另外的鍵值我建議大家不要修改。
?示例代碼
The following?sections describes?through an example how to use the Media Term component. Here are the basic steps
下面的段落敘述了一個使用Media Term組件的例子。下面是步驟:
初始化Media Term?組件,使用CoCreateInstance得到ICCNMediaTerm接口 (CCNMediaTerm)
·????????Initialize();
·????????Set?the startup parameters for transmit: Use G.711?Ulaw?Codec, 30ms packet size, No silence suppression. Transmit to?localhost?(127.0.0.1) to port 21243??設置傳輸的參數:
o???????SetAudioCodecTX(4, 30, 0, 0, 1, 0);
o???????SetAudioDestination(“127.0.0.1”, 21243);
·????????Start transmission using the default audio capture device?開始發送音頻流
o???????StartTX(-1);
·????????Mix the file “foo.wav” along with the transmitted stream. Play the file once.?混音文件“foo.wav”及傳輸流?,并播放。
o???????StartPlayingFileTX(“foo.wav”, 1, 0, 0, &sendFileCookie)
·????????Set the volume of the “foo.wav” file to 50%??設置音量為50%
o???????SetFilePlayVolume(sendFileCookie, 50)
·????????Change the codec from G.711?Ulaw?to G.723 at 5.3kbps and turn on silence suppression?改變codecs,打開靜音抑制
o???????SetAudioCodecTX(9, 30, 0, 1, 1, 0)
·????????Stop Transmitting (everything, including voice and files)?停止傳輸
o???????StopTX()
·????????Set?the startup parameters for receive: Use G.711?Ulaw?Codec, 30ms packet size. Receiving from local port 8000?設置接收參數
o???????SetAudioCodecRX(4, 30, 0, 0);
o???????SetAudioReceivePort(8000);
·????????Start receive side using the default audio playback device?使用默認的回放設備開始接收
o???????StartRX(-1);
·????????Mix the file “foo.wav” along with the received stream. Play the file continuously in a loop. Also play another file “foobar.wav” just once. Mix both files along with the received audio?混音文件“foo.wav”及接收流 ,循環播放文件,播放另一個文件“foobar.wav”一次?;?span id="ze8trgl8bvbq" class="GramE">音所有輸出。
o???????StartPlayingFileRX(“foo.wav”, 0, 0, 0, -1, &receiveFileCookie1);
o???????StartPlayingFileRX(“foobar.wav”, 1, 0, 0. –1, &receiveFileCookie2);
·????????Set the volume of the “foobar.wav” file to 25%??設置音量25%
o???????SetFilePlayVolume(receiveFileCookie2, 25)
·????????Stop playing the “foo.wav” file that was playing in a loop?停止“foo.wav”播放
o???????StopPlayingFileRX(receiveFileCookie1);
·????????Change the codec from G.711?Ulaw?to G.729 (30ms packet size), and also change the port to receive audio from 8000 to 9999?改變codecs和端口
o???????SetAudioCodecRX(11, 30, 0, 0)
o???????SetAudioReceivePort(9999)
·????????Stop receiving (everything, including voice and files). This method releases the speaker停止接收
o???????StopRX()
- Uninitialize()
?
I plan to release some sample C++ code to show how to use this component soon
我計劃不久后發布一些C++代碼來展示如何使用這些組件。
?未來的改進
Some of the future improvements that are being considered are?一些未來需要做的改進:
- Using the same local UDP port to do transmit and receive??使用相同的端口完成接受和傳輸
總結
以上是生活随笔為你收集整理的Cisco IP电话软件的WINRTP的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Nginx安装及配置教程
- 下一篇: 在C++编译器下,将代码按照C语言编译