User Tools

Site Tools


tutorial:input

====== Input ====== [[tutorial:index|Tutorial index]] ==== Introduction ==== In this tutorial we will add input support to our game. The input framework binds keyboard keys, mouse buttons and joystick buttons to input states to make different input configurations possible. You can download the source for this tutorial {{:tutorial:downloads:05_input.zip|here}}. ==== Create the input ==== First step is to include phxInput unit under the uses section. <code pascal> uses ... // Input framework phxInput; </code> Then we create the input variable as well as a variable that contains the current player position. <code pascal> TGame = class(TPHXApplication) private Device: TPHXDevice; Timer : TPHXTimer; Canvas: TPHXCanvas; Images: TPHXImageList; Input : TPHXInput; PlayerPosition: TVector2f; public procedure Init; override; procedure Update; override; procedure Render; override; procedure Shutdown; override; end; </code> Next is to create a instance of the input class and initialize the player position variable. <code pascal> procedure TGame.Init; ... // Create the input Input:= TPHXInput.Create; // Reset the player position PlayerPosition.X:= 200; PlayerPosition.Y:= 200; end; </code> ==== Updating the input ==== Add a call to the inputs [[http://phoenixlib.net/api/phxInput.TPHXInput.html#Update|Update]] function, this updates all bindings and states of the added devices. <code pascal> procedure TGame.Update; begin // Update the device Device.Update; // Update the timer Timer.Update; // Update the input Input.Update; end; </code> ==== Detecting input ==== To detect if a button is pressed we have to check if the input state is set in the [[http://phoenixlib.net/api/phxInput.TPHXInput.html#States|States]] property of the input. <code pascal> procedure TGame.Update; begin // Update the device Device.Update; // Update the timer Timer.Update; // Update the input Input.Update; if isLeft in Input.States then begin // Move the player to the left with a velocity of 200 pixels per second PlayerPosition.X:= PlayerPosition.X - 200 * Timer.FrameTime; end; if isRight in Input.States then begin // Move the player to the left with a velocity of 200 pixels per second PlayerPosition.X:= PlayerPosition.X + 200 * Timer.FrameTime; end; end; </code> It is also possible to check for a specific key even if its not bound to a state. <code pascal> // Check the keyboard for a key if Input.Keyboard[VK_TAB] then begin PlayerPosition.X:= Input.Mouse.X; PlayerPosition.Y:= Input.Mouse.Y; end; </code> This code moves the player to the position of the mouse while TAB is pressed. ==== Modifying the render method ==== Modify the rendering method to only draw the player. <code pascal> procedure TGame.Render; begin // Clear the back buffer Device.Clear; // Draw the image using the image index and pattern index Images[0].Draw(PlayerPosition.X, PlayerPosition.Y, 0); // Flush the canvas Canvas.Flush; // Flip the front and back buffers to show the scene Device.Flip; end; </code> When running the application you should be able to move the player left and right ==== Detecting input from a single device ==== Normally when checking if the input has a state we are testing all devices that has that input binding, to check if a single device has a state we have to check that device's state instead <code pascal> // Detect if the isButton1 state is set for the mouse device if isButton1 in Input.Mouse.States then begin // Do something when the left mouse button is pressed end; </code> ==== Trigger once ==== It is also possible to only trigger a action once every time a button is pressed, to do this we just have to remove the wanted input state from the [[http://phoenixlib.net/api/phxInput.TPHXInput.html#States|States]] property of the input or device. <code pascal> // Only perform a action when a button is pressed if isButton1 in Input.States then begin // TODO: Fire bullet // Remove the state Input.States:= Input.States - [isButton1]; end; </code> You can use the same method to remove a input state from a single device ==== Rebinding keys ==== To rebind a key we first have to remove all bound keys from the bindings and then add the new ones. The code snippet below shows how that's done <code pascal> // Remove all bindings from a state Input.Bindings.Remove(isButton3); // Bind a key to a state Input.Bindings.Add(isButton3, VK_F2); </code> It is possible to load and save the input bindings to a text file <code pascal> // Save the bindings to a file Input.SaveBindings('input.txt'); // Load the bindings from a file Input.LoadBindings('input.txt'); </code> The file looks like the following, first is the input state then the device and shortcut. <code> isLeft=1,285 isLeft=1,97 isLeft=1,306 isRight=1,286 isRight=1,100 isRight=1,308 </code> [[tutorial:index|Back to tutorial index]]

tutorial/input.txt · Last modified: 2013/08/17 12:27 by amnoxx