public IEffectNode CreateEffectNode(Dictionary <Guid, ElementNode> elementNodes) { // Create a element node lookup of elements that are currently valid. //Currently we only have one TargetNode per effect, so removing all the extra junk that sorts though //Multiples. If it changes in the future, we can change this around. //IEnumerable<Guid> targetNodeIds = TargetNodes.Select(x => x.NodeId); //IEnumerable<Guid> validElementIds = targetNodeIds.Intersect(elementNodes.Keys); IEffectModuleInstance effect = Modules.ModuleManagement.GetEffect(TypeId); effect.InstanceId = InstanceId; effect.TimeSpan = TimeSpan; effect.StartTime = StartTime; //effect.TargetNodes = validElementIds.Select(x => elementNodes[x]).ToArray(); if (elementNodes.TryGetValue(TargetNodes.First().NodeId, out var node)) { effect.TargetNodes = new IElementNode[] { node }; } else { effect.TargetNodes = new IElementNode[] { new ProxyElementNode(TargetNodes.First().NodeId, TargetNodes.First().Name) }; } return(new EffectNode(effect, StartTime)); }
private static EffectNode CreateEffectNode(IEffectModuleInstance effectInstance, ElementNode targetNode, TimeSpan timeSpan) { // populate the given effect instance with the appropriate target node and times, and wrap it in an effectNode effectInstance.TargetNodes = new[] { targetNode }; effectInstance.TimeSpan = timeSpan; return(new EffectNode(effectInstance, TimeSpan.Zero)); }
public EffectParameterSetup(IEffectModuleDescriptor descriptor, IEffectModuleInstance effect) { InitializeComponent(); Icon = Resources.Properties.Resources.Icon_Vixen3; _descriptor = descriptor; IEffectEditorControl[] controls = ApplicationServices.GetEffectEditorControls(descriptor.TypeId).ToArray(); for (int i = 0; i < descriptor.Parameters.Count; i++) { IEffectEditorControl effectEditorControl = controls[i]; Control control = effectEditorControl as Control; effectEditorControl.TargetEffect = effect; control.Dock = DockStyle.Top; tableLayoutPanel.Controls.Add(new Label { Text = descriptor.Parameters[i].Name }); tableLayoutPanel.Controls.Add(control); } object[] effectParameters = (effect != null) ? effect.ParameterValues : new object[_descriptor.Parameters.Count]; if (controls.Length == 1) { // One control for all parameters. controls[0].EffectParameterValues = effectParameters; } else { // One control per parameter. for (int i = 0; i < descriptor.Parameters.Count; i++) { controls[i].EffectParameterValues = new[] { effectParameters[i] }; } } }
public EffectParameterSetup(IEffectModuleDescriptor descriptor, IEffectModuleInstance effect) { InitializeComponent(); _descriptor = descriptor; IEffectEditorControl[] controls = ApplicationServices.GetEffectEditorControls(descriptor.TypeId).ToArray(); for(int i=0; i<descriptor.Parameters.Count; i++) { IEffectEditorControl effectEditorControl = controls[i]; Control control = effectEditorControl as Control; effectEditorControl.TargetEffect = effect; control.Dock = DockStyle.Top; tableLayoutPanel.Controls.Add(new Label { Text = descriptor.Parameters[i].Name }); tableLayoutPanel.Controls.Add(control); } object[] effectParameters = (effect != null) ? effect.ParameterValues : new object[_descriptor.Parameters.Count]; if(controls.Length == 1) { // One control for all parameters. controls[0].EffectParameterValues = effectParameters; } else { // One control per parameter. for(int i = 0; i < descriptor.Parameters.Count; i++) { controls[i].EffectParameterValues = new[] { effectParameters[i] }; } } }
public Command(Guid effectId, params object[] parameterValues) { _effect = Modules.ModuleManagement.GetEffect(effectId); if (_effect == null) { throw new ArgumentException("Effect does not exist."); } ParameterValues = parameterValues; }
public InputEffectMap(IInputModuleInstance inputModule, IEffectModuleInstance effectModule, IInputInput input, int parameterIndex, IEnumerable <Guid> nodes) { InputModuleId = inputModule.InstanceId; InputId = input.Name; InputValueParameterIndex = parameterIndex; Nodes = nodes.ToArray(); EffectModuleId = effectModule.Descriptor.TypeId; EffectParameterValues = effectModule.ParameterValues; }
public EffectModelCandidate(IEffectModuleInstance effect) { _moduleDataClass = effect.Descriptor.ModuleDataClass; DataContractSerializer ds = new DataContractSerializer(_moduleDataClass); TypeId = effect.Descriptor.TypeId; _effectData = new MemoryStream(); using (XmlDictionaryWriter w = XmlDictionaryWriter.CreateBinaryWriter(_effectData)) ds.WriteObject(w, effect.ModuleData); }
public EffectModelCandidate(IEffectModuleInstance effect) { _moduleDataClass = effect.Descriptor.ModuleDataClass; DataContractSerializer ds = new DataContractSerializer(_moduleDataClass); TypeId = effect.Descriptor.TypeId; _effectData = new MemoryStream(); using (XmlDictionaryWriter w = XmlDictionaryWriter.CreateBinaryWriter(_effectData)) ds.WriteObject(w, effect.ModuleData); }
public EffectNode GenerateEffect(IInputInput input, TimeSpan effectTimeSpan) { IEffectModuleInstance effect = ApplicationServices.Get <IEffectModuleInstance>(EffectModuleId); EffectParameterValues[InputValueParameterIndex] = input.Value; effect.ParameterValues = EffectParameterValues; effect.TimeSpan = effectTimeSpan; effect.TargetNodes = Nodes.Select(x => VixenSystem.Nodes.FirstOrDefault(y => y.Id == x)).ToArray(); EffectNode effectNode = new EffectNode(effect, TimeSpan.Zero); return(effectNode); }
static public bool AreAllEffectRequiredPropertiesPresent(IEffectModuleInstance effectModule) { // This only happens if the effect is created outside of us. // In that case, it's not really a module instance and we can't check for required properties. // They're on their own as far as the outcome. if (effectModule.Descriptor != null) { EffectModuleDescriptorBase effectDescriptor = Modules.GetDescriptorById <EffectModuleDescriptorBase>(effectModule.Descriptor.TypeId); return(effectModule.TargetNodes.All(x => x.Properties.Select(y => y.Descriptor.TypeId).Intersect(effectDescriptor.PropertyDependencies).Count() == effectDescriptor.PropertyDependencies.Length)); } return(true); }
private EffectNode GenerateSetLevelEffect(int eventValue, int startEvent, int endEvent, ElementNode targetNode) { IEffectModuleInstance setLevelInstance = ApplicationServices.Get <IEffectModuleInstance>(Guid.Parse("32cff8e0-5b10-4466-a093-0d232c55aac0")); // Clone() Doesn't work! :( setLevelInstance.TargetNodes = new ElementNode[] { targetNode }; setLevelInstance.TimeSpan = TimeSpan.FromMilliseconds(parsedV2Sequence.EventPeriod * (endEvent - startEvent + 1)); EffectNode effectNode = new EffectNode(setLevelInstance, TimeSpan.FromMilliseconds(parsedV2Sequence.EventPeriod * startEvent)); effectNode.Effect.ParameterValues = new object[] { ((double)eventValue / byte.MaxValue), Color.White }; return(effectNode); }
private void _SetEffectParameters() { using (EffectParametersForm effectParametersForm = new EffectParametersForm(_SelectedEffect)) { if (effectParametersForm.ShowDialog() == DialogResult.OK) { IEffectModuleInstance effect = ApplicationServices.Get <IEffectModuleInstance>(_SelectedEffect); effect.ParameterValues = effectParametersForm.EffectParameters; _Effect = effect; } else { _Effect = null; } } }
public IEffectNode CreateEffectNode() { // Create a element node lookup of elements that are currently valid. var elementNodes = VixenSystem.Nodes.Distinct().ToDictionary(x => x.Id); IEnumerable <Guid> targetNodeIds = TargetNodes.Select(x => x.NodeId); IEnumerable <Guid> validElementIds = targetNodeIds.Intersect(elementNodes.Keys); IEffectModuleInstance effect = Modules.ModuleManagement.GetEffect(TypeId); effect.InstanceId = InstanceId; effect.TimeSpan = TimeSpan; effect.TargetNodes = validElementIds.Select(x => elementNodes[x]).ToArray(); return(new EffectNode(effect, StartTime)); }
private EffectNode GeneratePulseEffect(int eventStartValue, int eventEndValue, int startEvent, int endEvent, ElementNode targetNode) { IEffectModuleInstance pulseInstance = ApplicationServices.Get <IEffectModuleInstance>(Guid.Parse("cbd76d3b-c924-40ff-bad6-d1437b3dbdc0")); // Clone() Doesn't work! :( pulseInstance.TargetNodes = new ElementNode[] { targetNode }; pulseInstance.TimeSpan = TimeSpan.FromMilliseconds(parsedV2Sequence.EventPeriod * (endEvent - startEvent + 1)); EffectNode effectNode = new EffectNode(pulseInstance, TimeSpan.FromMilliseconds(parsedV2Sequence.EventPeriod * startEvent)); effectNode.Effect.ParameterValues = new Object[] { new Curve(new PointPairList(new double[] { startX, endX }, new double[] { getY(eventStartValue), getY(eventEndValue) })), new ColorGradient() }; return(effectNode); }
public void Rasterize(IEffectModuleInstance effect, Graphics g) { double width = g.VisibleClipBounds.Width; double height = g.VisibleClipBounds.Height; // As recommended by R# if (Math.Abs(width - 0) < double.Epsilon || Math.Abs(height - 0) < double.Epsilon) { return; } Element[] elements = effect.TargetNodes.GetElements(); double heightPerElement = height / elements.Length; EffectIntents effectIntents = effect.Render(); IntentRasterizer intentRasterizer = new IntentRasterizer(); double y = 0; foreach (Element element in elements) { //Getting exception on null elements here... A simple check to look for these null values and ignore them if (element != null) { IntentNodeCollection elementIntents = effectIntents.GetIntentNodesForElement(element.Id); if (elementIntents != null) { foreach (IntentNode elementIntentNode in elementIntents) { double startPixelX = width * _GetPercentage(elementIntentNode.StartTime, effect.TimeSpan); double widthPixelX = width * _GetPercentage(elementIntentNode.TimeSpan, effect.TimeSpan); // these were options to try and get the rasterization to 'overlap' slightly to remove vertical splits between intents. // However, with the change to doubles and more precision, the issue seems to have disappeared. Nevertheless, leave these here. //startPixelX -= 0.2; //widthPixelX += 0.4; //startPixelX = Math.Floor(startPixelX); //widthPixelX = Math.Ceiling(widthPixelX); intentRasterizer.Rasterize(elementIntentNode.Intent, new RectangleF((float)startPixelX, (float)y, (float)widthPixelX, (float)heightPerElement), g); } } } y += heightPerElement; } }
} // closeChannel /// <summary> /// Add a constant level effect to the destination channel /// </summary> /// <param name="intensity">period intensity</param> /// <param name="startEvent">number of V2 events to skip</param> /// <param name="endEvent">Last V2 event in the block</param> /// <param name="targetNode">Destination channel structure</param> /// <param name="v3color">Color for this effect</param> /// <returns></returns> public EffectNode GenerateSetLevelEffect(uint intensity, uint startEvent, uint endEvent, ElementNode targetNode, Color v3color) { // Logging.Info("Vixen2xSequenceImport::GenerateSetLevelEffect - Entry"); EffectNode effectNode = null; IEffectModuleInstance setLevelInstance = null; do { if (null == (setLevelInstance = ApplicationServices.Get <IEffectModuleInstance>(Guid.Parse("32cff8e0-5b10-4466-a093-0d232c55aac0")))) { // could not get the structure Logging.Error("Vixen 2 import: Could not allocate an instance of IEffectModuleInstance"); break; } // Clone() Doesn't work! :( setLevelInstance.TargetNodes = new ElementNode[] { targetNode }; // calculate how long the event lasts setLevelInstance.TimeSpan = TimeSpan.FromMilliseconds(EventDuration * (endEvent - startEvent + 1)); // set the event and event starting time if (null == (effectNode = new EffectNode(setLevelInstance, TimeSpan.FromMilliseconds(EventDuration * startEvent)))) { // could not allocate the structure Logging.Error("Vixen 2 import: Could not allocate an instance of EffectNode"); break; } // set intensity and color effectNode.Effect.ParameterValues = new object[] { (Convert.ToDouble(intensity) / Convert.ToDouble(byte.MaxValue)), v3color }; } while (false); // Logging.Info("Vixen2xSequenceImport::GenerateSetLevelEffect - Exit"); return(effectNode); } // end GenerateSetLevelEffect
} // end GenerateSetLevelEffect /// <summary> /// Add a constantly increasing / deacreasing ramp /// </summary> /// <param name="eventStartValue"></param> /// <param name="eventEndValue"></param> /// <param name="startEvent"></param> /// <param name="endEvent"></param> /// <param name="targetNode"></param> /// <param name="v3color"></param> /// <returns></returns> public EffectNode GeneratePulseEffect(uint eventStartValue, uint eventEndValue, uint startEvent, uint endEvent, ElementNode targetNode, Color v3color) { EffectNode effectNode = null; const double startX = 0.0; const double endX = 100.0; do { IEffectModuleInstance pulseInstance = ApplicationServices.Get <IEffectModuleInstance>(Guid.Parse("cbd76d3b-c924-40ff-bad6-d1437b3dbdc0")); if (null == pulseInstance) { Logging.Error("Vixen 2 import: Could not allocate an instance of IEffectModuleInstance"); break; } // Clone() Doesn't work! :( pulseInstance.TargetNodes = new ElementNode[] { targetNode }; pulseInstance.TimeSpan = TimeSpan.FromMilliseconds(EventDuration * (endEvent - startEvent + 1)); if (null == (effectNode = new EffectNode(pulseInstance, TimeSpan.FromMilliseconds(EventDuration * startEvent)))) { // could not allocate the structure Logging.Error("Vixen 2 import: Could not allocate an instance of EffectNode"); break; } effectNode.Effect.ParameterValues = new Object[] { new Curve(new PointPairList(new double[] { startX, endX }, new double[] { getY(eventStartValue), getY(eventEndValue) })), new ColorGradient(v3color) }; } while (false); return(effectNode); } // end GeneratePulseEffect
public void Rasterize(IEffectModuleInstance effect, Graphics g) { double width = g.VisibleClipBounds.Width; double height = g.VisibleClipBounds.Height; // As recommended by R# if (Math.Abs(width - 0) < double.Epsilon || Math.Abs(height - 0) < double.Epsilon) return; Element[] elements = effect.TargetNodes.GetElements(); double heightPerElement = height / elements.Length; EffectIntents effectIntents = effect.Render(); IntentRasterizer intentRasterizer = new IntentRasterizer(); double y = 0; foreach(Element element in elements) { IntentNodeCollection elementIntents = effectIntents.GetIntentNodesForElement(element.Id); if(elementIntents != null) { foreach(IntentNode elementIntentNode in elementIntents) { double startPixelX = width * _GetPercentage(elementIntentNode.StartTime, effect.TimeSpan); double widthPixelX = width * _GetPercentage(elementIntentNode.TimeSpan, effect.TimeSpan); // these were options to try and get the rasterization to 'overlap' slightly to remove vertical splits between intents. // However, with the change to doubles and more precision, the issue seems to have disappeared. Nevertheless, leave these here. //startPixelX -= 0.2; //widthPixelX += 0.4; //startPixelX = Math.Floor(startPixelX); //widthPixelX = Math.Ceiling(widthPixelX); intentRasterizer.Rasterize(elementIntentNode.Intent, new RectangleF((float)startPixelX, (float)y, (float)widthPixelX, (float)heightPerElement), g); } } y += heightPerElement; } }
public static void Rasterize(TimedSequenceElement tsElement, Graphics g, TimeSpan visibleStartOffset, TimeSpan visibleEndOffset, int overallWidth) { //var sw = new System.Diagnostics.Stopwatch(); sw.Start(); IEffectModuleInstance effect = tsElement.EffectNode.Effect; if (effect.ForceGenerateVisualRepresentation || Vixen.Common.Graphics.DisableEffectsEditorRendering) { var startX = (int)((visibleStartOffset.Ticks / (float)tsElement.Duration.Ticks) * overallWidth); effect.GenerateVisualRepresentation(g, new Rectangle(-startX, 0, overallWidth, (int)g.VisibleClipBounds.Height)); } else { double width = g.VisibleClipBounds.Width; double height = g.VisibleClipBounds.Height; // As recommended by R# if (Math.Abs(width - 0) < double.Epsilon || Math.Abs(height - 0) < double.Epsilon) { return; } // limit the number of 'rows' rasterized int tmpsiz = (int)(height / 2) + 1; EffectIntents effectIntents = effect.Render(); int count = effectIntents.Count; int skipCount = count > tmpsiz ? count / tmpsiz: 1; double heightPerElement = height / (count / skipCount); double y = 0; int ctr = 0; var elements = effect.TargetNodes.GetElements(); foreach (var element in elements) { if (ctr++ % skipCount != 0) { continue; } IntentNodeCollection elementIntents = effectIntents.GetIntentNodesForElement(element.Id); //effectIntents.GetIntentNodesForElement(element.Id); if (elementIntents != null && elementIntents.Count > 0) { //Determine if we have parallel intents used on this element for this effect. var stack = new List <List <IIntentNode> > { new List <IIntentNode> { elementIntents[0] } }; for (int i = 1; i < elementIntents.Count; i++) { bool add = true; foreach (List <IIntentNode> t in stack) { if (elementIntents[i].StartTime >= t.Last().EndTime) { t.Add(elementIntents[i]); add = false; break; } } if (add) { stack.Add(new List <IIntentNode> { elementIntents[i] }); } } int skip = 0; //Check for base or minimum level intent. if (stack.Count > 1 && stack[0].Count == 1 && stack[0][0].TimeSpan.Equals(effect.TimeSpan) && stack[1][0].TimeSpan != effect.TimeSpan) { //this is most likely a underlying base intent like chase, spin and twinkle use to provide a minimum value //so render it full size as it is usually a lower intensity and the pulses can be drawn over the top and look nice. intentRasterizer.Rasterize(stack[0][0].Intent, new RectangleF(0, (float)y, (float)width, (float)heightPerElement), g, visibleStartOffset, stack[0][0].TimeSpan); skip = 1; } float h = (float)heightPerElement / (stack.Count - skip); int stackCount = 0; //Now we have a good idea what our element should look like, lets draw it up foreach (List <IIntentNode> intentNodes in stack.Skip(skip)) { foreach (IntentNode elementIntentNode in intentNodes) { if (elementIntentNode == null) { Logging.Error("Error: elementIntentNode was null when Rasterizing an effect (ID: " + effect.InstanceId + ")"); continue; } if (elementIntentNode.EndTime < visibleStartOffset || elementIntentNode.StartTime > visibleEndOffset) { continue; } TimeSpan visibleIntentStart = elementIntentNode.StartTime < visibleStartOffset ? visibleStartOffset - elementIntentNode.StartTime : TimeSpan.Zero; TimeSpan visibleIntentEnd = elementIntentNode.EndTime > visibleEndOffset ? visibleEndOffset - elementIntentNode.StartTime : elementIntentNode.TimeSpan; double startPixelX = overallWidth * _GetPercentage(elementIntentNode.StartTime, effect.TimeSpan); double widthPixelX = overallWidth * _GetPercentage(elementIntentNode.TimeSpan, effect.TimeSpan); widthPixelX = widthPixelX * ((visibleIntentEnd.TotalMilliseconds - visibleIntentStart.TotalMilliseconds) / elementIntentNode.TimeSpan.TotalMilliseconds); if (visibleIntentStart == TimeSpan.Zero) { startPixelX -= overallWidth * _GetPercentage(visibleStartOffset, effect.TimeSpan); } else { startPixelX = 0; } intentRasterizer.Rasterize(elementIntentNode.Intent, new RectangleF((float)startPixelX, (float)y + h * stackCount, (float)widthPixelX, h), g, visibleIntentStart, visibleIntentEnd); } stackCount++; } } y += heightPerElement; } //long tRast = sw.ElapsedMilliseconds - tRend; //if( tRast > 10) // Logging.Debug(" oh: {0}, rend: {1}, rast: {2}, eff: {3}, node:{4}", tOh, tRend, tRast, effect.EffectName, effect.TargetNodes[0].Name); } }
/// <summary> /// Wraps an effect instance in an EffectNode, adds it to the sequence, and an associated element to the timeline control. /// Adds a Undo record for the add as well. /// </summary> /// <param name="effectInstance">Effect instance</param> /// <param name="row">Common.Controls.Timeline.Row to add the effect instance to</param> /// <param name="startTime">The start time of the effect</param> /// <param name="timeSpan">The duration of the effect</param> private void addEffectInstance(IEffectModuleInstance effectInstance, Row row, TimeSpan startTime, TimeSpan timeSpan) { try { //Debug.WriteLine("{0} addEffectInstance(InstanceId={1})", (int)DateTime.Now.TimeOfDay.TotalMilliseconds, effectInstance.InstanceId); if ((startTime + timeSpan) > SequenceLength) { timeSpan = SequenceLength - startTime; } var effectNode = CreateEffectNode(effectInstance, row, startTime, timeSpan); // put it in the sequence and in the timeline display AddEffectNode(effectNode); sequenceModified(); var act = new EffectsAddedUndoAction(this, new[] { effectNode }); _undoMgr.AddUndoAction(act); } catch (Exception ex) { string msg = "TimedSequenceEditor: error adding effect of type " + effectInstance.Descriptor.TypeId + " to row " + ((row == null) ? "<null>" : row.Name); Logging.ErrorException(msg, ex); } }
private void saveVirtualEffect(IEffectModuleInstance moduleInstance) { if (_virtualEffectLibrary == null) return; VirtualEffectNameDialog dialog = new VirtualEffectNameDialog(); if (dialog.ShowDialog() == DialogResult.OK) { _virtualEffectLibrary.addEffect(Guid.NewGuid(), dialog.effectName, moduleInstance.TypeId, moduleInstance.ParameterValues); toolStripExVirtualEffects_Clear(); LoadVirtualEffects(); } }
public Command(Guid effectId, params object[] parameterValues) { _effect = Modules.ModuleManagement.GetEffect(effectId); if(_effect == null) throw new ArgumentException("Effect does not exist."); ParameterValues = parameterValues; }
private static EffectNode CreateEffectNode(IEffectModuleInstance effectInstance, Row row, TimeSpan startTime, TimeSpan timeSpan) { // get the target element var targetNode = (ElementNode) row.Tag; // populate the given effect instance with the appropriate target node and times, and wrap it in an effectNode effectInstance.TargetNodes = new[] {targetNode}; effectInstance.TimeSpan = timeSpan; return new EffectNode(effectInstance, startTime); }
private void buttonOK_Click(object sender, EventArgs e) { Effect = ApplicationServices.Get <IEffectModuleInstance>(_descriptor.TypeId); Effect.ParameterValues = panelContainer.Controls.Cast <IEffectEditorControl>().SelectMany(x => x.EffectParameterValues).ToArray(); }
public EffectNode(IEffectModuleInstance effect, TimeSpan startTime) { Effect = effect; StartTime = startTime; }
private EffectNode CreateEffectNode(IEffectModuleInstance effectInstance, Row row, TimeSpan startTime, TimeSpan timeSpan, object[] parameterValues = null) { // get the target element var targetNode = (ElementNode) row.Tag; // populate the given effect instance with the appropriate target node and times, and wrap it in an effectNode effectInstance.TargetNodes = new[] {targetNode}; effectInstance.TimeSpan = timeSpan; effectInstance.StartTime = startTime; if (parameterValues != null) effectInstance.ParameterValues = parameterValues; if (effectInstance.SupportsMedia) { effectInstance.Media = Sequence.SequenceData.Media; } return new EffectNode(effectInstance, startTime); }
public static void Rasterize(IEffectModuleInstance effect, Graphics g) { //var sw = new System.Diagnostics.Stopwatch(); sw.Start(); if (effect.ForceGenerateVisualRepresentation || Vixen.Common.Graphics.DisableEffectsEditorRendering) { effect.GenerateVisualRepresentation(g, new Rectangle(0, 0, (int)g.VisibleClipBounds.Width, (int)g.VisibleClipBounds.Height)); } else { double width = g.VisibleClipBounds.Width; double height = g.VisibleClipBounds.Height; // As recommended by R# if (Math.Abs(width - 0) < double.Epsilon || Math.Abs(height - 0) < double.Epsilon) { return; } IEnumerable <Element> elements = effect.TargetNodes.GetElements(); // limit the number of 'rows' rasterized int tmpsiz = (int)(height / 2) + 1; if (elements.Count() > tmpsiz) { int skip = elements.Count() / tmpsiz; elements = elements.Where((element, index) => (index + 1) % skip == 0); } double heightPerElement = height / elements.Count(); //long tOh = sw.ElapsedMilliseconds; EffectIntents effectIntents = effect.Render(); //long tRend = sw.ElapsedMilliseconds - tOh; double y = 0; foreach (Element element in elements) { //Getting exception on null elements here... A simple check to look for these null values and ignore them if (element != null) { IntentNodeCollection elementIntents = effectIntents.GetIntentNodesForElement(element.Id); if (elementIntents != null && elementIntents.Count > 0) { //Determine if we have parallel intents used on this element for this effect. var stack = new List <List <IIntentNode> > { new List <IIntentNode> { elementIntents[0] } }; for (int i = 1; i < elementIntents.Count; i++) { bool add = true; foreach (List <IIntentNode> t in stack) { if (elementIntents[i].StartTime >= t.Last().EndTime) { t.Add(elementIntents[i]); add = false; break; } } if (add) { stack.Add(new List <IIntentNode> { elementIntents[i] }); } } int skip = 0; //Check for base or minimum level intent. if (stack.Count > 1 && stack[0].Count == 1 && stack[0][0].TimeSpan.Equals(effect.TimeSpan) && stack[1][0].TimeSpan != effect.TimeSpan) { //this is most likely a underlying base intent like chase, spin and twinkle use to provide a minimum value //so render it full size as it is usually a lower intensity and the pulses can be drawn over the top and look nice. double startPixelX = width * _GetPercentage(stack[0][0].StartTime, effect.TimeSpan); double widthPixelX = width * _GetPercentage(stack[0][0].TimeSpan, effect.TimeSpan); intentRasterizer.Rasterize(stack[0][0].Intent, new RectangleF((float)startPixelX, (float)y, (float)widthPixelX, (float)heightPerElement), g); skip = 1; } float h = (float)heightPerElement / (stack.Count - skip); int stackCount = 0; //Now we have a good idea what our element should look like, lets draw it up foreach (List <IIntentNode> intentNodes in stack.Skip(skip)) { foreach (IntentNode elementIntentNode in intentNodes) { if (elementIntentNode == null) { Logging.Error("Error: elementIntentNode was null when Rasterizing an effect (ID: " + effect.InstanceId + ")"); continue; } double startPixelX = width * _GetPercentage(elementIntentNode.StartTime, effect.TimeSpan); double widthPixelX = width * _GetPercentage(elementIntentNode.TimeSpan, effect.TimeSpan); intentRasterizer.Rasterize(elementIntentNode.Intent, new RectangleF((float)startPixelX, (float)y + h * stackCount, (float)widthPixelX, h), g); } stackCount++; } } } y += heightPerElement; } //long tRast = sw.ElapsedMilliseconds - tRend; //if( tRast > 10) // Logging.Debug(" oh: {0}, rend: {1}, rast: {2}, eff: {3}, node:{4}", tOh, tRend, tRast, effect.EffectName, effect.TargetNodes[0].Name); } }
/// <summary> /// Wraps an effect instance in an EffectNode, adds it to the sequence, and an associated element to the timeline control. /// </summary> /// <param name="effectInstance">Effect instance</param> /// <param name="row">Common.Controls.Timeline.Row to add the effect instance to</param> /// <param name="startTime">The start time of the effect</param> /// <param name="timeSpan">The duration of the effect</param> private void addEffectInstance(IEffectModuleInstance effectInstance, Row row, TimeSpan startTime, TimeSpan timeSpan) { try { //Debug.WriteLine("{0} addEffectInstance(InstanceId={1})", (int)DateTime.Now.TimeOfDay.TotalMilliseconds, effectInstance.InstanceId); // get the target channel ChannelNode targetNode = (ChannelNode)row.Tag; // populate the given effect instance with the appropriate target node and times, and wrap it in an effectNode effectInstance.TargetNodes = new ChannelNode[] {targetNode}; effectInstance.TimeSpan = timeSpan; EffectNode effectNode = new EffectNode(effectInstance, startTime); // put it in the sequence and in the timeline display TimedSequenceElement newElement = AddEffectNode(effectNode); sequenceModified(); var act = new EffectsAddedUndoAction(this, new EffectNode[] {effectNode}); _undoMgr.AddUndoAction(act); } catch(Exception ex) { string msg = "TimedSequenceEditor: error adding effect of type " + effectInstance.Descriptor.TypeId + " to row " + ((row == null) ? "<null>" : row.Name); VixenSystem.Logging.Error(msg, ex); } }
private static EffectNode CreateEffectNode(IEffectModuleInstance effectInstance, ElementNode targetNode, TimeSpan timeSpan) { // populate the given effect instance with the appropriate target node and times, and wrap it in an effectNode effectInstance.TargetNodes = new[] { targetNode }; effectInstance.TimeSpan = timeSpan; return new EffectNode(effectInstance, TimeSpan.Zero); }
private void papagayoImportToolStripMenuItem_Click(object sender, EventArgs e) { PapagayoDoc papagayoFile = new PapagayoDoc(); FileDialog openDialog = new OpenFileDialog(); openDialog.Filter = @"Papagayo files (*.pgo)|*.pgo|All files (*.*)|*.*"; openDialog.FilterIndex = 1; if (openDialog.ShowDialog() != DialogResult.OK) { return; } string fileName = openDialog.FileName; papagayoFile.Load(fileName); TimelineElementsClipboardData result = new TimelineElementsClipboardData { FirstVisibleRow = -1, EarliestStartTime = TimeSpan.MaxValue, }; result.FirstVisibleRow = 0; int rownum = 0; foreach (string voice in papagayoFile.VoiceList) { List <PapagayoPhoneme> phonemes = papagayoFile.PhonemeList(voice); if (phonemes.Count > 0) { foreach (PapagayoPhoneme phoneme in phonemes) { if (phoneme.DurationMS == 0.0) { continue; } IEffectModuleInstance effect = ApplicationServices.Get <IEffectModuleInstance>(new LipSyncDescriptor().TypeId); ((LipSync)effect).StaticPhoneme = (App.LipSyncApp.PhonemeType)Enum.Parse(typeof(App.LipSyncApp.PhonemeType), phoneme.TypeName.ToUpper()); ((LipSync)effect).LyricData = phoneme.LyricData; TimeSpan startTime = TimeSpan.FromMilliseconds(phoneme.StartMS); EffectModelCandidate modelCandidate = new EffectModelCandidate(effect) { Duration = TimeSpan.FromMilliseconds(phoneme.DurationMS - 1), StartTime = startTime }; result.EffectModelCandidates.Add(modelCandidate, rownum); if (startTime < result.EarliestStartTime) { result.EarliestStartTime = startTime; } effect.Render(); } IDataObject dataObject = new DataObject(ClipboardFormatName); dataObject.SetData(result); Clipboard.SetDataObject(dataObject, true); _TimeLineSequenceClipboardContentsChanged(EventArgs.Empty); SequenceModified(); } rownum++; } string displayStr = rownum + " Voices imported to clipboard as seperate rows\n\n"; int j = 1; foreach (string voiceStr in papagayoFile.VoiceList) { displayStr += "Row #" + j + " - " + voiceStr + "\n"; j++; } //messageBox Arguments are (Text, Title, No Button Visible, Cancel Button Visible) MessageBoxForm.msgIcon = SystemIcons.Information; //this is used if you want to add a system icon to the message form. var messageBox = new MessageBoxForm(displayStr, @"Papagayo Import", false, false); messageBox.ShowDialog(); }
public static void Rasterize(IEffectModuleInstance effect, Graphics g) { //var sw = new System.Diagnostics.Stopwatch(); sw.Start(); if (effect.ForceGenerateVisualRepresentation || Vixen.Common.Graphics.DisableEffectsEditorRendering) { effect.GenerateVisualRepresentation(g, new Rectangle(0, 0, (int)g.VisibleClipBounds.Width, (int)g.VisibleClipBounds.Height)); } else { double width = g.VisibleClipBounds.Width; double height = g.VisibleClipBounds.Height; // As recommended by R# if (Math.Abs(width - 0) < double.Epsilon || Math.Abs(height - 0) < double.Epsilon) return; IEnumerable<Element> elements = effect.TargetNodes.GetElements(); // limit the number of 'rows' rasterized int tmpsiz = (int)(height / 2) + 1; if (elements.Count() > tmpsiz) { int skip = elements.Count() / tmpsiz; elements = elements.Where((element, index) => (index + 1) % skip == 0); } double heightPerElement = height / elements.Count(); //long tOh = sw.ElapsedMilliseconds; EffectIntents effectIntents = effect.Render(); //long tRend = sw.ElapsedMilliseconds - tOh; double y = 0; foreach (Element element in elements) { //Getting exception on null elements here... A simple check to look for these null values and ignore them if (element != null) { IntentNodeCollection elementIntents = effectIntents.GetIntentNodesForElement(element.Id); if (elementIntents != null && elementIntents.Count > 0) { //Determine if we have parallel intents used on this element for this effect. var stack = new List<List<IIntentNode>> {new List<IIntentNode> {elementIntents[0]}}; for (int i = 1; i < elementIntents.Count; i++) { bool add = true; foreach (List<IIntentNode> t in stack) { if (elementIntents[i].StartTime >= t.Last().EndTime) { t.Add(elementIntents[i]); add = false; break; } } if (add) stack.Add(new List<IIntentNode> { elementIntents[i] }); } int skip = 0; //Check for base or minimum level intent. if (stack.Count > 1 && stack[0].Count == 1 && stack[0][0].TimeSpan.Equals(effect.TimeSpan) && stack[1][0].TimeSpan != effect.TimeSpan) { //this is most likely a underlying base intent like chase, spin and twinkle use to provide a minimum value //so render it full size as it is usually a lower intensity and the pulses can be drawn over the top and look nice. double startPixelX = width * _GetPercentage(stack[0][0].StartTime, effect.TimeSpan); double widthPixelX = width * _GetPercentage(stack[0][0].TimeSpan, effect.TimeSpan); intentRasterizer.Rasterize(stack[0][0].Intent, new RectangleF((float)startPixelX, (float)y, (float)widthPixelX, (float)heightPerElement), g); skip=1; } float h = (float)heightPerElement / (stack.Count-skip); int stackCount = 0; //Now we have a good idea what our element should look like, lets draw it up foreach (List<IIntentNode> intentNodes in stack.Skip(skip)) { foreach (IntentNode elementIntentNode in intentNodes) { if (elementIntentNode == null) { Logging.Error("Error: elementIntentNode was null when Rasterizing an effect (ID: " + effect.InstanceId + ")"); continue; } double startPixelX = width * _GetPercentage(elementIntentNode.StartTime, effect.TimeSpan); double widthPixelX = width * _GetPercentage(elementIntentNode.TimeSpan, effect.TimeSpan); intentRasterizer.Rasterize(elementIntentNode.Intent, new RectangleF((float)startPixelX, (float)y+h*stackCount , (float)widthPixelX, h), g); } stackCount++; } } } y += heightPerElement; } //long tRast = sw.ElapsedMilliseconds - tRend; //if( tRast > 10) // Logging.Debug(" oh: {0}, rend: {1}, rast: {2}, eff: {3}, node:{4}", tOh, tRend, tRast, effect.EffectName, effect.TargetNodes[0].Name); } }
private void buttonOK_Click(object sender, EventArgs e) { Effect = ApplicationServices.Get<IEffectModuleInstance>(_descriptor.TypeId); Effect.ParameterValues = panelContainer.Controls.Cast<IEffectEditorControl>().SelectMany(x => x.EffectParameterValues).ToArray(); }