Introduction
Having a button in XNA is very usual and important, so let's make buttons with
MouseOver
and MouseClick
events.
I have used sound to create some action for the result of MouseOver
and
MouseDown
.
Using the code
First we should create Structs for our picture buttons:
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework.Input;
using Microsoft.Xna.Framework.Audio;
using Microsoft.Xna.Framework.Content;
using System.Collections.Generic;
using System.Linq;
using Microsoft.Xna.Framework.GamerServices;
using Microsoft.Xna.Framework.Media;
using System.Collections;
using Language_Learning_Application;
public struct picture
{
public string strfilename;
public string strfilename1;
public string strfilename2;
public string strfilename3;
public string strfilename4;
public string GiveMeTheCurrentFilename(int FormNumber,string Action)
{
if((Action!="LabelAnimation"))
{
if (FormNumber == 1) return strfilename;
if (FormNumber == 2) return strfilename1;
if (FormNumber == 3) return strfilename2;
}
return strfilename;
}
public string GiveMeTheCurrentFilenameSound(int SoundNumber)
{
if (SoundNumber == 1) return strfilename3;
if (SoundNumber == 2) return strfilename4;
return strfilename;
}
public SoundEffect soundEffect;
public int intCurrentForm;
public int CurrentSound;
public Rectangle rectangleDestination;
public bool boolisLoaded;
public string strplaceOfUse;
public int key;
public bool ShouldItBeShownInThisScreen;
public Texture2D Texture;
public string Action;
public string MousePictureState;
public bool PlayingSound ;
public bool HasItAnimation;
public bool IsAnimationOn;
public int TotalAnimationFrame;
public int CurentAnimationFrame;
public string OriginalFilenameWithoutIndex;
public int FramePerSecond;
}
And then we create a struct for our MouseButton
keys and features.
public struct MouseButton
{
public ButtonState LeftClick;
public ButtonState RightClick;
public ButtonState MiddleClick;
public int ScrollWheel ;
public bool IsThisPointInThisRectangle ;
}
Now we get ContentManager
form the main class:
private ContentManager content;
public ContentManager PropertyContent
{
set
{
content = value;
}
}
Now we define our buttons and labels:
public picture tex2dBtnAddNewWords;
public picture tex2dBtnLearn;
public picture tex2dBtnExit;
public picture tex2dBtnUpdate;
public picture lblPleaseWriteYourWordHere;
public picture txtWord;
Let's put our buttons and labels in a public array to use it everywhere in our project:
public picture[] mypictures=new picture[6];
Now we initialize our buttons and labels:
public void InitializeDefenitions()
{
string BaseDirectory = ".";
tex2dBtnAddNewWords.key = 1;
tex2dBtnAddNewWords.strfilename = BaseDirectory + "\\StartPage\\Buttons\\jpgAddNewWordsForm1";
tex2dBtnAddNewWords.strfilename1 = BaseDirectory + "\\StartPage\\Buttons\\jpgAddNewWordsForm2";
tex2dBtnAddNewWords.strfilename2 = BaseDirectory + "\\StartPage\\Buttons\\jpgAddNewWordsForm3";
tex2dBtnAddNewWords.strfilename3 = BaseDirectory + "\\StartPage\\Sounds\\ButtonMouseOverSound";
tex2dBtnAddNewWords.strfilename4 = BaseDirectory + "\\StartPage\\Sounds\\ButtonClickSound";
tex2dBtnAddNewWords.rectangleDestination = new Rectangle((WindowsScreenWidth - 778) / 2,
(WindowsScreenHeight - 124) / 2 - 124-124, 778, 124);
tex2dBtnAddNewWords.boolisLoaded = false;
tex2dBtnAddNewWords.strplaceOfUse = "StartPage";
tex2dBtnAddNewWords.ShouldItBeShownInThisScreen = true;
tex2dBtnAddNewWords.Texture = null;
tex2dBtnAddNewWords.Action = "Button";
tex2dBtnAddNewWords.intCurrentForm = 1;
tex2dBtnAddNewWords.MousePictureState = "OutOfControl";
tex2dBtnAddNewWords.CurrentSound = 1;
tex2dBtnLearn.key = 2;
tex2dBtnLearn.strfilename = BaseDirectory + "\\StartPage\\Buttons\\jpgLearnForm1";
tex2dBtnLearn.strfilename1 = BaseDirectory + "\\StartPage\\Buttons\\jpgLearnForm2";
tex2dBtnLearn.strfilename2 = BaseDirectory + "\\StartPage\\Buttons\\jpgLearnForm3";
tex2dBtnLearn.strfilename3 = BaseDirectory + "\\StartPage\\Sounds\\ButtonMouseOverSound";
tex2dBtnLearn.strfilename4 = BaseDirectory + "\\StartPage\\Sounds\\ButtonClickSound";
tex2dBtnLearn.rectangleDestination = new Rectangle(
(WindowsScreenWidth - 778) / 2, (WindowsScreenHeight - 124) / 2 +20 , 778, 124);
tex2dBtnLearn.boolisLoaded = false;
tex2dBtnLearn.strplaceOfUse = "StartPage";
tex2dBtnLearn.ShouldItBeShownInThisScreen = true;
tex2dBtnLearn.Texture = null;
tex2dBtnLearn.Action = "Button";
tex2dBtnLearn.intCurrentForm = 1;
tex2dBtnLearn.MousePictureState = "OutOfControl";
tex2dBtnLearn.CurrentSound = 1;
tex2dBtnExit.key = 3;
tex2dBtnExit.strfilename = BaseDirectory + "\\StartPage\\Buttons\\jpgExitForm1";
tex2dBtnExit.strfilename1 = BaseDirectory + "\\StartPage\\Buttons\\jpgExitForm2";
tex2dBtnExit.strfilename2 = BaseDirectory + "\\StartPage\\Buttons\\jpgExitForm3";
tex2dBtnExit.strfilename3 = BaseDirectory + "\\StartPage\\Sounds\\ButtonMouseOverSound";
tex2dBtnExit.strfilename4 = BaseDirectory + "\\StartPage\\Sounds\\ButtonClickSound";
tex2dBtnExit.rectangleDestination = new Rectangle((WindowsScreenWidth - 778) / 2,
(WindowsScreenHeight - 124) / 2+124 + 30, 778, 124);
tex2dBtnExit.boolisLoaded = false;
tex2dBtnExit.strplaceOfUse = "StartPage";
tex2dBtnExit.ShouldItBeShownInThisScreen = true;
tex2dBtnExit.Texture = null;
tex2dBtnExit.Action = "Button";
tex2dBtnExit.intCurrentForm = 1;
tex2dBtnExit.MousePictureState = "OutOfControl";
tex2dBtnExit.CurrentSound = 1;
tex2dBtnUpdate.key = 4;
tex2dBtnUpdate.strfilename = BaseDirectory + "\\StartPage\\Buttons\\jpgUpdateForm1";
tex2dBtnUpdate.strfilename1 = BaseDirectory + "\\StartPage\\Buttons\\jpgUpdateForm2";
tex2dBtnUpdate.strfilename2 = BaseDirectory + "\\StartPage\\Buttons\\jpgUpdateForm3";
tex2dBtnUpdate.strfilename3 = BaseDirectory + "\\StartPage\\Sounds\\ButtonMouseOverSound";
tex2dBtnUpdate.strfilename4 = BaseDirectory + "\\StartPage\\Sounds\\ButtonClickSound";
tex2dBtnUpdate.rectangleDestination = new Rectangle((WindowsScreenWidth - 778) / 2,
(WindowsScreenHeight - 124) / 2 + 10 - 124, 778, 124);
tex2dBtnUpdate.boolisLoaded = false;
tex2dBtnUpdate.strplaceOfUse = "StartPage";
tex2dBtnUpdate.ShouldItBeShownInThisScreen = true;
tex2dBtnUpdate.Texture = null;
tex2dBtnUpdate.Action = "Button";
tex2dBtnUpdate.intCurrentForm = 1;
tex2dBtnUpdate.MousePictureState = "OutOfControl";
tex2dBtnUpdate.CurrentSound = 1;
lblPleaseWriteYourWordHere.key = 5;
lblPleaseWriteYourWordHere.strfilename = BaseDirectory +
"\\AddNewWordsPage1\\Labels\\Please Write Your Word Here\\Please write your word Here1";
lblPleaseWriteYourWordHere.OriginalFilenameWithoutIndex = BaseDirectory +
"\\AddNewWordsPage1\\Labels\\Please Write Your Word Here\\Please write your word Here";
lblPleaseWriteYourWordHere.rectangleDestination =
new Rectangle((WindowsScreenWidth - 515) / 2, (WindowsScreenHeight - 63) / 2-63-63 , 515, 63);
lblPleaseWriteYourWordHere.boolisLoaded = false;
lblPleaseWriteYourWordHere.strplaceOfUse = "AddNewWords_Word";
lblPleaseWriteYourWordHere.ShouldItBeShownInThisScreen = false;
lblPleaseWriteYourWordHere.Texture = null;
lblPleaseWriteYourWordHere.Action = "LabelAnimation";
lblPleaseWriteYourWordHere.intCurrentForm = 1;
lblPleaseWriteYourWordHere.MousePictureState = "OutOfControl";
lblPleaseWriteYourWordHere.TotalAnimationFrame = 30;
lblPleaseWriteYourWordHere.CurentAnimationFrame = 1;
lblPleaseWriteYourWordHere.IsAnimationOn = true;
lblPleaseWriteYourWordHere.HasItAnimation = true;
lblPleaseWriteYourWordHere.FramePerSecond = 8;
txtWord.key = 6;
txtWord.strfilename = BaseDirectory + "\\AddNewWordsPage1\\Labels\\TextBox\\TextBox";
txtWord.strfilename3 = BaseDirectory +
"\\AddNewWordsPage1\\Labels\\Please Write Your Word Here\\Please write your word Here";
txtWord.rectangleDestination = new Rectangle((WindowsScreenWidth - 1000) / 2,
(WindowsScreenHeight - 300) / 2 + 50, 1000, 300);
txtWord.boolisLoaded = false;
txtWord.strplaceOfUse = "AddNewWords_Word";
txtWord.ShouldItBeShownInThisScreen = false;
txtWord.Texture = null;
txtWord.Action = "TextBox";
txtWord.intCurrentForm = 1;
txtWord.MousePictureState = "OutOfControl";
txtWord.CurrentSound = 1;
mypictures[0] = tex2dBtnAddNewWords;
mypictures[1] = tex2dBtnLearn;
mypictures[2] = tex2dBtnExit;
mypictures[3] = tex2dBtnUpdate;
mypictures[4] = lblPleaseWriteYourWordHere;
mypictures[5] = txtWord;
}
Now that we initialize our buttons let's loop through them to show them on screen
We create a loop engine here:
public int CurrentPicture=0;
public void fncEngineMotor()
{
for (int i=0; i < mypictures.Length; i++)
{
CurrentPicture = i;
myloadContent(ref mypictures[CurrentPicture]);
fncCheckForMouseMoveOnButton(Mouse.GetState(), ref mypictures[CurrentPicture]);
fncCheckForMouseEnterOnButtonSound(Mouse.GetState(), ref mypictures[CurrentPicture]);
DoAnimationFrame(ref mypictures[CurrentPicture]);
}
}
Here we load and unload content of every picture:
public void myloadContent(ref picture mypicture)
{
if (mypicture.strplaceOfUse == strProgramState)
{
if (mypicture.ShouldItBeShownInThisScreen == true)
{
mypicture.Texture = content.Load<Texture2D>(
mypicture.GiveMeTheCurrentFilename(mypicture.intCurrentForm, mypicture.Action));
if (mypicture.Action != "LabelAnimation" && mypicture.Action != "TextBox")
{
mypicture.soundEffect = content.Load<SoundEffect>(
mypicture.GiveMeTheCurrentFilenameSound(mypicture.CurrentSound));
}
}
if (mypicture.ShouldItBeShownInThisScreen == false)
{
mypicture.Texture = null;
mypicture.soundEffect = null;
}
}
}
Let's change the texture of buttons for user's attraction on mouse over and mouse click:
public void fncCheckForMouseMoveOnButton(MouseState MyMousestate,ref picture myPicture)
{
if (myPicture.ShouldItBeShownInThisScreen)
{
MouseButton result = fncIsThisPointInThisRectangle(MyMousestate.X, MyMousestate.Y,
MyMousestate.LeftButton, MyMousestate.RightButton, MyMousestate.MiddleButton,
MyMousestate.ScrollWheelValue, myPicture.rectangleDestination);
if (result.IsThisPointInThisRectangle)
{
if (myPicture.Action == "Button")
{
myPicture.intCurrentForm = 2;
if (result.LeftClick == ButtonState.Pressed)
{
myPicture.intCurrentForm = 3;
}
}
}
if (!result.IsThisPointInThisRectangle)
{
if (myPicture.Action == "Button")
{
if (myPicture.intCurrentForm != 1)
{
myPicture.intCurrentForm = 1;
}
}
}
}
}
Is mouse on The button?
To do this we need to see if mouse is on the button?
We do this here:
public MouseButton fncIsThisPointInThisRectangle(int MyMousestateX, int MyMousestateY,
Microsoft.Xna.Framework.Input.ButtonState LeftButton,
Microsoft.Xna.Framework.Input.ButtonState RightButton,
Microsoft.Xna.Framework.Input.ButtonState MiddleButton,
int ScrollWheelValue, Rectangle thisRectangle)
{
MouseButton result=new MouseButton();
if (MyMousestateX > thisRectangle.Left && MyMousestateX <
thisRectangle.Right && MyMousestateY < thisRectangle.Bottom &&
MyMousestateY > thisRectangle.Top)
{
result.IsThisPointInThisRectangle = true;
result.LeftClick = LeftButton;
result.MiddleClick = MiddleButton;
result.RightClick = RightButton;
result.ScrollWheel = ScrollWheelValue;
}
return result;
}
Mouse Events:
Now we need some some sound to get user happy on Mouse Over and Mouse Click.
Do it like this:
public int fncCheckForMouseEnterOnButtonSound(MouseState MyMousestate,ref picture myPicture)
{
int myreturn = 0;
if (myPicture.ShouldItBeShownInThisScreen)
{
MouseButton result = fncIsThisPointInThisRectangle(MyMousestate.X, MyMousestate.Y,
MyMousestate.LeftButton, MyMousestate.RightButton, MyMousestate.MiddleButton,
MyMousestate.ScrollWheelValue, myPicture.rectangleDestination);
if (result.IsThisPointInThisRectangle)
{
if (myPicture.Action == "Button")
{
if (result.LeftClick ==Microsoft.Xna.Framework.Input.ButtonState.Pressed)
{
if (myPicture.MousePictureState == "ControlPressed")
{
myPicture.CurrentSound = 1;
myPicture.MousePictureState = "ControlPressedRepetition";
myPicture.PlayingSound = false;
}
else if (myPicture.MousePictureState == "InControlRepetition")
{
myPicture.MousePictureState = "ControlPressed";
}
}
else if (myPicture.MousePictureState == "OutOfControl")
{
myPicture.CurrentSound = 1;
myPicture.MousePictureState = "InControlForTheFirstTime";
myPicture.PlayingSound = true;
fncPutAWavSoundOnBuffer(1);
}
else if (myPicture.MousePictureState == "InControlForTheFirstTime")
{
myPicture.MousePictureState = "InControlRepetition";
myPicture.PlayingSound = false;
}
else if (result.LeftClick == Microsoft.Xna.Framework.Input.ButtonState.Released)
{
if (myPicture.MousePictureState == "ControlPressedRepetition")
{
myPicture.MousePictureState = "InControlRepetition";
myPicture.CurrentSound = 2;
myPicture.PlayingSound = true;
fncPutAWavSoundOnBuffer(2);
OnPressButton(myPicture.key);
if (isarrlistMypicturesUnderConstruction)
{
isarrlistMypicturesUnderConstruction = false;
return 1000;
}
}
}
}
}
if (!result.IsThisPointInThisRectangle)
{
if (myPicture.Action == "Button")
{
myPicture.MousePictureState = "OutOfControl";
myPicture.PlayingSound = false;
}
}
}
return myreturn;
}
Clicked?
public void OnPressButton(int ButtonKey)
{
switch (ButtonKey)
{
case 0:
{
Dosth();
break;
}
case 1:
{
break;
}
case 2:
{
break;
}
case 3:
{
break;
}
case 4:
{
break;
}
case 5:
{
break;
}
case 6:
{
break;
}
case 7:
{
Dosth();
break;
}
case 8:
{
break;
}
default:
{
break;
}
}
}
Sound Buffer:
Now how to handle sounds, we create a buffer to handle simple sounds, every sound will be load and on it's turn will be played:
public bool songbuffer = false;
public bool soundbuffer = false;
public Song CurrentSong;
public SoundEffect CurrentSound;
public void fncPutAMP3SoundOnBuffer(int code)
{
CurrentSong = content.Load<Song>(GivemeSoundFileNameByCode(code));
songbuffer = true;
}
public void fncPutAWavSoundOnBuffer(int code)
{
CurrentSound = content.Load<SoundEffect>(GivemeSoundFileNameByCode(code));
soundbuffer = true;
}
Let's find if the sound file name is here:
public string GivemeSoundFileNameByCode(int code)
{
string BaseDirectory = ".";
switch (code)
{
case 1:
{
return BaseDirectory + "\\StartPage\\Sounds\\ButtonMouseOverSound";
}
case 2:
{
return BaseDirectory + "\\StartPage\\Sounds\\ButtonClickSound";
}
case 3:
{
return BaseDirectory + "\\AddNewWordsPage1\\Sounds\\mp3PleaseWiteYourWordHere";
}
default:
{
break;
}
}
return "";
}
Our main game update will be something like this:
protected override void Update(GameTime gameTime)
{
if (GamePad.GetState(PlayerIndex.One).Buttons.Back ==
Microsoft.Xna.Framework.Input.ButtonState.Pressed)
this.Exit();
clsMyDefenition.fncEngineMotor();
clsMyDefenition.fncGenerateTime();
PlaySound();
base.Update(gameTime);
}
To play sounds here:
public void PlaySound()
{
if (clsMyDefenition.soundbuffer)
{
clsMyDefenition.CurrentSound.Play();
clsMyDefenition.soundbuffer = false;
}
if (clsMyDefenition.songbuffer)
{
MediaPlayer.Play(clsMyDefenition.CurrentSong);
clsMyDefenition.songbuffer = false;
}
}
This will be our main Drawing
protected override void Draw(GameTime gameTime)
{
GraphicsDevice.Clear(Microsoft.Xna.Framework.Color.Black);
spriteBatch.Begin();
clsMyDefenition.DrawPictures(spriteBatch);
spriteBatch.End();
base.Draw(gameTime);
}
Base of our program:
public Game1()
{
graphics = new GraphicsDeviceManager(this);
graphics.PreferredBackBufferHeight = System.Windows.Forms.Screen.PrimaryScreen.WorkingArea.Height -
System.Windows.Forms.Screen.PrimaryScreen.WorkingArea.Height/10;
graphics.PreferredBackBufferWidth = System.Windows.Forms.Screen.PrimaryScreen.WorkingArea.Width -
System.Windows.Forms.Screen.PrimaryScreen.WorkingArea.Width/10;
graphics.ApplyChanges();
clsMyDefenition.PropertyWindowsScreenHeight = this.Window.ClientBounds.Height;
clsMyDefenition.PropertyWindowsScreenWidth = this.Window.ClientBounds.Width;
Content.RootDirectory = "Content";
clsMyDefenition.PropertyContent = Content;
}
And our main initialization here:
protected override void Initialize()
{
clsMyDefenition.InitializeDefenitions();
this.IsMouseVisible = true;
base.Initialize();
}
Now our Drawing picture Function:
public void DrawPictures(SpriteBatch mybatch)
{
for (int i = 0; i < mypictures.Length; i++)
{
if (mypictures[i].ShouldItBeShownInThisScreen)
{
mybatch.Draw(mypictures[i].Texture, mypictures[i].rectangleDestination,
Microsoft.Xna.Framework.Color.White);
}
}
}
Our Animation engine for label:
public void DoAnimationFrame(ref picture mypicture)
{
if (mypicture.ShouldItBeShownInThisScreen)
{
if (mypicture.HasItAnimation)
{
if (mypicture.IsAnimationOn)
{
if (second % mypicture.FramePerSecond == 0)
{
mypicture.strfilename = createFilename(mypicture.OriginalFilenameWithoutIndex,
ref mypicture, mypicture.TotalAnimationFrame);
mypicture.CurentAnimationFrame++;
}
}
}
}
}
public string createFilename(string OriginalFileName,ref picture mypicture,int TotalAnimationFrame)
{
mypicture.CurentAnimationFrame++;
string tempStr = "";
if (mypicture.CurentAnimationFrame > TotalAnimationFrame) mypicture.CurentAnimationFrame = 1;
tempStr = OriginalFileName + mypicture.CurentAnimationFrame.ToString();
return tempStr;
}
To have the trace of time:
public int second=0;
public int minute = 0;
public int hour=0;
public int day = 0;
public void fncGenerateTime()
{
second++;
if (second == 60)
{
second = 0;
minute++;
}
if (minute == 60)
{
minute = 0;
hour++;
}
if (hour == 24)
{
day++;
}
}
Points of Interest
So it was complete, any shortage in the article would be updated if mentioned.
We saw how to draw buttons, creating mouse events for buttons, how to create some animations for our labels and we
also beeped.
MP3 and wav file type were covered.
Wasn't it fun? Comment!
History
Started it 1/23/2013.
Updated Mouse events on1/29/2013