/// <summary> /// Constructor /// </summary> /// <param name="selector">An object used to refer to this port in the IRouting device's ExecuteSwitch method. /// May be string, number, whatever</param> /// <param name="parent">The IRoutingInputs object this lives on</param> /// <param name="funcs">A VideoStatusFuncsWrapper used to assign the callback funcs that will get /// the values for the various stats</param> public RoutingInputPortWithVideoStatuses(string key, eRoutingSignalType type, eRoutingPortConnectionType connType, object selector, IRoutingInputs parent, VideoStatusFuncsWrapper funcs) : base(key, type, connType, selector, parent) { VideoStatus = new VideoStatusOutputs(funcs); }
public RouteDescriptor(IRoutingOutputs source, IRoutingInputs destination, eRoutingSignalType signalType) { Destination = destination; Source = source; SignalType = signalType; Routes = new List <RouteSwitchDescriptor>(); }
/// <summary> /// Will release the existing route on the destination /// </summary> /// <param name="destination"></param> /// <param name="signalType"></param> public static void ReleaseRoute(this IRoutingInputs destination) { var current = RouteDescriptorCollection.DefaultCollection.RemoveRouteDescriptor(destination); if (current != null) { Debug.Console(2, destination, "Releasing current route: {0}", current.Source.Key); current.ReleaseRoutes(); } }
/// <summary> /// Returns the RouteDescriptor for a given destination and removes it from collection. /// Returns null if no route with the provided destination exists. /// </summary> public RouteDescriptor RemoveRouteDescriptor(IRoutingInputs destination) { var descr = GetRouteDescriptorForDestination(destination); if (descr != null) { RouteDescriptors.Remove(descr); } return(descr); }
/// <summary> /// Constructor for a virtual routing input port that lives inside a device. For example /// the ports that link a DM card to a DM matrix bus /// </summary> /// <param name="isInternal">true for internal ports</param> public RoutingInputPort(string key, eRoutingSignalType type, eRoutingPortConnectionType connType, object selector, IRoutingInputs parent, bool isInternal) : base(key, type, connType, selector, isInternal) { if (parent == null) { throw new ArgumentNullException("parent"); } ParentDevice = parent; }
/// <summary> /// /// </summary> /// <param name="device"></param> /// <param name="targetSource"></param> /// <param name="signalType"></param> /// <returns></returns> public static RouteDescriptor GetRouteToSource(this IRoutingInputs destination, IRoutingOutputs source, eRoutingSignalType signalType) { var routeTable = new RouteDescriptor(source, destination, signalType); Debug.Console(0, destination, "Attempting to build source route from {0}***", source.Key); if (!destination.GetRouteToSource(source, null, null, signalType, 0, routeTable)) { routeTable = null; } Debug.Console(0, destination, "Route{0} discovered ***", routeTable == null ? " NOT" : ""); return(routeTable); }
/// <summary> /// Gets any existing RouteDescriptor for a destination, clears it using ReleaseRoute /// and then attempts a new Route and if sucessful, stores that RouteDescriptor /// in RouteDescriptorCollection.DefaultCollection /// </summary> public static void ReleaseAndMakeRoute(this IRoutingInputs destination, IRoutingOutputs source, eRoutingSignalType signalType) { destination.ReleaseRoute(); if (source == null) { return; } var newRoute = destination.GetRouteToSource(source, signalType); if (newRoute == null) { return; } RouteDescriptorCollection.DefaultCollection.AddRouteDescriptor(newRoute); Debug.Console(2, destination, "Executing full route"); newRoute.ExecuteRoutes(); }
/// <summary> /// Gets any existing route for a destination, clears it, and then /// </summary> public static void ReleaseAndMakeRoute(this IRoutingInputs destination, IRoutingOutputs source, eRoutingSignalType signalType) { var sw = new Stopwatch(); sw.Start(); destination.ReleaseRoute(); if (source == null) { return; } var newRoute = destination.GetRouteToSource(source, signalType); if (newRoute == null) { return; } RouteDescriptorCollection.DefaultCollection.AddRouteDescriptor(newRoute); Debug.Console(2, destination, "Executing new route"); newRoute.ExecuteRoutes(); sw.Stop(); Debug.Console(2, destination, "Route took {0} ms", sw.ElapsedMilliseconds); }
/// <summary> /// Builds a RouteDescriptor that contains the steps necessary to make a route between devices. /// Routes of type AudioVideo will be built as two separate routes, audio and video. If /// a route is discovered, a new RouteDescriptor is returned. If one or both parts /// of an audio/video route are discovered a route descriptor is returned. If no route is /// discovered, then null is returned /// </summary> public static RouteDescriptor GetRouteToSource(this IRoutingInputs destination, IRoutingOutputs source, eRoutingSignalType signalType) { var routeDescr = new RouteDescriptor(source, destination, signalType); // if it's a single signal type, find the route if ((signalType & (eRoutingSignalType.Audio & eRoutingSignalType.Video)) == (eRoutingSignalType.Audio & eRoutingSignalType.Video)) { Debug.Console(1, destination, "Attempting to build source route from {0}", source.Key); if (!destination.GetRouteToSource(source, null, null, signalType, 0, routeDescr)) { routeDescr = null; } } // otherwise, audioVideo needs to be handled as two steps. else { Debug.Console(1, destination, "Attempting to build audio and video routes from {0}", source.Key); var audioSuccess = destination.GetRouteToSource(source, null, null, eRoutingSignalType.Audio, 0, routeDescr); if (!audioSuccess) { Debug.Console(1, destination, "Cannot find audio route to {0}", source.Key); } var videoSuccess = destination.GetRouteToSource(source, null, null, eRoutingSignalType.Video, 0, routeDescr); if (!videoSuccess) { Debug.Console(1, destination, "Cannot find video route to {0}", source.Key); } if (!audioSuccess && !videoSuccess) { routeDescr = null; } } //Debug.Console(1, destination, "Route{0} discovered", routeDescr == null ? " NOT" : ""); return(routeDescr); }
/// <summary> /// The recursive part of this. Will stop on each device, search its inputs for the /// desired source and if not found, invoke this function for the each input port /// hoping to find the source. /// </summary> /// <param name="destination"></param> /// <param name="source"></param> /// <param name="onSuccessOutputPort"></param> /// <param name="alreadyCheckedDevices"></param> /// <param name="signalType"></param> /// <param name="cycle"></param> /// <param name="routeTable"></param> /// <returns>true if source is hit</returns> static bool GetRouteToSource(this IRoutingInputs destination, IRoutingOutputs source, RoutingOutputPort onSuccessOutputPort, List <IRoutingInputsOutputs> alreadyCheckedDevices, eRoutingSignalType signalType, int cycle, RouteDescriptor routeTable) { cycle++; Debug.Console(0, destination, "SelectInput-cycle {1}. Finding {2} route back to {0}", source.Key, cycle, signalType); var destDevInputTies = TieLineCollection.Default.Where(t => t.DestinationPort.ParentDevice == destination && (t.Type == signalType || t.Type == eRoutingSignalType.AudioVideo)); // find a direct tie var directTie = destDevInputTies.FirstOrDefault( t => !(t.SourcePort.ParentDevice is IRoutingInputsOutputs) && t.DestinationPort.ParentDevice == destination && t.SourcePort.ParentDevice == source); RoutingInputPort inputPort = null; if (directTie != null) // Found a tie directly to the source { Debug.Console(0, destination, "Found direct tie to {0}**", source.Key); inputPort = directTie.DestinationPort; } else // no direct-connect. Walk back devices. { Debug.Console(0, destination, "is not directly connected to {0}. Walking down tie lines", source.Key); // No direct tie? Run back out on the inputs' attached devices... // Only the ones that are routing devices var attachedMidpoints = destDevInputTies.Where(t => t.SourcePort.ParentDevice is IRoutingInputsOutputs); foreach (var inputTieToTry in attachedMidpoints) { Debug.Console(0, destination, "Trying to find route on {0}", inputTieToTry.SourcePort.ParentDevice.Key); var upstreamDeviceOutputPort = inputTieToTry.SourcePort; var upstreamRoutingDevice = upstreamDeviceOutputPort.ParentDevice as IRoutingInputsOutputs; // Check if this previous device has already been walked if (!(alreadyCheckedDevices != null && alreadyCheckedDevices.Contains(upstreamRoutingDevice))) { // haven't seen this device yet. Do it. Pass the output port to the next // level to enable switching on success var upstreamRoutingSuccess = upstreamRoutingDevice.GetRouteToSource(source, upstreamDeviceOutputPort, alreadyCheckedDevices, signalType, cycle, routeTable); if (upstreamRoutingSuccess) { Debug.Console(0, destination, "Upstream device route found"); inputPort = inputTieToTry.DestinationPort; break; // Stop looping the inputs in this cycle } } } } // we have a route on corresponding inputPort. *** Do the route *** if (inputPort != null) { Debug.Console(0, destination, "adding route:"); if (onSuccessOutputPort == null) { // it's a sink device routeTable.Routes.Add(new RouteSwitchDescriptor(inputPort)); } else if (destination is IRouting) { routeTable.Routes.Add(new RouteSwitchDescriptor(onSuccessOutputPort, inputPort)); } else // device is merely IRoutingInputOutputs { Debug.Console(0, destination, " No routing. Passthrough device"); } Debug.Console(0, destination, "Exiting cycle {0}", cycle); return(true); } if (alreadyCheckedDevices == null) { alreadyCheckedDevices = new List <IRoutingInputsOutputs>(); } alreadyCheckedDevices.Add(destination as IRoutingInputsOutputs); Debug.Console(0, destination, "No route found to {0}", source.Key); return(false); }
public RouteDescriptor GetRouteDescriptorForDestination(IRoutingInputs destination) { return(RouteDescriptors.FirstOrDefault(rd => rd.Destination == destination)); }
/// <summary> /// Constructor for a basic RoutingInputPort /// </summary> /// <param name="selector">An object used to refer to this port in the IRouting device's ExecuteSwitch method. /// May be string, number, whatever</param> /// <param name="parent">The IRoutingInputs object this lives on</param> public RoutingInputPort(string key, eRoutingSignalType type, eRoutingPortConnectionType connType, object selector, IRoutingInputs parent) : this(key, type, connType, selector, parent, false) { }