Hey. The question is this: I saw the assignment of a reference to a function several times in the object; Suppose I need to make a class TMyAction, in which there are several parameters and a link to the procedure. How to organize this?

[...] type TMyAction = class(TObject) Param1: string; Param2: string; Param3: string; procedure Action; (* тут явно что-то должно быть *) var MyAction1, MyAction2: TMyAction; procedure someFunc; procedure someFunc2; [...] begin [...] MyAction1.Action := @someFunc; MyAction2.Action := @someFunc2; end. 

Something like that) That this is possible, I know, I watched. The question is - where in this piece is there something to add?

UPD is ideal such use

 if (act = 'go') then with MyAction1 do begin Param1 := var1; Param2 := var2; Action := goProcedure; end; 
  • access to parameters from procedures.

    3 answers 3

    In the comments there was not enough space))

    There are a lot of options. For this implementation, what kind of project we started with

     procedure someFunc (Sender:TObject); begin ShowMessage(TMyAction(Sender).Param1); end; procedure TForm1.FormCreate(Sender: TObject); var MyAction1: TMyAction; begin MyAction1 :=TMyAction.Create; MyAction1.Param1:='dsadasdas'; MyAction1.Action := someFunc; MyAction1.Action(MyAction1); end; 

    but I would be so

      TmyProcedure = procedure (Param1,Param2,Param3: string); TMyAction = class(TObject) Param1: string; Param2: string; Param3: string; Action: TmyProcedure end; 

    ...

     procedure someFunc (Param1,Param2,Param3: string); begin ShowMessage(Param1); end; procedure TForm1.FormCreate(Sender: TObject); var MyAction1: TMyAction; begin MyAction1 :=TMyAction.Create; MyAction1.Param1:='dsadasdas'; MyAction1.Action := someFunc; MyAction1.Action(MyAction1.Param1,MyAction1.Param3,MyAction1.Param3); end; 

    But it can be said a personal matter of each.

    • >> MyAction1.Action: = someFunc; >> MyAction1.Action (MyAction1.Param1, MyAction1.Param3, MyAction1.Param3); o_O Need to do: in TmyAction implement the method: public: ... procedure call (); begin if assigned (Action) then Action (Param1, Param2, Param3); end; Well, call the call accordingly, and not the action which also needs to pass parameters - Alex Kapustin
    • Oh, I remembered the construction with Sender as TMyAction do =) Here, fine, thanks) The second option is not quite ice, because it is planned to install something like Act := NextAction in the one event Act := NextAction , but in a completely different one (and possibly in another thread ) if Act.Ready then Act.Action(Act); . That is, the parameters are obtained and used in different streams, here. Thank you) - Sh4dow

    If the event mechanism is meant, then:

     TMyEvent = procedure(const Param1, Param2: string) of object; TMyAction = class(TObject) public FParam1: string; FParam2: string; FParam3: string; FAction1: TNotifyEvent; // Можно прикрутить стандартный обработчик procedure(Sender: TObject) FAction2: TMyEvent; // Свой формат обработчкчика procedure(const Param1, Param2: string) end; 

    In the code, to run, you will need to check whether the handler is assigned or not:

     if Assigned(FAction2) then begin FAction2("123", "234"); end; 
    • Events are an interesting option, thank you, but I will postpone it for the last attempts, it is still not what is necessary, but as a crutch will come down. - Sh4dow
    • In events the option of passing a pointer to an object method is implemented If you need to pass a pointer to ordinary functions, you can use something like: type TUserProc = procedure (Param1, Param2: String); But this option is not often used, in Delphi it is still more convenient to work with objects. - KiTE
    • And mine, it is you (@ Sh4dow) who are going to make a crutch. True, in the above code, 2 action is not needed. (FAction1: TNotifyEvent;) superfluous - Alex Kapustin
    • FAction1 and FAction2 I set to show the use of the usual TNotifyEvent and user. - KiTE
    • @shurik I'm going to make a class with a dynamic method (objects are one method and different). The dynamic method is the solution, and calling the event by a direct call (from another class, for example) is, in my opinion, a crutch) <pre> if (act = 'go') then with MyAction1 do begin Param1: = var1; Param2: = var2; Action: = goProcedure; end; </ pre> something like that is needed. - Sh4dow

    Almost guessed

      TMyAction = class(TObject) Param1: string; Param2: string; Param3: string; Action: procedure (Sender:TObject) 

    Approximately the class should look like

     procedure someFunc (Sender:TObject); begin end; procedure someFunc2 (Sender:TObject); begin end; [...] begin [...] MyAction1.Action := someFunc; MyAction2.Action := someFunc2; end. 

    This is approximately what the general principle looks like.

    • Damn, I can not get to the delphi now. Will I not receive Unsatisfied forward declration in this way? It means, there are absolutely no directives a la stdcall; and tp is not necessary? I would also like to be able to reassign them. - Sh4dow
    • If you have someFunc procedures from Dll, you need it. And Unsatisfied forward declration is issued if the ancestor class has a property with the same name but of a different type. Yes, and most importantly, Action and someFunc ads must match. TObject Action properties do not have this 100%))) - Vahan Av
    • Okay, but how to get to the parameters? - Sh4dow