ディスプレイの向き
向きの検出
既定の設定では Windows Phone ゲームは携帯端末を横に持った状態、すなわちディスプレイの横幅が高さよりも長い状態に設定されています。ディスプレイの向きは Winows PC や Xbox 360 向けのゲームには存在しない設定で、ゲーム画面を回転させるという概念はありません。
現在のディスプレイの向きは GameWindow クラスの CurrentOrientation プロパティから得られます。
public abstract DisplayOrientation CurrentOrientation { get; }
このプロパティは、ゲーム画面の現在の向きを表す Microsoft.Xna.Framework.DisplayOrientation 列挙型の値を返します。
[FlagsAttribute] public enum DisplayOrientation
この列挙型は表1のようなメンバが宣言されています。
メンバ | 解説 |
Default | 既定のディスプレイの向き。 |
LandscapeLeft | 反時計回りに 90 度回転した横向き。 |
LandscapeRight | 時計回りに 90 度回転した横向き。 |
Portrait | 縦向き。 |
Windows PC や Xbox 360 では Default メンバが設定されています。 これに対し Windows Phone では LandscapeLeft メンバや LandscapeRight メンバなどの値が得られます。ディスプレイの向きはユーザーが携帯端末の向きを変えることで、いつでも変更される可能性があります。
using System; using Microsoft.Xna.Framework; using Microsoft.Xna.Framework.Graphics; public class TestGame : Game { #if WINDOWS || XBOX public static void Main(string[] args) { using (Game game = new TestGame()) game.Run(); } #endif private GraphicsDeviceManager graphicsDeviceManager; private SpriteBatch sprite; private SpriteFont font; public TestGame() { graphicsDeviceManager = new GraphicsDeviceManager(this); Content.RootDirectory = "Content"; TargetElapsedTime = TimeSpan.FromMilliseconds(33.3333); InactiveSleepTime = TimeSpan.FromMilliseconds(1000); } protected override void LoadContent() { sprite = new SpriteBatch(GraphicsDevice); font = Content.Load<SpriteFont>("TestFont"); base.LoadContent(); } protected override void Draw(GameTime gameTime) { GraphicsDevice.Clear(Color.CornflowerBlue); sprite.Begin(); sprite.DrawString(font, Window.CurrentOrientation.ToString(), Vector2.Zero, Color.Black); sprite.End(); base.Draw(gameTime); } }
コード1は CurrentOrientation プロパティの値を文字列として画面に表示しているだけのプログラムです。Windows Phone の向きを変更すると、文字列が変化することが確認できます。
ただし XNA Framework ゲームの既定の設定では縦向きがサポートされていません。通常のゲームであれば横向き前提に画面が設計されるため、縦向きの画面に対応する必要はありませんが、GraphicsDeviceManager クラスの SupportedOrientations プロパティを変更することで縦向きにも対応できます。
public DisplayOrientation SupportedOrientations { get; set; }
DisplayOrientation 列挙型は FlagsAttribute 属性を持つため論理演算子で組み合わせられます。ゲームが対応する画面の向きを論理和演算子 | で組み合わせて設定することで、その画面の向きに対応できます。縦向きに対応するには Portrait メンバを加えてください。
using System; using Microsoft.Xna.Framework; using Microsoft.Xna.Framework.Graphics; public class TestGame : Game { #if WINDOWS || XBOX public static void Main(string[] args) { using (Game game = new TestGame()) game.Run(); } #endif private GraphicsDeviceManager graphicsDeviceManager; private SpriteBatch sprite; private SpriteFont font; public TestGame() { graphicsDeviceManager = new GraphicsDeviceManager(this); graphicsDeviceManager.SupportedOrientations = DisplayOrientation.LandscapeLeft | DisplayOrientation.LandscapeRight | DisplayOrientation.Portrait; Content.RootDirectory = "Content"; TargetElapsedTime = TimeSpan.FromMilliseconds(33.3333); InactiveSleepTime = TimeSpan.FromMilliseconds(1000); } protected override void LoadContent() { sprite = new SpriteBatch(GraphicsDevice); font = Content.Load<SpriteFont>("TestFont"); base.LoadContent(); } protected override void Draw(GameTime gameTime) { GraphicsDevice.Clear(Color.CornflowerBlue); sprite.Begin(); sprite.DrawString(font, Window.CurrentOrientation.ToString(), Vector2.Zero, Color.Black); sprite.End(); base.Draw(gameTime); } }
コード2は SupportedOrientations プロパティに Portrait メンバを追加しているため、縦向きの画面に対応しています。コード1とは異なり GameWindow オブジェクトの CurrentOrientation プロパティが Portrait メンバになることが確認できます。
向き変更イベント
ユーザーが携帯端末の向きを変えると、ゲーム中にいつでも画面の向きが変更されて今います。GameWindow クラスの CurrentOrientation プロパティを Update() メソッド内で監視することで画面の向きが変更したかどうかを調べることもできますが、画面の向きが変更されたときに呼び出される OrientationChanged イベントを用いた方が効率的です。
public event EventHandler<EventArgs> OrientationChanged
このイベントは CurrentOrientation プロパティの値が変更されると発生します。画面の向きが変更したときに、何らかの処理を実行する必要がある場合に使えます。
using System; using Microsoft.Xna.Framework; using Microsoft.Xna.Framework.Graphics; public class TestGame : Game { #if WINDOWS || XBOX public static void Main(string[] args) { using (Game game = new TestGame()) game.Run(); } #endif private GraphicsDeviceManager graphicsDeviceManager; private Color color = Color.Red; public TestGame() { graphicsDeviceManager = new GraphicsDeviceManager(this); Content.RootDirectory = "Content"; TargetElapsedTime = TimeSpan.FromMilliseconds(33.3333); InactiveSleepTime = TimeSpan.FromMilliseconds(1000); Window.OrientationChanged += Window_OrientationChanged; } void Window_OrientationChanged(object sender, EventArgs e) { switch (Window.CurrentOrientation) { case DisplayOrientation.LandscapeLeft: color = Color.Red; break; case DisplayOrientation.LandscapeRight: color = Color.Blue; break; } } protected override void Draw(GameTime gameTime) { GraphicsDevice.Clear(color); base.Draw(gameTime); } }
コード3は向きが変更されると画面の塗りつぶしに用いられている color フィールドの値を変更するプログラムです。画面の向きが変わると OrientationChanged イベントに登録している Window_OrientationChanged() メソッドが呼び出され、向きに応じた色が設定されることが確認できます。