private void Initialize() { var xyzDataSeries3D = new XyzDataSeries3D <double>(); for (int i = 0, pointIndex = 0; i < Count; i++) { var m1 = _random.Next(2) == 0 ? -1 : 1; var m2 = _random.Next(2) == 0 ? -1 : 1; var x1 = _random.NextDouble() * m1; var x2 = _random.NextDouble() * m2; if (x1 * x1 + x2 * x2 > 1) { continue; } var x = 2 * x1 * Math.Sqrt(1 - x1 * x1 - x2 * x2); var y = 2 * x2 * Math.Sqrt(1 - x1 * x1 - x2 * x2); var z = 1 - 2 * (x1 * x1 + x2 * x2); // Append an XYZ Point with random color // Set the PointMetadata.Tag which we bind to in the View xyzDataSeries3D.Append(x, y, z, new PointMetadata3D(GetRandomColor(), 3.0f, false, string.Format("PointMetadata Index {0}", ++pointIndex))); } SciChart.RenderableSeries[0].DataSeries = xyzDataSeries3D; }
private void OnLoaded(object sender, RoutedEventArgs routedEventArgs) { // Create our data in another thread to stop the UI from being stalled. // It's not appending to SciChart Dataseries that is the problem, its Calling Rand.Next() two million times which is pretty slow :) TimedMethod.Invoke(() => { var dataSeries = new XyDataSeries <double, double>() { AcceptsUnsortedData = true }; var rand = new FasterRandom(); // Allow 1M points in WPF/DirectX. In Silverlight or software rendering, 100k points is enough to stress the renderer int count = FeaturesHelper.Instance.SupportsHardwareAcceleration ? (int)1E6 : (int)1E5; // Append some data for (int i = 0; i < count; i++) { dataSeries.Append(rand.NextDouble(), rand.NextDouble()); } // Bind to scichart Action bindData = () => { BindData(dataSeries); }; Dispatcher.BeginInvoke(bindData); }).After(200).OnThread(TimedMethodThread.Background).Go(); }
private void OnTimerTick(object sender, EventArgs e) { // Subsequent load, update point positions using a sort of brownian motion by using random // // Access Raw 'arrays' to the inner data series. This is the fastest way to read and access data, however // any operations will not be thread safe, and will not trigger a redraw. This is why we invalidate below // // See also XyzDataSeries.Append, Update, Remove, Insert which are atomic operations // // Note that the count of raw arrays may be greater than _xyzData.Count double[] xDataRaw = _xyzData.XValues.ToUncheckedList(); double[] yDataRaw = _xyzData.YValues.ToUncheckedList(); double[] zDataRaw = _xyzData.ZValues.ToUncheckedList(); // Update the data positions simulating 3D random walk / brownian motion for (int i = 0, count = _xyzData.Count; i < count; i++) { xDataRaw[i] += _random.NextDouble() - 0.5; yDataRaw[i] += _random.NextDouble() - 0.5; zDataRaw[i] += _random.NextDouble() - 0.5; } // Raise DataSeriesChanged event and trigger chart updates _xyzData.IsDirty = true; _xyzData.OnDataSeriesChanged(DataSeriesUpdate.DataChanged, DataSeriesAction.Update); }
public double GetGaussianRandomNumber(double mean, double stdDev) { double u1 = _random.NextDouble(); //these are uniform(0,1) random doubles double u2 = _random.NextDouble(); double randStdNormal = Math.Sqrt(-2.0 * Math.Log(u1)) * Math.Sin(2.0 * Math.PI * u2); //random normal(0,1) double randNormal = mean + stdDev * randStdNormal; //random normal(mean,stdDev^2) return(randNormal); }
private void FillDataSeries(WaterfallDataSeries3D <double> dataSeries, int sliceCount, int pointsPerSlice) { var count = pointsPerSlice * 2; var re = new double[count]; var im = new double[count]; for (int sliceIndex = 0; sliceIndex < sliceCount; ++sliceIndex) { for (var i = 0; i < count; i++) { re[i] = 2.0 * Math.Sin(2 * Math.PI * i / 20) + 5 * Math.Sin(2 * Math.PI * i / 10) + 2.0 * _random.NextDouble(); im[i] = -10; } _transform.run(re, im); var scaleCoef = Math.Pow(1.5, sliceIndex * 0.3) / Math.Pow(1.5, sliceCount * 0.3); for (var pointIndex = 0; pointIndex < pointsPerSlice; pointIndex++) { var mag = Math.Sqrt(re[pointIndex] * re[pointIndex] + im[pointIndex] * im[pointIndex]); var yVal = _random.Next(10, 20) * Math.Log10(mag / pointsPerSlice); yVal = (yVal <-25 || yVal> -5) ? (yVal < -25) ? -25 : _random.Next(-6, -3) : yVal; dataSeries[sliceIndex, pointIndex] = -yVal * scaleCoef; } } }
private void UpdateData() { lock (this) { for (int i = 0; i < Count; i++) { _re[i] = 2.0 * Math.Sin(2 * Math.PI * i / 20) + 5.0 * Math.Sin(2 * Math.PI * i / 10) + 2.0 * _random.NextDouble(); _im[i] = IsFrequencyDomain ? 0.0 : i; } if (IsFrequencyDomain) { _transform.run(_re, _im); for (int i = 0; i < Count; i++) { double mag = Math.Sqrt(_re[i] * _re[i] + _im[i] * _im[i]); _re[i] = 20 * Math.Log10(mag / Count); _im[i] = i; } } _dataSeries.SeriesName = YAxisTitle; _dataSeries.Clear(); _dataSeries.Append(_im, _re); } }
// Add 100 new data to DataSeries's private void OnNewData(object sender, EventArgs e) { _tick++; if (_tick == 2) { _tick = 0; _step = _random.Next(0, 11); } var massVal = new double[100]; for (int i = 0; i < 100; i++) { double y = _step * Math.Sin(((2 * Math.PI) * 0.4) * t) + _random.NextDouble() * 2; _yValues[i] = y; _tValues[i] = t; massVal[i] = y + 10; t += dt; } var sortData = massVal.OrderByDescending(x => x); using (_series0.SuspendUpdates()) using (_series1.SuspendUpdates()) using (_series2.SuspendUpdates()) { _series0.Append(_tValues, _yValues); _series1.PushRow(sortData.ToArray()); _series2.PushRow(sortData.ToArray()); } }
private void OnTick(object sender, EventArgs e) { // Ensure only one timer Tick processed at a time lock (_syncRoot) { for (int i = 0; i < _channelViewModels.Count; i++) { // Get the dataseries created for this channel var channel = _channelViewModels[i]; var dataseries = channel.ChannelDataSeries; // Preload previous value with k-1 sample, or 0.0 if the count is zero double xValue = dataseries.Count > 0 ? dataseries.XValues[dataseries.Count - 1] : 0.0; // Add points 10 at a time for efficiency for (int j = 0; j < BufferSize; j++) { // Generate a new X,Y value in the random walk xValue = xValue + 1; double yValue = _random.NextDouble(); xBuffer[j] = xValue; yBuffer[j] = yValue; } // Append block of values dataseries.Append(xBuffer, yBuffer); // For reporting current size to GUI _currentSize = dataseries.Count; } } }
private void FillSeries(HlcDataSeries <double, double> hlcDataSeries, DoubleSeries sourceData, double scale) { var xData = sourceData.XData; var yData = sourceData.YData.Select(x => x * scale).ToArray(); // Generate some random error data. Errors must be absolute values, // e.g. if a series has a Y-value of 5.0, and YError of =/-10% then you must enter YErrorHigh=5.5, YErrorLow=4.5 into the HlcDataSeries var random = new FasterRandom(); var yErrorHigh = yData.Select(y => y + random.NextDouble() * 0.2); var yErrorLow = yData.Select(y => y - random.NextDouble() * 0.2); // HlcDataSeries requires X, Y, High, Low. // For Error bars the High, Low becomes the High Low error, // while X,Y is the location of the error hlcDataSeries.Append(xData, yData, yErrorHigh, yErrorLow); }
private XyDataSeries <double, double> UpdateXyDataSeries() { var doubleSeries = new XyDataSeries <double, double>(); var _re = new double[1024]; var _im = new double[1024]; for (var i = 0; i < 1024; i++) { _re[i] = 2.0 * Math.Sin(2 * Math.PI * i / 20) + 5 * Math.Sin(2 * Math.PI * i / 10) + 2.0 * _random.NextDouble(); _im[i] = -10; } _transform.run(_re, _im); var _re2 = new double[500]; var _im2 = new double[500]; for (var i = 0; i < 500; i++) { var mag = Math.Sqrt(_re[i] * _re[i] + _im[i] * _im[i]); var yVal = 20 * Math.Log10(mag / 500); _re2[i] = (yVal <-25 || yVal> -5) ? (yVal < -25) ? -25 : _random.Next(-6, -3) : yVal; _im2[i] = i; } _re2[0] = -25; doubleSeries.Append(_im2, _re2); return(doubleSeries); }
private IEnumerable <BoxPoint> GetBoxPlotData() { var dates = Enumerable.Range(0, PointsCount).Select(i => i).ToArray(); var medianValues = new RandomWalkGenerator().GetRandomWalkSeries(PointsCount).YData; var random = new FasterRandom(); for (int i = 0; i < PointsCount; i++) { double med = medianValues[i]; double min = med - random.NextDouble(); double max = med + random.NextDouble(); double lower = (med - min) * random.NextDouble() + min; double upper = (max - med) * random.NextDouble() + med; yield return(new BoxPoint(dates[i], min, lower, med, upper, max)); } }
private void OnNewData(object sender, EventArgs e) { // Compute our three series values double y1 = 3.0 * Math.Sin(((2 * Math.PI) * 1.4) * t) + _random.NextDouble() * 0.5; double y2 = 2.0 * Math.Cos(((2 * Math.PI) * 0.8) * t) + _random.NextDouble() * 0.5; double y3 = 1.0 * Math.Sin(((2 * Math.PI) * 2.2) * t) + _random.NextDouble() * 0.5; // Suspending updates is optional, and ensures we only get one redraw // once all three dataseries have been appended to using (sciChart.SuspendUpdates()) { // Append x,y data to previously created series series0.Append(t, y1); series1.Append(t, y2); series2.Append(t, y3); } // Increment current time t += dt; }
private IXyDataSeries <double, double> CreateDataSeries() { var dataSeries = new XyDataSeries <double, double>(); dataSeries.SeriesName = "Random Series"; int i = 0; // Samples 0,1,2 append double.NaN for (; i < 3; i++) { dataSeries.Append(i, double.NaN); } // Samples 3,4,5,6 append values for (; i < 7; i++) { dataSeries.Append(i, _random.NextDouble()); } // Samples 7,8,9 append double.NaN for (; i < 10; i++) { dataSeries.Append(i, double.NaN); } // Samples 10,11,12,13 append values for (; i < 14; i++) { dataSeries.Append(i, -_random.NextDouble()); } // Samples 14,15,16 append double.NaN for (; i < 16; i++) { dataSeries.Append(i, double.NaN); } return(dataSeries); }
private static WaterfallDataSeries3D <double> GetWaterfallDataSeries() { var pointsPerSlice = 100; var sliceCount = 20; var logBase = 10; var slicePositions = new double[sliceCount]; for (int i = 0; i < sliceCount; ++i) { slicePositions[i] = i; } var dataSeries = new WaterfallDataSeries3D <double>(pointsPerSlice, slicePositions); dataSeries.StartX = 10; dataSeries.StepX = 1; _transform.init((uint)Math.Log(pointsPerSlice, 2)); var count = pointsPerSlice * 2; var re = new double[count]; var im = new double[count]; for (int sliceIndex = 0; sliceIndex < sliceCount; ++sliceIndex) { for (var i = 0; i < count; i++) { re[i] = 2.0 * Math.Sin(2 * Math.PI * i / 20) + 5 * Math.Sin(2 * Math.PI * i / 10) + 2.0 * _random.NextDouble(); im[i] = -10; } _transform.run(re, im); var scaleCoef = Math.Pow(1.5, sliceIndex * 0.3) / Math.Pow(1.5, sliceCount * 0.3); for (var pointIndex = 0; pointIndex < pointsPerSlice; pointIndex++) { var mag = Math.Sqrt(re[pointIndex] * re[pointIndex] + im[pointIndex] * im[pointIndex]); var yVal = _random.Next(10, 20) * Math.Log10(mag / pointsPerSlice); yVal = (yVal <-25 || yVal> -5) ? (yVal < -25) ? -25 : _random.Next(-6, -3) : yVal; dataSeries[sliceIndex, pointIndex] = -yVal * scaleCoef; } } return(dataSeries); }
private void Initialize() { var xyzDataSeries3D = new XyzDataSeries3D <double>(); for (var i = 0; i < Count; i++) { var m1 = _random.Next(2) == 0 ? -1 : 1; var m2 = _random.Next(2) == 0 ? -1 : 1; var x1 = _random.NextDouble() * m1; var x2 = _random.NextDouble() * m2; if (x1 * x1 + x2 * x2 < 1) { var x = 2 * x1 * Math.Sqrt(1 - x1 * x1 - x2 * x2); var y = 2 * x2 * Math.Sqrt(1 - x1 * x1 - x2 * x2); var z = 1 - 2 * (x1 * x1 + x2 * x2); xyzDataSeries3D.Append(x, y, z); } } SciChart.RenderableSeries[0].DataSeries = xyzDataSeries3D; }
private IDataSeries CreateSeries() { var rnd = new FasterRandom(); int w = 24, h = 7; var data = new double[h, w]; for (int x = 0; x < w; x++) { for (int y = 0; y < h; y++) { data[y, x] = Math.Pow(rnd.NextDouble(), 0.15) * x / (w - 1) * y / (h - 1) * 100; } } return(new UniformHeatmapDataSeries <int, int, double>(data, 0, 1, 0, 1)); }
/// <summary> /// Every X milliseconds we create a new DataSeries and append new data to it. /// Then, DataSeries are re-assigned to RenderableSeries. /// </summary> private void TimerOnElapsed(object sender, EventArgs e) { var newDataSeries = new XyDataSeries <double, double>(); // Create a noisy sinewave and cache // All this code is about the generation of data to create a nice randomized sinewave with // varying phase and amplitude var randomAmplitude = Constrain(_lastAmplitude + ((_random.NextDouble()) - 0.50) / 2, -2.0, 2.0); const double phase = 0.0; var noisySinewave = DataManager.Instance.GetNoisySinewave(randomAmplitude, phase, 1000, 0.25); _lastAmplitude = randomAmplitude; // Append to a new dataseries newDataSeries.Append(noisySinewave.XData, noisySinewave.YData); lineSeries.DataSeries = newDataSeries; }
public DoubleSeries GetRandomWalkSeries(int count) { var doubleSeries = new DoubleSeries(count); // Generate a slightly positive biased random walk // y[i] = y[i-1] + random, // where random is in the range -0.5, +0.5 for (int i = 0; i < count; i++) { double next = _last + (_random.NextDouble() - 0.5 + _bias); _last = next; doubleSeries.Add(new XYPoint() { X = _i++, Y = next }); } return(doubleSeries); }
public Simple3DHeatmapChart() { InitializeComponent(); var meshDataSeries = new UniformGridDataSeries3D <double>(XSize, ZSize) { StepX = 1, StepZ = 1 }; for (var x = 0; x < XSize; x++) { for (var z = 0; z < ZSize; z++) { var v = (1 + Math.Sin(x * 0.04 + Angle)) * 50 + (1 + Math.Sin(z * 0.1 + Angle)) * 50 * (1 + Math.Sin(Angle * 2)); var r = Math.Sqrt((x - Cx) * (x - Cx) + (z - Cy) * (z - Cy)); var exp = Math.Max(0, 1 - r * 0.008); meshDataSeries[z, x] = (v * exp + _random.NextDouble() * 50); } } //Trace.WriteLine(meshDataSeries.To2DArray().ToStringArray2D()); surfaceMesh.DataSeries = meshDataSeries; }
private void UpdateXyDataSeries() { lock (this) { for (int i = 0; i < 1024; i++) { _re[i] = 2.0 * Math.Sin(2 * Math.PI * i / 20) + 5 * Math.Sin(2 * Math.PI * i / 10) + 2.0 * _random.NextDouble(); _im[i] = -10; } _transform.run(_re, _im); for (int i = 0; i < 1024; i++) { double mag = Math.Sqrt(_re[i] * _re[i] + _im[i] * _im[i]); _re[i] = 20 * Math.Log10(mag / 1024); _im[i] = i; } _xyDataSeries.Clear(); _xyDataSeries.Append(_im, _re); } }
private void UsePointMarkers_OnLoaded(object sender, RoutedEventArgs e) { var dataSeries1 = new XyDataSeries <double, double>() { SeriesName = "Ellipse Marker" }; var dataSeries2 = new XyDataSeries <double, double>() { SeriesName = "Square Marker" }; var dataSeries3 = new XyDataSeries <double, double>() { SeriesName = "Triangle Marker" }; var dataSeries4 = new XyDataSeries <double, double>() { SeriesName = "Cross Marker" }; var dataSeries5 = new XyDataSeries <double, double>() { SeriesName = "Sprite Marker" }; const int dataSize = 30; var rnd = new FasterRandom(); for (int i = 0; i < dataSize; i++) { dataSeries1.Append(i, rnd.NextDouble()); } for (int i = 0; i < dataSize; i++) { dataSeries2.Append(i, 1 + rnd.NextDouble()); } for (int i = 0; i < dataSize; i++) { dataSeries3.Append(i, 1.8 + rnd.NextDouble()); } for (int i = 0; i < dataSize; i++) { dataSeries4.Append(i, 2.5 + rnd.NextDouble()); } for (int i = 0; i < dataSize; i++) { dataSeries5.Append(i, 3.5 + rnd.NextDouble()); } // insert a break into the line - we do this to test double.NaN for the point marker types dataSeries1.Update(dataSeries1.XValues[15], double.NaN); dataSeries2.Update(dataSeries1.XValues[15], double.NaN); dataSeries3.Update(dataSeries1.XValues[15], double.NaN); dataSeries4.Update(dataSeries1.XValues[15], double.NaN); dataSeries5.Update(dataSeries1.XValues[15], double.NaN); using (this.sciChart.SuspendUpdates()) { this.lineSeries1.DataSeries = dataSeries1; this.lineSeries2.DataSeries = dataSeries2; this.lineSeries3.DataSeries = dataSeries3; this.lineSeries4.DataSeries = dataSeries4; this.lineSeries5.DataSeries = dataSeries5; } this.sciChart.ZoomExtents(); }
public TenorCurves3DChart() { InitializeComponent(); _random = new FasterRandom(); int xSize = 25; int zSize = 25; var meshDataSeries = new UniformGridDataSeries3D <double, double, DateTime>(xSize, zSize); var lineDataSeries = new XyDataSeries <double>(); var mountainDataSeries = new XyDataSeries <double, double>(); meshDataSeries.StartZ = new DateTime(2010, 1, 1); meshDataSeries.StepZ = new TimeSpan(1, 0, 0, 0).ToDateTime(); double step; for (int x = 0; x < xSize; x++) { switch (x) { case 5: case 10: step = 0.309; break; case 4: case 9: step = 0.303; break; case 6: case 11: step = 0.303; break; case 23: step = 0.291; break; case 22: step = 0.294; break; case 24: step = 0.295; break; default: step = 0.3; break; } for (int z = 0; z < zSize; z++) { var y = (z != 0) ? Math.Pow((double)z + _random.NextDouble(), step) : Math.Pow((double)z + 1, 0.3); meshDataSeries[z, x] = y; } } double average; for (int x = 0; x < xSize; x++) { average = 0; for (int z = 0; z < zSize; z++) { average += meshDataSeries[x, z]; } var y = average / 25; lineDataSeries.Append(x, y); mountainDataSeries.Append(x, meshDataSeries[12, x]); } mountainRenderSeries.DataSeries = mountainDataSeries; LineRenderableSeries.DataSeries = lineDataSeries; surfaceMeshRenderableSeries.Maximum = (double)meshDataSeries.YRange.Max; surfaceMeshRenderableSeries.Minimum = (double)meshDataSeries.YRange.Min; surfaceMeshRenderableSeries.DataSeries = meshDataSeries; }