Change CheckBox state without calling OnClick Event
Asked Answered
C

10

14

I'm wondering so when I change state of CheckBox

CheckBox->Checked=false;

It calls CheckBoxOnClick Event , how to avoid it ?

Camail answered 15/2, 2010 at 6:34 Comment(1)
By using a tButton with a ✓ at the .text property. The height and width 25x25 so it looks like a checkbox. Start with .text empty. When the button is pressed the label is changed to a ✓. onClick can test if the label is empty or a ✓ mark. Using an if mylabel.text = '' then ...change the text to the ✓ else mylabel.text:='✓'; Thats it. Anywhere else in your code you can read the mylabel.text value to see if its ✓ or not. I have found that when using a stylebook there is no way around, for me to have the checkbox in an unchecked state on form.create. Good solution and I hope it helps you.Ylla
A
10

You could surround the onClick event code with something like

if myFlag then
  begin
    ...event code...
  end;

If you don't want it to be executed, set myFlag to false and after the checkbox state's change set it back to true.

Addax answered 15/2, 2010 at 7:18 Comment(1)
yes ... :-S that's really easy. Don't know why I didn't made it myself >_<Camail
N
11

In newer Delphi versions you can use class helpers to add this functionality:

CheckBox.SetCheckedWithoutClick(False);

by using the following class helper for a VCL TCheckBox:

TCheckBoxHelper = class helper for TCheckBox
    procedure SetCheckedWithoutClick(AChecked: Boolean);
end;

procedure TCheckBoxHelper.SetCheckedWithoutClick(AChecked: Boolean);
begin
    ClicksDisabled := True;
    try
        Checked := AChecked;
    finally
        ClicksDisabled := False;
    end;
end;

Just for completeness: A FMX TCheckBox will behave similar (triggering OnChange). You can workaround this by using the following class helper:

TCheckBoxHelper = class helper for TCheckBox
    procedure SetCheckedWithoutClick(AChecked: Boolean);
end;

procedure TCheckBoxHelper.SetCheckedWithoutClick(AChecked: Boolean);
var
    BckEvent: TNotifyEvent;
begin
    BckEvent := OnChange;
    OnChange := nil;
    try
        IsChecked := AChecked;
    finally
        OnChange := BckEvent;
    end;
end;

Disclaimer: Thanks, dummzeuch for the original idea. Be aware of the usual hints regarding class helpers.

Negligence answered 28/1, 2014 at 10:15 Comment(1)
It is just what I was looking for !! ThanksDeice
A
10

You could surround the onClick event code with something like

if myFlag then
  begin
    ...event code...
  end;

If you don't want it to be executed, set myFlag to false and after the checkbox state's change set it back to true.

Addax answered 15/2, 2010 at 7:18 Comment(1)
yes ... :-S that's really easy. Don't know why I didn't made it myself >_<Camail
C
10

Another option is to change the protected ClicksDisable property using an interposer class like this:

type
  THackCheckBox = class(TCustomCheckBox)
  end;

procedure TCheckBox_SetCheckedNoOnClick(_Chk: TCustomCheckBox; _Checked: boolean);
var
  Chk: THackCheckBox;
begin
  Chk := THackCheckBox(_Chk);
  Chk.ClicksDisabled := true;
  try
    Chk.Checked := _Checked;
  finally
    Chk.ClicksDisabled := false;
  end;
end;
Corm answered 15/2, 2010 at 7:57 Comment(0)
N
7

I hope there's a button solution but you could store the current event in a TNotifyEvent var, then set Checkbox.OnChecked to nil and afterwards restore it.

Neonate answered 15/2, 2010 at 7:2 Comment(1)
CheckBox->Checked=false is on button but it even calls onClick event. So I'll try it. Thank you.Camail
G
4

try this way:

Checkbox.OnClick := nil;
try
  Checkbox.Checked := yourFlag;
finally
  Checkbox.OnClick := CheckboxClick;
end;
Gredel answered 28/3, 2016 at 10:50 Comment(1)
Worked for me. It seems to be the easiest solution.Numismatics
R
2

Use the focused property to establish if the control has been clicked or the checked has been updated outside the control.

If tcheckbox.focused then

 run the content of the method

else

skip the content 
Rare answered 27/1, 2021 at 22:16 Comment(0)
A
1

Some other and much easier solution is not avoiding the the OnClick event but modifying the event handler not to respond unless the DataSet.State is in either dsEdit or dsInsert as initiated by a user triggered TDBCheckBox click e.g.:

procedure TForm1.chkSelectClick(Sender: TObject);
begin
  if chkSelect.Checked = True then
    if DataSource1.DataSet.State in [dsEdit,dsInsert] then
      begin
        { your event handler }
      end;
end;
Acroterion answered 20/5, 2020 at 16:6 Comment(0)
E
0

Simple solution is to put your onclick code in onmouseup event;

Emmy answered 18/5, 2017 at 6:19 Comment(0)
W
0

foudn this on scalabium.com

Sometimes it's necessary to change a state of TCheckBox component, but without operation of OnClick event. This task can be solved so:

{set a checked}

yourCheckBox.Perform(BM_SETCHECK, 1, 0);

{set a unchecked}

yourCheckBox.Perform(BM_SETCHECK, 0, 0);
Westminster answered 23/2 at 18:14 Comment(0)
T
-1

CheckBox.State := cbUnchecked; works in Delphi, this doesn't fire onClickEvent AFAIK

Triclinic answered 11/10, 2011 at 13:47 Comment(1)
I thought so but tried it in XE7 and setting State to CBChecked or CBUnchecked fires the OnClickEvent.Pipeline

© 2022 - 2024 — McMap. All rights reserved.