T.Guilleminot wrote:
> 1. I'm unsure of chronology of things to do in the program body. Is the
> following correct :
>    a) Create GTK stuff
>    b) SDL Hack/SDL_WINDOWID
>    c) SDL_INIT
>    d) Show GTK widgets
> 

Yes that's right. With the only exception being that you have to use
gtk_widget_realize on whatever gtk widget you are using for sdl so that
the x11 window will be allocated.

> 2. You mentioned "this is for gtk1 only. gtk2 is similar but different".
> What to do for GTK2 ?
> 

I've attached a simple program that will compile for gtk1 or gtk2. you
can change a define at the top of the source to switch between gtk 1 or 2.

> 3. Which kind of GTK Object "APanel" can be ?
> 
> 4. FPC complains on "handle". What's wrong ?
> 

Sorry I thought you were using the LCL and so my example was for that. I
attached an example program that doesn't use the LCL.

> Thanks Again.
> Tom
> 
> 

It's worth noting that you cannot have more than one sdl window per
application. It's a limitation of sdl.

Andrew
program Project1;

{$mode objfpc}{$H+}

{$DEFINE GTK1}

uses
  Classes, SysUtils,
  {$IFDEF GTK2} Gtk2, Gdk2, Gdk2x, Glib2, {$ENDIF}
  {$IFDEF GTK1} Gtk, Gdk, Glib,{$ENDIF}
  X, sdl, sdlutils;
  
var
  MainWindow,
  Drawable: PGtkWidget;
  SDLSurface: PSDL_Surface = nil;



procedure InitGtk;
begin
  gtk_init(@argc, @argv);
  
  MainWindow := gtk_window_new(GTK_WINDOW_TOPLEVEL);
  gtk_window_set_title(PGtkWindow(MainWindow), 'Hey there''s SDL in this 
window!');

  Drawable := gtk_drawing_area_new;

  gtk_widget_set_app_paintable(Drawable, False);
  {$IFDEF GTK2}
  gtk_widget_set_double_buffered(Drawable, False);
  {$ENDIF}

  gtk_container_add(PGtkContainer(MainWindow), Drawable);
  {$IFDEF GTK1}
  gtk_widget_show(MainWindow);
  {$ENDIF}
end;

procedure ResizeSDL(AWidget: PGtkWidget; Allocation: PGtkAllocation; userdata: 
pointer); cdecl;
begin
  SDLSurface := SDL_SetVideoMode(Allocation^.width, Allocation^.height, 0, 
SDL_HWSURFACE);
end;

procedure ExposeSDL(widget: PGtkWidget; event: PGdkEventExpose; Data: Pointer); 
cdecl;
var
  Col1, Col2: TSDL_Color;
  ARect: TSDL_Rect;

begin
  Col1.r := 255;
  Col1.b := 0;
  Col1.g := 0;

  Col2.r := 0;
  Col2.b := 255;
  Col2.g := 0;

  ARect := SDLRect(0,0,Drawable^.allocation.width, Drawable^.allocation.height);

  SDL_FillRect(SDLSurface, @ARect, $FFFF0000);
  SDL_Flip(SDLSurface);
end;

procedure SetGtkCallbacks;
begin
  gtk_signal_connect(GTK_OBJECT(Drawable), 'expose-event', 
TGtkSignalFunc(@ExposeSDL), nil);
  gtk_signal_connect(GTK_OBJECT(Drawable), 'size-allocate', 
TGtkSignalFunc(@ResizeSDL), nil);

  gtk_signal_connect(GTK_OBJECT(MainWindow), 'destroy', 
TGtkSignalFunc(@gtk_main_quit), nil)
end;

function GetX11Window(AWidget: PGtkWidget): X.TWindow;
begin
  // first make sure the x11 window is created for the gtk widget
  if GTK_WIDGET_REALIZED(AWidget) = False then
    gtk_widget_realize(AWidget);


  // now retrieve the X window
  {$IFDEF GTK2}
  Result := GDK_WINDOW_XWINDOW(PGdkDrawAble(AWidget^.window));
  {$ENDIF}
  {$IFDEF GTK1}
  Result := GDK_WINDOW_XWINDOW(PGdkWindowPrivate(AWidget^.window));
  {$ENDIF}

end;

procedure SetSDLWidget(AWidget: PGtkWidget);
var
  X11Window: QWord;
  SDL_WINDOWID: String;
begin
 X11Window := GetX11Window(AWidget);
 SDL_WINDOWID := 'SDL_WINDOWID='+IntToStr(PtrUint(X11Window));
 _putenv(PChar(SDL_WINDOWID));
end;

procedure SyncGtk;
begin
  gtk_main_iteration_do(True);
end;

procedure InitSDL;
begin
  SDL_Init(SDL_INIT_VIDEO or SDL_INIT_JOYSTICK);
  SDLSurface := SDL_SetVideoMode(Drawable^.allocation.width, 
Drawable^.allocation.height, 0, SDL_HWSURFACE);
end;

procedure Run;
begin
  gtk_widget_show_all(MainWindow);
  gtk_main;
end;

begin
  InitGtk;
  SetGtkCallbacks;
  SetSDLWidget(Drawable);
  SyncGtk;
  InitSDL;
  Run;
end.

_______________________________________________
fpc-pascal maillist  -  fpc-pascal@lists.freepascal.org
http://lists.freepascal.org/mailman/listinfo/fpc-pascal

Reply via email to