Форум: "Игры";
Текущий архив: 2009.06.28;
Скачать: [xml.tar.bz2];
ВнизПроблемы с OpenGL Найти похожие ветки
← →
HARIER (2007-05-25 20:43) [0]Почему дёргается экран. Когда передвигаю мышку или нажимаю любую клавишу.
Такое творится только при разрешении 1024 х 768.
Почему? Внизу код.
===================== Unit =================================
interface
uses
Windows,
Messages,
OpenGL,
ANSORO_UTILITS;
const
ENGINE_NAME = "HARIER";
ENGINE_VERSION = "0.1";
type
TOnRender = procedure;
TOnUpdate = procedure;
TOnInit = procedure;
type
TEngine = class
h_Msg : TMSG;
h_Wnd : hWnd;
h_wc: TWndClassEX;
h_DC : HDC;
h_RC: HGLRC;
PFD: TPixelFormatDescriptor;
nPFD: integer;
private
FOnRender: TOnRender;
FOnUpdate: TOnUpdate;
FOnInit : TOnInit;
public
constructor Create;
destructor Destroy;
public
// SYSTEM
procedure Init(name: PChar; width, height: integer; bpp: byte; FullScreen: Boolean = false);
procedure SetFullScreen(width, height: integer; bpp: byte);
procedure Quit;
procedure Loop;
// OPENGL
procedure InitGL;
procedure SetPFD;
property OnRender: TOnRender read FOnRender write FOnRender;
property OnUpdate: TOnUpdate read FOnUpdate write FOnupdate;
property OnInit: TOnInit read FOnInit write FOnInit;
private
eFullScreen: boolean;
eWidth,eHeight: integer;
eBpp: Byte;
eFinished: Boolean;
end;
procedure InitEngine;
var
engine: TEngine;
implementation
procedure InitEngine;
begin
engine := TEngine.Create;
end;
constructor TEngine.Create;
begin
eFinished := false;
end;
function WndProc(h_wnd:hWND; events: Integer; wparam: wparam; lparam: lparam):lresult;stdcall;
begin
case events of
WM_CREATE: begin end;
WM_DESTROY: begin PostQuitMessage(0); Result:= 0; exit; end;
WM_PAINT: begin
glClear(GL_DEPTH_BUFFER_BIT OR GL_COLOR_BUFFER_BIT);
glClearColor(0,1,0,0);
// ValidateRect(h_wnd,nil); result := 0; exit;
end;
end;
Result := DefWindowProc(h_wnd, events, wparam, lparam);
end;
procedure TEngine.SetPFD;
begin
FillChar(pfd, sizeof(pfd), 0);
pfd.nVersion := 1;
pfd.nSize := sizeof(pfd);
pfd.dwFlags := PFD_DOUBLEBUFFER or PFD_DRAW_TO_WINDOW or PFD_SUPPORT_OPENGL;
pfd.iPixelType := PFD_TYPE_RGBA;
pfd.cColorBits := eBpp;
pfd.cStencilBits := 0;
pfd.cDepthBits := 32;
nPFD := ChoosePixelFormat(h_dc, @pfd);
SetPixelFormat( H_DC, nPFD, @pfd );
end;
procedure TEngine.InitGL;
begin
SetPFD;
h_rc := wglCreateContext(h_dc);
wglMakeCurrent(h_dc, h_rc);
glClear(GL_DEPTH_BUFFER_BIT OR GL_COLOR_BUFFER_BIT);
glClearColor(0,1,0,0);
end;
procedure TEngine.SetFullScreen(width: Integer; height: Integer; bpp: Byte);
var
dm: DevMode;
hr: HRESULT;
DC: hdc;
begin
FillChar(dm, SizeOf(dm),0);
dm.dmSize := SizeOf(DevMode);
dm.dmFields := DM_PELSWIDTH OR DM_PELSHEIGHT OR DM_BITSPERPEL OR DM_DISPLAYFREQUENCY;
dm.dmPelsWidth := width;
dm.dmPelsHeight:= height;
dm.dmBitsPerPel := bpp;
dm.dmDisplayFrequency := 75;
HR := ChangeDisplaySettings(dm, CDS_FULLSCREEN);
end;
procedure TEngine.Init(name: PChar; width: Integer; height: Integer; bpp: Byte; FullScreen: Boolean = False);
var
dwExStyle : DWord;
dwStyle : DWord;
begin
eWidth := width;
eHeight:= height;
eBpp := bpp;
ZeroMemory(@h_wc,SizeOf(h_wc));
h_wc.style := CS_HREDRAW OR CS_VREDRAW OR CS_OWNDC;
h_wc.cbSize := sizeof(h_wc);
h_wc.lpfnWndProc := @WndProc;
h_wc.hInstance := hInstance;
h_wc.hbrBackground:= COLOR_BTNFACE+1;
h_wc.hCursor := LoadCursor(0,IDC_ARROW);
h_wc.lpszClassName:= ENGINE_NAME;
WINDOWS.RegisterClassEx(h_wc);
if FullScreen then
begin
eFullScreen := true;
dwExStyle := WS_OVERLAPPED or WS_EX_TOPMOST; // поверх всех окон
dwStyle := WS_POPUP OR WS_CLIPCHILDREN OR WS_CLIPSIBLINGS;
SetFullScreen(width,height,bpp);
end
else
begin
eFullScreen := false;
dwExStyle := WS_OVERLAPPED or WS_EX_TOPMOST; // поверх всех окон
dwStyle := WS_SYSMENU OR WS_MINIMIZEBOX OR WS_CLIPCHILDREN OR WS_CLIPSIBLINGS;
end;
h_wnd := CreateWindowEX(dwExStyle,ENGINE_NAME,name,dwStyle,0,0,Width,Height,0,0,hInstance ,nil);
h_dc := GetDC(h_wnd);
InitGL;
ShowWindow(h_wnd,SW_SHOW);
SetForegroundWindow(h_Wnd);
end;
procedure TEngine.Loop;
begin
while GetMessage(h_msg,0,0,0) do
begin
DispatchMessage(h_msg);
TranslateMessage(h_msg);
SwapBuffers(h_dc);
end;
end;
procedure TEngine.Quit;
begin
eFinished := true;
end;
destructor TEngine.Destroy;
begin
Quit;
DestroyWindow(h_wnd);
UnRegisterClass(ENGINE_NAME,hInstance);
wglDeleteContext(h_rc);
ReleaseDC(h_wnd,h_dc);
wglMakeCurrent(0, 0);
wglDeleteContext(h_RC);
ReleaseDC(h_Wnd, h_DC);
if eFullscreen then ChangeDisplaySettings(TDevMode(nil^), CDS_FULLSCREEN);
end;
===================== Application =================================
program APP;
uses
Windows,
OpenGL,
ENGINE in "ANSORO_ENGINE.pas",
UTILITS in "ANSORO_UTILITS.pas";
begin
InitEngine;
engine.Init("APP",1024,768,32,true);
engine.Loop;
end.
← →
@!!ex © (2007-05-25 21:30) [1]Частота не поддерживаемая этим разрешением. Отсюда и косяк.
Попробуй не трогать частоту. ;)
← →
Rial © (2007-05-25 22:53) [2]Зачем вообще принудительно менять разрешение ?..
Если что то уже настроено, значит пользователю
так удобно :)
← →
homm © (2007-05-25 23:09) [3]> [2] Rial ©
+1
Конечно, если не даеться выбор разрешений по вкусу :)
← →
HARIER (2007-05-26 00:28) [4]убрал частоту не помогло.
Я двигаю мышку и тогда начинает перерисоваться экран .
Странно. Серый потом зелёный. если не двигаю мышку то нормально.
Такое только в полноекранном режиме.
← →
HARIER (2007-05-26 00:31) [5]Rial © (25.05.07 22:53) [2]
Объясни что ты имел ввиду. Я чегото непонял :-)
← →
Домик (2007-05-26 02:11) [6]> Rial © (25.05.07 22:53) [2]
У меня, к примеру, разрешение рабочего стола 1600x1200. Не каждая 3D игра будет производительна в таком разрешение, а 2D игрушки даже таких разрешений, как правило, не знают...
← →
@!!ex © (2007-05-26 09:46) [7]Может быть косяки видеокарты.
ПРишли ехешник, мы потестим на своих машинах.
← →
HARIER (2007-05-26 10:28) [8]А где я могу его выложить?
← →
HARIER (2007-05-26 17:03) [9]Вообще я думаю что то я всётаки на портачил так пробовал исходники
с сайта Sulaco . Его исходники идут нормально.
Еще вопрос. Что лучше использовать.
PGL_WindowInit = ^TGL_WindowInit;
TGL_WindowInit = record // Window Creation Info
application: PApplication; // Application Structure
title: PAnsiChar; // Window Title
width: Integer; // Width
height: Integer; // Height
bitsPerPixel: Integer; // Bits Per Pixel
isFullScreen: Boolean; // FullScreen?
end;
или
TGL_WindowInit = class // Window Creation Info
application: PApplication; // Application Structure
title: PAnsiChar; // Window Title
width: Integer; // Width
height: Integer; // Height
bitsPerPixel: Integer; // Bits Per Pixel
isFullScreen: Boolean; // FullScreen?
end;
← →
@!!ex © (2007-05-26 17:12) [10]нафиг класс?
← →
ElectriC © (2007-05-26 17:18) [11]ИМХО, лучше так:
>var
> GL_WindowInit : packed record // Window Creation Info
> application: PApplication; // Application Structure
> title: PAnsiChar; // Window Title
> width: Integer; // Width
> height: Integer; // Height
> bitsPerPixel: Integer; // Bits Per Pixel
> isFullScreen: Boolean; // FullScreen?
> end;
← →
@!!ex © (2007-05-26 18:30) [12]Почему запаковынный рекорд луычше? Медленней же работает.
← →
ElectriC © (2007-05-26 19:55) [13]
> Почему запаковынный рекорд луычше? Медленней же работает.
Ну поставь обычный)))
← →
HARIER (2007-05-26 20:04) [14]А вообще Записи не нужно ни конструктора ни деструтора.
Может біть она всётаки лучше.
Что лучше делать класс движка или запись?
← →
ElectriC © (2007-05-26 20:20) [15]
> А вообще Записи не нужно ни конструктора ни деструтора.
Нет.
> Что лучше делать класс движка или запись?
Ну я б лучше делал запись => быстрее и экономнее ;)))
← →
Rial © (2007-05-26 20:23) [16]> [14] HARIER (26.05.07 20:04)
> Что лучше делать класс движка или запись?
В начале нужно сделать что угодно, работающее без сбоев
и глюков. А вообще, запись - это метод представления данных,
а класс - это нечто большее.
С одной стороны, для отладки проще обойтись записями,
потом все это завернуть в красивую обертку, обеспечивающую
целостность данных.
Возможно, наступит такой момент, когда классы в итоге будут
ощутимо замедлять работу... но это маловероятно.
> [5] HARIER (26.05.07 00:31)
> Rial © (25.05.07 22:53) [2]
> Объясни что ты имел ввиду. Я чегото непонял :-)
У меня стоит разрешение 1024*768, частота обновление 75Гц...
если какая то программа принудительно меняет его- это
80% шанс отправиться в корзину ежеминутно.
← →
@!!ex © (2007-05-26 20:26) [17]> У меня стоит разрешение 1024*768, частота обновление 75Гц...
> если какая то программа принудительно меняет его- это
> 80% шанс отправиться в корзину ежеминутно.
Практически любая игра меняет разрешение...
НЕ играешь чтоли совсем? :))
← →
Rial © (2007-05-26 21:19) [18]> [11] ElectriC © (26.05.07 17:18)
> ИМХО, лучше так:
> >var
> > GL_WindowInit : packed record // Window Creation
> Info
> > application: PApplication; // Application Structure
> > title: PAnsiChar; // Window Title
> > width: Integer; // Width
> > height: Integer; // Height
> > bitsPerPixel: Integer; // Bits Per Pixel
> > isFullScreen: Boolean; // FullScreen?
> > end;
Конкретно в данном случае вставка слова "packed" не играет
никакой роли. Почему? - можно почитать о правилах выравнивания полей.
Конечно, когда составляешь свою структуру записи, лучше
сразу выбирать такой порядок полей, чтобы размер записи был
минимальным.
А необходимоть в "packed" в основном возникает при переносе
кода с других языков.
> [17] @!!ex © (26.05.07 20:26)
> НЕ играешь чтоли совсем? :))
Нет...
← →
HARIER (2007-05-27 03:00) [19]Мучался весь день. И ни чего не получилось.
Мне нужно написать модуль который создаёт окно и контекст.
Первый пример я делал по книге. Своими мозгами. А второй по
исходникам с Sulaco. И что получилось выдаются ошибки:
Невозможно создать класс, создать окно ....
У меня уже голова не варит. Как нужно правильно сделать.
Получается что своими мозгами заработало но с глюками, а
метом Копировать Вставить вообще не работает.
Я думаю вы уже много раз писали подобное :-)
Помогите пожалуйста...
unit ENGINE;
interface
uses
Windows,
Messages,
OpenGL,
UTILITS;
const
ENGINE_NAME = "ANSORO";
ENGINE_VERSION = "1.0";
type
TOnRender = procedure;
TOnUpdate = procedure;
TOnInit = procedure;
{ FOnRender: TOnRender;
FOnUpdate: TOnUpdate;
FOnInit : TOnInit;
}
{
property OnRender: TOnRender read FOnRender write FOnRender;
property OnUpdate: TOnUpdate read FOnUpdate write FOnupdate;
property OnInit: TOnInit read FOnInit write FOnInit;
}
ENG = ^Tengine;
TEngine = class
h_wnd: HWND;
h_msg: TMsg;
h_wc: TWndClassEX;
h_dc: HDC;
h_rc: HGLRC;
eFullScreen: Boolean;
eWidth,
eHeight: Integer;
public
procedure InitEngine(name: PChar; width, height: integer; bpp: integer; FullScreen: Boolean = false);
procedure Loop;
procedure Quit;
procedure glInit;
procedure glKillWnd(Fullscreen : Boolean);
private
constructor Create;
destructor Destroy;
end;
procedure EngineInit;
var
engine: TEngine;
eFinished: Boolean;
implementation
procedure EngineInit;
begin
engine := TEngine.Create;
end;
constructor TEngine.Create;
begin
eFinished := false;
end;
////////////////////////////////////////////////////////////////////////////////
/// Private unit function
////////////////////////////////////////////////////////////////////////////////
procedure TEngine.glInit;
begin
glClearColor(0.0, 0.0, 0.0, 0.0); // Black Background
end;
procedure glResizeWnd(Width, Height : Integer);
begin
// This Function will be handled in a later chapter
if (Height = 0) then // prevent divide by zero exception
Height := 1;
glViewport(0, 0, Width, Height); // Set the viewport for the OpenGL window
glMatrixMode(GL_PROJECTION); // Change Matrix Mode to Projection
glLoadIdentity(); // Reset View
gluPerspective(45.0, Width/Height, 1.0, 100.0); // Do the perspective calculations. Last value = max clipping depth
glMatrixMode(GL_MODELVIEW); // Return to the modelview matrix
glLoadIdentity(); // Reset View
end;
function WndProc(hWnd: HWND; Msg: UINT; wParam: WPARAM; lParam: LPARAM): LRESULT; stdcall;
begin
case (Msg) of
WM_CREATE:
begin
// eFinished := false;
end;
WM_CLOSE:
begin
PostQuitMessage(0);
Result := 0
end;
WM_KEYDOWN: // Set the pressed key (wparam) to equal true so we can check if its pressed
begin
// keys[wParam] := True;
Result := 0;
end;
WM_KEYUP: // Set the released key (wparam) to equal false so we can check if its pressed
begin
// keys[wParam] := False;
Result := 0;
end;
WM_SIZE: // Resize the window with the new width and height
begin
glResizeWnd(LOWORD(lParam),HIWORD(lParam));
Result := 0;
end;
else
Result := DefWindowProc(hWnd, Msg, wParam, lParam); // Default result if nothing happens
end;
end;
← →
HARIER (2007-05-27 03:05) [20]
procedure TEngine.glKillWnd(Fullscreen : Boolean);
begin
if Fullscreen then // Change back to non fullscreen
begin
ChangeDisplaySettings(devmode(nil^), 0);
ShowCursor(True);
end;
// Makes current rendering context not current, and releases the device
// context that is used by the rendering context.
if (not wglMakeCurrent(h_DC, 0)) then
MessageBox(0, "Release of DC and RC failed!", "Error", MB_OK or MB_ICONERROR);
// Attempts to delete the rendering context
if (not wglDeleteContext(h_rc)) then
begin
MessageBox(0, "Release of rendering context failed!", "Error", MB_OK or MB_ICONERROR);
h_RC:= 0;
end;
// Attemps to release the device context
if ((h_DC > 0) and (ReleaseDC(h_Wnd, h_DC) = 0)) then
begin
MessageBox(0, "Release of device context failed!", "Error", MB_OK or MB_ICONERROR);
h_DC := 0;
end;
// Attempts to destroy the window
if ((h_Wnd <> 0) and (not DestroyWindow(h_Wnd))) then
begin
MessageBox(0, "Unable to destroy window!", "Error", MB_OK or MB_ICONERROR);
h_Wnd := 0;
end;
// Attempts to unregister the window class
if (not UnRegisterClass(ENGINE_NAME, hInstance)) then
begin
MessageBox(0, "Unable to unregister window class!", "Error", MB_OK or MB_ICONERROR);
hInstance := 0;
end;
end;
////////////////////////////////////////////////////////////////////////////////
/// Public unit function
////////////////////////////////////////////////////////////////////////////////
procedure TEngine.InitEngine(name: PAnsiChar; width: Integer; height: Integer; bpp: Integer; FullScreen: Boolean = False);
var
dwStyle : DWORD; // Window styles
dwExStyle : DWORD; // Extended window styles
dmScreenSettings : DEVMODE; // Screen settings (fullscreen, etc...)
PixelFormat : GLuint; // Settings for the OpenGL rendering
// h_Instance : HINST; // Current instance
pfd : TPIXELFORMATDESCRIPTOR; // Settings for the OpenGL window
begin
// h_Instance := GetModuleHandle(nil); //Grab An Instance For Our Window
ZeroMemory(@h_wc, SizeOf(h_wC)); // Clear the window class structure
with h_wc do // Set up the window class
begin
style := CS_HREDRAW or // Redraws entire window if length changes
CS_VREDRAW or // Redraws entire window if height changes
CS_OWNDC; // Unique device context for the window
lpfnWndProc := @WndProc; // Set the window procedure to our func WndProc
// hInstance := h_Instance;
hCursor := LoadCursor(0, IDC_ARROW);
lpszClassName := ENGINE_NAME;
end;
RegisterClassEX(h_wc);
eFullScreen := FullScreen;
// Change to fullscreen if so desired
if Fullscreen then
begin
ZeroMemory(@dmScreenSettings, SizeOf(dmScreenSettings));
with dmScreenSettings do begin // Set parameters for the screen setting
dmSize := SizeOf(dmScreenSettings);
dmPelsWidth := Width; // Window width
dmPelsHeight := Height; // Window height
dmBitsPerPel := bpp; // Window color depth
dmFields := DM_PELSWIDTH or DM_PELSHEIGHT or DM_BITSPERPEL;
end;
// Try to change screen mode to fullscreen
if (ChangeDisplaySettings(dmScreenSettings, CDS_FULLSCREEN) = DISP_CHANGE_FAILED) then
begin
MessageBox(0, "Unable to switch to fullscreen!", "Error", MB_OK or MB_ICONERROR);
Fullscreen := False;
end;
end;
// If we are still in fullscreen then
if (Fullscreen) then
begin
dwStyle := WS_POPUP or // Creates a popup window
WS_CLIPCHILDREN // Doesn"t draw within child windows
or WS_CLIPSIBLINGS; // Doesn"t draw within sibling windows
dwExStyle := WS_EX_APPWINDOW; // Top level window
ShowCursor(False); // Turn of the cursor (gets in the way)
end
else
begin
dwStyle := WS_OVERLAPPEDWINDOW or // Creates an overlapping window
WS_CLIPCHILDREN or // Doesn"t draw within child windows
WS_CLIPSIBLINGS; // Doesn"t draw within sibling windows
dwExStyle := WS_EX_APPWINDOW or // Top level window
WS_EX_WINDOWEDGE; // Border with a raised edge
end;
// Attempt to create the actual window
h_Wnd := CreateWindowEx(dwExStyle, // Extended window styles
ENGINE_NAME, // Class name
NAME, // Window title (caption)
dwStyle, // Window styles
0, 0, // Window position
Width, Height, // Size of window
0, // No parent window
0 , // No menu
hInstance, // Instance
nil); // Pass nothing to WM_CREATE
if h_Wnd = 0 then
begin
glKillWnd(Fullscreen); // Undo all the settings we"ve changed
MessageBox(0, "Unable to create window!", "Error", MB_OK or MB_ICONERROR);
Exit;
end;
// Try to get a device context
h_DC := GetDC(h_Wnd);
if (h_DC = 0) then
begin
glKillWnd(Fullscreen);
MessageBox(0, "Unable to get a device context!", "Error", MB_OK or MB_ICONERROR);
Exit;
end;
← →
ElectriC © (2007-05-27 03:08) [21]Приведи листинг основного файла (.dpr).
← →
HARIER (2007-05-27 03:08) [22]
// Settings for the OpenGL window
with pfd do
begin
nSize := SizeOf(TPIXELFORMATDESCRIPTOR); // Size Of This Pixel Format Descriptor
nVersion := 1; // The version of this data structure
dwFlags := PFD_DRAW_TO_WINDOW // Buffer supports drawing to window
or PFD_SUPPORT_OPENGL // Buffer supports OpenGL drawing
or PFD_DOUBLEBUFFER; // Supports double buffering
iPixelType := PFD_TYPE_RGBA; // RGBA color format
cColorBits := BPP; // OpenGL color depth
cRedBits := 0; // Number of red bitplanes
cRedShift := 0; // Shift count for red bitplanes
cGreenBits := 0; // Number of green bitplanes
cGreenShift := 0; // Shift count for green bitplanes
cBlueBits := 0; // Number of blue bitplanes
cBlueShift := 0; // Shift count for blue bitplanes
cAlphaBits := 0; // Not supported
cAlphaShift := 0; // Not supported
cAccumBits := 0; // No accumulation buffer
cAccumRedBits := 0; // Number of red bits in a-buffer
cAccumGreenBits := 0; // Number of green bits in a-buffer
cAccumBlueBits := 0; // Number of blue bits in a-buffer
cAccumAlphaBits := 0; // Number of alpha bits in a-buffer
cDepthBits := 16; // Specifies the depth of the depth buffer
cStencilBits := 0; // Turn off stencil buffer
cAuxBuffers := 0; // Not supported
iLayerType := PFD_MAIN_PLANE; // Ignored
bReserved := 0; // Number of overlay and underlay planes
dwLayerMask := 0; // Ignored
dwVisibleMask := 0; // Transparent color of underlay plane
dwDamageMask := 0; // Ignored
end;
// Attempts to find the pixel format supported by a device context that is the best match to a given pixel format specification.
PixelFormat := ChoosePixelFormat(h_DC, @pfd);
if (PixelFormat = 0) then
begin
glKillWnd(Fullscreen);
MessageBox(0, "Unable to find a suitable pixel format", "Error", MB_OK or MB_ICONERROR);
Exit;
end;
// Sets the specified device context"s pixel format to the format specified by the PixelFormat.
if (not SetPixelFormat(h_DC, PixelFormat, @pfd)) then
begin
glKillWnd(Fullscreen);
MessageBox(0, "Unable to set the pixel format", "Error", MB_OK or MB_ICONERROR);
Exit;
end;
// Create a OpenGL rendering context
h_RC := wglCreateContext(h_DC);
if (h_RC = 0) then
begin
glKillWnd(Fullscreen);
MessageBox(0, "Unable to create an OpenGL rendering context", "Error", MB_OK or MB_ICONERROR);
Exit;
end;
// Makes the specified OpenGL rendering context the calling thread"s current rendering context
if (not wglMakeCurrent(h_DC, h_RC)) then
begin
glKillWnd(Fullscreen);
MessageBox(0, "Unable to activate OpenGL rendering context", "Error", MB_OK or MB_ICONERROR);
Exit;
end;
// Settings to ensure that the window is the topmost window
ShowWindow(h_Wnd, SW_SHOW);
SetForegroundWindow(h_Wnd);
SetFocus(h_Wnd);
// Ensure the OpenGL window is resized properly
glResizeWnd(Width, Height);
glInit(); // Initialise any OpenGL States and variables
end;
procedure TEngine.Loop;
begin
while GetMessage(h_msg, 0,0,0) do
begin // Else translate and dispatch the message to this window
TranslateMessage(h_msg);
DispatchMessage(h_msg);
end;
end;
procedure TEngine.Quit;
begin
eFinished := true;
end;
destructor TEngine.Destroy;
begin
glKillWnd(eFullscreen);
end;
end.
← →
ElectriC © (2007-05-27 03:09) [23]Приведи исходник .dpr файла.
← →
HARIER (2007-05-27 03:12) [24]код файла dpr
program game;
uses
Windows,
OpenGL,
ENGINE in "ENGINE.pas",
GAME_ENGINE in "GAME_ENGINE.pas",
UTILITS in "UTILITS.pas";
begin
EngineInit;
engine.InitEngine("name",1024,768,32,false);
engine.Loop;
end.
← →
ElectriC © (2007-05-27 03:14) [25]вообще-то в loop нужно писать, ИМХО:
...
Msg : MSG;
...
ZeroMemory(@Msg, SizeOf(MSG));
while True do
If (PeekMessage(Msg, 0, 0, 0, PM_NOREMOVE)) then
begin
If not GetMessage(Msg, 0, 0, 0) then Exit;
TranslateMessage (Msg);
DispatchMessage (Msg);
end
else
If Active then //Активность приложения
begin
//тут рисуем OpenGL сцену
end else WaitMessage;
← →
HARIER (2007-05-27 03:20) [26]ElectriC © (27.05.07 03:14) [25]
Учту. :-)
Посмотри на код может я чтото еще не праввильно делаю.
Напиши что имено. Я исправлю.
Завтра с утра начну заново писать.
Как думаешь лучше смотреть на исходники или в книгу.
← →
ElectriC © (2007-05-27 03:26) [27]
> HARIER
Совет - не спеши!!! Обдумай всё заранее!!!
Когда я писал движок > http://slil.ru/24404040/874845188/School_54.rar < (хотя и сейчас продолжаю писать) смотрел больше на исходники, а в меньше
степени - на книги (Хотя старался совмещать и то и другое).
Я погляжу, что можно сделать!
← →
ElectriC © (2007-05-27 03:48) [28]1. Могу предположить что [25] поможет!
Так-как в твоём случае перерисовка экрана присходит тока тогда, когда
курсор мыши ползает по экрану!
2. ValidateRect(h_wnd,nil); - не нужен!
3. WM_CREATE: begin// eFinished := false; end; - не нужен!
← →
HARIER (2007-05-28 01:08) [29]Так ни чего и не получилось.
Посмотрел свои старые проекты делал 3D сцены в любых видеорежимах.
Всё идёт очень быстро и без глюков.
Я На грани дипресии :-(
Мне нужно сдать игру до 1 октября. Может можно написать игру в одном DPR файле как вы думаете.
ДУмаю может оставить все функии по инициализации окна и графики.
в главном файле DPR. Как вы считаете?
Тогда у меня вдальнейшем может возникнуть другая проблема, Когда мне
например надо будет писать Спрайтовый модуль и тп. То как мне вних
использовать такие важные переменные как h_wnd, h_dc ...
Пожалуйста посоветуйте мне как поступить.
Внизу привёл пример одного из своих проектов:
program Example14;
uses
Windows,
Messages,
OpenGL;
const
APP_NAME = "Example14"; // Название приложения
mat_specular : array [0..3] of GLfloat = ( 1.0, 1.0, 1.0, 1.0 ); // Интенсивность зеркального света
mat_shininess : GLfloat = 100.0; // Яркость света
light_position : array [0..3] of GLfloat = ( 0.0, 0.0, 1.0, 0.0 ); // Позиция света
white_light : array [0..3] of GLfloat = ( 1.0, 0.9, 0.8, 0.0 ); // Цвет света
light_ambient: array [0..3] of GLfloat = ( 0.5, 0.0, 0.8, 0.0 ); // Цвет фона
fog_color: array [0..3] of GLfloat = ( 0.9, 0.9, 0.8, 0.0 ); // Цвет тумана
var
h_wnd: HWND;
h_wc: TWndClassEx;
h_dc: HDC;
h_rc: HGLRC;
msg : TMsg;
keys: array[0..255] of Boolean;
finished : Boolean;
i: integer;
fogMode : GLint; // Режим тумана
rot: real;
sph: gluQuadricObj;
roll, pitch, heading, planex, planey, planez: GLFloat;
distance, twist, elevation, azimuth: GLfloat;
// UPS
ups_time_old: integer;
ups_time: integer;
// FPS
fps_time: Integer;
fps_cur: Integer;
_FPS: integer;
Time, Time_delta: integer;
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
{ Функция переводит Integer -> String }
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
function IntToStr(n: integer):String;
begin
STR(n, Result);
end;
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
{ Камера пилота }
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
procedure PilotView(roll, pitch, heading, planex, planey, planez: GLFloat);
begin
glRotatef(roll,0,0,1);
glRotatef(roll,0,0,1);
glRotatef(roll,0,0,1);
glTranslatef(-planex, -planey, -planez);
end;
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
{ Камера полярная }
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
procedure PolarView(distance, twist, elevation, azimuth: GLfloat);
begin
glTranslatef(0,0,-distance);
glRotatef(-twist, 0,0,1);
glRotatef(-elevation, 1,0,0);
glRotatef(azimuth, 0,0,1);
end;
procedure LST(x,y: integer);
begin
fogMode := GL_EXP2;
glFogi(GL_FOG_MODE, fogMode);
glFogfv(GL_FOG_COLOR, @fog_color);
glFogf(GL_FOG_DENSITY, 0.05);
glHint(GL_FOG_HINT, GL_NICEST);
glFogf(GL_FOG_START, -10.0);
glFogf(GL_FOG_END, 10.0);
gluSphere(sph, 1.0, 100, 100);
end;
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
{ Процедура рисования сцены }
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
procedure Draw();
begin
glLoadIdentity(); // Очистить матрицу
glClear(GL_COLOR_BUFFER_BIT or GL_DEPTH_BUFFER_BIT); // Очистить буфер цвета
glTranslatef(1.0,1.0,-15.0);
glOrtho(0.0, 1.0, 0.0, 1.0, -1.0, 1.0); // Установить ортогональную проекции
glColor3f(1.0,0.0,0.0);
gluLookAt(0,0,5,0,0,0,0,1,0);
{
Parameters:
eyex, eyey, eyez
The position of the eye point.
centerx, centery, centerz
The position of the reference point.
upx, upy, upz
The direction of the up vector.
}
PilotView(roll, pitch, heading, planex, planey, planez);
PolarView(distance, twist, elevation, azimuth);
glEnable(GL_FOG);
glRotatef(rot,1,1,1);
glTranslatef(1,0,0);
glPushMatrix;
glCallList(1);
glPopMatrix;
glRotatef(rot,1,0,0);
glTranslatef(1,0,0);
glPushMatrix;
glCallList(1);
glPopMatrix;
glRotatef(rot,1,1,0);
glTranslatef(0,1,0);
glPushMatrix;
glCallList(1);
glPopMatrix;
glRotatef(rot,1,1,0);
glTranslatef(-1,0,0);
glPushMatrix;
glCallList(1);
glPopMatrix;
glFlush;
end;
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
{ Процедура обновления }
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
procedure Update;
begin
rot := rot+0.1;
//roll, pitch, heading, planex, planey, planez: GLFloat
if keys[vk_left] then
begin
roll := roll + 0.001;
pitch := pitch + 0.001;
heading := heading + 0.001;
planex := planex + 0.001;
planey := planey + 0.001;
planez := planez + 0.001;
end;
if keys[vk_right] then
begin
roll := roll - 0.001;
pitch := pitch - 0.001;
heading := heading - 0.001;
planex := planex - 0.001;
planey := planey - 0.001;
planez := planez - 0.001;
end;
// distance, twist, elevation, azimuth
if keys[49] then
begin
distance := distance + 0.01;
twist := twist + 0.01;
elevation := elevation + 0.01;
azimuth := azimuth + 0.01;
end;
if keys[50] then
begin
distance := distance - 0.01;
twist := twist - 0.01;
elevation := elevation - 0.01;
azimuth := azimuth - 0.01;
end;
if keys[51] then fogMode := GL_EXP;
if keys[52] then fogMode := GL_EXP2;
if keys[53] then fogMode := GL_LINEAR;
if keys[27] then finished := true; // Завершаем программу если нажата клавиша esc
end;
← →
HARIER (2007-05-28 01:10) [30]
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
{ Процедура инициализации }
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
procedure Init;
begin
glClearColor(1.0,1.0,1.0,1.0); // Устанавливаем цвет очистки белый
glShadeModel(GL_smooth); // Позволяет применить цвет интерполированным
// Создание новых объектов
sph := gluNewQuadric();
gluQuadricNormals(sph, GLU_SMOOTH);
gluQuadricTexture(sph, GL_TRUE);
glMaterialfv(GL_FRONT, GL_SPECULAR, @mat_specular);
glMaterialfv(GL_FRONT, GL_SHININESS, @mat_shininess);
glLightfv(GL_LIGHT0, GL_DIFFUSE, @white_light);
glLightfv(GL_LIGHT0, GL_AMBIENT, @light_ambient);
glLightf(GL_LIGHT0, GL_SPOT_CUTOFF , 100);
glLightfv(GL_LIGHT0, GL_SPOT_DIRECTION, @light_position);
glEnable(GL_LIGHTING);
glEnable(GL_LIGHT0);
glEnable(GL_DEPTH_TEST);
glNewList(1,GL_COMPILE);
LST(1,1);
glEndList();
end;
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
{ Процедура уничтожения программы }
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
procedure DestroyWnd(Fullscreen : Boolean);
begin
if Fullscreen then
begin
ChangeDisplaySettings(devmode(nil^), 0);
ShowCursor(True);
end;
wglMakeCurrent(h_DC, 0);
wglDeleteContext(h_RC);
ReleaseDC(h_Wnd, h_DC);
DestroyWindow(h_Wnd);
UnRegisterClass("OpenGL", hInstance);
end;
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
{ Процедура отвечающая за измененние размеров окна }
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
procedure Resize(Width, Height : Integer);
begin
glViewport(0, 0, Width, Height); // Установить порт просмотра OpenGL
glMatrixMode(GL_PROJECTION); // Установить проекционную матрицу
glLoadIdentity(); // Очистить матрицу
gluPerspective(45.0, Width/Height, 1.0, 100.0); // Установить перспективу
glMatrixMode(GL_MODELVIEW); // Установить матрицу отображения
glLoadIdentity(); // Очистить матрицу
end;
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
{ Процедура перехода в полноекраный режим }
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
procedure DoFullScreen(width,height,bits: integer);
var
dm: DevMode;
hr: HRESULT;
DC: HDC;
begin
FillChar(dm, SizeOF(dm), 0); // Заполнить структуру dm нулями
dm.dmSize := SizeOf(DevMode); // Устанавливаем размер dm
dm.dmFields:= DM_PELSWIDTH or DM_PELSHEIGHT or DM_BITSPERPEL or DM_DISPLAYFREQUENCY;
dm.dmPelsWidth := width; // Ширина окна
dm.dmPelsHeight := height; // Высота окна
dm.dmBitsPerPel := bits; // Глубина цвета
dm.dmDisplayFrequency := 75; // Частота обновления экрана
hr := ChangeDisplaySettings(dm,CDS_FULLSCREEN); // включить полноекранный режим
end;
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
{ Главная процедура обработки сообщений }
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
function WndProc(hwnd: HWND; msg: integer; wparam: WPARAM; lparam: LPARAM):LResult; stdcall;
begin
case msg of
WM_CREATE: begin end;
WM_DESTROY: begin PostQuitMessage(0); Result := 0; end;
WM_SIZE: begin Resize(LOWORD(lparam), HIWORD(lparam)); Result := 0; end;
WM_KEYDOWN: begin keys[wparam] := true; result := 0; end;
WM_KEYUP: begin keys[wparam] := false; result := 0; end;
else
Result := DefWindowProc(hwnd, msg, wparam, lparam);
end;
end;
← →
HARIER (2007-05-28 01:11) [31]
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
{ Процедура создаёт окно и инициализирует OpenGL }
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
procedure CreateAPP(width, height: integer; FullScreen: Boolean = false);
var
pfd: TPixelFormatDescriptor;
nPixelFormat: Integer;
dwStyle : DWORD; // Window styles
dwExStyle : DWORD; // Extended window styles
begin
// Заполнить структуру h_wc нулями
FillChar(h_wc, SizeOf(h_wc), 0);
// Установка основных параметров класса
h_wc.cbSize := SizeOf(h_wc);
h_wc.style := CS_OWNDC or CS_VREDRAW or CS_HREDRAW; // позволяет перерисовывывать окно
h_wc.lpfnWndProc := @WndProc; // указатель на процедуру обработки сообщений
h_wc.hInstance := HInstance; // экземпляр приложения
h_wc.lpszMenuName := nil; // отсутствие меню (nil)
h_wc.hCursor := LoadCursor(0, IDC_ARROW); // устанавливаем стандартный курсор
// h_wc.hbrBackground := COLOR_BTNFACE+1; // цвет окна
h_wc.lpszClassName := "OpenGL"; // имя класса
// Регистрация класса окна в системе
WINDOWS.RegisterClassEx(h_wc);
// Создаётся окно
if (Fullscreen) then
begin
dwStyle := WS_POPUP or WS_CLIPCHILDREN or WS_CLIPSIBLINGS;
dwExStyle := WS_EX_APPWINDOW;
ShowCursor(False);
end
else
begin
dwStyle := WS_OVERLAPPEDWINDOW or WS_CLIPCHILDREN or WS_CLIPSIBLINGS;
dwExStyle := WS_EX_APPWINDOW or WS_EX_WINDOWEDGE;
end;
// Создать окно
h_Wnd := CreateWindowEx(dwExStyle,"OpenGL",APP_NAME, dwStyle, 0, 0, Width, Height, 0, 0, hInstance, nil);
h_dc := GetDC(h_wnd); // Получить контекст окна
// Настройка формата пикселей
with pfd do
begin
nSize := SizeOf(TPixelFormatDescriptor); // размер структуры
nVersion := 1; // номер версии
dwFlags := PFD_DOUBLEBUFFER or PFD_DRAW_TO_WINDOW or PFD_SUPPORT_OPENGL; // множество битовых флагов, определяющих устройство и интерфейс
iPixelType := PFD_TYPE_RGBA; // режим для изображения цветов
cColorBits := 32; // число битовых плоскостей в каждом буфере цвета
cRedBits := 0; // число битовых плоскостей красного в каждом буфере RGBA
cRedShift := 0; // смещение от начала числа битовых плоскостей красного в каждом буфере RGBA
cGreenBits := 0; // число битовых плоскостей зелёного в каждом буфере RGBA
cGreenShift := 0; // смещение от начала числа битовых плоскостей зелёного в каждом буфере RGBA
cBlueBits := 0; // число битовых плоскостей синего в каждом буфере RGBA
cBlueShift := 0; // смещение от начала числа битовых плоскостей синего в каждом буфере RGBA
cAlphaBits := 0; // число битовых плоскостей альфа в каждом буфере RGBA
cAlphaShift := 0; // смещение от начала числа битовых плоскостей альфа в каждом буфере RGBA
cAccumBits := 0; // общее число битовых плоскостей в буфере аккумулятора
cAccumRedBits := 0; // число битовых плоскостей красного в буфере аккумулятора
cAccumGreenBits := 0; // число битовых плоскостей зелёного в буфере аккумулятора
cAccumBlueBits := 0; // число битовых плоскостей синего в буфере аккумулятора
cAccumAlphaBits := 0; // число битовых плоскостей альфа в буфере аккумулятора
cDepthBits := 32; // размер буфера глубины (ось z)
cStencilBits := 0; // размер буфера трафарета
cAuxBuffers := 0; // число вспомогательных буферов
iLayerType := PFD_MAIN_PLANE;// тип плоскости
bReserved := 0; // число плоскостей переднего и заднего плана
dwLayerMask := 0; // игнорируется
dwVisibleMask := 0; // индекс или цвет прозрачности нижней плоскости
dwDamageMask := 0; // игнорируется
end;
nPixelFormat := ChoosePixelFormat( H_DC, @pfd ); // запрос системе - поддерживается ли выбранный формат пикселей
SetPixelFormat( H_DC, nPixelFormat, @pfd ); // устанавливаем формат пикселей в контексте устройства
h_rc := wglCreateContext(h_dc);
wglMakeCurrent(h_dc, h_rc);
// Установить полноекранный режим
if FullScreen then DoFullScreen(width, height, 32);
// Отображается окно
ShowWindow(h_wnd, SW_SHOW);
SetForegroundWindow(h_Wnd);
SetFocus(h_Wnd);
Resize(width,height);
Init;
end;
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
{ Процедура получает системное время }
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
function GetTime: integer;
var
T: LARGE_INTEGER;
F: LARGE_INTEGER;
begin
// Сверхточный таймер
QueryPerformanceFrequency(Int64(F));
QueryPerformanceCounter(Int64(T));
Result:= Trunc(1000 * T.QuadPart / F.QuadPart);
end;
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
{ Процедура сбрасывает значение таймера }
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
procedure ResetTimer;
begin
ups_time_old := GetTime;
end;
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
{ Функция получает FPS }
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
function FPS: integer;
begin
Result := _FPS;
end;
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
{ Главный цикл сообщений }
{~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~}
procedure Loop(UPS: Integer);
begin
ups_time_old := GetTime - 1000 div UPS;
ups_time := GetTime;
fps_time := GetTime;
while not finished do
begin
while PeekMessage(msg,0,0,0,PM_REMOVE) do
begin
if msg.message = WM_QUIT then finished := true else begin
TranslateMessage(msg);
DispatchMessage(msg);
end;
end;
while GetTime - ups_time_old >= (1000 div ups) do
begin
Update;
inc(ups_time_old, 1000 div ups);
end;
Draw;
SwapBuffers(h_dc);
if fps_time <= GetTime then
begin
fps_time := GetTime + 1000;
_FPS := fps_cur;
fps_cur := 0;
end;
inc(fps_cur);
SetWindowText(h_Wnd, PChar(APP_NAME + " [" + intToStr(_FPS) + " FPS]"));
end;
DestroyWND(false);
end;
begin
CreateAPP(1024,768, true);
Loop(500);
end.
← →
@!!ex © (2007-05-28 07:43) [32]> Мне нужно сдать игру до 1 октября. Может можно написать
> игру в одном DPR файле как вы думаете.
> ДУмаю может оставить все функии по инициализации окна и
> графики.
> в главном файле DPR. Как вы считаете?
Нельзя писать игру в одном DPR.
Я в свое время написал один такой проект и понял что оно нафиг не надо, там черт ногму сломит.
Модульности рулит.
> Тогда у меня вдальнейшем может возникнуть другая проблема,
> Когда мне
> например надо будет писать Спрайтовый модуль и тп. То как
> мне вних
> использовать такие важные переменные как h_wnd, h_dc ...
ДЛя глобальных переменных лично я использую отдельный модуль.
← →
HARIER (2007-05-28 10:08) [33]@!!ex © (28.05.07 07:43) [32]
Так что ты мне посоветуеш делать ...
← →
@!!ex © (2007-05-28 10:18) [34]> HARIER (28.05.07 10:08)
Мне бы кто посоветовал. $)
← →
Rial © (2007-05-28 12:35) [35]> [33] HARIER (28.05.07 10:08)
> Так что ты мне посоветуеш делать ...
На конкретный вопрос - конкретный ответ...
В чем именно проблема то ?
← →
ElectriC © (2007-05-28 15:28) [36]Да раздели код движка по модулям (привожу код своего движ):
1. Допустим главный модуль Engine:
Туда напиши:
var
Engine : record
Han : THandle; // Хэндл движка
WC : TWndClassEx; // Класс окна движка
MSG : MSG; // Сообщения окна движка
WinParam : packed record // Структура параметров окна движка
Width, Height : Word; // Ширина /Высота
Hz, Bits : Byte; // Частота/Бит
end;
...
end;
2. WinApi - модуль создания окна, обработка сообщений, посланных Windows:
uses Engine;
...
function InitWin : HRESULT;
begin
Result := E_FAIL;
with Engine do with WC do
begin
ZeroMemory(@WC, SizeOf(TWndClassEx));
cbSize := SizeOf(WC);
lpszClassName := "Engine";
lpfnWndProc := @WinProc;
style := CS_VREDRAW or CS_HREDRAW;
hInstance := Han;
hIcon := LoadIcon(Han, nil);
hIconSm := LoadIcon(Han, nil);
hCursor := LoadCursor(0, IDC_ARROW);
hbrBackground := COLOR_WINDOW + 3;
lpszMenuName := nil; cbClsExtra := 0; cbWndExtra := 0;
If RegisterClassEx(SLWC) = 0 then Exit;
Han := CreateWindowEx(0, lpszClassName, "Engine", WS_POPUP,
0, 0, 100, 100, 0, 0, hInstance, nil);
If Han = 0 then Exit;
ShowWindow (Han, SW_SHOW); UpdateWindow(Han);
end;
Result := S_OK;
end;
...
P.S. Строй движок по такому принципу!!!
← →
HARIER (2007-05-28 19:14) [37]У меня такие вопросы.
1. Допустим у меня такие модули
Engine - таймер , установка процесов..
Window - создание окна
GL - Создание контекста.
Как их обьеденить?
2. Как привильно создавать классы что бы не выскакивала Runtime error?
3. Тоесть В каждом модуле класс модуля как этот класс использовать в других модулях.
← →
@!!ex © (2007-05-28 19:30) [38]> Как привильно создавать классы что бы не выскакивала Runtime
> error?
У меня не выскакивает... Что я делаю не так7 :)))
> Тоесть В каждом модуле класс модуля как этот класс использовать
> в других модулях.
Не понял вопроса.
Вот у меня есть класс, например:
TEffects = class
public
Player:^x_vector;
Constructor Create;
Procedure Add(Effect:PSimpleEffect; Position:x_vector; LifeTime:integer; HalfSize:single; const Velocity:x_vector; Color:x_vector; GlobalMove:boolean = false); overload;
Procedure AddLinked(Effect:PSimpleEffect; Position:px_vector; LifeTime:integer; HalfSize:single; const Color:x_vector);
Procedure Add(Effect:PSimpleEffect; Position:x_vector; LifeTime:integer; HalfSize:single; const Velocity,Accelerate:x_vector; const Color, ChangeColor:x_vector; Source:boolean; VelocityLink:px_vector; GlobalMove:boolean = false); overload;
Procedure Update(dt:integer);
Procedure Draw();
Procedure Clear;
Procedure GlobalMove(const Vector:x_Vector);
protected
Items:array of TAliveEffect;
Size:integer;
Count:integer;
end;
Описанный в модуле Effects.
Использую я его очень просто:
var
Effects:TEffects;
...
Effects:=TEffects.Create;
Effects.Player:=@PlayerPosition; //Для поворота спрайтов к камере.
...
Effects.Update(dt);
...
Effects.Draw;
...
Effects.Free;
← →
HARIER (2007-05-29 00:38) [39]Где имено создовать класс. так чтобы его можно было использовать в модулях движка.
← →
@!!ex_ (2007-05-29 07:51) [40]У меня есть главный класс движка, который рулит всем. Вот в нем я и создаю почти все объекты.
Страницы: 1 2 вся ветка
Форум: "Игры";
Текущий архив: 2009.06.28;
Скачать: [xml.tar.bz2];
Память: 0.67 MB
Время: 0.007 c