2 using System.Collections.Generic;
26 #region ISupportsSetValues Member
33 public void SetValues(
int FirstOutput, byte[] Values)
35 if (FirstOutput >= LedData.Length)
return;
36 if (FirstOutput < 0)
return;
37 int CopyLength = (LedData.Length - FirstOutput).Limit(0, Values.Length);
38 if (CopyLength < 1)
return;
42 Buffer.BlockCopy(Values, 0, LedData, FirstOutput, CopyLength);
43 UpdateRequired =
true;
50 private byte[] LedData =
new byte[0];
52 private byte[] OutputLedData =
new byte[0];
55 private int _ControllerNumber = 1;
63 public int ControllerNumber
65 get {
return _ControllerNumber; }
66 set { _ControllerNumber = value; }
70 private int _NumberOfLeds = 1;
78 public int NumberOfLeds
80 get {
return _NumberOfLeds; }
83 _NumberOfLeds = value.Limit(0, 4006);
84 LedData =
new byte[_NumberOfLeds * 3];
85 OutputLedData =
new byte[_NumberOfLeds * 3];
90 private bool _PackData =
false;
101 get {
return _PackData; }
102 set { _PackData = value; }
106 private object UpdateLocker =
new object();
107 private bool UpdateRequired =
true;
114 private readonly
int[] ColNrLookup = { 1, 0, 2 };
123 IOutput ON = ChangedOutput;
124 int ByteNr = ON.
Number - 1;
125 ByteNr = (ByteNr / 3) * 3 + ColNrLookup[ByteNr % 3];
133 if (LedData[ByteNr] != ON.
Value)
135 LedData[ByteNr] = ON.
Value;
136 UpdateRequired =
true;
143 Log.
Exception(
"DirectStripController {0} with number {1} has received a update with a illegal or to high output number ({2}).".Build(Name, ControllerNumber, ON.
Number), E);
150 private void AddOutputs()
152 for (
int i = 1; i <= NumberOfLeds * 3; i++)
156 Outputs.Add(
new LedStripOutput() { Name =
"{0}.{1}".Build(Name, i), Number = i });
172 Log.
Write(
"DirectStripController {0} with number {1} initialized and updaterthread started.".Build(Name, ControllerNumber));
181 FinishUpdaterThread();
182 Log.
Write(
"DirectStripController {0} with number {1} finished and updaterthread stopped.".Build(Name, ControllerNumber));
192 UpdaterThreadSignal();
198 #region UpdaterThread
199 private void InitUpdaterThread()
206 if (!UpdaterThreadIsActive)
208 KeepUpdaterThreadAlive =
true;
211 UpdaterThread =
new Thread(UpdaterThreadDoIt);
212 UpdaterThread.Name =
"DirectStripController {0} named {1} updater thread ".Build(ControllerNumber, Name);
213 UpdaterThread.Start();
217 Log.
Exception(
"DirectStripController {0} named {1} updater thread could not start.".Build(ControllerNumber, Name), E);
218 throw new Exception(
"DirectStripController {0} named {1} updater thread could not start.".Build(ControllerNumber, Name), E);
227 private void FinishUpdaterThread()
229 if (UpdaterThread != null)
233 KeepUpdaterThreadAlive =
false;
234 UpdaterThreadSignal();
235 if (!UpdaterThread.Join(1000))
237 UpdaterThread.Abort();
239 UpdaterThread = null;
243 Log.Exception(
"A error occured during termination of DirectStripController updater thread.", E);
244 throw new Exception(
"A error occured during termination of DirectStripController updater thread.", E);
253 public bool UpdaterThreadIsActive
257 if (UpdaterThread != null)
259 if (UpdaterThread.IsAlive)
271 private void UpdaterThreadSignal()
274 lock (UpdaterThreadLocker)
276 Monitor.Pulse(UpdaterThreadLocker);
281 private Thread UpdaterThread {
get; set; }
282 private object UpdaterThreadLocker =
new object();
283 private bool KeepUpdaterThreadAlive =
true;
288 private DirectStripControllerApi Controller = null;
293 private void UpdaterThreadDoIt()
295 if (Controller == null)
297 Controller =
new DirectStripControllerApi(ControllerNumber);
298 if (!Controller.DeviceIsPresent)
300 Log.
Warning(
"WS2811 Strip Controller Nr. {0} is not present. Will not send updates.".Build(ControllerNumber));
306 OutputLedData.Fill((byte)0);
307 if (Controller != null)
311 Controller.SetAndDisplayPackedData(OutputLedData);
315 Controller.SetAndDisplayData(OutputLedData);
318 while (KeepUpdaterThreadAlive)
325 UpdateRequired =
false;
327 Buffer.BlockCopy(LedData, 0, OutputLedData, 0, LedData.Length);
330 if (Controller != null)
334 Controller.SetAndDisplayPackedData(OutputLedData);
338 Controller.SetAndDisplayData(OutputLedData);
343 if (KeepUpdaterThreadAlive)
345 lock (UpdaterThreadLocker)
347 while (UpdateRequired ==
false && KeepUpdaterThreadAlive)
349 Monitor.Wait(UpdaterThreadLocker, 50);
356 OutputLedData.Fill((byte)0);
357 if (Controller != null)
361 Controller.SetAndDisplayPackedData(OutputLedData);
365 Controller.SetAndDisplayData(OutputLedData);
The Cabinet object describes the parts of a pinball cabinet (toys, outputcontrollers, outputs and more).
int Number
Gets or sets the number of the Output object.
override void OnOutputValueChanged(IOutput ChangedOutput)
This method is called whenever the value of a output in the Outputs property changes its value...
byte Value
Value of the output.
static void Warning(string Message)
Writes a warning message to the log.
This output controller class is used to control the direct strip controller by Swisslizard.
void SetValues(int FirstOutput, byte[] Values)
Sets the values for one or several outputs of the controller.
static void Write(string Message)
Writes the specified message to the logfile.
A simple logger used to record important events and exceptions.
override void Update()
Notifies the updater thread to sdend data to the controller hardware.
A simple wrapper for the OutputNumbered class. This might be replaced with some more sophisticated so...
Common interface for outputs of any output controller. The Output class implements this interface and...
Abstract OutputController base class to be used for IOutputController implementations. Implements IOutputController.
This interface defines additional methods for output controllers which allow for direct modification ...
override void Finish()
Finishes the output controller.
DirectStripController()
Initializes a new instance of the DirectStripController class.
The namespace DirectOutput.General contains classes for general use.
override void Init(Cabinet Cabinet)
Initializes the output controller.
static void Exception(string Message, Exception E=null)
Writes a exception message to the log.