diff --git a/applications/lazstats/source/LazStats.lpi b/applications/lazstats/source/LazStats.lpi index c97b8fb83..484a66c44 100644 --- a/applications/lazstats/source/LazStats.lpi +++ b/applications/lazstats/source/LazStats.lpi @@ -49,7 +49,7 @@ - + @@ -744,12 +744,11 @@ - + - @@ -1421,6 +1420,14 @@ + + + + + + + + diff --git a/applications/lazstats/source/LazStats.lpr b/applications/lazstats/source/LazStats.lpr index 69c2a28dc..28053d22e 100644 --- a/applications/lazstats/source/LazStats.lpr +++ b/applications/lazstats/source/LazStats.lpr @@ -8,7 +8,8 @@ uses {$ENDIF}{$ENDIF} Interfaces, // this includes the LCL widgetset Forms, tachartlazaruspkg, tachartprint, lhelpcontrolpkg, - Globals, LicenseUnit, OptionsUnit, DictionaryUnit, MainDM, MainUnit; + Globals, LicenseUnit, OptionsUnit, DictionaryUnit, MainDM, MainUnit, +cumsumunit; {$R LazStats.res} @@ -28,6 +29,7 @@ begin end; Application.CreateForm(TMainDataModule, MainDataModule); Application.CreateForm(TOS3MainFrm, OS3MainFrm); + Application.CreateForm(TCUSUMChartForm, CUSUMChartForm); Application.Run; end. diff --git a/applications/lazstats/source/forms/analysis/statistical_process_control/basicspcunit.pas b/applications/lazstats/source/forms/analysis/statistical_process_control/basicspcunit.pas index 44d7f38b8..1be1af2df 100644 --- a/applications/lazstats/source/forms/analysis/statistical_process_control/basicspcunit.pas +++ b/applications/lazstats/source/forms/analysis/statistical_process_control/basicspcunit.pas @@ -56,7 +56,7 @@ type function GetFileName: String; procedure PlotMeans(ATitle, AXTitle, AYTitle, ADataTitle, AGrandMeanTitle: String; const Groups: StrDyneVec; const Means: DblDyneVec; - UCL, LCL, GrandMean, TargetSpec, LowerSpec, UpperSpec: double); + UCL, LCL, GrandMean, TargetSpec, LowerSpec, UpperSpec: double); virtual; procedure Reset; virtual; procedure Compute; virtual; function Validate(out AMsg: String; out AControl: TWinControl): Boolean; virtual; @@ -243,14 +243,23 @@ begin FChartFrame.Chart.BottomAxis.Marks.style := smsLabel; end; - FChartFrame.HorLine(GrandMean, clRed, psSolid, AGrandMeanTitle); - rightLabels.Add(GrandMean, GrandMean, AGrandMeanTitle); + if not IsNaN(GrandMean) then + begin + FChartFrame.HorLine(GrandMean, clRed, psSolid, AGrandMeanTitle); + rightLabels.Add(GrandMean, GrandMean, AGrandMeanTitle); + end; - FChartFrame.HorLine(UCL, CL_COLOR, CL_STYLE, 'UCL/LCL'); - rightLabels.Add(UCL, UCL, 'UCL'); + if not IsNaN(UCL) then + begin + FChartFrame.HorLine(UCL, CL_COLOR, CL_STYLE, 'UCL/LCL'); + rightLabels.Add(UCL, UCL, 'UCL'); + end; - FChartFrame.HorLine(LCL, CL_COLOR, CL_STYLE, ''); - rightLabels.Add(UCL, LCL, 'LCL'); + if not IsNaN(LCL) then + begin + FChartFrame.HorLine(LCL, CL_COLOR, CL_STYLE, ''); + rightLabels.Add(UCL, LCL, 'LCL'); + end; if not IsNan(UpperSpec) then begin diff --git a/applications/lazstats/source/forms/analysis/statistical_process_control/cumsumunit.lfm b/applications/lazstats/source/forms/analysis/statistical_process_control/cumsumunit.lfm index d65cdd07b..7d037ee84 100644 --- a/applications/lazstats/source/forms/analysis/statistical_process_control/cumsumunit.lfm +++ b/applications/lazstats/source/forms/analysis/statistical_process_control/cumsumunit.lfm @@ -1,354 +1,234 @@ -object CUMSUMFrm: TCUMSUMFrm - Left = 717 - Height = 346 - Top = 262 - Width = 476 +inherited CUSUMChartForm: TCUSUMChartForm HelpType = htKeyword HelpKeyword = 'html/CUMSUMChart.htm' - AutoSize = True - Caption = 'CUMSUM Chart' - ClientHeight = 346 - ClientWidth = 476 + Caption = 'Cumulative Sum Control Chart' OnActivate = FormActivate - OnCreate = FormCreate - OnShow = FormShow - Position = poMainFormCenter - LCLVersion = '2.1.0.0' - object Label1: TLabel - AnchorSideLeft.Control = Owner - AnchorSideTop.Control = Owner - Left = 8 - Height = 15 - Top = 8 - Width = 97 - BorderSpacing.Left = 8 - BorderSpacing.Top = 8 - Caption = 'Selection Variables' - ParentColor = False - end - object Label2: TLabel - AnchorSideLeft.Control = GroupEdit - AnchorSideTop.Control = Owner - Left = 242 - Height = 15 - Top = 8 - Width = 77 - BorderSpacing.Top = 8 - Caption = 'Group Variable' - ParentColor = False - end - object Label3: TLabel - AnchorSideLeft.Control = MeasEdit - AnchorSideTop.Control = GroupEdit - AnchorSideTop.Side = asrBottom - Left = 242 - Height = 15 - Top = 64 - Width = 117 - BorderSpacing.Top = 16 - Caption = 'Measurement Variable' - ParentColor = False - end - object VarList: TListBox - AnchorSideLeft.Control = Owner - AnchorSideTop.Control = Label1 - AnchorSideTop.Side = asrBottom - AnchorSideRight.Control = GroupBox2 - AnchorSideBottom.Control = Bevel2 - Left = 8 - Height = 272 - Top = 25 - Width = 226 - Anchors = [akTop, akLeft, akRight, akBottom] - BorderSpacing.Left = 8 - BorderSpacing.Top = 2 - BorderSpacing.Right = 8 - ItemHeight = 0 - OnClick = VarListClick - TabOrder = 0 - end - object GroupEdit: TEdit - AnchorSideLeft.Control = GroupBox2 - AnchorSideTop.Control = Label2 - AnchorSideTop.Side = asrBottom - AnchorSideRight.Control = Owner - AnchorSideRight.Side = asrBottom - Left = 242 - Height = 23 - Top = 25 - Width = 226 - Anchors = [akTop, akLeft, akRight] - BorderSpacing.Top = 2 - BorderSpacing.Right = 8 - ReadOnly = True - TabOrder = 1 - Text = 'GroupEdit' - end - object MeasEdit: TEdit - AnchorSideLeft.Control = GroupBox2 - AnchorSideTop.Control = Label3 - AnchorSideTop.Side = asrBottom - AnchorSideRight.Control = Owner - AnchorSideRight.Side = asrBottom - Left = 242 - Height = 23 - Top = 81 - Width = 226 - Anchors = [akTop, akLeft, akRight] - BorderSpacing.Top = 2 - BorderSpacing.Right = 8 - ReadOnly = True - TabOrder = 2 - Text = 'MeasEdit' - end - object GroupBox1: TGroupBox - AnchorSideLeft.Control = GroupBox2 - AnchorSideTop.Control = MeasEdit - AnchorSideTop.Side = asrBottom - AnchorSideRight.Control = Owner - AnchorSideRight.Side = asrBottom - Left = 242 - Height = 107 - Top = 120 - Width = 226 - Anchors = [akTop, akLeft, akRight] - BorderSpacing.Top = 16 - BorderSpacing.Right = 8 - Caption = 'CUMSUM V-Mask Specifications' - ClientHeight = 87 - ClientWidth = 222 - TabOrder = 3 - object Label4: TLabel - AnchorSideLeft.Control = GroupBox1 - AnchorSideTop.Control = DeltaEdit - AnchorSideTop.Side = asrCenter - Left = 12 - Height = 15 - Top = 6 - Width = 94 - BorderSpacing.Left = 12 - Caption = 'Delta (Effect Size):' - ParentColor = False + inherited SpecsPanel: TPanel + Width = 432 + ClientWidth = 432 + inherited ButtonPanel: TPanel + Width = 432 + ClientWidth = 432 + TabOrder = 5 + inherited CloseBtn: TButton + Left = 377 + TabOrder = 3 + end + inherited ComputeBtn: TButton + Left = 293 + TabOrder = 2 + end + inherited ResetBtn: TButton + Left = 231 + TabOrder = 1 + end + inherited HelpBtn: TButton + Left = 180 + TabOrder = 0 + end + inherited Bevel1: TBevel + Width = 424 + end end - object Label5: TLabel - AnchorSideLeft.Control = GroupBox1 - AnchorSideTop.Control = AlphaEdit - AnchorSideTop.Side = asrCenter - Left = 12 - Height = 15 - Top = 33 - Width = 94 - BorderSpacing.Left = 12 - Caption = 'Alpha Probability:' - ParentColor = False - end - object Label6: TLabel - AnchorSideLeft.Control = GroupBox1 - AnchorSideTop.Control = BetaEdit - AnchorSideTop.Side = asrCenter - Left = 12 - Height = 15 - Top = 60 - Width = 86 - BorderSpacing.Left = 12 - Caption = 'Beta Probability:' - ParentColor = False - end - object DeltaEdit: TEdit - AnchorSideLeft.Control = AlphaEdit - AnchorSideTop.Control = GroupBox1 - AnchorSideRight.Control = GroupBox1 - AnchorSideRight.Side = asrBottom - Left = 114 - Height = 23 - Top = 2 - Width = 100 - Alignment = taRightJustify - Anchors = [akTop, akLeft, akRight] - BorderSpacing.Top = 2 - BorderSpacing.Right = 8 - TabOrder = 0 - Text = 'DeltaEdit' - end - object AlphaEdit: TEdit - AnchorSideLeft.Control = Label5 - AnchorSideLeft.Side = asrBottom - AnchorSideTop.Control = DeltaEdit - AnchorSideTop.Side = asrBottom - AnchorSideRight.Control = GroupBox1 - AnchorSideRight.Side = asrBottom - Left = 114 - Height = 23 - Top = 29 - Width = 100 - Alignment = taRightJustify - Anchors = [akTop, akLeft, akRight] - BorderSpacing.Left = 8 - BorderSpacing.Top = 4 - BorderSpacing.Right = 8 - TabOrder = 1 - Text = 'AlphaEdit' - end - object BetaEdit: TEdit - AnchorSideLeft.Control = AlphaEdit - AnchorSideTop.Control = AlphaEdit - AnchorSideTop.Side = asrBottom - AnchorSideRight.Control = GroupBox1 - AnchorSideRight.Side = asrBottom - Left = 114 - Height = 23 - Top = 56 - Width = 100 - Alignment = taRightJustify - Anchors = [akTop, akLeft, akRight] - BorderSpacing.Top = 4 - BorderSpacing.Right = 8 - BorderSpacing.Bottom = 8 - TabOrder = 2 - Text = 'BetaEdit' - end - end - object GroupBox2: TGroupBox - AnchorSideTop.Control = GroupBox1 - AnchorSideTop.Side = asrBottom - AnchorSideRight.Control = Owner - AnchorSideRight.Side = asrBottom - Left = 242 - Height = 51 - Top = 243 - Width = 226 - Anchors = [akTop, akRight] - AutoSize = True - BorderSpacing.Top = 16 - BorderSpacing.Right = 8 - Caption = 'Option:' - ClientHeight = 31 - ClientWidth = 222 - TabOrder = 4 - object TargetChk: TCheckBox - AnchorSideLeft.Control = GroupBox2 - AnchorSideTop.Control = TargetEdit - AnchorSideTop.Side = asrCenter - Left = 12 - Height = 19 - Top = 2 - Width = 141 - AutoSize = False - BorderSpacing.Left = 12 - BorderSpacing.Right = 12 - Caption = 'Use Target Specification:' + inherited VarList: TListBox + Width = 212 TabOrder = 0 end - object TargetEdit: TEdit - AnchorSideLeft.Control = TargetChk - AnchorSideLeft.Side = asrBottom - AnchorSideTop.Control = GroupBox2 - AnchorSideRight.Side = asrBottom - Left = 165 - Height = 23 - Top = 0 - Width = 49 - Alignment = taRightJustify - BorderSpacing.Left = 12 - BorderSpacing.Right = 8 - BorderSpacing.Bottom = 8 - TabOrder = 1 - Text = 'TargetEdit' + inherited GroupLabel: TLabel + Left = 228 end - end - object Bevel2: TBevel - AnchorSideTop.Control = Panel1 - AnchorSideRight.Control = Owner - AnchorSideRight.Side = asrBottom - AnchorSideBottom.Control = Panel1 - Left = 0 - Height = 8 - Top = 297 - Width = 476 - Anchors = [akLeft, akRight, akBottom] - Shape = bsBottomLine - end - object Panel1: TPanel - Left = 0 - Height = 41 - Top = 305 - Width = 476 - Align = alBottom - AutoSize = True - BevelOuter = bvNone - ClientHeight = 41 - ClientWidth = 476 - TabOrder = 5 - object ResetBtn: TButton - AnchorSideLeft.Control = Panel1 - AnchorSideTop.Control = Panel1 - AnchorSideRight.Control = ComputeBtn - Left = 267 - Height = 25 - Top = 8 - Width = 54 - Anchors = [akTop, akRight] - AutoSize = True - BorderSpacing.Top = 8 - BorderSpacing.Right = 8 - BorderSpacing.Bottom = 8 - Caption = 'Reset' - OnClick = ResetBtnClick + inherited GroupEdit: TEdit + Left = 228 + Width = 204 TabOrder = 1 end - object ComputeBtn: TButton - AnchorSideLeft.Control = Panel1 - AnchorSideTop.Control = Panel1 - AnchorSideRight.Control = CloseBtn - Left = 329 - Height = 25 - Top = 8 - Width = 76 - Anchors = [akTop, akRight] - AutoSize = True - BorderSpacing.Top = 8 - BorderSpacing.Right = 8 - BorderSpacing.Bottom = 8 - Caption = 'Compute' - OnClick = ComputeBtnClick + inherited MeasLabel: TLabel + Left = 228 + end + inherited MeasEdit: TEdit + Left = 228 + Width = 204 TabOrder = 2 end - object HelpBtn: TButton - Tag = 141 - AnchorSideLeft.Control = Panel1 - AnchorSideTop.Control = Panel1 - AnchorSideRight.Control = ResetBtn - Left = 208 - Height = 25 - Top = 8 - Width = 51 - Anchors = [akTop, akRight] - AutoSize = True - BorderSpacing.Left = 8 - BorderSpacing.Top = 8 - BorderSpacing.Right = 8 - BorderSpacing.Bottom = 8 - Caption = 'Help' - OnClick = HelpBtnClick - TabOrder = 0 + inherited Bevel2: TBevel + Left = 205 end - object CloseBtn: TButton - AnchorSideLeft.Control = Panel1 - AnchorSideTop.Control = Panel1 - AnchorSideRight.Control = Panel1 + object GroupBox1: TGroupBox[8] + AnchorSideLeft.Control = MeasEdit + AnchorSideTop.Control = MeasEdit + AnchorSideTop.Side = asrBottom + AnchorSideRight.Control = MeasEdit AnchorSideRight.Side = asrBottom - Left = 413 - Height = 25 - Top = 8 - Width = 55 - Anchors = [akTop, akRight] - AutoSize = True - BorderSpacing.Top = 8 - BorderSpacing.Right = 8 - BorderSpacing.Bottom = 8 - Caption = 'Close' - ModalResult = 11 + Left = 228 + Height = 107 + Top = 120 + Width = 204 + Anchors = [akTop, akLeft, akRight] + BorderSpacing.Top = 24 + Caption = 'CUMSUM V-Mask Specifications' + ClientHeight = 87 + ClientWidth = 200 TabOrder = 3 + object Label4: TLabel + AnchorSideLeft.Control = GroupBox1 + AnchorSideTop.Control = DeltaEdit + AnchorSideTop.Side = asrCenter + Left = 12 + Height = 15 + Top = 6 + Width = 94 + BorderSpacing.Left = 12 + Caption = 'Delta (Effect Size):' + ParentColor = False + end + object Label5: TLabel + AnchorSideLeft.Control = GroupBox1 + AnchorSideTop.Control = AlphaEdit + AnchorSideTop.Side = asrCenter + Left = 12 + Height = 15 + Top = 33 + Width = 94 + BorderSpacing.Left = 12 + Caption = 'Alpha Probability:' + ParentColor = False + end + object Label6: TLabel + AnchorSideLeft.Control = GroupBox1 + AnchorSideTop.Control = BetaEdit + AnchorSideTop.Side = asrCenter + Left = 12 + Height = 15 + Top = 60 + Width = 86 + BorderSpacing.Left = 12 + Caption = 'Beta Probability:' + ParentColor = False + end + object DeltaEdit: TEdit + AnchorSideLeft.Control = AlphaEdit + AnchorSideTop.Control = GroupBox1 + AnchorSideRight.Control = GroupBox1 + AnchorSideRight.Side = asrBottom + Left = 114 + Height = 23 + Top = 2 + Width = 78 + Alignment = taRightJustify + Anchors = [akTop, akLeft, akRight] + BorderSpacing.Top = 2 + BorderSpacing.Right = 8 + Constraints.MinWidth = 64 + TabOrder = 0 + Text = 'DeltaEdit' + end + object AlphaEdit: TEdit + AnchorSideLeft.Control = Label5 + AnchorSideLeft.Side = asrBottom + AnchorSideTop.Control = DeltaEdit + AnchorSideTop.Side = asrBottom + AnchorSideRight.Control = GroupBox1 + AnchorSideRight.Side = asrBottom + Left = 114 + Height = 23 + Top = 29 + Width = 78 + Alignment = taRightJustify + Anchors = [akTop, akLeft, akRight] + BorderSpacing.Left = 8 + BorderSpacing.Top = 4 + BorderSpacing.Right = 8 + Constraints.MinWidth = 64 + TabOrder = 1 + Text = 'AlphaEdit' + end + object BetaEdit: TEdit + AnchorSideLeft.Control = AlphaEdit + AnchorSideTop.Control = AlphaEdit + AnchorSideTop.Side = asrBottom + AnchorSideRight.Control = GroupBox1 + AnchorSideRight.Side = asrBottom + Left = 114 + Height = 23 + Top = 56 + Width = 78 + Alignment = taRightJustify + Anchors = [akTop, akLeft, akRight] + BorderSpacing.Top = 4 + BorderSpacing.Right = 8 + BorderSpacing.Bottom = 8 + Constraints.MinWidth = 64 + TabOrder = 2 + Text = 'BetaEdit' + end + end + object GroupBox2: TGroupBox[9] + AnchorSideLeft.Control = GroupBox1 + AnchorSideTop.Control = GroupBox1 + AnchorSideTop.Side = asrBottom + AnchorSideRight.Control = MeasEdit + AnchorSideRight.Side = asrBottom + Left = 228 + Height = 51 + Top = 243 + Width = 204 + Anchors = [akTop, akLeft, akRight] + AutoSize = True + BorderSpacing.Top = 16 + BorderSpacing.Bottom = 8 + Caption = 'Option:' + ClientHeight = 31 + ClientWidth = 200 + TabOrder = 4 + object TargetChk: TCheckBox + AnchorSideLeft.Control = GroupBox2 + AnchorSideTop.Control = TargetEdit + AnchorSideTop.Side = asrCenter + Left = 12 + Height = 19 + Top = 2 + Width = 108 + BorderSpacing.Left = 12 + BorderSpacing.Right = 8 + Caption = 'Use Target Specs' + TabOrder = 0 + end + object TargetEdit: TEdit + AnchorSideLeft.Control = TargetChk + AnchorSideLeft.Side = asrBottom + AnchorSideTop.Control = GroupBox2 + AnchorSideRight.Control = GroupBox2 + AnchorSideRight.Side = asrBottom + Left = 128 + Height = 23 + Top = 0 + Width = 64 + Alignment = taRightJustify + Anchors = [akTop, akLeft, akRight] + BorderSpacing.Left = 8 + BorderSpacing.Right = 8 + BorderSpacing.Bottom = 8 + Constraints.MinWidth = 64 + TabOrder = 1 + Text = 'TargetEdit' + end + end + end + inherited SpecsSplitter: TSplitter + Left = 435 + end + inherited PageControl1: TPageControl + Left = 443 + Width = 478 + inherited ReportPage: TTabSheet + ClientWidth = 470 + inherited Panel1: TPanel + Width = 458 + ClientWidth = 454 + inherited ReportMemo: TMemo + Width = 446 + end + end end end end diff --git a/applications/lazstats/source/forms/analysis/statistical_process_control/cumsumunit.pas b/applications/lazstats/source/forms/analysis/statistical_process_control/cumsumunit.pas index f66aca8fd..5ffabf094 100644 --- a/applications/lazstats/source/forms/analysis/statistical_process_control/cumsumunit.pas +++ b/applications/lazstats/source/forms/analysis/statistical_process_control/cumsumunit.pas @@ -1,10 +1,3 @@ -// File for testing: "BoltSizes.laz" -// Lot No --> Group variable -// BoltLngth --> Measurement variable -// Delta --> 0.01 -// Alpha --> 0.05 -// Beta ---> 0.20 - unit CUMSUMUnit; {$mode objfpc}{$H+} @@ -12,527 +5,342 @@ unit CUMSUMUnit; interface uses - Classes, SysUtils, FileUtil, LResources, Forms, Controls, Graphics, Dialogs, - StdCtrls, ExtCtrls, Buttons, - MainUnit, Globals, DataProcs, OutputUnit, BlankFrmUnit, ContextHelpUnit; + Classes, SysUtils, Forms, Controls, Graphics, Dialogs, ComCtrls, ExtCtrls, + StdCtrls, Globals, BasicSPCUnit; type - { TCUMSUMFrm } + { TCUSUMChartForm } - TCUMSUMFrm = class(TForm) - Bevel2: TBevel; - ComputeBtn: TButton; - HelpBtn: TButton; - Panel1: TPanel; - ResetBtn: TButton; - CloseBtn: TButton; - ReturnBtn1: TButton; - TargetEdit: TEdit; - TargetChk: TCheckBox; - DeltaEdit: TEdit; + TCUSUMChartForm = class(TBasicSPCForm) AlphaEdit: TEdit; BetaEdit: TEdit; + DeltaEdit: TEdit; GroupBox1: TGroupBox; GroupBox2: TGroupBox; Label4: TLabel; Label5: TLabel; Label6: TLabel; - MeasEdit: TEdit; - GroupEdit: TEdit; - Label1: TLabel; - Label2: TLabel; - Label3: TLabel; - VarList: TListBox; - procedure ComputeBtnClick(Sender: TObject); + TargetChk: TCheckBox; + TargetEdit: TEdit; procedure FormActivate(Sender: TObject); - procedure FormCreate(Sender: TObject); - procedure FormShow(Sender: TObject); - procedure HelpBtnClick(Sender: TObject); - procedure ResetBtnClick(Sender: TObject); - procedure VarListClick(Sender: TObject); private - { private declarations } - FAutoSized: boolean; - semean: double; - procedure PlotMeans(var Means: DblDyneVec; NoGrps: integer; GrandMean: double); - function Validate(out AMsg: String; out AControl: TWinControl): Boolean; - public - { public declarations } - end; + SEMean: Double; + protected + procedure Compute; override; + procedure PlotMeans(ATitle, AXTitle, AYTitle, ADataTitle, AGrandMeanTitle: String; + const Groups: StrDyneVec; const Means: DblDyneVec; + UCL, LCL, GrandMean, TargetSpec, LowerSpec, UpperSpec: double); override; + procedure Reset; override; + function Validate(out AMsg: String; out AControl: TWinControl): Boolean; override; + end; var - CUMSUMFrm: TCUMSUMFrm; + CUSUMChartForm: TCUSUMChartForm; + implementation +{$R *.lfm} + uses - Math; + Math, TAChartUtils, TASeries, + Utils, MainUnit, DataProcs; -{ TCUMSUMFrm } +{ TCUSUMChartForm } -procedure TCUMSUMFrm.ResetBtnClick(Sender: TObject); -VAR i : integer; -begin - VarList.Clear; - GroupEdit.Text := ''; - MeasEdit.Text := ''; - DeltaEdit.Text := ''; - TargetEdit.Text := ''; - TargetChk.Checked := false; - for i := 1 to NoVariables do - VarList.Items.Add(OS3MainFrm.DataGrid.Cells[i,0]); -end; - -procedure TCUMSUMFrm.VarListClick(Sender: TObject); +procedure TCUSUMChartForm.Compute; var - index: integer; + i, j, grpIndex, numGrps, grpSize, oldGrpSize, numValues: Integer; + X, Xsq, Xmin, Xmax, target, grandMean, grandSum, grandSD, UCL, LCL: Double; + sizeError: Boolean; + grp: String; + groups: StrDyneVec = nil; + means: DblDyneVec = nil; + stdDev: DblDyneVec = nil; + cumSums: DblDyneVec = nil; + count: IntDyneVec = nil; + ColNoSelected: IntDyneVec = nil; + lReport: TStrings; + begin - index := VarList.ItemIndex; - if index > -1 then + SetLength(ColNoSelected, 2); + ColNoSelected[0] := GrpVar; + ColNoSelected[1] := MeasVar; + + groups := GetGroups(); + numGrps := Length(groups); + grpSize := 0; + oldGrpSize := 0; + + SetLength(means, numGrps); + SetLength(count, numGrps); + SetLength(stdDev, numGrps); + SetLength(cumSums, numGrps); + SEMean := 0.0; + grandMean := 0.0; + grandSum := 0.0; + sizeError := false; + + // Count "good" data points + numValues := 0; + for i := 1 to NoCases do + if GoodRecord(i, Length(ColNoSelected), ColNoSelected) then inc(numValues); + + // calculate group ranges, grand mean, group sd's, semeans + for j := 0 to numGrps - 1 do // groups begin - if GroupEdit.Text = '' then - GroupEdit.Text := VarList.Items[index] - else - MeasEdit.Text := VarList.Items[index]; - VarList.Items.Delete(index); + Xmin := Infinity; + Xmax := -Infinity; + for i := 1 to NoCases do + begin + if not GoodRecord(i, Length(ColNoSelected), ColNoSelected) then continue; + grp := Trim(OS3MainFrm.DataGrid.Cells[GrpVar, i]); + grpIndex := IndexOfString(groups, grp); + if grpIndex = j then + begin + X := StrToFloat(Trim(OS3MainFrm.DataGrid.Cells[MeasVar, i])); + Xsq := X * X; + if X > Xmax then Xmax := X; + if X < Xmin then Xmin := X; + inc(count[grpIndex]); + means[grpIndex] := means[grpIndex] + X; + stddev[grpIndex] := stddev[grpIndex] + Xsq; + SEMean := SEMean + Xsq; + grandMean := grandMean + X; + end; + end; // next case + + grpSize := count[j]; + if j = 0 then oldgrpSize := grpSize; + if (oldGrpsize <> grpSize) or (grpSize < 2) then + begin + sizeError := true; + break; + end; + + stdDev[j] := stddev[j] - sqr(means[j]) / grpSize; + stddev[j] := stddev[j] / (grpSize - 1); + stddev[j] := sqrt(stddev[j]); + means[j] := means[j] / grpSize; + end; // next group + + if (grpSize < 2) or (grpSize > 25) or sizeError then + begin + ErrorMsg('Group size error.'); + exit; end; + + // now get cumulative deviations of means from target + if TargetChk.Checked then + target := StrToFloat(TargetEdit.Text) + else + target := means[numGrps-1]; + cumsums[0] := means[0] - target; + grandSum := grandSum + (means[0] - target); + for j := 1 to numGrps-1 do + begin + cumsums[j] := cumsums[j-1] + (means[j] - target); + grandSum := grandSum + (means[j] - target); + end; + + SEMean := SEMean - sqr(grandMean)/numValues; + SEMean := sqrt(SEMean/(numValues - 1)); + grandSD := SEMean; + SEMean := SEMean/sqrt(numValues); + grandMean := grandMean/numValues; // mean of all observations + grandSum := grandSum/numGrps; // mean of the group means + UCL := grandMean + 3.0*SEMean; + LCL := grandMean - 3.0*SEMean; + if (LCL < 0.0) then LCL := 0.0; + + // Print results + lReport := TStringList.Create; + try + lReport.Clear; + lReport.Add('CUMSUM Chart Results'); + lReport.Add(''); + lReport.Add(' Group Size Mean Std.Dev. Cum.Dev. of' ); + lReport.Add(' Mean from Target'); + lReport.Add('------- ---- -------- -------- ----------------'); + for i := 0 to numGrps - 1 do + lReport.Add('%7d %4d %8.2f %8.2f %16.2f', [i+1, count[i], means[i], stddev[i], cumsums[i]]); + lReport.Add(''); + lReport.Add('Mean of group deviations: %8.3f', [grandSum]); + lReport.Add('Mean of all observations: %8.3f', [grandMean]); + lReport.Add('Std. Dev. of Observations: %8.3f', [grandSD]); + lReport.Add('Standard Error of Mean: %8.3f', [SEMean]); + lReport.Add('Target Specification: %8.3f', [target]); + lReport.Add('Lower Control Limit: %8.3f', [LCL]); + lReport.Add('Upper Control Limit: %8.3f', [UCL]); + + ReportMemo.Lines.Assign(lReport); + finally + lReport.Free; + end; + + // Show graph + PlotMeans( + Format('Cumulative Sum Chart for "%s"', [GetFileName]), // chart title + GroupEdit.Text, // x title + 'CUSUM of ' + MeasEdit.Text, // y title + 'Data', // series title + 'Mean deviation', // mean label at right + groups, cumSums, + NaN, NaN, grandSum, + NaN, NaN, NaN + ); end; -procedure TCUMSUMFrm.FormActivate(Sender: TObject); + +procedure TCUSUMChartForm.FormActivate(Sender: TObject); var w: Integer; begin - if FAutoSized then - exit; - w := MaxValue([HelpBtn.Width, ResetBtn.Width, ComputeBtn.Width, CloseBtn.Width]); HelpBtn.Constraints.MinWidth := w; ResetBtn.Constraints.MinWidth := w; ComputeBtn.Constraints.MinWidth := w; CloseBtn.Constraints.MinWidth := w; - VarList.Constraints.MinWidth := GroupBox1.Width * 8 div 10; - VarList.Constraints.MinHeight := GroupBox2.Top + GroupBox2.Height - VarList.Top; - - Constraints.MinWidth := Width; - Constraints.MinHeight := Height; - - FAutoSized := true; + DisableAutoSizing; + try + GroupBox2.Anchors := GroupBox2.Anchors - [akRight]; + VarList.Constraints.MinWidth := VarListLabel.Width; + SpecsPanel.Constraints.MinWidth := Max( + CloseBtn.Left + CloseBtn.Width - HelpBtn.Left + HelpBtn.BorderSpacing.Around, + GroupBox2.Width * 2 + VarList.BorderSpacing.Right + VarList.BorderSpacing.Left + ); + Constraints.MinHeight := GroupBox2.Top + GroupBox2.Height + GroupBox2.BorderSpacing.Bottom + ButtonPanel.Height; + GroupBox2.Anchors := GroupBox2.Anchors + [akRight]; + finally + EnableAutoSizing; + end; end; -procedure TCUMSUMFrm.FormCreate(Sender: TObject); + +{ Overridden to draw the V-Mark } +procedure TCUSUMChartForm.PlotMeans(ATitle, AXTitle, AYTitle, ADataTitle, AGrandMeanTitle: String; + const Groups: StrDyneVec; const Means: DblDyneVec; + UCL, LCL, GrandMean, TargetSpec, LowerSpec, UpperSpec: double); +var + alpha, beta, delta, deltaSD, gamma, d, h, k: Double; + ser: TLineSeries; + ext: TDoubleRect; + x0, y0, x1, y1, x2, y2, x3, y3: Double; begin - Assert(OS3MainFrm <> nil); - if BlankFrm = nil then - Application.CreateForm(TBlankFrm, BlankFrm); + inherited; + if DeltaEdit.Text = '' then + exit; + + alpha := StrToFloat(AlphaEdit.Text); + beta := StrToFloat(BetaEdit.Text); + delta := StrToFloat(DeltaEdit.Text); // This is in data units + deltaSD := delta / SEMean; // This is in multiples of std deviations + + // see : https://www.itl.nist.gov/div898/handbook/pmc/section3/pmc323.htm + d := 2.0 / sqr(deltaSD) * ln((1.0 - beta)/alpha); + k := deltaSD * SEMean / 2.0; + h := d * k; + + ser := TLineSeries.Create(FChartFrame.Chart); + FChartFrame.Chart.AddSeries(ser); + ser.SeriesColor := clBlue; + ser.Title := 'V-Mask'; + + ext := FChartFrame.Chart.GetFullExtent; + x1 := Length(Means); // 1-based! + y1 := Means[High(Means)] + h; + x0 := 1; + y0 := y1 - k*(x0 - x1); + + x2 := x1; + y2 := Means[High(Means)] - h; + x3 := x0; + y3 := y2 + k*(x3 - x2); + + ser.AddXY(x0, y0); + ser.AddXY(x1, y1); + ser.AddXY(x2, y2); + ser.AddXY(x3, y3); +end; + + +procedure TCUSUMChartForm.Reset; +begin + inherited; + DeltaEdit.Clear; AlphaEdit.Text := FormatFloat('0.00', DEFAULT_ALPHA_LEVEL); BetaEdit.Text := FormatFloat('0.00', DEFAULT_BETA_LEVEL); + TargetEdit.Clear; end; -procedure TCUMSUMFrm.FormShow(Sender: TObject); -begin - ResetBtnClick(self); -end; -procedure TCUMSUMFrm.HelpBtnClick(Sender: TObject); -begin - if ContextHelpForm = nil then - Application.CreateForm(TContextHelpForm, ContextHelpForm); - ContextHelpForm.HelpMessage((Sender as TButton).tag); -end; - -procedure TCUMSUMFrm.ComputeBtnClick(Sender: TObject); -var - i, j, GrpVar, MeasVar, mingrp, maxgrp, G, range, grpsize : integer; - oldgrpsize : integer; - X, UCL, LCL : double; - xmin, xmax, GrandMean, GrandSD : double; - Target, GrandSum : double; - Means, StdDev, CumSums: DblDyneVec; - count : IntDyneVec; - cellstring: string; - sizeError: boolean; - ColNoSelected : IntDyneVec; - NoSelected : integer; - lReport: TStrings; - msg: String; - C: TWinControl; - - procedure CleanUp; - begin - CumSums := nil; - StdDev := nil; - Count := nil; - Means := nil; - ColNoSelected := nil; - end; - -begin - if not Validate(msg, C) then - begin - C.SetFocus; - MessageDlg(msg, mtError, [mbOK], 0); - exit; - end; - - SetLength(ColNoSelected,NoVariables); - GrpVar := 1; - MeasVar := 2; - grpsize := 0; - oldgrpsize := 0; - - for i := 1 to NoVariables do - begin - cellstring := OS3MainFrm.DataGrid.Cells[i,0]; - if cellstring = GroupEdit.Text then GrpVar := i; - if cellstring = MeasEdit.Text then MeasVar := i; - end; - NoSelected := 2; - ColNoSelected[0] := GrpVar; - ColNoSelected[1] := MeasVar; - - mingrp := 10000; - maxgrp := -10000; - for i := 1 to NoCases do - begin - if not GoodRecord(i,NoSelected,ColNoSelected) then continue; - G := round(StrToFloat(Trim(OS3MainFrm.DataGrid.Cells[GrpVar,i]))); - if G < mingrp then mingrp := G; - if G > maxgrp then maxgrp := G; - end; - range := maxgrp - mingrp + 1; - - SetLength(means,range); - SetLength(count,range); - SetLength(stddev,range); - SetLength(cumsums,range); - - for i := 0 to range-1 do - begin - count[i] := 0; - means[i] := 0.0; - stddev[i] := 0.0; - cumsums[i] := 0.0; - end; - semean := 0.0; - GrandMean := 0.0; - sizeerror := false; - GrandSum := 0.0; - if TargetChk.Checked then Target := StrToFloat(TargetEdit.Text) - else Target := 0.0; - - // calculate group ranges, grand mean, group sd's, semeans - for j := 1 to range do // groups - begin - xmin := 10000.0; - xmax := -10000.0; - for i := 1 to NoCases do - begin - if not GoodRecord(i,NoSelected,ColNoSelected) then continue; - G := round(StrToFloat(Trim(OS3MainFrm.DataGrid.Cells[GrpVar,i]))); - G := G - mingrp + 1; - if G = j then - begin - X := StrToFloat(Trim(OS3MainFrm.DataGrid.Cells[MeasVar,i])); - if X > xmax then xmax := X; - if X < xmin then xmin := X; - count[G-1] := count[G-1] + 1; - stddev[G-1] := stddev[G-1] + (X * X); - semean := semean + (X * X); - means[G-1] := means[G-1] + X; - GrandMean := GrandMean + X; - end; - end; // next case - stddev[j-1] := stddev[j-1] - (means[j-1] * means[j-1] / count[j-1]); - stddev[j-1] := stddev[j-1] / (count[j-1] - 1); - stddev[j-1] := sqrt(stddev[j-1]); - grpsize := count[j-1]; - means[j-1] := means[j-1] / count[j-1]; - if j = 1 then oldgrpsize := grpsize; - if oldgrpsize <> grpsize then sizeerror := true; - end; // next group - - // now get cumulative deviations of means from target - if Target = 0.0 then Target := means[range-1]; - cumsums[0] := means[0] - Target; - GrandSum := GrandSum + (means[0] - Target); - for j := 2 to range do - begin - cumsums[j-1] := cumsums[j-2] + (means[j-1] - Target); - GrandSum := GrandSum + (means[j-1] - Target); - end; - - if (grpsize < 2) or (grpsize > 25) or (sizeerror) then - begin - MessageDlg('Group sizes error.', mtError, [mbOK], 0); - CleanUp; - exit; - end; - - semean := semean - ((GrandMean * GrandMean) / NoCases); - semean := semean / (NoCases - 1); - semean := sqrt(semean); - GrandSD := semean; - semean := semean / sqrt(NoCases); - GrandMean := GrandMean / NoCases; // mean of all observations - GrandSum := GrandSum / range; // mean of the group means - UCL := GrandMean + (3.0 * semean); - LCL := GrandMean - (3.0 * semean); - if (LCL < 0.0) then LCL := 0.0; - - // printed results - lReport := TStringList.Create; - try - lReport.Clear; - lReport.Add('CUMSUM Chart Results'); - lReport.Add(''); - lReport.Add('Group Size Mean Std.Dev. Cum.Dev. of'); - lReport.Add(' Mean from Target'); - lReport.Add('----- ---- -------- -------- ----------------'); - for i := 0 to range-1 do - lReport.Add(' %3d %3d %8.2f %8.2f %8.2f', [i+1, count[i], means[i], stddev[i], cumsums[i]]); - lReport.Add(''); - lReport.Add('Mean of group deviations: %8.3f', [GrandSum]); - lReport.Add('Mean of all observations: %8.3f', [GrandMean]); - lReport.Add('Std. Dev. of Observations: %8.3f', [GrandSD]); - lReport.Add('Standard Error of Mean: %8.3f', [seMean]); - lReport.Add('Target Specification: %8.3f', [Target]); - lReport.Add('Lower Control Limit: %8.3f', [LCL]); - lReport.Add('Upper Control Limit: %8.3f', [UCL]); - - DisplayReport(lReport); - finally - lReport.Free; - end; - - // show graph - PlotMeans(cumsums, range, GrandSum); - - // Clean up - CleanUp; -end; - -procedure TCUMSUMFrm.PlotMeans(var Means: DblDyneVec; NoGrps: integer; - GrandMean: double); -var - i, xpos, ypos, hleft, hright, vtop, vbottom, imagewide : integer; - vhi, hwide, offset, strhi, grpnospc, distx : integer; - imagehi, maxval, minval, valincr, Yvalue : double; - alpha, beta, delta, gamma, theta, kfactor, d : double; - Title : string; -begin - maxval := -10000.0; - minval := 10000.0; - for i := 0 to NoGrps-1 do - begin - if means[i] > maxval then maxval := means[i]; - if means[i] < minval then minval := means[i]; - end; -// BlankFrm.Image1.Canvas.Clear; - BlankFrm.Show; - Title := 'CUMSUM CHART FOR : ' + OS3MainFrm.FileNameEdit.Text; - BlankFrm.Caption := Title; - imagewide := BlankFrm.Image1.Width; - imagehi := BlankFrm.Image1.Height; - vtop := 20; - vbottom := round(imagehi) - 80; - vhi := vbottom - vtop; - hleft := 100; - hright := imagewide - 80; - hwide := hright - hleft; - - BlankFrm.Image1.Canvas.Brush.Color := clLtGray; - BlankFrm.Image1.Canvas.FillRect(0, 0, BlankFrm.Image1.Width, BlankFrm.Image1.Height); - - // Draw chart border - BlankFrm.Image1.Canvas.Pen.Color := clBlack; - BlankFrm.Image1.Canvas.Brush.Color := clWhite; - BlankFrm.Image1.Canvas.Rectangle(hleft,vtop-10,hleft+hwide,vtop+vhi+10); - - // draw Grand Mean - ypos := round(vhi * ( (maxval - GrandMean) / (maxval - minval))); - ypos := ypos + vtop; - xpos := hleft; - BlankFrm.Image1.Canvas.MoveTo(xpos,ypos); - xpos := hright; - BlankFrm.Image1.Canvas.Pen.Color := clRed; - BlankFrm.Image1.Canvas.LineTo(xpos,ypos); - Title := 'AVG.DEV.'; - strhi := BlankFrm.Image1.Canvas.TextHeight(Title); - ypos := ypos - strhi div 2; - BlankFrm.Image1.Canvas.Brush.Style := bsClear; - BlankFrm.Image1.Canvas.TextOut(xpos,ypos,Title); - - // draw horizontal axis - BlankFrm.Image1.Canvas.MoveTo(hleft,vbottom + 20); - BlankFrm.Image1.Canvas.LineTo(hright,vbottom + 20); - for i := 1 to NoGrps do - begin - ypos := vbottom + 10; - xpos := round((hwide / NoGrps)* i + hleft); - BlankFrm.Image1.Canvas.MoveTo(xpos,ypos); - ypos := ypos + 10; - BlankFrm.Image1.Canvas.LineTo(xpos,ypos); - Title := format('%d',[i]); - offset := BlankFrm.Image1.Canvas.TextWidth(Title) div 2; - strhi := BlankFrm.Image1.Canvas.TextHeight(Title); - xpos := xpos - offset; - ypos := ypos + strhi; - BlankFrm.Image1.Canvas.Pen.Color := clBlack; - BlankFrm.Image1.Canvas.TextOut(xpos,ypos,Title); - xpos := 10; - BlankFrm.Image1.Canvas.TextOut(xpos,ypos,'GROUPS:'); - end; - - // Draw vertical axis - valincr := (maxval - minval) / 10.0; - for i := 1 to 11 do - begin - Title := format('%8.2f',[maxval - ((i-1)*valincr)]); - strhi := BlankFrm.Image1.Canvas.TextHeight(Title); - xpos := 10; - Yvalue := maxval - (valincr * (i-1)); - ypos := round(vhi * ( (maxval - Yvalue) / (maxval - minval))); - ypos := ypos + vtop - strhi div 2; - BlankFrm.Image1.Canvas.TextOut(xpos,ypos,Title); - end; - - // draw lines for means of the groups - ypos := round(vhi * ( (maxval - means[0]) / (maxval - minval))); - ypos := ypos + vtop; - xpos := round((hwide / NoGrps) + hleft); - BlankFrm.Image1.Canvas.MoveTo(xpos,ypos); - BlankFrm.Image1.Canvas.Pen.Color := clBlack; - for i := 2 to NoGrps do - begin - ypos := round(vhi * ( (maxval - means[i-1]) / (maxval - minval))); - ypos := ypos + vtop; - xpos := round((hwide / NoGrps)* i + hleft); - BlankFrm.Image1.Canvas.LineTo(xpos,ypos); - end; - - // Draw V Mask - if DeltaEdit.Text = '' then exit; // not elected - BlankFrm.Image1.Canvas.Pen.Color := clBlue; - delta := StrToFloat(DeltaEdit.Text); - gamma := delta / semean; - alpha := StrToFloat(AlphaEdit.Text); - beta := StrToFloat(BetaEdit.Text); - kfactor := 2.0 * semean; - d := (2.0 / (gamma * gamma)) * ln((1.0 - beta)/alpha); - theta := arctan(delta / (2.0 * kfactor)); - grpnospc := round(hwide / NoGrps); - xpos := hleft + (grpnospc * (NoGrps)); // last group - ypos := round(vhi * ( (maxval - means[NoGrps-1]) / (maxval - minval))); - ypos := ypos + vtop; - BlankFrm.Image1.Canvas.MoveTo(xpos,ypos); - xpos := round(xpos + (d * grpnospc / hwide)); // scaled d - BlankFrm.Image1.Canvas.LineTo(xpos,ypos); // line 0 to A - - // draw upper angle line - xpos := hleft + (grpnospc * NoGrps); // last group - xpos := round(xpos + (d * grpnospc / hwide)); // plus scaled d - ypos := round(vhi * ( (maxval - means[NoGrps-1]) / (maxval - minval))); - ypos := ypos + vtop; - BlankFrm.Image1.Canvas.MoveTo(xpos,ypos); - ypos := vtop; // draw angle up to top of graph - distx := round(vhi / tan(theta)); // x unscaled distance - xpos := round(xpos - (distx * grpnospc / hwide)); - BlankFrm.Image1.Canvas.LineTo(xpos,ypos); - - // draw lower angle line - xpos := hleft + (grpnospc * NoGrps); // last group - xpos := round(xpos + (d * grpnospc / hwide)); // plus scaled d - ypos := round(vhi * ( (maxval - means[NoGrps-1]) / (maxval - minval))); - ypos := ypos + vtop; - BlankFrm.Image1.Canvas.MoveTo(xpos,ypos); - ypos := vbottom; - xpos := round(xpos - (distx * grpnospc / hwide)); - BlankFrm.Image1.Canvas.LineTo(xpos,ypos); - BlankFrm.Image1.Canvas.Pen.Color := clBlack; -end; - -function TCUMSUMFrm.Validate(out AMsg: String; out AControl: TWinControl): Boolean; +function TCUSUMChartForm.Validate(out AMsg: String; out AControl: TWinControl): Boolean; var x: Double; + n: Integer; begin - Result := False; - - if GroupEdit.Text = '' then - begin - AMsg := 'Group variable not specified.'; - AControl := GroupEdit; + Result := inherited; + if not Result then exit; + + Result := false; + + if (DeltaEdit.Text <> '') then + begin + if not TryStrToFloat(DeltaEdit.Text, x) then + begin + AMsg := 'No valid number given for Delta.'; + AControl := DeltaEdit; + exit; + end; + + if (AlphaEdit.Text = '') then + begin + AMsg := 'Alpha not specified.'; + AControl := AlphaEdit; + exit; + end; + if not TryStrToFloat(AlphaEdit.Text, x) then + begin + AMsg := 'No valid number given for Alpha.'; + AControl := AlphaEdit; + exit; + end; + + if (BetaEdit.Text = '') then + begin + AMsg := 'Beta not specified.'; + AControl := BetaEdit; + exit; + end; + if not TryStrToFloat(BetaEdit.Text, x) then + begin + AMsg := 'No valid number given for Beta.'; + AControl := BetaEdit; + exit; + end; end; - if MeasEdit.Text = '' then + if TargetChk.Checked then begin - AMsg := 'Measurement variable not specified.'; - AControl := MeasEdit; - exit; + if (TargetEdit.Text = '') then + begin + AMsg := 'Target not specified.'; + AControl := TargetEdit; + exit; + end; + if not TryStrToFloat(TargetEdit.Text, x) then + begin + AMsg := 'No valid number given for target specification.'; + AControl := TargetEdit; + exit; + end; end; - if DeltaEdit.Text = '' then - begin - AMsg := 'Delta parameter not specified.'; - AControl := DeltaEdit; - exit; - end; - if not TryStrToFloat(DeltaEdit.Text, x) then - begin - AMsg := 'Delta parameter is not a valid number.'; - AControl := DeltaEdit; - exit; - end; - - if AlphaEdit.Text = '' then - begin - AMsg := 'Alpha probability is not specified.'; - AControl := AlphaEdit; - exit; - end; - if not TryStrToFloat(AlphaEdit.Text, x) then - begin - AMsg := 'Alpha probability is not a valid number.'; - AControl := AlphaEdit; - exit; - end; - - if BetaEdit.Text = '' then - begin - AMsg := 'Beta probability is not specified.'; - AControl := BetaEdit; - exit; - end; - if not TryStrtoFloat(BetaEdit.Text, x) then - begin - AMsg := 'Beta probability is not a valid number,'; - AControl := BetaEdit; - exit; - end; - - if TargetChk.Checked then - begin - if TargetEdit.Text = '' then - begin - AMsg := 'Target is not specified.'; - AControl := TargetEdit; - exit; - end; - if not TryStrToFloat(TargetEdit.Text, x) then - begin - AMsg := 'Target specification is not a valid number.'; - AControl := TargetEdit; - exit; - end; - end; - Result := true; end; -initialization - {$I cumsumunit.lrs} - end. diff --git a/applications/lazstats/source/forms/analysis/statistical_process_control/rchartunit.lfm b/applications/lazstats/source/forms/analysis/statistical_process_control/rchartunit.lfm index 27bc3ed67..29158f0a3 100644 --- a/applications/lazstats/source/forms/analysis/statistical_process_control/rchartunit.lfm +++ b/applications/lazstats/source/forms/analysis/statistical_process_control/rchartunit.lfm @@ -1,7 +1,7 @@ inherited RChartForm: TRChartForm HelpType = htKeyword HelpKeyword = 'html/RangeChart.htm' - Caption = 'Range Chart' + Caption = 'Range Control Chart' inherited SpecsPanel: TPanel HelpType = htKeyword HelpKeyword = 'html/RangeChart.htm' diff --git a/applications/lazstats/source/forms/analysis/statistical_process_control/schartunit.lfm b/applications/lazstats/source/forms/analysis/statistical_process_control/schartunit.lfm index 065a945a2..1ccce9ce8 100644 --- a/applications/lazstats/source/forms/analysis/statistical_process_control/schartunit.lfm +++ b/applications/lazstats/source/forms/analysis/statistical_process_control/schartunit.lfm @@ -1,5 +1,5 @@ inherited SChartForm: TSChartForm HelpType = htKeyword HelpKeyword = 'html/SControlChart.htm' - Caption = 'Sigma Chart' + Caption = 'Sigma Control Chart' end diff --git a/applications/lazstats/source/forms/analysis/statistical_process_control/uchartunit.lfm b/applications/lazstats/source/forms/analysis/statistical_process_control/uchartunit.lfm index 07743a2cc..a4800aae8 100644 --- a/applications/lazstats/source/forms/analysis/statistical_process_control/uchartunit.lfm +++ b/applications/lazstats/source/forms/analysis/statistical_process_control/uchartunit.lfm @@ -1,7 +1,7 @@ inherited UChartForm: TUChartForm HelpType = htKeyword HelpKeyword = 'html/DefectsperUnituChart.htm' - Caption = 'Defects per unit U Chart' + Caption = 'Defects per unit U Control Chart' OnActivate = FormActivate inherited SpecsPanel: TPanel Width = 432 diff --git a/applications/lazstats/source/forms/analysis/statistical_process_control/xbarchartunit.lfm b/applications/lazstats/source/forms/analysis/statistical_process_control/xbarchartunit.lfm index 95520a265..63f13af68 100644 --- a/applications/lazstats/source/forms/analysis/statistical_process_control/xbarchartunit.lfm +++ b/applications/lazstats/source/forms/analysis/statistical_process_control/xbarchartunit.lfm @@ -3,7 +3,7 @@ inherited XBarChartForm: TXBarChartForm Top = 215 HelpType = htKeyword HelpKeyword = 'html/XBarChart.htm' - Caption = 'X-Bar Chart' + Caption = 'X-Bar Control Chart' OnActivate = FormActivate inherited SpecsPanel: TPanel Width = 475 diff --git a/applications/lazstats/source/forms/mainunit.pas b/applications/lazstats/source/forms/mainunit.pas index 59cd683a9..7159db56a 100644 --- a/applications/lazstats/source/forms/mainunit.pas +++ b/applications/lazstats/source/forms/mainunit.pas @@ -510,7 +510,7 @@ uses BinomialUnit, KendallTauUnit, KaplanMeierUnit, // Statistical process control - XBarChartUnit, RChartUnit, SChartUnit, CUMSUMUNIT, CChartUnit, + XBarChartUnit, RChartUnit, SChartUnit, CUMSUMUnit, CChartUnit, PChartUnit, UChartUnit, CorSimUnit, @@ -2130,9 +2130,9 @@ end; // Menu "Analysis" > "Statistical Process Control" > "CUMSUM Chart" procedure TOS3MainFrm.mnuAnalysisSPC_CUMSUMClick(Sender: TObject); begin - if CUMSUMFrm = nil then - Application.CreateForm(TCUMSUMFrm, CUMSUMFrm); - CUMSUMFrm.ShowModal; + if CUMSUMChartForm = nil then + Application.CreateForm(TCUMSUMChartForm, CUMSUMChartForm); + CUMSUMChartForm.ShowModal; end;