real-time measuring and plotting into a graph. HOW?
-
- Enthusiast
- Posts: 290
- Joined: Thu Dec 16, 2010 2:05 pm
- Location: Delfzijl ( The Netherlands )
- Contact:
real-time measuring and plotting into a graph. HOW?
i have several real-time measuring progams in pure basic.
I like to see a graph while i am measuring.
So every new measurement must give a new pixel in the graph.
for example i do 2 measurements per second.
So the graph will grow while i am measuring.
I do not know how to do this.
the startdrawing and stopdrawing commands are
( as far as i know ) not usable......?
Wim
I like to see a graph while i am measuring.
So every new measurement must give a new pixel in the graph.
for example i do 2 measurements per second.
So the graph will grow while i am measuring.
I do not know how to do this.
the startdrawing and stopdrawing commands are
( as far as i know ) not usable......?
Wim
Re: real-time measuring and plotting into a graph. HOW?
There is an excellent piece of code by uwekel: http://www.purebasic.fr/english/viewtop ... 14&t=59038
Slightly modified to make it scroll:
Slightly modified to make it scroll:
Code: Select all
;{ Chart
Macro Section
;this macro is just for code folding and indentation
EndMacro
Macro EndSection
EndMacro
Macro Iter(Object, ListOrMap)
ListOrMap
Object=ListOrMap
EndMacro
Macro Max(a, b)
((a) * Bool((a) >=(b)) + (b) * Bool((b) > (a)))
EndMacro
Macro Min(a, b)
((a) * Bool((a) <=(b)) + (b) * Bool((b) < (a)))
EndMacro
Macro New(Object)
AllocateMemory(SizeOf(Object))
EndMacro
Procedure.l ChangeColor(Color.l, Offset.l)
Protected i, a.a
;split color
For i = 0 To 2
a = PeekA(@color + i)
If a + Offset < 0
a = 0
ElseIf a + Offset > 255
a = 255
Else
a + Offset
EndIf
PokeA(@color + i, a)
Next
;return new color
ProcedureReturn Color
EndProcedure
Enumeration ;flags
#ChartFlagBorder = 1
#ChartFlagLegendRight = 2
#ChartFlagLegendBottom = 4
#ChartFlagXAxis = 8
#ChartFlagYAxis = 16
#ChartFlagHGrid = 32
#ChartFlagVGrid = 64
#ChartFlagStapled = 128
#ChartFlagBarsBorderless = 256
#ChartFlagXAxisVAlign = 512
#ChartFlagSortColumns = 1024
#ChartFlagSortRows = 2048
EndEnumeration
Enumeration ;attributes
#ChartSetFlags
#ChartSetFont
#ChartSetBackColor
#ChartSetFrontColor
#ChartSetAreaColor
#ChartSetGridColor
#ChartSetValueColor
#ChartSetAxisColor
#ChartSetLineWidth
#ChartSetPointSize
#ChartSetPadding
#ChartSetDecimalPlaces
#ChartSetFillStyle
EndEnumeration
Enumeration ;text types
#ChartTextTitle
#ChartTextYAxis
#ChartTextXAxis
#ChartTextUnit
EndEnumeration
Enumeration ;row types
#ChartRowTypeBar
#ChartRowTypeLine
EndEnumeration
Enumeration ;row flags
#ChartRowFlagValues = 1
#ChartRowFlagPoints = 2
EndEnumeration
Enumeration ;value flags
#ChartValueFlagReplace
#ChartValueFlagSum
;FEAT average
EndEnumeration
Enumeration ;fill styles
#ChartFillStyleSolid
#ChartFillStyleGradient
#ChartFillStyleEmbossed
;FEAT more fill styles
EndEnumeration
Enumeration ;clear flags
#ChartClearKeepRows = 1
#ChartClearKeepColumns = 2
EndEnumeration
Structure _ChartRow
Name.s
Type.b
Color.l
Flags.i
LastY.i
EndStructure
Structure _ChartColumn
Name.s
Minimum.f
Maximum.f
EndStructure
Structure _ChartValue
Row.s
Column.s
Value.f
EndStructure
Structure _Chart
Title.s
YTitle.s
XTitle.s
Unit.s
BackColor.l
FrontColor.l
AreaColor.l
GridColor.l
ValueColor.l
AxisColor.l
LineWidth.i
PointSize.i
Padding.i
DecimalPlaces.i
FillStyle.i
Minimum.f
Maximum.f
Flags.i
Font.i
TextHeight.i
StepValue.f
BarRowCount.i
List Rows._ChartRow()
List Columns._ChartColumn()
List Values._ChartValue()
EndStructure
Procedure.l _ChartBlendColor(Color1.l, Color2.l, Index, Count)
Protected.a r1, g1, b1, r2, g2, b2, r, g, b
;split first color
r1 = Red(Color1)
g1 = Green(Color1)
b1 = Blue(Color1)
;split second color
r2 = Red(Color2)
g2 = Green(Color2)
b2 = Blue(Color2)
;blend colors
Protected f.f = Index / Count
r = r1 + (r2 - r1) * f
g = g1 + (g2 - g1) * f
b = b1 + (b2 - b1) * f
;return new color
ProcedureReturn RGB(r, g, b)
EndProcedure
Procedure.f _ChartRoundUp(Value.f, StepValue.f)
;rounds a value to the next higher step
Protected negative, v.f
;convert negative to positive
If Value < 0
negative = #True
Value * -1
EndIf
;round value
v = Int(Value / StepValue) * StepValue
If v < Value
v + StepValue
EndIf
;restore negative value
If negative
v * -1
EndIf
;return result
ProcedureReturn v
EndProcedure
Procedure.f _ChartRoundStepValue(Value.f)
;returns a good step range value for a data point value
Protected n
;avoid errors if value is zero
If Not Value
ProcedureReturn 1
EndIf
;move value between 1 and 10
While Value > 10
Value / 10
n - 1
Wend
While Value < 1
Value * 10
n + 1
Wend
;round
Select Value
Case 1 To 2.5
Value = 2.5
Case 2.5 To 5
Value = 5
Default
Value = 10
EndSelect
;move value to original position
While n > 0
Value / 10
n - 1
Wend
While n < 0
Value * 10
n + 1
Wend
;return rounded result
ProcedureReturn Value
EndProcedure
Procedure _ChartPoint(X, Y, Radius)
;FEAT FillColor
Protected xl, xr, yt, yb, i, yo
;get corner positions
xl = x - Radius
xr = x + Radius
yt = y - Radius
yb = y + Radius
;filling
For i = Radius To 0 Step -1
yo = Radius - i
LineXY(x - i, y - yo, x + i, y - yo)
LineXY(x - i, y + yo, x + i, y + yo)
Next
;border
LineXY(xl, y, x, yt, 0)
LineXY(x, yt, xr, y, 0)
LineXY(xl, y, x, yb, 0)
LineXY(x, yb, xr, y, 0)
EndProcedure
Procedure _ChartLine(X, Y, x3, y3, Color, Thickness)
;paints a chart line with anti-aliasing
Protected.f thick, x2, y2, app, hypo, cosphi, sinphi
Protected.l color1, color2, r, g, b, r1, g1, b1
Protected signx, signy, n, nn, w, h, xp, yp
w = x3 - X
h = y3 - Y
If w >= 0
signx = 1
Else
signx = -1
w = -w
EndIf
If h >= 0
signy = 1
Else
signy = -1
h = -h
EndIf
thick.f = Thickness / 2
hypo.f = Sqr(w * w + h * h)
cosphi.f = w / hypo
sinphi.f = -Sin(ACos(cosphi))
For n = -Thickness To w + Thickness
For nn = -Thickness To h + Thickness
x2 = n * cosphi - nn * sinphi
y2 = Abs(n * sinphi + nn * cosphi)
If y2 <= thick + 0.5
app = 0.5 + thick - y2
If app > 1
app = 1
EndIf
If x2 > -1 And x2 < hypo + 1
If x2 < 0
app * (1 + x2)
ElseIf x2 > hypo
app * (1 - x2 + hypo)
EndIf
Else
app = 0
EndIf
If app > 0
xp = X + n * signx
If xp >= 0 And xp < OutputWidth()
yp = Y + nn * signy
If yp >= 0 And yp < OutputHeight()
If app >= 1
Plot(xp, yp, Color)
Else
color1 = Point(xp, yp)
r = Color & $FF
g = Color >> 8 & $FF
b = Color >> 16
r1 = color1 & $FF
g1 = color1 >> 8 & $FF
b1 = color1 >> 16
r = r * app + r1 * (1 - app)
g = g * app + g1 * (1 - app)
b = b * app + b1 * (1 - app)
color2 = RGB(r, g, b)
Plot(xp, yp, color2)
EndIf
EndIf
EndIf
EndIf
EndIf
Next
Next
EndProcedure
Procedure _ChartPaintValue(*c._Chart, X, Y, Value.f)
;paint value
Protected w, h, s.s
;get value string
s = StrF(Value, *c\DecimalPlaces)
;coordinates
w = TextWidth(s)
h = *c\TextHeight
X - w / 2
Y - *c\TextHeight / 2
;draw
DrawText(X, Y, s, *c\FrontColor, *c\ValueColor)
DrawingMode(#PB_2DDrawing_Outlined)
X - 1: Y - 1: w + 2: h + 2
Box(X, Y, w, h, *c\ValueColor)
X - 1: Y - 1: w + 2: h + 2
Box(X, Y, w, h, 0)
DrawingMode(#PB_2DDrawing_Default)
EndProcedure
Procedure _ChartPaintBar(*c._Chart, *r._ChartRow, x, y, w, h)
Protected i, c1.l, c2.l
;rotate coordinates if hight is negative (to avoid further problems when painting)
If h < 0
y + h
h * -1
EndIf
;paint bar
Select *c\FillStyle
Case #ChartFillStyleSolid
Box(x, y, w, h, *r\Color)
Case #ChartFillStyleGradient
c1 = ChangeColor(*r\Color, $50)
For i = 0 To w / 2
c2 = _ChartBlendColor(*r\Color, c1, i, w / 2)
Line(x + i, y, 1, h, c2)
Line(x + w - 1 - i, y, 1, h, c2)
Next
Case #ChartFillStyleEmbossed
Box(x, y, w, h, *r\Color)
For i = 1 To 4
c1 = ChangeColor(*r\Color, 50 - i * 10) ;light
c2 = ChangeColor(*r\Color, -50 + i * 10) ;dark
Line(x + i, y + i, w - 1 - i * 2, 1, c1)
Line(x + i, y + i, 1, h - 1 - i * 2, c1)
Line(x + w - i, y + i, 1, h - i * 2, c2)
Line(x + i, y + h - i, w - i * 2 + 1, 1, c2)
Next
EndSelect
;paint bar borders
If Not *c\Flags & #ChartFlagBarsBorderless
Line(x, y, 1, h, 0)
Line(x, y, w, 1, 0)
Line(x + w, y, 1, h, 0)
Line(x, y + h, w + 1, 1, 0)
EndIf
EndProcedure
Procedure _ChartPaintLegend(*c._Chart, *r._ChartRow, x, y)
;paint legend item
Protected i, cx, cy, ps
Select *r\Type
Case #ChartRowTypeBar
_ChartPaintBar(*c, *r, x + 1, y + 1, *c\TextHeight - 3, *c\TextHeight - 2)
Case #ChartRowTypeLine
cy = y + *c\TextHeight / 2
_ChartLine(x + 1, cy, x + *c\TextHeight - 2, cy, *r\Color, *c\LineWidth)
;limit pointsize to textsize
cx = x + *c\TextHeight / 2 - 1
ps = Min(*c\PointSize, *c\TextHeight / 2 - 2)
_ChartPoint(cx, cy, ps)
EndSelect
;row name
DrawText(x + *c\TextHeight + 1, y, *r\Name, *c\FrontColor, *c\BackColor)
EndProcedure
Procedure ChartPaint(Gadget)
;paint the whole chart
Protected *g._Chart, *c._ChartColumn, *r._ChartRow, *v._ChartValue
Protected x, y, w, h, font, xah, yaw, areah, splits, v.f, x1, y1, cw.f, i, xr, s.s, tw, cx, bw, zypos, zyneg, zy, bx, vh, px, py, lx, ly, lw, pass
#_ChartAxisLimiterLength = 8
#_ChartLegendPad = 8
#_ChartXAxisPad = 4
*g = GetGadgetData(Gadget)
With *g
StartDrawing(CanvasOutput(Gadget))
;preparation
Section
;drawing area size
w = OutputWidth()
h = OutputHeight()
;create and measure font
DrawingFont(\Font)
\TextHeight = TextHeight("Xg")
;paint background
Box(x, y, w, h, \BackColor)
;add padding
If \Padding
x + \Padding
y + \Padding
w - \Padding * 2
h - \Padding * 2
EndIf
EndSection
;paint top title
Section
If \Title
tw = TextWidth(\Title)
DrawText((w - tw) / 2, y, \Title, \FrontColor, \BackColor)
y + \TextHeight + \Padding
h - \TextHeight - \Padding
ElseIf \Flags & #ChartFlagYAxis
;at least use half height of text as spacing for y-axis values
y + \TextHeight / 2
h - \TextHeight / 2
EndIf
EndSection
;paint legend
Section
If \Flags & #ChartFlagLegendRight
;maximum row name width
ly = y + h / 2
ForEach Iter(*r, \Rows())
tw = TextWidth(*r\Name)
If tw > lw
lw = tw
EndIf
ly - (\TextHeight + #_ChartLegendPad) / 2
Next
tw + \TextHeight
lx = x + w - tw
ForEach Iter(*r, \Rows())
_ChartPaintLegend(*g, *r, lx, ly)
ly + \TextHeight + #_ChartLegendPad
Next
w - tw - \Padding
ElseIf \Flags & #ChartFlagLegendBottom
;get total width
ly = y + h - \TextHeight - \Padding
lx = x + w / 2
ForEach Iter(*r, \Rows())
;#_ChartLegendPad = 8
lx - (TextWidth(*r\Name) + \TextHeight - #_ChartLegendPad) / 2
Next
ForEach Iter(*r, \Rows())
tw = TextWidth(*r\Name)
_ChartPaintLegend(*g, *r, lx, ly + \Padding)
lx + tw + \TextHeight + #_ChartLegendPad
Next
h - \TextHeight - \Padding
EndIf
EndSection
;left title of y-axis
Section
If \YTitle
tw = TextWidth(\YTitle)
DrawRotatedText(x, y + (h + tw) / 2, \YTitle, 90, \FrontColor)
x + \TextHeight + \Padding
w - \TextHeight - \Padding
EndIf
EndSection
;bottom title of x-axis
Section
If \XTitle
tw = TextWidth(\XTitle)
DrawText(x + (w - tw) / 2, y + h - \TextHeight, \XTitle, \FrontColor, \BackColor)
h - \TextHeight - \Padding
EndIf
EndSection
;x-axis height
Section
If \Flags & #ChartFlagXAxis
xah = #_ChartAxisLimiterLength
If \Flags & #ChartFlagXAxisVAlign
ForEach \Columns()
xah = Max(xah, TextWidth(\Columns()\Name))
Next
Else
xah = Max(xah, \TextHeight)
EndIf
;add small gap between
xah + #_ChartXAxisPad * 2
;reduce remain space for area
h - xah
EndIf
EndSection
;value range
Section
If h > 0
;get value range for each column
ForEach Iter(*c, \Columns())
*c\Minimum = 0
*c\Maximum = 0
ForEach Iter(*v, \Values())
If *v\Column = *c\Name
If \Flags & #ChartFlagStapled ;sum stapled bars
ForEach Iter(*r, \Rows())
If *r\Name = *v\Row
If *r\Type = #ChartRowTypeBar
If *v\Value > 0
*c\Maximum + *v\Value
Else
*c\Minimum + *v\Value
EndIf
EndIf
Break
EndIf
Next
ElseIf *v\Value < *c\Minimum
*c\Minimum = *v\Value
ElseIf *v\Value > *c\Maximum
*c\Maximum = *v\Value
EndIf
EndIf
Next
Next
;calculate min/max for chart (over all columns)
\Minimum = 0
\Maximum = 0
ForEach Iter(*c, \Columns())
If *c\Minimum < \Minimum
\Minimum = *c\Minimum
EndIf
If *c\Maximum > \Maximum
\Maximum = *c\Maximum
EndIf
Next
;widen range to avoid later errors (division by 0)
If \Maximum = \Minimum
\Maximum + 1
EndIf
;number of splits
Select h
Case 0 To 50
splits = 1
Case 0 To 100
splits = 2
Case 100 To 500
splits = 5
Default
splits = 10
EndSelect
;calculate and round step value
\StepValue = (\Maximum - \Minimum) / splits
\StepValue = _ChartRoundStepValue(\StepValue)
;round min/max
\Minimum = _ChartRoundUp(\Minimum, \StepValue)
\Maximum = _ChartRoundUp(\Maximum, \StepValue)
EndIf
EndSection
;y-axis width
Section
If \Flags & #ChartFlagYAxis
yaw = TextWidth(StrF(\Maximum, \DecimalPlaces) + \Unit)
tw = TextWidth(StrF(\Minimum, \DecimalPlaces) + \Unit)
If tw > yaw
yaw = tw
EndIf
yaw + #_ChartAxisLimiterLength
x + yaw
w - yaw
EndIf
EndSection
;paint area
Section
If h > 0
;background
Box(x, y, w, h, \AreaColor)
;paint horizontal grid of x-axis
If \Flags & #ChartFlagHGrid
v = \Minimum
While v <= \Maximum
y1 = y + h - h * (v - \Minimum) / (\Maximum - \Minimum)
Line(x, y1, w, 1, \GridColor)
v + \StepValue
Wend
EndIf
;paint vertical grid of y-axis
If \Flags & #ChartFlagVGrid
cw = w / ListSize(\Columns())
Line(x, y, 1, h, \GridColor)
ForEach \Columns()
i + 1
x1 = x + cw * i
Line(x1, y, 1, h, \GridColor)
Next
EndIf
;black line at zero position
y1 = y + h - h * -\Minimum / (\Maximum - \Minimum)
If y1 >= y And y1 <= y + h
Line(x, y1, w + 1, 1, \AxisColor)
EndIf
EndIf
EndSection
;paint values
Section
If FirstElement(\Values())
;reset last y-positions per row (for line chart)
ForEach \Rows()
\Rows()\LastY = 0
Next
;single column width
#Gap = 0.125
cw = w / ListSize(\Columns())
;single bar width
bw = cw * (1 - #Gap - #Gap)
;share width of bars if not stapled
If Not \Flags & #ChartFlagStapled And \BarRowCount > 1
bw / \BarRowCount
EndIf
;paint bars then lines
For pass = 1 To 3
ForEach Iter(*c, \Columns())
;column x-position
cx = x + ListIndex(\Columns()) * cw
;zero line y-position
zypos = y + h - h * -\Minimum / (\Maximum - \Minimum)
zyneg = zypos
bx = cx + cw * #Gap
ForEach Iter(*r, \Rows())
ForEach Iter(*v, \Values())
If *v\Row = *r\Name And *v\Column = *c\Name
vh = h * *v\Value / (\Maximum - \Minimum)
If pass = 1 And *r\Type = #ChartRowTypeBar
Section ;paint bars in first pass
;positive values above zero line, negatives below
If *v\Value > 0 Or Not \Flags & #ChartFlagStapled
zy = zypos
Else
zy = zyneg
EndIf
;paint bar
_ChartPaintBar(*g, *r, bx, zy - vh, bw, vh)
;paint value
If *r\Flags & #ChartRowFlagValues
_ChartPaintValue(*g, bx + bw / 2, zy - vh / 2, *v\Value)
EndIf
;shift to next bar position
If Not \Flags & #ChartFlagStapled
bx + bw ;next is right
ElseIf *v\Value > 0
zypos - vh ;next positve value is above
Else
zyneg - vh ;next negative value is below
EndIf
EndSection
ElseIf *r\Type = #ChartRowTypeLine
;value point position
px = cx + cw / 2
py = zypos - vh
If pass = 2
Section ;paint lines in second pass
;line is possible from the second value
If \Rows()\LastY
_ChartLine(px - cw, *r\LastY, px, py, *r\Color, \LineWidth)
EndIf
;remember this y-position so a line can be drawn next
*r\LastY = py
EndSection
ElseIf pass = 3
Section ;paint data points and values in third pass
_ChartPoint(px, py, \PointSize)
;paint value
If *r\Flags & #ChartRowFlagValues
If *v\Value >= 0
;positiv above line
py - \PointSize - \TextHeight + 4
Else
;negative below line
py + \PointSize + \TextHeight - 4
EndIf
_ChartPaintValue(*g, px, py, *v\Value)
EndIf
EndSection
EndIf
EndIf
EndIf
Next
Next
Next
Next
EndIf
EndSection
;paint y-axis
Section
If \Flags & #ChartFlagYAxis
;vertical line
Line(x, y, 1, h, \AxisColor)
;delimiters and values
v = \Minimum
While v <= \Maximum
y1 = y + h - h * (v - \Minimum) / (\Maximum - \Minimum)
Line(x - #_ChartAxisLimiterLength + 1, y1, #_ChartAxisLimiterLength, 1, \AxisColor)
s = StrF(v, \DecimalPlaces) + \Unit
DrawText(x - #_ChartAxisLimiterLength - TextWidth(s), y1 - \TextHeight / 2, s, \FrontColor, \BackColor)
v + \StepValue
Wend
EndIf
EndSection
;paint x-axis
Section
If \Flags & #ChartFlagXAxis
y + h
cw = w / ListSize(\Columns())
Line(x, y, w + 1, 1, \AxisColor)
Line(x, y, 1, #_ChartAxisLimiterLength, \AxisColor)
i = 0
ForEach Iter(*c, \Columns())
i + 1
xr = x + cw * i
Line(xr, y, 1, #_ChartAxisLimiterLength, \AxisColor)
If \Flags & #ChartFlagXAxisVAlign
DrawRotatedText(xr - (cw + \TextHeight) / 2, y + xah - #_ChartXAxisPad, *c\Name, 90, \FrontColor)
Else
tw = TextWidth(*c\Name)
DrawRotatedText(xr - cw / 2 - tw / 2, y + #_ChartXAxisPad, *c\Name, 0, \FrontColor)
EndIf
Next
EndIf
EndSection
StopDrawing()
EndWith
EndProcedure
Procedure ChartSet(Gadget, Setting, Value)
;setup chart attributes
Protected *g._Chart = GetGadgetData(Gadget)
Select Setting
Case #ChartSetFlags
*g\Flags = Value
Case #ChartSetFont
*g\Font = Value
Case #ChartSetBackColor
*g\BackColor = Value
Case #ChartSetFrontColor
*g\FrontColor = Value
Case #ChartSetAreaColor
*g\AreaColor = Value
Case #ChartSetGridColor
*g\GridColor = Value
Case #ChartSetValueColor
*g\ValueColor = Value
Case #ChartSetLineWidth
*g\LineWidth = Value
Case #ChartSetPointSize
*g\PointSize = Value
Case #ChartSetPadding
*g\Padding = Value
Case #ChartSetDecimalPlaces
*g\DecimalPlaces = Value
Case #ChartSetFillStyle
*g\FillStyle = Value
EndSelect
EndProcedure
Procedure ChartRow(Gadget, Name.s, Type.b, Color.l, Flags=0)
;add a row to the chart
Protected *g._Chart, *r._ChartRow
*g = GetGadgetData(Gadget)
;insert sorted by name
If *g\Flags & #ChartFlagSortRows
ForEach *g\Rows()
If *g\Rows()\Name > Name
*r = InsertElement(*g\Rows())
Goto Set:
EndIf
Next
EndIf
*r = AddElement(*g\Rows())
Set:
*r\Name = Name
*r\Type = Type
*r\Color = Color
*r\Flags = Flags
;count number of rows with bars
If Type = #ChartRowTypeBar
*g\BarRowCount + 1
EndIf
EndProcedure
Procedure ChartColumn(Gadget, Name.s)
;add a column to the chart
Protected *g._Chart, *c._ChartColumn
*g = GetGadgetData(Gadget)
;insert sorted by name
If *g\Flags & #ChartFlagSortColumns
ForEach *g\Columns()
If *g\Columns()\Name > Name
*c = InsertElement(*g\Columns())
Goto Set
EndIf
Next
EndIf
;append new column
*c = AddElement(*g\Columns())
Set:
*c\Name = Name
EndProcedure
Procedure ChartValue(Gadget, Row.s, Column.s, Value.f, Flags=0)
;add or update chart value
Protected *g._Chart, *v._ChartValue
*g = GetGadgetData(Gadget)
;update existing value
ForEach Iter(*v, *g\Values())
If *v\Row = Row And *v\Column = Column
Select Flags
Case #ChartValueFlagReplace
*v\Value = Value
Case #ChartValueFlagSum
*v\Value + Value
EndSelect
ProcedureReturn
EndIf
Next
;add new value
*v = AddElement(*g\Values())
*v\Row = Row
*v\Column = Column
*v\Value = Value
EndProcedure
Procedure ChartText(Gadget, Type, Text.s)
Protected *c._Chart = GetGadgetData(Gadget)
Select Type
Case #ChartTextTitle
*c\Title = Text
Case #ChartTextYAxis
*c\YTitle = Text
Case #ChartTextXAxis
*c\XTitle = Text
Case #ChartTextUnit
*c\Unit = Text
EndSelect
EndProcedure
Procedure ChartClear(Gadget, Flags=0)
;remove all data from the chart
Protected *g._Chart = GetGadgetData(Gadget)
*g\BarRowCount = 0
ClearList(*g\Values())
If Not Flags & #ChartClearKeepColumns
ClearList(*g\Columns())
EndIf
If Not Flags & #ChartClearKeepRows
ClearList(*g\Rows())
EndIf
EndProcedure
Procedure ChartGadget(Gadget, x, y, w, h, Flags=0)
;create new chart gadget (from CanvasGadget)
Protected *c._Chart, canvasflag, id
If Flags & #ChartFlagBorder
canvasflag = #PB_Canvas_Border
EndIf
id = CanvasGadget(Gadget, x, y, w, h, canvasflag)
;support #PB_Any
If Gadget = #PB_Any
Gadget = id
EndIf
;create and store additional object data
*c = New(_Chart)
SetGadgetData(Gadget, *c)
NewList *c\Columns()
NewList *c\Rows()
NewList *c\Values()
;default settings
*c\Font = GetGadgetFont(#PB_Default)
*c\BackColor = $FFFFFF
*c\FrontColor = $000000
*c\AreaColor = $E0F0FF
*c\GridColor = $D0E0F0
*c\ValueColor = $8CE6F0
*c\AxisColor = $000000
*c\LineWidth = 3
*c\PointSize = 5
*c\Padding = 8
*c\Flags = Flags
;initial paint
ChartPaint(Gadget)
;return result
ProcedureReturn id
EndProcedure
;}
Enumeration #PB_Event_FirstCustomValue
#Event_update_captcha_chart
EndEnumeration
Procedure UpdateChart(i)
Repeat
PostEvent(#Event_update_captcha_chart)
Delay(300)
ForEver
EndProcedure
OpenWindow(0, 0, 0, 800, 500, "Chart-Test", #PB_Window_SystemMenu | #PB_Window_SizeGadget | #PB_Window_ScreenCentered)
flags = #ChartFlagBorder
;flags | #ChartFlagLegendBottom
flags | #ChartFlagYAxis
flags | #ChartFlagXAxis
;flags | #ChartFlagXAxisVAlign
flags | #ChartFlagHGrid
flags | #ChartFlagVGrid
;flags | #ChartFlagStapled
ChartGadget(0, 10, 10, 780, 480, flags)
ChartText(0, #ChartTextTitle, "")
ChartText(0, #ChartTextYAxis, "Percent")
ChartText(0, #ChartTextXAxis, "Time")
ChartText(0, #ChartTextUnit, " %")
;ChartSet(0, #ChartSetPadding, 32)
ChartSet(0, #ChartSetPointSize, 5)
;ChartSet(0, #ChartSetFont, FontID(LoadFont(#PB_Any, "Courier", 12)))
ChartSet(0, #ChartSetLineWidth, 3)
ChartSet(0, #ChartSetFillStyle, #ChartFillStyleGradient)
;ChartSet(0, #ChartSetBackColor, $000000)
ChartSet(0, #ChartSetFrontColor, $000000)
ChartSet(0, #ChartSetAreaColor, $000000)
ChartSet(0, #ChartSetGridColor, $C9C9C9)
;ChartRow(0, "Positive", #ChartRowTypeBar, $009060)
;ChartRow(0, "Negative", #ChartRowTypeBar, $2020E0)
ChartRow(0, "Average", #ChartRowTypeLine, $00D7FF, #ChartRowFlagValues)
;add some data columns
NewList Values()
For i = 1 To 12
month.s = StringField("Jan|Feb|Mar|Apr|May|Jun|Jul|Aug|Sep|Oct|Nov|Dec", i, "|")
ChartColumn(0, month)
AddElement(Values())
Values() = Random(100, 1)
ChartValue(0, "Average", month, Values())
Next
ChartPaint(0)
CreateThread(@UpdateChart(), 0)
Repeat
Select WaitWindowEvent()
Case #PB_Event_SizeWindow
;resize the chart and redraw it
ResizeGadget(0, 10, 10, WindowWidth(0) - 20, WindowHeight(0) - 20)
ChartPaint(0)
Case #PB_Event_CloseWindow
Break
Case #Event_update_captcha_chart
ChartText(0, #ChartTextTitle, Str(Random(10000000)))
FirstElement(Values())
DeleteElement(Values())
LastElement(Values())
AddElement(Values())
Values() = Random(100, 1)
FirstElement(Values())
For i = 1 To 12
month.s = StringField("Jan|Feb|Mar|Apr|May|Jun|Jul|Aug|Sep|Oct|Nov|Dec", i, "|")
NextElement(Values())
ChartValue(0, "Average", month, Values())
Next
ChartPaint(0)
EndSelect
ForEver
Re: real-time measuring and plotting into a graph. HOW?
Hi Wim,
Bernd
Code: Select all
Procedure DrawNewPixel(YPos.i)
;Debug YPos
GrabImage(0, 1, 1, 0, 779, 580)
StartDrawing(ImageOutput(0))
DrawImage(ImageID(1), 0, 0)
LineXY(779, 0, 779, 579, 0)
Plot(779, YPos, $FFFFFF)
StopDrawing()
FreeImage(1)
SetGadgetState(1, ImageID(0))
EndProcedure
OpenWindow(0, 0, 0, 800, 600, "Wims PixelChart", #PB_Window_SystemMenu|#PB_Window_ScreenCentered)
CreateImage(0, 780, 580)
ImageGadget(1, 10, 10, 780, 580, ImageID(0))
AddWindowTimer(0, 1, 100)
Repeat
Event = WaitWindowEvent()
Select Event
Case #PB_Event_Timer
If EventTimer() = 1
DrawNewPixel(Sin(Count / 100) * 280 + 290)
Count + 1
If Count = 628
Count = 0
EndIf
EndIf
Case #PB_Event_CloseWindow
Exit = #True
EndSelect
Until Exit
Re: real-time measuring and plotting into a graph. HOW?
If you want to see a closed line, than you need to have 3 points in x per pixel and
use LineXY() with the last point as start point.
You can use for that.
Bernd
use LineXY() with the last point as start point.
You can use
Code: Select all
Static LastY.i
Code: Select all
Procedure DrawNewPixel(YPos.i)
Static LastY.i
;Debug YPos
GrabImage(0, 1, 3, 0, 777, 580)
StartDrawing(ImageOutput(0))
DrawImage(ImageID(1), 0, 0)
Box(777, 0, 779, 579, 0)
LineXY(777, LastY, 779, YPos, $FFFFFF)
StopDrawing()
FreeImage(1)
SetGadgetState(1, ImageID(0))
LastY = YPos
EndProcedure
OpenWindow(0, 0, 0, 800, 600, "Wims PixelChart", #PB_Window_SystemMenu|#PB_Window_ScreenCentered)
CreateImage(0, 780, 580)
ImageGadget(1, 10, 10, 780, 580, ImageID(0))
AddWindowTimer(0, 1, 100)
Repeat
Event = WaitWindowEvent()
Select Event
Case #PB_Event_Timer
If EventTimer() = 1
DrawNewPixel(Random(580))
EndIf
Case #PB_Event_CloseWindow
Exit = #True
EndSelect
Until Exit
-
- Enthusiast
- Posts: 290
- Joined: Thu Dec 16, 2010 2:05 pm
- Location: Delfzijl ( The Netherlands )
- Contact:
Re: real-time measuring and plotting into a graph. HOW?
Hi , thanks for your help folks.
Ostapas, your program is not working here ( bool() is not a function etc..)
Infratec: what you gave is exactly what i need.
most of the time i need the pixel program, but the line program is sometimes
needed as well.
It will take some time to study this examples, but i will report here
my progres!
Thanks both of you!!!
Wim
Ostapas, your program is not working here ( bool() is not a function etc..)
Infratec: what you gave is exactly what i need.
most of the time i need the pixel program, but the line program is sometimes
needed as well.
It will take some time to study this examples, but i will report here
my progres!
Thanks both of you!!!
Wim
Re: real-time measuring and plotting into a graph. HOW?
Hi Wim,
for Bool() you need a higher PB version
for Bool() you need a higher PB version

Re: real-time measuring and plotting into a graph. HOW?
@infratec,
Nice example using such a paucity of code.
Great to learn something new.
Thank you, very much.
Nice example using such a paucity of code.
Great to learn something new.
Thank you, very much.

DE AA EB
Re: real-time measuring and plotting into a graph. HOW?
A shorter solution is most the better one
Thanks for the flowers
Bernd

Thanks for the flowers

Bernd
-
- Enthusiast
- Posts: 290
- Joined: Thu Dec 16, 2010 2:05 pm
- Location: Delfzijl ( The Netherlands )
- Contact:
Re: real-time measuring and plotting into a graph. HOW?
okee infratec,
i put one of my measuring programs (with making and digitising of a
.wav file) in it and it works perfect.
But now, i like to change it a bit.
I like to have a graph of 1440 * 60 points horizontal and let us say 1000 vertical.
This will be a matter of scaling; No problem. (i know , i will get more points on
one pixel.)
The real problem is then:
i will be able to put a point at every position horizontally and every position vertically.
every already plotted point will stay visible.
(then i am back to my old Quick Basic time...hi hi)
so the procedure drawnewpixel must be changed for an x and y
i tried to do it myself but did not succeed.....
Wim
i put one of my measuring programs (with making and digitising of a
.wav file) in it and it works perfect.
But now, i like to change it a bit.
I like to have a graph of 1440 * 60 points horizontal and let us say 1000 vertical.
This will be a matter of scaling; No problem. (i know , i will get more points on
one pixel.)
The real problem is then:
i will be able to put a point at every position horizontally and every position vertically.
every already plotted point will stay visible.
(then i am back to my old Quick Basic time...hi hi)
so the procedure drawnewpixel must be changed for an x and y
i tried to do it myself but did not succeed.....
Wim
Re: real-time measuring and plotting into a graph. HOW?
Hi Wim,
so you don't need scrolling, but you want to place the pixels where you want in the complete picture.
Is this right?
Bernd
so you don't need scrolling, but you want to place the pixels where you want in the complete picture.
Is this right?
Bernd
-
- Enthusiast
- Posts: 290
- Joined: Thu Dec 16, 2010 2:05 pm
- Location: Delfzijl ( The Netherlands )
- Contact:
Re: real-time measuring and plotting into a graph. HOW?
yes Bernd,
that is right
Wim
that is right
Wim
Re: real-time measuring and plotting into a graph. HOW?
Hi Wim,
here you are:
Bernd
here you are:
Code: Select all
Procedure DrawNewPixel(XPos.i, YPos.i)
StartDrawing(ImageOutput(0))
Plot(XPos, YPos, $FFFFFF)
StopDrawing()
SetGadgetState(1, ImageID(0))
EndProcedure
OpenWindow(0, 0, 0, 800, 600, "Wims PixelChart", #PB_Window_SystemMenu|#PB_Window_ScreenCentered)
CreateImage(0, 780, 580)
ImageGadget(1, 10, 10, 780, 580, ImageID(0))
AddWindowTimer(0, 1, 100)
Repeat
Event = WaitWindowEvent()
Select Event
Case #PB_Event_Timer
If EventTimer() = 1
DrawNewPixel(Random(779), Random(579))
EndIf
Case #PB_Event_CloseWindow
Exit = #True
EndSelect
Until Exit
-
- Enthusiast
- Posts: 290
- Joined: Thu Dec 16, 2010 2:05 pm
- Location: Delfzijl ( The Netherlands )
- Contact:
Re: real-time measuring and plotting into a graph. HOW?
So bernd,
that is fast..... hi hi
i will test it now
thanks i will report
Wim
that is fast..... hi hi
i will test it now
thanks i will report
Wim
-
- Enthusiast
- Posts: 290
- Joined: Thu Dec 16, 2010 2:05 pm
- Location: Delfzijl ( The Netherlands )
- Contact:
Re: real-time measuring and plotting into a graph. HOW?
Yes Bernd,
this works perfect.
I will , later this day, put it into one of my measuring programs.
(that will cost some time...)
I will report my results here.
A lot of flowers to you.....
Wim
this works perfect.
I will , later this day, put it into one of my measuring programs.
(that will cost some time...)
I will report my results here.
A lot of flowers to you.....
Wim
-
- Enthusiast
- Posts: 290
- Joined: Thu Dec 16, 2010 2:05 pm
- Location: Delfzijl ( The Netherlands )
- Contact:
Re: real-time measuring and plotting into a graph. HOW?
Hi Infratec,
I made a starting program for my measurements.
It works great.
but the procedure cls ( clear screen) does not work correct.
It deletes lines and text, but not circles and plots.
I will give here a part of the program, so you can maybe see what is wrong
with the procedure cls.
If you need the complete program, i will post it here.
I made a starting program for my measurements.
It works great.
but the procedure cls ( clear screen) does not work correct.
It deletes lines and text, but not circles and plots.
I will give here a part of the program, so you can maybe see what is wrong
with the procedure cls.
If you need the complete program, i will post it here.
Code: Select all
OpenWindow(0, 0, 0, 900, 540, "Realtime grafiek PA0SLT realtimegrafiek1.pb", #PB_Window_SystemMenu|#PB_Window_ScreenCentered)
CreateImage(0, 880, 520)
ImageGadget(1, 10, 10, 880, 520, ImageID(0))
AddWindowTimer(0, 1, 100)
tekenassen() ; draws x and y axes with labels
Repeat
Event = WaitWindowEvent()
Select Event
Case #PB_Event_Timer
If EventTimer() = 1
; HIER KOMT HET REAL-TIME MEET GEDEELTE
; demo voor het plotten van een pixel
x = 12 * 60 * 60 ; in seconden
y = 5500
verschaal()
drawnewpixel(xw,yw)
x = 10 * 60 * 60
y = 5200
verschaal()
drawnewcirkle(xw,yw)
cls() ; this is not working correct
EndIf
Case #PB_Event_CloseWindow
Exit = #True
EndSelect
Until Exit
End
;======================================================================================
;======================================================================================
;====================== Procedures =============================================
;======================================================================================
;======================================================================================
Procedure cls()
StartDrawing(ImageOutput(0))
DrawingMode(#PB_2DDrawing_Default) ;2D shapes like Box are filled
Box(0, 0, ImageW, ImageH, 0)
StopDrawing()
EndProcedure
Procedure DrawNewPixel(XPos.i, YPos.i)
StartDrawing(ImageOutput(0))
Plot(XPos, YPos, RGB(255,255,0)) ; geel
StopDrawing()
SetGadgetState(1, ImageID(0))
EndProcedure
Procedure DrawNewcirkle(XPos.i, YPos.i)
StartDrawing(ImageOutput(0))
Circle(xw,yw,3,RGB(255,0,0)) ; rood
StopDrawing()
SetGadgetState(1, ImageID(0))
EndProcedure