📄 player.cs
字号:
//---------------------------------------------------------------------
// This file is part of the Microsoft .NET Framework SDK Code Samples.
//
// Copyright (C) Microsoft Corporation. All rights reserved.
//
//This source code is intended only as a supplement to Microsoft
//Development Tools and/or on-line documentation. See these other
//materials for detailed information regarding Microsoft code samples.
//
//THIS CODE AND INFORMATION ARE PROVIDED AS IS WITHOUT WARRANTY OF ANY
//KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE
//IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A
//PARTICULAR PURPOSE.
//---------------------------------------------------------------------
using System;
using System.Data;
using System.Collections;
using System.Diagnostics;
using System.Windows.Forms;
using System.Globalization;
using GraphicsLibrary;
using InputLibrary;
namespace GameApp
{
/// <summary>
/// The player object represents the player in the world. The player is
/// a special case of a world object.
/// </summary>
public class Player : WorldObject
{
/// <summary>
/// Player's current animation cycle.
/// </summary>
AnimationCycle curCycle = null;
/// <summary>
/// Player's animation state during the previous update frame.
/// </summary>
private AnimationState prevState = AnimationState.Stop | AnimationState.Walk;
/// <summary>
/// Time since the last shot was fired.
/// </summary>
private float shotTime = 0.0F;
/// <summary>
/// Specifies if the player shot a misfire during the current frame.
/// This is only set for one frame.
/// </summary>
public bool Misfire { get { return misfireValue; } }
private bool misfireValue = false;
/// <summary>
/// Buttons available to the player. These are indices into the
/// button map.
/// </summary>
public enum Buttons
{
ResetLevel,
ToggleDebug,
Quit,
FireShot
}
#if SMARTPHONE
static readonly int[] buttonMapValue = { 1, 2, 3, 6 };
#else
static readonly int[] buttonMapValue = { 0, 2, 1, 3 };
#endif
/// <summary>
/// Specifies if a shot is in the process of being fired, i.e., the
/// shot bar is loading.
/// </summary>
private bool shotStarted = false;
/// <summary>
/// Length of time, in seconds, for a shot to be fully loaded.
/// </summary>
private float shotChargeTime;
/// <summary>
/// Percent chance of a misfire when a shot is fired with an empty
/// shot bar.
/// </summary>
private float shotMisfireMin;
/// <summary>
/// Percent chance of a misfire when a shot is fired with a full
/// shot bar.
/// </summary>
private float shotMisfireMax;
/// <summary>
/// X velocity of a shot when fired with an empty shot bar.
/// </summary>
private float shotVelocityXMin;
/// <summary>
/// X velocity of a shot when fired with a full shot bar.
/// </summary>
private float shotVelocityXMax;
/// <summary>
/// Y velocity of a shot when fired with an empty shot bar.
/// </summary>
private float shotVelocityYMin;
/// <summary>
/// Y velocity of a shot when fired with a full shot bar.
/// </summary>
private float shotVelocityYMax;
/// <summary>
/// Minimim range of a misfired shot's x velocity.
/// </summary>
private float shotMisfireVelocityXMin;
/// <summary>
/// Maximum range of a misfired shot's x velocity.
/// </summary>
private float shotMisfireVelocityXMax;
/// <summary>
/// Minimim range of a misfired shot's y velocity.
/// </summary>
private float shotMisfireVelocityYMin;
/// <summary>
/// Maximim range of a misfired shot's y velocity.
/// </summary>
private float shotMisfireVelocityYMax;
/// <summary>
/// Index of audio to play when the player dies.
/// </summary>
public int DeathAudioId { get { return audioDeathId; } }
private int audioDeathId;
/// <summary>
/// Gets the percentage of the shot bar that is currently
/// charged
/// </summary>
public float CurrentShotBarPercent
{
get
{
float perc = shotTime / this.shotChargeTime;
return perc >= 1.0F ? 1.0F : perc;
}
}
/// <summary>
/// Create an instance of the player.
/// </summary>
/// <param name="ds">DataSet defining the player</param>
/// <param name="graphics">Graphics instance</param>
/// <param name="animList">List of level animations</param>
public Player(DataSet ds, IGraphics graphics, ArrayList animationList)
{
// Yes, this world object is the player
Player = true;
// The player is always active and collidable
Active = true;
Collidable = true;
// Allocate space fore all animation cycles
for (int i = 0; i < (int)AnimationType.Count; i++)
{
SetAnimationCycle(i, new AnimationCycle());
Debug.Assert(GetAnimationCycle(i) != null,
"Player.Player: Failed to allocate animation cycle");
}
// Start location
DataTable dt = ds.Tables["StartLocation"];
Debug.Assert(dt != null && dt.Rows != null,
"Player.Player: Invalid start location data");
WorldX = float.Parse((string)(dt.Rows[0]["X"]),
CultureInfo.InvariantCulture);
WorldY = float.Parse((string)(dt.Rows[0]["Y"]),
CultureInfo.InvariantCulture);
// Walk animation
dt = ds.Tables["Walk"];
Debug.Assert(dt != null && dt.Rows != null && dt.Rows[0] != null,
"Player.Player: Walk animation data not valid");
WalkCycle.AnimationRate = int.Parse((string)(
dt.Rows[0]["NormalAnimationRate"]),
CultureInfo.InvariantCulture);
WalkCycle.ForceAnimationRate = int.Parse(
(string)(dt.Rows[0]["ForceAnimationRate"]),
CultureInfo.InvariantCulture);
WalkCycle.MoveRate = float.Parse(
(string)(dt.Rows[0]["MovementRate"]),
CultureInfo.InvariantCulture);
WalkCycle.StartCell = int.Parse(
(string)(dt.Rows[0]["StartCell"]),
CultureInfo.InvariantCulture);
WalkCycle.EndCell = int.Parse((string)(dt.Rows[0]["EndCell"]),
CultureInfo.InvariantCulture);
WalkCycle.Bounds = new Bounds(dt.Rows[0]);
// Attack animation
dt = ds.Tables["Attack"];
Debug.Assert(dt != null && dt.Rows != null &&
dt.Rows[0] != null,
"Player.Player: Attack animation data not valid");
AttackCycle.AnimationRate = int.Parse(
(string)(dt.Rows[0]["NormalAnimationRate"]),
CultureInfo.InvariantCulture);
AttackCycle.ForceAnimationRate = int.Parse(
(string)(dt.Rows[0]["ForceAnimationRate"]),
CultureInfo.InvariantCulture);
AttackCycle.MoveRate = float.Parse(
(string)(dt.Rows[0]["MovementRate"]),
CultureInfo.InvariantCulture);
AttackCycle.StartCell = int.Parse(
(string)(dt.Rows[0]["StartCell"]),
CultureInfo.InvariantCulture);
AttackCycle.EndCell = int.Parse(
(string)(dt.Rows[0]["EndCell"]),
CultureInfo.InvariantCulture);
AttackCycle.Bounds = new Bounds(dt.Rows[0]);
// Crawl animation
dt = ds.Tables["Crawl"];
Debug.Assert(dt != null && dt.Rows != null && dt.Rows[0] != null,
"Player.Player: Attack animation data not valid");
DuckCycle.AnimationRate = int.Parse(
(string)(dt.Rows[0]["NormalAnimationRate"]),
CultureInfo.InvariantCulture);
DuckCycle.ForceAnimationRate = int.Parse(
(string)(dt.Rows[0]["ForceAnimationRate"]),
CultureInfo.InvariantCulture);
DuckCycle.MoveRate = float.Parse(
(string)(dt.Rows[0]["MovementRate"]),
CultureInfo.InvariantCulture);
DuckCycle.StartCell = int.Parse(
(string)(dt.Rows[0]["StartCell"]),
CultureInfo.InvariantCulture);
DuckCycle.EndCell = int.Parse(
(string)(dt.Rows[0]["EndCell"]),
CultureInfo.InvariantCulture);
DuckCycle.Bounds = new Bounds(dt.Rows[0]);
// Death animation
dt = ds.Tables["Death"];
Debug.Assert(dt != null && dt.Rows != null &&
dt.Rows[0] != null,
"Player.Player: Death animation data not valid");
DeathCycle.AnimationRate = int.Parse(
(string)(dt.Rows[0]["AnimationRate"]),
CultureInfo.InvariantCulture);
DeathCycle.StartCell = int.Parse(
(string)(dt.Rows[0]["StartCell"]),
CultureInfo.InvariantCulture);
DeathCycle.EndCell = int.Parse((string)(dt.Rows[0]["EndCell"]),
CultureInfo.InvariantCulture);
// Shot
dt = ds.Tables["Shot"];
Debug.Assert(dt != null && dt.Rows != null && dt.Rows[0] != null,
"Player.Player: Shot info data not valid");
ShotInfo[] tempShotInfo = new ShotInfo[1];
tempShotInfo[0] = new ShotInfo(dt.Rows[0]);
SetShotInfo(tempShotInfo);
Debug.Assert(GetShotInfo() != null,
"Player.Player: Failed to allocate shot info");
// General
dt = ds.Tables["General"];
Debug.Assert(dt != null && dt.Rows != null && dt.Rows[0] != null,
"Player.Player: General info data not valid");
DataRow dr = dt.Rows[0];
shotChargeTime = float.Parse((string)(dr["ShotChargeTime"]),
CultureInfo.InvariantCulture);
shotMisfireMin = float.Parse(
(string)(dr["ShotMisfireMin"]),
CultureInfo.InvariantCulture) / 100.0F;
shotMisfireMax = float.Parse(
(string)(dr["ShotMisfireMax"]),
CultureInfo.InvariantCulture) / 100.0F;
shotVelocityXMin = float.Parse(
(string)(dr["ShotVelocityXMin"]),
CultureInfo.InvariantCulture) / 100.0F;
shotVelocityXMax = float.Parse(
(string)(dr["ShotVelocityXMax"]),
CultureInfo.InvariantCulture) / 100.0F;
shotVelocityYMin = float.Parse(
(string)(dr["ShotVelocityYMin"]),
CultureInfo.InvariantCulture) / 100.0F;
shotVelocityYMax = float.Parse(
(string)(dr["ShotVelocityYMax"]),
CultureInfo.InvariantCulture) / 100.0F;
shotMisfireVelocityXMin = float.Parse(
(string)(dr["ShotMisfireVelocityXMin"]),
CultureInfo.InvariantCulture) / 100.0F;
shotMisfireVelocityXMax = float.Parse(
(string)(dr["ShotMisfireVelocityXMax"]),
CultureInfo.InvariantCulture) / 100.0F;
shotMisfireVelocityYMin = float.Parse(
(string)(dr["ShotMisfireVelocityYMin"]),
CultureInfo.InvariantCulture) / 100.0F;
shotMisfireVelocityYMax = float.Parse(
(string)(dr["ShotMisfireVelocityYMax"]),
CultureInfo.InvariantCulture) / 100.0F;
audioDeathId = int.Parse((string)(dr["DeathAudioId"]),
CultureInfo.InvariantCulture);
// Animation
int animationId = int.Parse((string)(dr["AnimationId"]),
CultureInfo.InvariantCulture);
Debug.Assert(animationId >= 0 && animationId < animationList.Count,
"Player.Player: Animation ID out of range");
Animation = new Animation((Animation)animationList[animationId], 0, 0);
Debug.Assert(Animation != null && Animation.Init,
"Player.Player: Failed to load animationation");
// Start with the walk cycle
Animation.SetCycle(WalkCycle.StartCell, WalkCycle.EndCell, 0);
curCycle = WalkCycle;
// Check if drawing requires transparency
if (bool.Parse((string)(dt.Rows[0]["Transparency"])))
{
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -