将我的 GameWindow 设置为全屏会将其拉伸至桌面分辨率
Setting my GameWindow to fullscreen will stretch it to the desktop resolution
将我的 GameWindow 设置为全屏会拉伸它,如何将其设置为全屏而不丢失原始 window 分辨率并使用黑条?
这是我的代码:
using System;
using System.Collections.Generic;
using System.Text;
using OpenTK;
using OpenTK.Graphics;
using OpenTK.Graphics.OpenGL;
using OpenTK.Windowing.Common;
using OpenTK.Windowing.GraphicsLibraryFramework;
using OpenTK.Windowing.Desktop;
using System.Drawing;
namespace OnlineGame
{
public class Game : GameWindow
{
public Game(GameWindowSettings gameWindowSettings, NativeWindowSettings nativeWindowSettings)
: base(gameWindowSettings, nativeWindowSettings)
{
WindowState = WindowState.Fullscreen;
}
protected override void OnUpdateFrame(FrameEventArgs e)
{
if (KeyboardState.IsKeyDown(Keys.Escape))
{
Close();
}
base.OnUpdateFrame(e);
GL.Clear(ClearBufferMask.ColorBufferBit);
GL.ClearColor(Color.CornflowerBlue);
this.SwapBuffers();
}
}
}
使用GL.Viewport
将视口矩形设置为window的子区域。 GL.Clear
中的“复制”操作不受视口矩形的影响。因此,你还需要设置一个Scissors Test.
您需要知道 window (current_w
, current_h
) 的当前大小和 window (original_w
, original_h
)。计算当前window(current_aspect
)和原始window(original_aspect
)的纵横比:
double current_aspect = (double)current_w / current_h;
double original_aspect = (double)original_w / original_h;
计算子区域并设置视口和剪刀矩形:
int w = (int)(current_w * original_aspect / current_aspect);
int x = (current_w - w) / 2;
GL.Scissor(x, 0, w, this.Size.Y);
GL.Viewport(x, 0, w, this.Size.Y);
用黑色清除整个window。然后限制视口矩形并启用剪刀测试。
注意你必须在GL.Clear
指令之前设置清除颜色(GL.ClearColor
)。
protected override void OnUpdateFrame(FrameEventArgs e)
{
if (KeyboardState.IsKeyDown(Keys.Escape))
{
Close();
}
base.OnUpdateFrame(e);
int original_w = ...;
int original_h = ...;
int current_w = this.Size.X;
int current_h = this.Size.Y;
double current_aspect = (double)current_w / current_h;
double original_aspect = (double)original_w / original_h;
GL.Disable(EnableCap.ScissorTest);
GL.Viewport(0, 0, current_w, current_h);
GL.ClearColor(0.0f, 0.0f, 0.0f, 0.0f);
GL.Clear(ClearBufferMask.ColorBufferBit);
GL.Enable(EnableCap.ScissorTest);
if (current_aspect > original_aspect)
{
int w = (int)(current_w * original_aspect / current_aspect);
int x = (current_w - w) / 2;
GL.Scissor(x, 0, w, this.Size.Y);
GL.Viewport(x, 0, w, this.Size.Y);
}
else
{
int h = (int)(current_h * current_aspect / original_aspect);
int y = (current_h - h) / 2;
GL.Scissor(0, y, this.Size.X, h);
GL.Viewport(0, y, this.Size.X, h);
}
GL.ClearColor(Color.CornflowerBlue);
GL.Clear(ClearBufferMask.ColorBufferBit);
// [...]
this.SwapBuffers();
}
将我的 GameWindow 设置为全屏会拉伸它,如何将其设置为全屏而不丢失原始 window 分辨率并使用黑条?
这是我的代码:
using System;
using System.Collections.Generic;
using System.Text;
using OpenTK;
using OpenTK.Graphics;
using OpenTK.Graphics.OpenGL;
using OpenTK.Windowing.Common;
using OpenTK.Windowing.GraphicsLibraryFramework;
using OpenTK.Windowing.Desktop;
using System.Drawing;
namespace OnlineGame
{
public class Game : GameWindow
{
public Game(GameWindowSettings gameWindowSettings, NativeWindowSettings nativeWindowSettings)
: base(gameWindowSettings, nativeWindowSettings)
{
WindowState = WindowState.Fullscreen;
}
protected override void OnUpdateFrame(FrameEventArgs e)
{
if (KeyboardState.IsKeyDown(Keys.Escape))
{
Close();
}
base.OnUpdateFrame(e);
GL.Clear(ClearBufferMask.ColorBufferBit);
GL.ClearColor(Color.CornflowerBlue);
this.SwapBuffers();
}
}
}
使用GL.Viewport
将视口矩形设置为window的子区域。 GL.Clear
中的“复制”操作不受视口矩形的影响。因此,你还需要设置一个Scissors Test.
您需要知道 window (current_w
, current_h
) 的当前大小和 window (original_w
, original_h
)。计算当前window(current_aspect
)和原始window(original_aspect
)的纵横比:
double current_aspect = (double)current_w / current_h;
double original_aspect = (double)original_w / original_h;
计算子区域并设置视口和剪刀矩形:
int w = (int)(current_w * original_aspect / current_aspect);
int x = (current_w - w) / 2;
GL.Scissor(x, 0, w, this.Size.Y);
GL.Viewport(x, 0, w, this.Size.Y);
用黑色清除整个window。然后限制视口矩形并启用剪刀测试。
注意你必须在GL.Clear
指令之前设置清除颜色(GL.ClearColor
)。
protected override void OnUpdateFrame(FrameEventArgs e)
{
if (KeyboardState.IsKeyDown(Keys.Escape))
{
Close();
}
base.OnUpdateFrame(e);
int original_w = ...;
int original_h = ...;
int current_w = this.Size.X;
int current_h = this.Size.Y;
double current_aspect = (double)current_w / current_h;
double original_aspect = (double)original_w / original_h;
GL.Disable(EnableCap.ScissorTest);
GL.Viewport(0, 0, current_w, current_h);
GL.ClearColor(0.0f, 0.0f, 0.0f, 0.0f);
GL.Clear(ClearBufferMask.ColorBufferBit);
GL.Enable(EnableCap.ScissorTest);
if (current_aspect > original_aspect)
{
int w = (int)(current_w * original_aspect / current_aspect);
int x = (current_w - w) / 2;
GL.Scissor(x, 0, w, this.Size.Y);
GL.Viewport(x, 0, w, this.Size.Y);
}
else
{
int h = (int)(current_h * current_aspect / original_aspect);
int y = (current_h - h) / 2;
GL.Scissor(0, y, this.Size.X, h);
GL.Viewport(0, y, this.Size.X, h);
}
GL.ClearColor(Color.CornflowerBlue);
GL.Clear(ClearBufferMask.ColorBufferBit);
// [...]
this.SwapBuffers();
}