Search Home Members Contacts
About Us
Products
Downloads
Community
Support
Pages: [1]
  Print  
Author Topic: Eaccess violation in AppIdle routine  (Read 193 times)
zuffle
Customers
Community Member
*****
Posts: 9


« on: September 26, 2008, 04:09:00 PM »

Hi,

Having problems with calls within my AppIdle routine (Eaccess violation raised!).
I have a modal form TfmRotateModel (yes, I'm using Delphi guys!) that holds tv3d to preview my models stuff. When open it, it runs OK, and can see my models n'that, problem is when I close it.

Modal routine looks like this:

Code:
procedure TfmMainForm.sbModelRotateClick(Sender: TObject);
var
  fmRotateModel : TfmRotateModel;
begin
  fmRotateModel := TfmRotateModel.Create(self);
  try
    begin
      fmRotateModel.GetMRUList;
      fmRotateModel.ShowModal();
    end;
    finally
      begin
        fmRotateModel.Free();
        sbModelRotate.Down := false;
      end;
  end;

end;

The forms own create routine looks like this:
Code:
procedure TfmRotateModel.EngineCreate;
begin
    TV := CoTVEngine.Create;
    TV.Init3DWindowed(handle,true);
    TV.SetDebugMode(true, true, true, true);
    TV.SetDebugFile(ExtractFilePath(Application.ExeName) + '6_5_debugfile.txt');
    // Lets display the FPS:
    TV.DisplayFPS(true, 0);

    Scene := CoTVScene.Create;

    Global := CoTVGlobals.Create;

    Atmos := CoTVAtmosphere.Create;

    Inp:= CoTVInputEngine.Create;
    Inp.Initialize(True, True);  // Lets init both keyboard and mouse:

    Land := Scene.CreateLandscape('Landscape1');

    TexFactory := CoTVTextureFactory.Create;

    //Tank := TTVMesh.Create(self);
//    Actor := CoTVActor.Create;
end;


My AppIdle routine looks like:

Code:
procedure TfmRotateModel.AppIdle(Sender: TObject; var Done: Boolean);
begin
  if TV <> nil then
  begin
    // This tells Windows it isnt done, so it will continue to loop.
    done := false;

    if Scene <> nil then
      GetPosRotData;


    // The actual render loop:
    TV.Clear(false);

    Atmos.Atmosphere_Render;
    Land.Render;


    //////////////////////////////
    if Actor <> nil then
      Actor.Render(true);

    TV.RenderToScreen;

    Application.ProcessMessages;

  end
  else
    done := true;
end;

So, I'm testing that the TV pointers aren't null before using the Tv objects, seems that EVEN after the TForm closed, code enters the on Appidle routine and gets past  the
Code:
  if TV <> nil then
  begin

and the
Code:
    if Scene <> nil then
      GetPosRotData;

into the 'GetPosRotData;' routine, which has another test, la:

Code:
procedure TfmRotateModel.GetPosRotData;
begin
  if Scene <> nil then
  begin
    Scene.GetCamera.SetPosition(CameraPos.x,CameraPos.y,CameraPos.z);
    Scene.GetCamera.SetRotation(RotateAngle.x,RotateAngle.y,RotateAngle.z);
  end;
end;

Appears that the 'scene' object is not nil either, as calls the Scene.GetCamera.SetPosition routine,
which raises the exception.

Now, when the modal form is destroyed I attempt to clear all the memory allocated, and set
the pointers to nil, so behvaiour is unexpected. The Forms destroy routine looks like:

Code:
procedure TfmRotateModel.FormDestroy(Sender: TObject);
begin

  if Actor <> nil then
  begin
    Actor.Destroy;
    Actor:= nil;
  end;

  if TV <> nil then
  begin


    Scene := nil;

    Inp := nil;
    Global := nil;
    Atmos := nil;
    Land := nil;
    TexFactory := nil;

    //
    TV.ReleaseAll();
    TV := nil;


  end;

end;

This routine is defnt. entered when close Form, but seems the routines held within the
forms AppIdle are entered (even though form destroyed Huh). So the Tv objects that have been set to nil, appear to pass the 'if object <> nil' test (even though I've set them to nil). So its not until the object is actually being used 'Scene.GetCamera.SetPosition' that the exception is raised.

Am I doing something daft?

Any clues anyone?

Ta,

Z














Logged
Raine
Customers
Community Member
*****
Posts: 1189


« Reply #1 on: September 26, 2008, 05:12:42 PM »

Hai Z,
The AppIdle message is sent when the form has received and processed all the incoming messages. Not sure why you get an AppIdle handler with a var bool param, considering it's another message telling the form to close down (just wondering). It could be that the appidle is repeated as long as you keep "done" false, waiting to be restarted when the message queue has been processed.

It looks like you're relying on the TV object pointer to either enter the appidle handler or be done with it(duh!). I wouldn't do that. Have you considered a different approach? It could be the object is not nulled yet, but TV has already been destructed, thus producing an access violation (either wrong windows message handling sequence or an inconstency of the tv wrapper).

« Last Edit: September 26, 2008, 05:14:27 PM by Raine » Logged

zuffle
Customers
Community Member
*****
Posts: 9


« Reply #2 on: September 26, 2008, 05:48:56 PM »

Thanks Raine,

Your comment made me have a re-think.
Problem was cos I had a Modal form tied to the main applications onidle event.
So it was entring the destroyed foems routine when it shouldn't have.

So now call the Modal form to render, from the mainforms Appidle event, and only when the modal from isn't nil.
Seems to work.

Ta
Z
Logged
Raine
Customers
Community Member
*****
Posts: 1189


« Reply #3 on: September 27, 2008, 03:50:03 AM »

Glad you fixed it, have fun =)
Logged

AriusEso
Customers
Community Member
*****
Posts: 377

Esoteric


« Reply #4 on: September 27, 2008, 08:13:04 PM »

I would advise you don't use AppIdle. I know the delphi template does and it's dirty imo. Instead do something like this:

Code:
procedure TForm1.ProcessFrame();
begin
  while loop = true do
  begin
    TV.Clear(false);
    //Render Junk.
    TV.RenderToScreen;

    Input();
    UpdateScene();
    //Process message queue here.
    Application.ProcessMessages;
  end;

  TV.ReleaseAll;
  TV := nil;
  Application.Terminate;
end;

Then in the forms close event simply do a "loop := false;".
Logged

Pages: [1]
  Print  
 
Jump to:  

Powered by SMF 1.1.3 | SMF © 2006-2007, Simple Machines LLC
Seo4Smf v0.2 © Webmaster's Talks