private void CreateRxAudio(Rs <RdSrvRxRs> rs, string rsId) { int port = SipAgent.CreateRdRxPort(rs.Info, Top.SipIp); _RxPorts[rsId] = port; if (AnySquelch) { MixerDev dev = (_AudioVia == RdRxAudioVia.HeadPhones ? MixerDev.MhpRd : (_AudioVia == RdRxAudioVia.HfSpeaker ? MixerDev.SpkHf : MixerDev.SpkRd)); Top.Mixer.Link(port, dev, MixerDir.Send, Mixer.RD_PRIORITY, FuentesGlp.RxRadio); } _Logger.Debug("*** CreateRxAudio. Llamando a CreateRdRxPort({0}) {1}", port, Literal); }
/// <summary> /// Redirige al audio hacia el destino indicado (altavoz o auricular) con las siguientes condiciones: /// 1-Si no hay PTT, se conecta el audio siempre. /// 2-Si hay PTT propio no se hace nada, no está permitido cambiar la salida del audio. /// 3-Si hay PTT que procede de una RTX de otro SQ y estoy en el puesto propietario del grupo y el SQ es propio, /// no conecto mi audio porque se debe escuchar el que se está retransmitiendo. /// </summary> /// <param name="audioVia"></param> public void SetAudioVia(RdRxAudioVia audioVia) { if (/*Rx && */ (_AudioVia != audioVia) && ((audioVia == RdRxAudioVia.Speaker && Top.Hw.RdSpeaker) || (audioVia == RdRxAudioVia.HfSpeaker && Top.Hw.HfSpeaker) || (audioVia == RdRxAudioVia.HeadPhones && (Top.Hw.InstructorJack || Top.Hw.AlumnJack) && !Top.Mixer.ModoSoloAltavoces))) { if (InhiboMiAudio(_Ptt, _AssociateFrRs.Info) == false) { foreach (int port in _RxPorts.Values) { Top.Mixer.Unlink(port); MixerDev dev = (audioVia == RdRxAudioVia.HeadPhones ? MixerDev.MhpRd : (audioVia == RdRxAudioVia.HfSpeaker ? MixerDev.SpkHf : MixerDev.SpkRd)); Top.Mixer.Link(port, dev, MixerDir.Send, Mixer.RD_PRIORITY, FuentesGlp.RxRadio); } } AudioVia = audioVia; } }
private Timer _PttOffTimer = new Timer(); //Timer que se activa al producirse un PTT off private void OnPttOffTimer(object sender, ElapsedEventArgs e) { Top.WorkingThread.Enqueue("OnPttOffTimer", delegate() { //Al vencer el timer hay que reactivar la recepcion del Audio de Radio Rx si procede if (InhiboMiAudio(_Ptt, _AssociateFrRs.Info) == true) { foreach (int port in _RxPorts.Values) { Top.Mixer.Unlink(port); } } else if (Rx && (Squelch == SquelchState.SquelchOnlyPort)) { foreach (int port in _RxPorts.Values) { MixerDev dev = (_AudioVia == RdRxAudioVia.HeadPhones ? MixerDev.MhpRd : (_AudioVia == RdRxAudioVia.HfSpeaker ? MixerDev.SpkHf : MixerDev.SpkRd)); Top.Mixer.Link(port, dev, MixerDir.Send, Mixer.RD_PRIORITY, FuentesGlp.RxRadio); } } }); }
public bool InSpeaker(RdRxAudioVia speaker) { bool ret = false; if (AudioVia == speaker) { ret = true; } else if (AudioVia == RdRxAudioVia.HeadPhones) { MixerDev dev = (speaker == RdRxAudioVia.HfSpeaker) ? dev = MixerDev.SpkHf: MixerDev.SpkRd; foreach (int port in _RxPorts.Values) { if (Top.Mixer.MatchActiveLink(dev, port)) { ret = true; break; } } } return(ret); }
private void OnFrChanged(object sender) { Rs <RdSrvFrRs> rs = (Rs <RdSrvFrRs>)sender; bool changed = false; bool changedQidx = false; if (!rs.IsValid) { RxOff(); // Provocar la liberación del transmisor HF // en caso de que estuviera ocupado por este usuario if (_TipoFrecuencia == TipoFrecuencia_t.HF) { _RtxGroup = Math.Min(_RtxGroup, 0); Tx = false; Top.Registry.SetTx(_Literal, false, _Priority, false); } _Rx = AssignState.Idle; _RtxGroup = 0; _Squelch = SquelchState.Unavailable; _Ptt = PttState.Unavailable; _PttSrcId = string.Empty; _Estado = RdSrvFrRs.FrequencyStatusType.NotAvailable; _QidxValue = 0; _QidxResource = string.Empty; changed = true; } else { RdSrvFrRs frRs = rs.Info; if (frRs.PttSrcId == "TxHfOff") { if (_Tx == AssignState.Set) { // Reflejar el estado real de Tx. Puede que el recurso no // esté disponble en la configuración de la pasarela. En // cuyo caso se debe quitar de transmisión _Tx = AssignState.Idle; _Ptt = PttState.NoPtt; _PttSrcId = frRs.PttSrcId; // Actualizar estado de Tx a Off General.SafeLaunchEvent(StateChanged, this); // Enviar mensaje para ventana de error General.SafeLaunchEvent(TxHfAlreadyAssigned, this, (uint)0xFE); } frRs.PttSrcId = string.Empty; //return; } // // Tratamiento del cambio en el estado de Squelch // switch (_TipoFrecuencia) { case TipoFrecuencia_t.FD: if (_Squelch != (SquelchState)frRs.Squelch) { _Squelch = (SquelchState)frRs.Squelch; changed = true; } if (ChangeInQidxInfo(frRs)) { // BSS Information _QidxMethod = frRs.QidxMethod; _QidxResource = _Squelch == SquelchState.NoSquelch ? string.Empty : frRs.SqSite; _QidxValue = _Squelch == SquelchState.NoSquelch ? 0 : frRs.QidxValue; changedQidx = true; } break; // EM case TipoFrecuencia_t.ME: if (_Squelch != (SquelchState)frRs.Squelch && (frRs.SqSite == Alias || frRs.SqSite == string.Empty)) { _Squelch = (SquelchState)frRs.Squelch; changed = true; // BSS Information _QidxMethod = frRs.QidxMethod; _QidxResource = frRs.SqSite; _QidxValue = frRs.QidxValue; } break; default: if (_Squelch != (SquelchState)frRs.Squelch) { _Squelch = (SquelchState)frRs.Squelch; changed = true; } break; } if (_Squelch != (SquelchState)frRs.Squelch && (frRs.SqSite == Alias || frRs.SqSite == string.Empty)) { _Squelch = (SquelchState)frRs.Squelch; changed = true; } // // Tratamiento del cambio en el estado de PTT // PttState ptt = GetPtt(frRs.PttSrcId); if ((frRs.PttSrcId != _PttSrcId) && (ptt == PttState.Error)) { Top.Rd.GenerateBadOperationTone(2000); } // Es posible que no cambie el ptt (externo) pero si cambie su procedencia: // Cambio de ptt externo de rtx a externo de otro HMI. // En este caso hay que evaluar el audio if (ptt != _Ptt || changed || frRs.PttSrcId != _PttSrcId) { if (ptt != _Ptt) { if (ptt == PttState.NoPtt) { if ((_Ptt == PttState.ExternPtt) || (_Ptt == PttState.PttOnlyPort) || (_Ptt == PttState.PttPortAndMod)) { //Al desactivarse el Ptt arranca un timer durante el cual se inhibe el audio de Rd Rx //Solo cuando el estado anterior es un ptt #3830 _PttOffTimer.Enabled = true; } } else { //Cualquier activacion del Ptt anula el timer _PttOffTimer.Enabled = false; } } // Si estoy en Ptt o // Estoy en RTX de otro SQ del grupo y soy dueño del grupo (dejo el otro audio) // no conecto mi audio if (InhiboMiAudio(ptt, frRs) == true) { foreach (int port in _RxPorts.Values) { Top.Mixer.Unlink(port); } } else { foreach (int port in _RxPorts.Values) { if (Rx) { if (Squelch == SquelchState.SquelchOnlyPort) { MixerDev dev = (_AudioVia == RdRxAudioVia.HeadPhones ? MixerDev.MhpRd : (_AudioVia == RdRxAudioVia.HfSpeaker ? MixerDev.SpkHf : MixerDev.SpkRd)); Top.Mixer.Link(port, dev, MixerDir.Send, Mixer.RD_PRIORITY, FuentesGlp.RxRadio); } else if (Squelch == SquelchState.NoSquelch) { Top.Mixer.Unlink(port); } } } } _Ptt = ptt; _PttSrcId = frRs.PttSrcId; changed = true; } // // Tratamiento del cambio en el estado de la retransmisión // int rtxGroup = 0; if (frRs.RtxGroupId != 0) { rtxGroup = frRs.RtxGroupOwner == Top.HostId ? (int)frRs.RtxGroupId : -1; } if (rtxGroup != _RtxGroup) { _RtxGroup = rtxGroup; changed = true; } // // Tratamiento del cambio en el estado de disponibilidad de la frecuencia. // if (frRs.FrequencyStatus != _Estado) { _Estado = frRs.FrequencyStatus; changed = true; } } if (changed || changedQidx) { General.SafeLaunchEvent(StateChanged, this); } }