XNA框架:操纵屏幕亮度
本文关键字:屏幕 亮度 操纵 框架 XNA | 更新日期: 2023-09-27 18:16:31
我正在做一个使用XNA框架的游戏项目。
我使用OptionsMenuScreen
类向用户显示不同的游戏选项/设置。
我在屏幕上添加了两个UP
和DOWN
按钮(Texture2D
),可以增加或减少屏幕的亮度。
我无法找到我需要用来操纵屏幕亮度的逻辑。
如果您能给我指一下正确的方向,我将非常感激。相关代码如下:
class OptionsMenuScreen : MenuScreen
{
SpriteBatch spriteBatch;
MenuEntry brightness;
Texture2D brightnessUp;
Texture2D brightnessDown;
ContentManager contentManager;
public OptionsMenuScreen() : base("Options")
{
brightness = new MenuEntry("Brightness");
MenuEntries.Add(brightness);
}
public override void LoadContent()
{
if (contentManager == null)
{
contentManager = new ContentManager(ScreenManager.Game.Services, "Content");
}
brightnessUp = contentManager.Load<Texture2D>("handup");
brightnessDown = contentManager.Load<Texture2D>("handdown");
}
public override void Draw(GameTime gameTime)
{
spriteBatch = ScreenManager.SpriteBatch;
var brightnessDownPosition =
new Vector2(brightness.Position.X - 50, brightness.Position.Y - 12);
var brightnessUpPosition =
new Vector2(brightness.Position.X
+ brightness.GetWidth(this) + 8, brightness.Position.Y - 12);
spriteBatch.Begin();
spriteBatch.Draw(brightnessDown,
new Rectangle((int)brightnessDownPosition.X, (int)brightnessDownPosition.Y,
30, 30), Color.White);
spriteBatch.Draw(brightnessUp,
new Rectangle((int)brightnessUpPosition.X, (int)brightnessUpPosition.Y,
30, 30), Color.White);
spriteBatch.End();
base.Draw(gameTime);
}
public override void Update(GameTime gameTime, bool otherScreenHasFocus, bool coveredByOtherScreen)
{
base.Update(gameTime, otherScreenHasFocus, coveredByOtherScreen);
foreach (TouchLocation t in TouchPanel.GetState())
{
if (t.Position.X >= brightnessDown.Bounds.Left
&& t.Position.X <= brightnessDown.Bounds.Right
&& t.Position.Y >= brightnessDown.Bounds.Top
&& t.Position.X <= brightnessDown.Bounds.Bottom)
{
// What should I do here?
}
else if (t.Position.X >= brightnessUp.Bounds.Left
&& t.Position.X <= brightnessUp.Bounds.Right
&& t.Position.Y >= brightnessUp.Bounds.Top
&& t.Position.X <= brightnessUp.Bounds.Bottom)
{
// What should I do here?
}
}
}
}
非常感谢你的调查:)
根据这个帖子,有几种方法可以做到:
- 使用
GraphicsDevice.SetGammaRamp(...)
- 使用黑色纹理和alpha透明度
- 调整场景中所有对象的材质和/或纹理上的灯光
- 使用像素着色器重新计算逐像素颜色
第一个选项是最简单的,但有一些缺点(设置时的图形效果很难看——主要是选项菜单的效果),并且并不总是支持。
您可以使用SupportsFullScreenGamma
和CanCalibrateGamma
来确定是否支持,如果不支持,则退回到另一个方法。
编辑
在Windows Phone 7上,你可能无法使用这些选项。
该网站(目前坏了,但如果你谷歌它,你可以找到一个缓存的副本)建议你使用全屏四边形与alpha混合方法,与这些特定的混合模式:
Brightness: source = ZERO, dest = SOURCECOLOR
Contrast: source = DESTCOLOR, dest = SOURCECOLOR
下面是一些代码(从那篇文章中偷来的):
// In your game class:
Texture2D whiteTexture;
// In LoadContent:
whiteTexture = new Texture2D(GraphicsDevice, 1, 1);
whiteTexture.SetData<Color>(new Color[] { Color.White });
// In the appropriate class (the game class? not sure...):
int brightness;
int contrast;
BlendState brightnessBlend;
BlendState contrastBlend;
// In Initialize:
brightness = 255;
contrast = 128;
brightnessBlend = new BlendState();
brightnessBlend.ColorSourceBlend = brightnessBlend.AlphaSourceBlend = Blend.Zero;
brightnessBlend.ColorDestinationBlend = brightnessBlend.AlphaDestinationBlend = Blend.SourceColor;
contrastBlend = new BlendState();
contrastBlend.ColorSourceBlend = contrastBlend.AlphaSourceBlend = Blend.DestinationColor;
contrastBlend.ColorDestinationBlend = contrastBlend.AlphaDestinationBlend = Blend.SourceColor;
// In Draw:
spriteBatch.Begin(SpriteSortMode.Immediate, brightnessBlend);
spriteBatch.Draw(whiteTexture, new Rectangle(0, 0, 480, 800), new Color (brightness, brightness, brightness, 255));
spriteBatch.End();
spriteBatch.Begin(SpriteSortMode.Immediate, contrastBlend);
spriteBatch.Draw(whiteTexture, new Rectangle(0, 0, 480, 800), new Color(contrast, contrast, contrast, 255));
spriteBatch.End();
GraphicsDevice.BlendState = BlendState.Opaque;