Brug af lagparametre til at oprette sprite-kontekst
resumé
Brug lagets dybdeværdi til at angive konteksten for sprite.
Driftsmiljø
Forudsætninger
Understøttede XNA-versioner |
|
Understøttede platforme |
|
Windows påkrævet Vertex Shader-version | 2.0 |
Windows påkrævet Pixel Shader-version | 2.0 |
Driftsmiljø
perron |
|
stof
Normalt, når du tegner en sprite, tegnes den, så det, du tegner senere, er foran dig, men ved at sortere efter dybdeværdi kan du gøre konteksten klar, uanset i hvilken rækkefølge SpriteBatch.Draw-metoden kaldes.
Hvis du vil sortere efter sprite-dybdeværdi, skal du angive "SpriteSortMode.BackToFront" som det første argument til metoden "SpriteBatch.Begin". Det er en behandlingsmetode, der trækker fra spriten bagpå og overskriver spriten i forgrunden.
// 一つでも半透明、透明要素があるスプライトの場合はこちらの引数を使用
this.spriteBatch.Begin(SpriteSortMode.BackToFront, null);
Men hvis du kun vil tegne en sprite, der er halvgennemsigtig eller slet ikke har gennemsigtige elementer, kan du tegne den hurtigere ved at angive følgende.
// 深度バッファを使用して前後関係を有効にし描画するように指定
// 完全な不透明スプライトのみ描画する場合はこちらが高速
this.spriteBatch.Begin(SpriteSortMode.FrontToBack,
BlendState.Opaque,
null,
DepthStencilState.Default,
null);
Det fjerde argument er "DepthStencilState.Default", som også skriver "dybde"-oplysninger til hver pixel, når spriten tegnes. Når dybdeinformationen er skrevet, er det muligt at bestemme, at objektet, der skal tegnes (i pixels) efter denne position, ikke behøver at blive skrevet, så tegningsomkostningerne reduceres kraftigt.
Hvis du tegner spriten i forgrunden først, vil tegningsomkostningerne for den sprite, der overlapper bag den, falde af ovenstående grunde, så den sorteres, så den tegnes forfra ved at angive "SpriteSortMode.FrontToBack" som det første argument, der skal tegnes fra forgrunden.
Dette er dog kun nyttigt, når du tegner en uigennemsigtig sprite med et helt ubetydeligt farveelement bagved. I tilfælde af halvgennemsigtige eller uigennemsigtige sprites skrives dybdeværdien til hver pixel, selvom det er en halvgennemsigtig eller gennemsigtig pixel, så hvis du tegner forfra, vil spriten bag dig ikke blive vist. Dette er grunden til, at "SpriteSortMode.BackToFront" er angivet i tegntegningen. (Fordi andre pixel end tekstens form er gennemsigtige)
Forresten, som et resultat af en test med at tegne 30.000 sprites i mit miljø, var det omkring 3 gange hurtigere at tegne forfra ved hjælp af dybdeværdien end bagfra. Det afhænger selvfølgelig af antallet af ark, der skal tegnes, graden af overlapning, størrelsen osv. samt udførelsesmiljøet, så prøv det selv.
SpriteBatch.Begin
metode
Kald det, før du tegner spriten. Internt foretager vi de nødvendige indstillinger for at tegne sprites.
sortMode | SpriteSortMode | Angiver den rækkefølge, som sprites trækkes i fra SpriteSortMode-optællingen. Hvis du vil tegne bagfra, skal du angive SpriteSortMode.BackToFront. Hvis du vil tegne forfra, skal du angive SpriteSortMode.FrontToBack. |
blendState | BlendState | Sådan blandes farven på den sprite, der skal tegnes, med baggrundsfarven. Som standard er BlendState.AlphaBlend angivet, men i dette tilfælde er den sprite, der skal tegnes, helt uigennemsigtig, så BlendState.Opaque er angivet uden at tage hensyn til baggrundsfarven. |
samplerState | SamplerState | Hvordan teksturen prøves. Hvis null er angivet, er standarden SamplerState.LinearClamp angivet. |
dybdeStencilState | Dybde StencilState | Angiver, hvordan dybdestencilbufferen bruges. Hvis null er angivet, bruges DepthStencilState.None, som ikke bruger en dybdestencilbuffer. Hvis du vil bruge en dybdestencilbuffer, skal du angive DepthStencilState.Default. |
rasterizerStat | RasterizerState | Angiver en rasteriseringsmetode, f.eks. tilbagesletning. Hvis null er angivet, er standarden RasterizerState.CullCounterClockwise angivet. |
Hvis du vil tegne en sprite, skal du angive en dybdeværdi som det niende argument til metoden SpriteBatch.Draw. De værdier, der kan indstilles her, er i området 0.0~1.0, hvor 0.0 er den forreste og 1.0 er den bagerste.
// 最背面に描画(赤)
this.spriteBatch.Draw(this.texture, new Vector2(150.0f, 50.0f), null,
Color.Red, 0.0f, Vector2.Zero, 1.0f, SpriteEffects.None, 1.0f);
// 最前面に描画(緑)
this.spriteBatch.Draw(this.texture, new Vector2(110.0f, 90.0f), null,
Color.Green, 0.0f, Vector2.Zero, 1.0f, SpriteEffects.None, 0.0f);
// 2つのスプライトの間に描画(青)
this.spriteBatch.Draw(this.texture, new Vector2(190.0f, 130.0f), null,
Color.Blue, 0.0f, Vector2.Zero, 1.0f, SpriteEffects.None, 0.5f);
SpriteBatch.Draw
metode
Føjer en sprite til batchlisten over sprite-tegninger.
tekstur | Tekstur 2D | Angiver den tekstur, der skal vises som en sprite. |
position | Vector2 | Den position, hvor spriten skal vises. Angiv i skærmkoordinater i forhold til øverst til venstre på skærmen. Oprindelsen af spriten vil være i øverste venstre position. |
sourceRectangle | Null-<rektangel> | Angiver overførselsområdet for teksturen. Hvis hele teksturen skal vises som en sprite, kan du angive null. Hvis du angiver denne parameter, kan du kun få et vilkårligt område til at blive vist som en sprite. |
farve | Farve | Angiver den farve, der skal multipliceres farven på sprite. Hvis du angiver Farve.Hvid, vises den i spritens primære farve. Hvis Color.Black er angivet, vises sprite-spriten i fuld sort, uanset farven. Formlen er "Resultat = spritefarve * farve". |
rotation | flyde | Spritens rotationsvinkl. Enheder er angivet i radian. Rotationsaksen vil være øverst til venstre på spriten. |
oprindelse | Vector2 | Angiver rotationsaksens position, når spriten roteres. Du angiver, hvilken position af sprite, der er rotationsaksen, men i virkeligheden er rotationsaksens position fastgjort øverst til venstre for sprite, og sprajtens visningsposition flyttes af -origin. |
skæl | flyde | Angiver forstørrelsen af sprite. Skaleres lodret og vandret i forhold til 1,0. Oprindelsen af forstørrelsen vil være i øverste venstre hjørne af spriten. |
effekter | SpriteEffects | Angiver spejlvendingseffekten af sprite. Hvis du ikke gør andet, skal du angive SpriteEffects.None. |
layerDepth | flyde | Angiver den dybde, som spriten vises i. Det bruges hovedsageligt til at vise sprites i forgrunden og bagpå. Angiv i området 0.0~1.0, hvor 0.0 er forsiden og 1.0 er bagsiden. |
I ovenstående program kaldes SpriteBatch.Draw-metoden i rækkefølgen "rød", "grøn" og "blå", men hver dybdeværdi er sat til "rød (1.0)", "grøn (0.0)" og "blå (0.5)", så du kan se, at rød er tegnet bagerst og grøn er tegnet i forgrunden.
Alle koder
using System;
using System.Collections.Generic;
using System.Linq;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Audio;
using Microsoft.Xna.Framework.Content;
using Microsoft.Xna.Framework.GamerServices;
using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework.Input;
using Microsoft.Xna.Framework.Media;
#if WINDOWS_PHONE
using Microsoft.Xna.Framework.Input.Touch;
#endif
namespace LayerDepthSprite
{
<summary>
ゲームメインクラス
</summary>
public class GameMain : Microsoft.Xna.Framework.Game
{
<summary>
グラフィックデバイス管理クラス
</summary>
private GraphicsDeviceManager graphics = null;
<summary>
スプライトのバッチ化クラス
</summary>
private SpriteBatch spriteBatch = null;
<summary>
テクスチャー
</summary>
private Texture2D texture = null;
<summary>
GameMain コンストラクタ
</summary>
public GameMain()
{
// グラフィックデバイス管理クラスの作成
this.graphics = new GraphicsDeviceManager(this);
// ゲームコンテンツのルートディレクトリを設定
this.Content.RootDirectory = "Content";
#if WINDOWS_PHONE
// Windows Phone のデフォルトのフレームレートは 30 FPS
this.TargetElapsedTime = TimeSpan.FromTicks(333333);
// バックバッファサイズの設定
this.graphics.PreferredBackBufferWidth = 480;
this.graphics.PreferredBackBufferHeight = 800;
// フルスクリーン表示
this.graphics.IsFullScreen = true;
#endif
}
<summary>
ゲームが始まる前の初期化処理を行うメソッド
グラフィック以外のデータの読み込み、コンポーネントの初期化を行う
</summary>
protected override void Initialize()
{
// TODO: ここに初期化ロジックを書いてください
// コンポーネントの初期化などを行います
base.Initialize();
}
<summary>
ゲームが始まるときに一回だけ呼ばれ
すべてのゲームコンテンツを読み込みます
</summary>
protected override void LoadContent()
{
// テクスチャーを描画するためのスプライトバッチクラスを作成します
this.spriteBatch = new SpriteBatch(this.GraphicsDevice);
// テクスチャーをコンテンツパイプラインから読み込む
this.texture = this.Content.Load<Texture2D>("Texture");
}
<summary>
ゲームが終了するときに一回だけ呼ばれ
すべてのゲームコンテンツをアンロードします
</summary>
protected override void UnloadContent()
{
// TODO: ContentManager で管理されていないコンテンツを
// ここでアンロードしてください
}
<summary>
描画以外のデータ更新等の処理を行うメソッド
主に入力処理、衝突判定などの物理計算、オーディオの再生など
</summary>
<param name="gameTime">このメソッドが呼ばれたときのゲーム時間</param>
protected override void Update(GameTime gameTime)
{
// Xbox 360 コントローラ、Windows Phone の BACK ボタンを押したときに
// ゲームを終了させます
if (GamePad.GetState(PlayerIndex.One).Buttons.Back == ButtonState.Pressed)
{
this.Exit();
}
// TODO: ここに更新処理を記述してください
// 登録された GameComponent を更新する
base.Update(gameTime);
}
<summary>
描画処理を行うメソッド
</summary>
<param name="gameTime">このメソッドが呼ばれたときのゲーム時間</param>
protected override void Draw(GameTime gameTime)
{
// 画面を指定した色でクリアします
this.GraphicsDevice.Clear(Color.CornflowerBlue);
// 深度バッファを使用して前後関係を有効にし描画するように指定
// 完全な不透明スプライトのみ描画する場合はこちらが高速
this.spriteBatch.Begin(SpriteSortMode.FrontToBack,
BlendState.Opaque,
null,
DepthStencilState.Default,
null);
// 一つでも半透明、透明要素があるスプライトの場合はこちらの引数を使用
//this.spriteBatch.Begin(SpriteSortMode.BackToFront, null);
// 最背面に描画(赤)
this.spriteBatch.Draw(this.texture, new Vector2(150.0f, 50.0f), null,
Color.Red, 0.0f, Vector2.Zero, 1.0f, SpriteEffects.None, 1.0f);
// 最前面に描画(緑)
this.spriteBatch.Draw(this.texture, new Vector2(110.0f, 90.0f), null,
Color.Green, 0.0f, Vector2.Zero, 1.0f, SpriteEffects.None, 0.0f);
// 2つのスプライトの間に描画(青)
this.spriteBatch.Draw(this.texture, new Vector2(190.0f, 130.0f), null,
Color.Blue, 0.0f, Vector2.Zero, 1.0f, SpriteEffects.None, 0.5f);
// スプライトの一括描画
this.spriteBatch.End();
// 登録された DrawableGameComponent を描画する
base.Draw(gameTime);
}
}
}