PDA

View Full Version : Question about lnet :)



NickS
28-08-2011, 05:44 PM
So I've been playing around with lnet console and I can't manage to receive messages. I can receive and send messages fine with lnet visual but I can only send with lnet console.

I imagine it has something to do with this line:

FCon.OnReceive := OnRe;

I'm thinking that assigning OnReceive to OnRe isn't actually doing what I want. The original code from the example is:

FCon.OnReceive := @OnRe;

But that doesn't compile in Lazarus unless you add {$mode objfpc}{$H+} which I can't for my project.

Anyone have any advice they can give? Any help is appreciated :)

Thank you! 8)

code_glitch
28-08-2011, 09:53 PM
Perhaps try


{$Mode Delphi}


or


type
pOnReType = OnReType^;

NickS
28-08-2011, 11:28 PM
Haha awesome signature code_glitch, will try these tricks when I get home. Thank you! :)

NickS
29-08-2011, 02:28 AM
I tried {$Mode Delphi} and that didn't work.

I'm not sure what to do with pOnReType = OnReType^; though, could you provide an example for me so I can understand the context its used in? :)

NickS
29-08-2011, 02:33 AM
Here's the code I'm using:


{$IFDEF WINDOWS}
{$R *.res}
{$ENDIF}
{$DEFINE STATIC}

{$Mode Delphi}

uses
lnet, crt, classes;

type
{ TLTCPTest }
TLTCPTest = class
private
FQuit: boolean;
FCon: TLTcp; // the connection
{ these are all events which happen on our server connection. They are called inside CallAction
OnEr gets fired when a network error occurs.
OnRe gets fired when any of the server sockets receives new data.
OnDs gets fired when any of the server sockets disconnects gracefully.
}
procedure OnDs(aSocket: TLSocket);
procedure OnRe(aSocket: TLSocket);
procedure OnEr(const msg: string; aSocket: TLSocket);
public
message: string;
received: TStringlist;
constructor Create;
destructor Destroy; override;
end;

procedure TLTCPTest.OnDs(aSocket: TLSocket);
begin
//
end;

procedure TLTCPTest.OnRe(aSocket: TLSocket);
var
s: string;
begin
if aSocket.GetMessage(s) > 0 then
begin
message:='Received message "'+s+'"';
end;
end;

procedure TLTCPTest.OnEr(const msg: string; aSocket: TLSocket);
begin
//
end;

constructor TLTCPTest.Create;
begin
FCon := TLTCP.Create(nil);
FCon.OnError := OnEr;
FCon.OnReceive := OnRe;
FCOn.OnDisconnect := OnDs;
FCon.Timeout := 100;
end;

destructor TLTCPTest.Destroy;
begin
FCon.Free; // free the connection
inherited Destroy;
end;

procedure netconnect(server, portz: string);
var
Address: string;
Port: Word;
attempt: integer;
quitting: boolean;
begin
address:=server;
port:=word(strtoint(portz));
attempt:=0;
quitting:=false;
tcp.FCon.Connect(Address, Port);
repeat
tcp.FCon.CallAction;
attempt:=attempt+1;
if attempt=9001 then quitting:=true;
until tcp.fcon.Connected or quitting;
end;

procedure netmessage(str: string);
begin
tcp.FCon.SendMessage(str+#13#10);
end;

Begin
tcp:=tltcptest.create;
netconnect('192.168.0.1', '1111');
netmessage('hello!');


And after netmessage('hello!'); I use some other code that uses messages received and other stuff.

code_glitch
29-08-2011, 11:17 AM
Ah, OnRe is a procedure.... Hmm. I thought it was just a variable and that it was one of those times where the @ trick didn't work for the memory address and thus a pointer to it as a variable type might however that usually doesn't work with a procedure.

The problem, after looking at the code, is that you are trying to set the variable FCon.OnRecieve to a procedure - which cannot be done. The example is correct in saying that IF FCon.Onrecieve is of type procedure you could tell it the memory address of the procedure with the @.

Ignoring all of the above, whats the error message the compiler gives exactly? My suggestion coming from a pure FPC perspective would be to do



if FCon.OnRecieve then OnRe;


However this assumes that FCon.OnRecieve is of type Boolean and that, as the code indicates, OnRe is a procedure. However, this is from a FPC perspective as my lazarus knowledge is very limited.

NickS
29-08-2011, 02:45 PM
Yes OnRe is a procedure so it doesn't return any value. Here is the code for FCon.OnReceive:

property OnReceive: TLSocketEvent read FOnReceive write FOnReceive;

I'm not sure how properties work so that's probably why I'm stumped on this :P


When I compile with the code being:

FCon.OnReceive := @OnRe;

It says: Variable identifier expected.

I really appreciate your help Code_Glitch, I hope we can sort this issue out because I'm this ->||<- close to having multiplayer for my game :D

code_glitch
29-08-2011, 06:10 PM
I read this page: http://wiki.freepascal.org/User_Changes_2.4.0#Treating_direct-mapped_properties_as_regular_fields

My understanding from it is that the 'property' maps onto a variable of some type and that it can be used as a sort of splitter. Ie: The property can be read and it will read from a value and the property can be written to in which case it can write to another value. I only had a skim so I'm not sure how it could apply. I'll think it over and hopefully come up with a solution later this evening - hungry as ever so unable to work on it much right now :D

NickS
29-08-2011, 10:00 PM
Interesting :P

NickS
18-09-2011, 02:31 PM
Fixed it :) just forgot to do FCon.Callaction;