diff options
author | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-04-19 00:47:55 +0000 |
---|---|---|
committer | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-04-19 00:47:55 +0000 |
commit | 26a029d407be480d791972afb5975cf62c9360a6 (patch) | |
tree | f435a8308119effd964b339f76abb83a57c29483 /third_party/libwebrtc/examples/unityplugin/README | |
parent | Initial commit. (diff) | |
download | firefox-26a029d407be480d791972afb5975cf62c9360a6.tar.xz firefox-26a029d407be480d791972afb5975cf62c9360a6.zip |
Adding upstream version 124.0.1.upstream/124.0.1
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to 'third_party/libwebrtc/examples/unityplugin/README')
-rw-r--r-- | third_party/libwebrtc/examples/unityplugin/README | 309 |
1 files changed, 309 insertions, 0 deletions
diff --git a/third_party/libwebrtc/examples/unityplugin/README b/third_party/libwebrtc/examples/unityplugin/README new file mode 100644 index 0000000000..da8f07aa11 --- /dev/null +++ b/third_party/libwebrtc/examples/unityplugin/README @@ -0,0 +1,309 @@ +This directory contains an example Unity native plugin for Windows OS and Android. + +The APIs use Platform Invoke (P/Invoke) technology as required by Unity native plugin. +This plugin dll can also be used by Windows C# applications other than Unity. + +For detailed build instruction on Android, see ANDROID_INSTRUCTION + +An example of wrapping native plugin into a C# managed class in Unity is given as following: + +using System; +using System.Collections.Generic; +using System.Runtime.InteropServices; + +namespace SimplePeerConnectionM { + // A class for ice candidate. + public class IceCandidate { + public IceCandidate(string candidate, int sdpMlineIndex, string sdpMid) { + mCandidate = candidate; + mSdpMlineIndex = sdpMlineIndex; + mSdpMid = sdpMid; + } + string mCandidate; + int mSdpMlineIndex; + string mSdpMid; + + public string Candidate { + get { return mCandidate; } + set { mCandidate = value; } + } + + public int SdpMlineIndex { + get { return mSdpMlineIndex; } + set { mSdpMlineIndex = value; } + } + + public string SdpMid { + get { return mSdpMid; } + set { mSdpMid = value; } + } + } + + // A managed wrapper up class for the native c style peer connection APIs. + public class PeerConnectionM { + private const string dllPath = "webrtc_unity_plugin"; + + //create a peerconnection with turn servers + [DllImport(dllPath, CallingConvention = CallingConvention.Cdecl)] + private static extern int CreatePeerConnection(string[] turnUrls, int noOfUrls, + string username, string credential); + + [DllImport(dllPath, CallingConvention = CallingConvention.Cdecl)] + private static extern bool ClosePeerConnection(int peerConnectionId); + + [DllImport(dllPath, CallingConvention = CallingConvention.Cdecl)] + private static extern bool AddStream(int peerConnectionId, bool audioOnly); + + [DllImport(dllPath, CallingConvention = CallingConvention.Cdecl)] + private static extern bool AddDataChannel(int peerConnectionId); + + [DllImport(dllPath, CallingConvention = CallingConvention.Cdecl)] + private static extern bool CreateOffer(int peerConnectionId); + + [DllImport(dllPath, CallingConvention = CallingConvention.Cdecl)] + private static extern bool CreateAnswer(int peerConnectionId); + + [DllImport(dllPath, CallingConvention = CallingConvention.Cdecl)] + private static extern bool SendDataViaDataChannel(int peerConnectionId, string data); + + [DllImport(dllPath, CallingConvention = CallingConvention.Cdecl)] + private static extern bool SetAudioControl(int peerConnectionId, bool isMute, bool isRecord); + + [UnmanagedFunctionPointer(CallingConvention.Cdecl)] + private delegate void LocalDataChannelReadyInternalDelegate(); + public delegate void LocalDataChannelReadyDelegate(int id); + [DllImport(dllPath, CallingConvention = CallingConvention.Cdecl)] + private static extern bool RegisterOnLocalDataChannelReady( + int peerConnectionId, LocalDataChannelReadyInternalDelegate callback); + + [UnmanagedFunctionPointer(CallingConvention.Cdecl)] + private delegate void DataFromDataChannelReadyInternalDelegate(string s); + public delegate void DataFromDataChannelReadyDelegate(int id, string s); + [DllImport(dllPath, CallingConvention = CallingConvention.Cdecl)] + private static extern bool RegisterOnDataFromDataChannelReady( + int peerConnectionId, DataFromDataChannelReadyInternalDelegate callback); + + [UnmanagedFunctionPointer(CallingConvention.Cdecl)] + private delegate void FailureMessageInternalDelegate(string msg); + public delegate void FailureMessageDelegate(int id, string msg); + [DllImport(dllPath, CallingConvention = CallingConvention.Cdecl)] + private static extern bool RegisterOnFailure(int peerConnectionId, + FailureMessageInternalDelegate callback); + + [UnmanagedFunctionPointer(CallingConvention.Cdecl)] + private delegate void AudioBusReadyInternalDelegate(IntPtr data, int bitsPerSample, + int sampleRate, int numberOfChannels, int numberOfFrames); + public delegate void AudioBusReadyDelegate(int id, IntPtr data, int bitsPerSample, + int sampleRate, int numberOfChannels, int numberOfFrames); + [DllImport(dllPath, CallingConvention = CallingConvention.Cdecl)] + private static extern bool RegisterOnAudioBusReady(int peerConnectionId, + AudioBusReadyInternalDelegate callback); + + // Video callbacks. + [UnmanagedFunctionPointer(CallingConvention.Cdecl)] + private delegate void I420FrameReadyInternalDelegate( + IntPtr dataY, IntPtr dataU, IntPtr dataV, + int strideY, int strideU, int strideV, + uint width, uint height); + public delegate void I420FrameReadyDelegate(int id, + IntPtr dataY, IntPtr dataU, IntPtr dataV, + int strideY, int strideU, int strideV, + uint width, uint height); + [DllImport(dllPath, CallingConvention = CallingConvention.Cdecl)] + private static extern bool RegisterOnLocalI420FrameReady(int peerConnectionId, + I420FrameReadyInternalDelegate callback); + [DllImport(dllPath, CallingConvention = CallingConvention.Cdecl)] + private static extern bool RegisterOnRemoteI420FrameReady(int peerConnectionId, + I420FrameReadyInternalDelegate callback); + + [UnmanagedFunctionPointer(CallingConvention.Cdecl)] + private delegate void LocalSdpReadytoSendInternalDelegate(string type, string sdp); + public delegate void LocalSdpReadytoSendDelegate(int id, string type, string sdp); + [DllImport(dllPath, CallingConvention = CallingConvention.Cdecl)] + private static extern bool RegisterOnLocalSdpReadytoSend(int peerConnectionId, + LocalSdpReadytoSendInternalDelegate callback); + + [UnmanagedFunctionPointer(CallingConvention.Cdecl)] + private delegate void IceCandidateReadytoSendInternalDelegate( + string candidate, int sdpMlineIndex, string sdpMid); + public delegate void IceCandidateReadytoSendDelegate( + int id, string candidate, int sdpMlineIndex, string sdpMid); + [DllImport(dllPath, CallingConvention = CallingConvention.Cdecl)] + private static extern bool RegisterOnIceCandidateReadytoSend( + int peerConnectionId, IceCandidateReadytoSendInternalDelegate callback); + + [DllImport(dllPath, CallingConvention = CallingConvention.Cdecl)] + private static extern bool SetRemoteDescription(int peerConnectionId, string type, string sdp); + + [DllImport(dllPath, CallingConvention = CallingConvention.Cdecl)] + private static extern bool AddIceCandidate(int peerConnectionId, string sdp, + int sdpMlineindex, string sdpMid); + + public PeerConnectionM(List<string> turnUrls, string username, string credential) { + string[] urls = turnUrls != null ? turnUrls.ToArray() : null; + int length = turnUrls != null ? turnUrls.Count : 0; + mPeerConnectionId = CreatePeerConnection(urls, length, username, credential); + RegisterCallbacks(); + } + + public void ClosePeerConnection() { + ClosePeerConnection(mPeerConnectionId); + mPeerConnectionId = -1; + } + + // Return -1 if Peerconnection is not available. + public int GetUniqueId() { + return mPeerConnectionId; + } + + public void AddStream(bool audioOnly) { + AddStream(mPeerConnectionId, audioOnly); + } + + public void AddDataChannel() { + AddDataChannel(mPeerConnectionId); + } + + public void CreateOffer() { + CreateOffer(mPeerConnectionId); + } + + public void CreateAnswer() { + CreateAnswer(mPeerConnectionId); + } + + public void SendDataViaDataChannel(string data) { + SendDataViaDataChannel(mPeerConnectionId, data); + } + + public void SetAudioControl(bool isMute, bool isRecord) { + SetAudioControl(mPeerConnectionId, isMute, isRecord); + } + + public void SetRemoteDescription(string type, string sdp) { + SetRemoteDescription(mPeerConnectionId, type, sdp); + } + + public void AddIceCandidate(string candidate, int sdpMlineindex, string sdpMid) { + AddIceCandidate(mPeerConnectionId, candidate, sdpMlineindex, sdpMid); + } + + private void RegisterCallbacks() { + localDataChannelReadyDelegate = new LocalDataChannelReadyInternalDelegate( + RaiseLocalDataChannelReady); + RegisterOnLocalDataChannelReady(mPeerConnectionId, localDataChannelReadyDelegate); + + dataFromDataChannelReadyDelegate = new DataFromDataChannelReadyInternalDelegate( + RaiseDataFromDataChannelReady); + RegisterOnDataFromDataChannelReady(mPeerConnectionId, dataFromDataChannelReadyDelegate); + + failureMessageDelegate = new FailureMessageInternalDelegate(RaiseFailureMessage); + RegisterOnFailure(mPeerConnectionId, failureMessageDelegate); + + audioBusReadyDelegate = new AudioBusReadyInternalDelegate(RaiseAudioBusReady); + RegisterOnAudioBusReady(mPeerConnectionId, audioBusReadyDelegate); + + localI420FrameReadyDelegate = new I420FrameReadyInternalDelegate( + RaiseLocalVideoFrameReady); + RegisterOnLocalI420FrameReady(mPeerConnectionId, localI420FrameReadyDelegate); + + remoteI420FrameReadyDelegate = new I420FrameReadyInternalDelegate( + RaiseRemoteVideoFrameReady); + RegisterOnRemoteI420FrameReady(mPeerConnectionId, remoteI420FrameReadyDelegate); + + localSdpReadytoSendDelegate = new LocalSdpReadytoSendInternalDelegate( + RaiseLocalSdpReadytoSend); + RegisterOnLocalSdpReadytoSend(mPeerConnectionId, localSdpReadytoSendDelegate); + + iceCandidateReadytoSendDelegate = + new IceCandidateReadytoSendInternalDelegate(RaiseIceCandidateReadytoSend); + RegisterOnIceCandidateReadytoSend( + mPeerConnectionId, iceCandidateReadytoSendDelegate); + } + + private void RaiseLocalDataChannelReady() { + if (OnLocalDataChannelReady != null) + OnLocalDataChannelReady(mPeerConnectionId); + } + + private void RaiseDataFromDataChannelReady(string data) { + if (OnDataFromDataChannelReady != null) + OnDataFromDataChannelReady(mPeerConnectionId, data); + } + + private void RaiseFailureMessage(string msg) { + if (OnFailureMessage != null) + OnFailureMessage(mPeerConnectionId, msg); + } + + private void RaiseAudioBusReady(IntPtr data, int bitsPerSample, + int sampleRate, int numberOfChannels, int numberOfFrames) { + if (OnAudioBusReady != null) + OnAudioBusReady(mPeerConnectionId, data, bitsPerSample, sampleRate, + numberOfChannels, numberOfFrames); + } + + private void RaiseLocalVideoFrameReady( + IntPtr dataY, IntPtr dataU, IntPtr dataV, + int strideY, int strideU, int strideV, + uint width, uint height) { + if (OnLocalVideoFrameReady != null) + OnLocalVideoFrameReady(mPeerConnectionId, dataY, dataU, dataV, strideY, strideU, strideV, + width, height); + } + + private void RaiseRemoteVideoFrameReady( + IntPtr dataY, IntPtr dataU, IntPtr dataV, + int strideY, int strideU, int strideV, + uint width, uint height) { + if (OnRemoteVideoFrameReady != null) + OnRemoteVideoFrameReady(mPeerConnectionId, dataY, dataU, dataV, strideY, strideU, strideV, + width, height); + } + + + private void RaiseLocalSdpReadytoSend(string type, string sdp) { + if (OnLocalSdpReadytoSend != null) + OnLocalSdpReadytoSend(mPeerConnectionId, type, sdp); + } + + private void RaiseIceCandidateReadytoSend(string candidate, int sdpMlineIndex, string sdpMid) { + if (OnIceCandidateReadytoSend != null) + OnIceCandidateReadytoSend(mPeerConnectionId, candidate, sdpMlineIndex, sdpMid); + } + + public void AddQueuedIceCandidate(List<IceCandidate> iceCandidateQueue) { + if (iceCandidateQueue != null) { + foreach (IceCandidate ic in iceCandidateQueue) { + AddIceCandidate(mPeerConnectionId, ic.Candidate, ic.SdpMlineIndex, ic.SdpMid); + } + } + } + + private LocalDataChannelReadyInternalDelegate localDataChannelReadyDelegate = null; + public event LocalDataChannelReadyDelegate OnLocalDataChannelReady; + + private DataFromDataChannelReadyInternalDelegate dataFromDataChannelReadyDelegate = null; + public event DataFromDataChannelReadyDelegate OnDataFromDataChannelReady; + + private FailureMessageInternalDelegate failureMessageDelegate = null; + public event FailureMessageDelegate OnFailureMessage; + + private AudioBusReadyInternalDelegate audioBusReadyDelegate = null; + public event AudioBusReadyDelegate OnAudioBusReady; + + private I420FrameReadyInternalDelegate localI420FrameReadyDelegate = null; + public event I420FrameReadyDelegate OnLocalVideoFrameReady; + + private I420FrameReadyInternalDelegate remoteI420FrameReadyDelegate = null; + public event I420FrameReadyDelegate OnRemoteVideoFrameReady; + + private LocalSdpReadytoSendInternalDelegate localSdpReadytoSendDelegate = null; + public event LocalSdpReadytoSendDelegate OnLocalSdpReadytoSend; + + private IceCandidateReadytoSendInternalDelegate iceCandidateReadytoSendDelegate = null; + public event IceCandidateReadytoSendDelegate OnIceCandidateReadytoSend; + + private int mPeerConnectionId = -1; + } +} |