/// <summary>
 /// Call this method when you turn on LiveScrolling.
 /// </summary>
 public void SetCurrentValue(DataValue value)
 {
     System.Threading.Interlocked.Exchange<DataValue>(ref currentValue, value);
 }
        private void SmoothScroll(DataValue newValue)
        {
            if (this.series == null)
            {
                this.series = new DataSeries() { Name = "", Values = new List<DataValue>() };
            }

            // we do not use the data value x coordinates right now because they are timestamp values
            // and they bunch up and are not smooth...due to random network noise, so until we figure
            // out something better the graph is smoothing out the x values.
            double x = 0;
            if (this.series.Values.Count > 0)
            {
                x = this.series.Values[this.series.Values.Count - 1].X + 1;
            }

            DataValue copy = new Model.DataValue()
            {
                X = x,
                Y = newValue.Y
            };

            this.series.Values.Add(copy);

            PathGeometry g = Graph.Data as PathGeometry;
            if (g == null)
            {
                UpdateChart();
                return;
            }
            PathFigure f = g.Figures[0];

            if (ComputeScale() || g.Bounds.Width > 2 * this.ActualWidth)
            {
                // can't do incremental, have to reset scaled values.
                if (this.series != null && this.series.Values.Count > 2 * this.ActualWidth)
                {
                    // purge history since this is an infinite scrolling stream...
                    this.series.Values.RemoveRange(0, this.series.Values.Count - (int)this.ActualWidth);
                    System.Diagnostics.Debug.WriteLine("Trimming data series {0} back to {1} values", this.series.Name, this.series.Values.Count);
                }
                UpdateChart();
            }
            else
            {
                AddScaledValues(f, updateIndex, series.Values.Count);
                Graph.UpdateLayout();
                if (g.Bounds.Width >= this.ActualWidth)
                {
                    Canvas.SetLeft(Graph, Canvas.GetLeft(Graph) - 1);
                }
                updateIndex = series.Values.Count;
            }
        }
Example #3
0
        internal DataValue GetDataValue(LogItemSchema schema, Message msg)
        {
            // we support 3 levels of nesting, so schema could be the row, the column or an array item.
            LogItemSchema rowSchema    = schema;
            LogItemSchema columnSchema = schema;
            LogItemSchema arraySchema  = schema;

            if (rowSchema.Parent != this.schema)
            {
                rowSchema = rowSchema.Parent;
            }
            if (rowSchema.Parent != this.schema)
            {
                columnSchema = rowSchema;
                rowSchema    = rowSchema.Parent;
            }

            StringBuilder textBuilder = new StringBuilder();
            var           row         = msg.TypedValue;

            if (row != null && row.GetType().Name == rowSchema.Type)
            {
                // get a time value for this message.
                FieldInfo fi = row.GetType().GetField(columnSchema.Name, BindingFlags.Public | BindingFlags.Instance);
                if (fi != null)
                {
                    object    value = fi.GetValue(row);
                    DataValue data  = new DataValue()
                    {
                        X = msg.Timestamp.Ticks / 10, UserData = row
                    };                                                                                 // microseconds (Ticks are in 100 nanoseconds).

                    // byte array is special (we treat this like text).
                    if (value is byte[])
                    {
                        textBuilder.Length = 0;
                        byte[] text   = (byte[])value;
                        bool   binary = false;
                        // see if this is binary or text.
                        for (int i = 0, n = text.Length; i < n; i++)
                        {
                            byte b = text[i];
                            if (b != 0 && b < 0x20 || b > 0x80)
                            {
                                binary = true;
                            }
                        }

                        for (int i = 0, n = text.Length; i < n; i++)
                        {
                            byte b = text[i];
                            if (b != 0)
                            {
                                if (binary)
                                {
                                    textBuilder.Append(b.ToString("x2"));
                                    textBuilder.Append(" ");
                                }
                                else
                                {
                                    char ch = Convert.ToChar(b);
                                    textBuilder.Append(ch);
                                }
                            }
                        }

                        data.Label = textBuilder.ToString();
                    }
                    else if (value is string)
                    {
                        data.Label = (string)value;
                    }
                    else
                    {
                        if (fi.FieldType.IsArray)
                        {
                            // then we are expecting an array selector as well...
                            Array a     = (Array)value;
                            int   index = 0;
                            int.TryParse(arraySchema.Name, out index);
                            if (a.Length > index)
                            {
                                value = a.GetValue(index);
                            }
                        }

                        data.Y     = ConvertToNumeric(value);
                        data.Label = GetLabel(row, columnSchema.Name);
                    };
                    return(data);
                }
            }
            return(null);
        }