diff --git a/projects/core/src/lib/component/lobby/lobby.component.ts b/projects/core/src/lib/component/lobby/lobby.component.ts index 7d98500..534108a 100644 --- a/projects/core/src/lib/component/lobby/lobby.component.ts +++ b/projects/core/src/lib/component/lobby/lobby.component.ts @@ -120,10 +120,10 @@ export class LobbyComponent implements OnInit { startCamera(settings: DeviceSettings) { this.devices.getUserMedia(settings) .then((stream: any) => { - if(this.localGuest?.stream) { + if (this.localGuest?.stream) { this.localGuest?.stream.getTracks().forEach(t => { - t.stop() - }) + t.stop(); + }); } this.localGuest = LobbyMediaStream.buildLocal('me', stream); this.localGuest$.next(this.localGuest); @@ -156,7 +156,7 @@ export class LobbyComponent implements OnInit { streams.set(LobbyMediaPurpose.STREAM, this.mixer.getMixedStream()); } - this.lobbyService.join(streams, this.spaceId, this.streamId, this.config).then(() => this.isInLobby = true); + this.lobbyService.join(streams, this.spaceId, this.streamId, this.config, 'Guest').then(() => this.isInLobby = true); } } @@ -221,7 +221,7 @@ export class LobbyComponent implements OnInit { leaveLobby(): void { if (this.streamId != undefined && this.spaceId != undefined) { this.lobbyService.leaveLobby(this.spaceId, this.streamId).subscribe(() => { - window.location.reload() + window.location.reload(); }); } } diff --git a/projects/core/src/lib/entities/index.ts b/projects/core/src/lib/entities/index.ts index b4324fa..ed4f672 100644 --- a/projects/core/src/lib/entities/index.ts +++ b/projects/core/src/lib/entities/index.ts @@ -1,12 +1,20 @@ export * from './channel.msg'; +export * from './constraints'; export * from './device-settings'; -export * from './media-devices'; -export * from './lobby-media'; export * from './lobby-media.event'; +export * from './lobby-media'; +export * from './lobby-media-muted'; export * from './lobby-media-purpose'; +export * from './lobby-media-stream'; +export * from './media-devices'; +export * from './sdp-media-info'; +export * from './sdp-media-line'; export * from './space'; export * from './stream'; export * from './stream-live-data'; export * from './stream-live-status'; export * from './user'; -export * from './lobby-media-stream'; + + + + diff --git a/projects/core/src/lib/entities/lobby-media-muted.ts b/projects/core/src/lib/entities/lobby-media-muted.ts new file mode 100644 index 0000000..76b1fb5 --- /dev/null +++ b/projects/core/src/lib/entities/lobby-media-muted.ts @@ -0,0 +1,12 @@ +export enum LobbyMediaMuted { + Muted = 1, + NotMuted = 2 +} + +export function getLobbyMediaMuted(muted: boolean | undefined): LobbyMediaMuted { + return (muted !== undefined && muted) ? LobbyMediaMuted.Muted : LobbyMediaMuted.NotMuted; +} + +export function getMuted(media: string): boolean { + return (media === '1'); +} diff --git a/projects/core/src/lib/entities/sdp-media-info.ts b/projects/core/src/lib/entities/sdp-media-info.ts new file mode 100644 index 0000000..b234a3f --- /dev/null +++ b/projects/core/src/lib/entities/sdp-media-info.ts @@ -0,0 +1,7 @@ +import {LobbyMediaPurpose} from './lobby-media-purpose'; + +export interface SdpMediaInfo { + purpose: LobbyMediaPurpose; + muted: boolean; + info: string; +} diff --git a/projects/core/src/lib/entities/sdp-media-line.ts b/projects/core/src/lib/entities/sdp-media-line.ts index 572f071..dd4b84f 100644 --- a/projects/core/src/lib/entities/sdp-media-line.ts +++ b/projects/core/src/lib/entities/sdp-media-line.ts @@ -6,6 +6,7 @@ export interface SdpMediaLine { streamId: string kind: 'audio' | 'video'; direction: 'sendrecv' | 'recvonly' | 'sendonly' | 'inactive'; + muted: boolean; purpose: LobbyMediaPurpose; info: string; } diff --git a/projects/core/src/lib/provider/lobby.service.ts b/projects/core/src/lib/provider/lobby.service.ts index b747184..1f1f0a0 100644 --- a/projects/core/src/lib/provider/lobby.service.ts +++ b/projects/core/src/lib/provider/lobby.service.ts @@ -36,23 +36,23 @@ export class LobbyService { constructor(private http: HttpClient, private messageService: MessageService, private params: ParameterService) { } - public join(stream: Map, spaceId: string, streamId: string, config: RTCConfiguration): Promise { - return this.createSendingConnection(stream, spaceId, streamId, config) + public join(stream: Map, spaceId: string, streamId: string, config: RTCConfiguration, info: string): Promise { + return this.createSendingConnection(stream, spaceId, streamId, config, info) .then((messenger) => this.createReceivingConnection(messenger, spaceId, streamId, config)); } - private createSendingConnection(streams: Map, spaceId: string, streamId: string, config: RTCConfiguration): Promise { - this.ingress = new WebrtcConnection(config, "ingress"); + private createSendingConnection(streams: Map, spaceId: string, streamId: string, config: RTCConfiguration, info: string): Promise { + this.ingress = new WebrtcConnection(config, 'ingress'); const msg = new ChannelMessenger(this.ingress.createDataChannel()); this.messenger = msg; - return this.ingress.createOffer(streams) + return this.ingress.createOffer(streams, info) .then((offer) => this.sendWhip(offer, spaceId, streamId)) .then((answer) => this.ingress?.setAnswer(answer)) .then(() => msg); } private createReceivingConnection(messenger: ChannelMessenger, spaceId: string, streamId: string, config: RTCConfiguration): Promise { - const wc = new WebrtcConnection(config, "egress"); + const wc = new WebrtcConnection(config, 'egress'); this.egress = wc; messenger.subscribe((msg) => { @@ -189,7 +189,7 @@ export class LobbyService { } const mid = this.ingress?.getMid(trackId); if (mid !== null) { - console.log("##############-mid", mid) + console.log('##############-mid', mid); this.messenger?.send(({ type: ChannelMsgType.MuteMsg, id: 0, diff --git a/projects/core/src/lib/provider/sdp-parser.ts b/projects/core/src/lib/provider/sdp-parser.ts index 068bba7..2daff90 100644 --- a/projects/core/src/lib/provider/sdp-parser.ts +++ b/projects/core/src/lib/provider/sdp-parser.ts @@ -1,15 +1,19 @@ import * as sdpTransform from 'sdp-transform'; -import {getMediaStreamTypeByNumber, LobbyMediaPurpose} from '../entities'; +import {getMediaStreamTypeByNumber, LobbyMediaPurpose, SdpMediaInfo} from '../entities'; import {SdpMediaLine} from '../entities/sdp-media-line'; +import {getLobbyMediaMuted, getMuted, LobbyMediaMuted} from '../entities/lobby-media-muted'; export class SdpParser { - public static mungeOfferInfo(sdp: RTCSessionDescription, info: Map): RTCSessionDescription { + public static mungeOfferInfo(sdp: RTCSessionDescription, info: Map): RTCSessionDescription { const res = sdpTransform.parse(sdp.sdp); res.media.forEach((m) => { - m.description = (m.msid && info.has(m.msid)) - ? `${info.get(m.msid.trim())}` - : `${LobbyMediaPurpose.GUEST}`; + if (m.msid && info.has(m.msid)) { + const val = info.get(m.msid); + m.description = `${val?.purpose} ${getLobbyMediaMuted(val?.muted)} ${val?.info}`; + } else { + m.description = `${LobbyMediaPurpose.GUEST} ${LobbyMediaMuted.Muted} Guest`; + } }); const sdpStr = sdpTransform.write(res); return { @@ -27,7 +31,7 @@ export class SdpParser { res.media.forEach((m) => { if (m.type !== 'application') { let {track, stream} = SdpParser.readMediaId(m.msid); - let {purpose, info} = SdpParser.readDescription(m.description); + let {purpose, muted, info} = SdpParser.readDescription(m.description); const line: SdpMediaLine = { mid: (m.mid !== undefined) ? Number(m.mid) : -1, trackId: track, @@ -35,7 +39,8 @@ export class SdpParser { kind: (m.type === 'audio' || m.type === 'video') ? m.type : 'audio', direction: (m.direction !== undefined) ? m.direction : 'inactive', purpose: purpose, - info: info + info: info, + muted: muted }; mediaLines.push(line); } @@ -43,13 +48,17 @@ export class SdpParser { return mediaLines; } - private static readDescription(description: string | undefined): { purpose: LobbyMediaPurpose, info: string } { + private static readDescription(description: string | undefined): SdpMediaInfo { let purpose: LobbyMediaPurpose = LobbyMediaPurpose.GUEST; + let muted: boolean = false; let info: string = 'Guest'; if (description !== undefined) { - purpose = getMediaStreamTypeByNumber(Number(description)); + const dataArray = description.split(' '); + purpose = getMediaStreamTypeByNumber(Number(dataArray[0])); + muted = getMuted(dataArray[1]); + info = dataArray[2]; } - return {purpose, info}; + return {purpose, muted, info}; } private static readMediaId(msid: string | undefined): { track: string, stream: string } { diff --git a/projects/core/src/lib/provider/webrtc-connection.ts b/projects/core/src/lib/provider/webrtc-connection.ts index a6dd2d9..6d7c817 100644 --- a/projects/core/src/lib/provider/webrtc-connection.ts +++ b/projects/core/src/lib/provider/webrtc-connection.ts @@ -1,5 +1,13 @@ import {EventEmitter} from '@angular/core'; -import {ChannelMsg, ChannelMsgType, LobbyMedia, LobbyMediaEvent, LobbyMediaIndex, LobbyMediaPurpose} from '../entities'; +import { + ChannelMsg, + ChannelMsgType, + LobbyMedia, + LobbyMediaEvent, + LobbyMediaIndex, + LobbyMediaPurpose, + SdpMediaInfo +} from '../entities'; import {SdpParser} from './sdp-parser'; export class WebrtcConnection extends EventEmitter { @@ -9,7 +17,7 @@ export class WebrtcConnection extends EventEmitter { constructor( private readonly config: RTCConfiguration, - private readonly type: "ingress" | "egress" + private readonly type: 'ingress' | 'egress' ) { super(true); this.pc = new RTCPeerConnection(this.config); @@ -35,13 +43,17 @@ export class WebrtcConnection extends EventEmitter { return this.dataChannel; } - public createOffer(streams: Map): Promise { - const trackInfo = new Map(); + public createOffer(streams: Map, info: string): Promise { + const trackInfo = new Map(); streams.forEach((ms, streamType) => { let streamId = ms.id; ms.getTracks().forEach((track) => { this.pc.addTrack(track, ms); - trackInfo.set(`${streamId} ${track.id}`.trim(), streamType); + trackInfo.set(`${streamId} ${track.id}`.trim(), { + purpose: streamType, + muted: !track.enabled, + info: info + }); }); }); @@ -130,7 +142,7 @@ export class WebrtcConnection extends EventEmitter { purpose: line.purpose, info: line.info, kind: line.kind, - muted: true, + muted: line.muted, trackId: line.trackId, streamId: line.streamId, }; @@ -160,7 +172,7 @@ export class WebrtcConnection extends EventEmitter { public muteRemoteMedia(mid: string, mute: boolean) { const media = this.remoteMedia.get(Number(mid)); - console.log("####---", this.type) + console.log('####---', this.type); if (!!media) { media.muted = mute; this.remoteMedia.set(Number(mid), media);