Hi. I am making a game in 2d, but will look 3D. So when i'm doing this i want to use the SFML Scale function, but it seems like it shrinks both the bottom and the top, so when i walk inwards or outwards with the character he walks too fast because his feet are moved up / down (inwards / outwards). So i did this:
float characterHeightLastFrame = Character.GetSize().y;
//Set Scale
Character.SetScale(character.y / screenHeight, character.y / screenHeight);
characterWidth = Character.GetSize().x;
characterHeight = Character.GetSize().y;
//Adjustment for scaling
if (moveUp == true)
character.y += (characterHeightLastFrame - characterHeight) * 0.5;
else if (moveDown == true)
character.y -= (characterHeight - characterHeightLastFrame) * 0.5;
That was better, but he walks faster down (outwards), than inwards. So i tried this:
//Adjustment for scaling
if (moveUp == true)
character.y += (characterHeightLastFrame - characterHeight) * 0.2;
else if (moveDown == true)
character.y -= (characterHeight - characterHeightLastFrame) * 0.8;
Then it looks better, but does anyone have any idea why it is like this, and any exact numbers on how much it scales each direction? (Prefferably math i can understand, like my 0.2 / 0.
, and maybe the X axis aswell.
Thanks for your time.
Edit: the more i think about this the less i understand it and i probably did it the wrong way trying to solve it, i hope you can help me with it. Also i guess this line is important since it sets the speed.
//Speed of character
character.speed = 1 * Character.GetPosition().y / screenHeight;
Full code:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <SFML/Graphics.hpp>
#include <SFML/System.hpp>
struct sSlot{
int xMin;
int xMax;
int yMin;
int yMax;
int itemNumber;
};
struct sCharacter{
float x;
float y;
int xCenter;
int yCenter;
float stepX;
float stepY;
float speed;
};
sCharacter character;
void moveIconsInSlots(int a, int bX, int bY,
sf::Sprite *inventoryIcon){
for (int d = 0; d<=15; d++){
if (a == d)
inventoryIcon[d].SetPosition(bX, bY);
}
}
int main(int argc, char** argv)
{
sf::WindowSettings Settings;
Settings.DepthBits = 24; // Request a 24 bits depth buffer
Settings.StencilBits = 8; // Request a 8 bits stencil buffer
Settings.AntialiasingLevel = 2; // Request 2 levels of antialiasing
//Create the Window
sf::RenderWindow App(sf::VideoMode(1280, 1024, 32), "SFML Game", sf::Style::Fullscreen, Settings);
// Limit FPS
App.SetFramerateLimit(0);
//Vertical sync
App.UseVerticalSync(true);
//Load Images
sf::Image Image[5];
if (!Image[0].LoadFromFile("Background.png"))
return 0;
sf::Sprite background;
background.SetImage(Image[0]);
if (!Image[1].LoadFromFile("InventoryBag.png"))
return 0;
sf::Sprite inventoryBag;
inventoryBag.SetImage(Image[1]);
if (!Image[2].LoadFromFile("character.png"))
return 0;
sf::Sprite Character;
Character.SetImage(Image[2]);
if (!Image[3].LoadFromFile("InventoryIcons.png"))
return 0;
sf::Sprite inventoryIcon[16];
for (int i = 0; i<=15; i++){
inventoryIcon[i].SetImage(Image[3]);
}
//Set Rects in inventoryIcon Images
int numItemRows = 4;
int numItemCols = 4;
int iconWidth = 79;
int iconHeight = 79;
int icon = 0;
for (int colk = 0; colk < numItemCols; colk++){
for (int rowk = 0; rowk < numItemRows; rowk++) {
int iconLeft = rowk *(iconWidth + 1);
int iconTop = colk *(iconHeight + 1);
int iconRight = iconLeft + iconWidth;
int iconBottom = iconTop + iconHeight;
inventoryIcon[icon].SetSubRect(sf::IntRect(iconLeft,iconTop,iconRight,iconBottom));
icon += 1;
}
}
//Set invisible color
sf::Color ColorKey(255, 0, 255, 255);
for (int i = 0; i<=4; i++){
Image[i].CreateMaskFromColor(ColorKey, 0);
}
// Get the backgrounds dimensions
int screenWidth = background.GetSize().x;
int screenHeight = background.GetSize().y;
// Get the Characters dimensions
int characterWidth = Character.GetSize().x;
int characterHeight = Character.GetSize().y;
//Set Positions
inventoryBag.SetPosition(screenWidth - 521, screenHeight - 431);
character.x = screenWidth / 2 - characterWidth / 2;
character.y = screenHeight - characterHeight;
//Inventory Slots
sSlot Slot[16]=
{
{921, 1000, 673, 752, 0},
{1004, 1083, 673, 752, 1},
{1087, 1166, 673, 752, 2},
{1170, 1249, 673, 752, 3},
{921, 1000, 756, 835, 4},
{1004, 1083, 756, 835, 5},
{1087, 1166, 756, 835, 6},
{1170, 1249, 756, 835, -1},
{921, 1000, 839, 918, -1},
{1004, 1083, 839, 918, -1},
{1087, 1166, 839, 918, -1},
{1170, 1249, 839, 918, -1},
{921, 1000, 922, 1001, -1},
{1004, 1083, 922, 1001, -1},
{1087, 1166, 922, 1001, -1},
{1170, 1249, 922, 1001, -1}
};
bool inventory = false;
int ax;
int ay;
int itemOnMouse = -1;
int mousePos;
int dragFromSlot;
int a = 0;
int bX = 0;
int bY = 0;
bool mouseOnInventory = false;
float moveToX = character.x + characterWidth / 2;
float moveToY = character.y + characterHeight;
bool movement = false;
float rangeX = 1;
float rangeY = 1;
bool animationStanding = true;
bool animationLeft = false;
bool animationRight = false;
bool animationUp = false;
bool animationDown = false;
bool animationUpLeft = false;
bool animationUpRight = false;
bool animationDownLeft = false;
bool animationDownRight = false;
bool moveLeft = false;
bool moveRight = false;
bool moveUp = false;
bool moveDown = false;
while (App.IsOpened())
{
sf::Event Event;
while (App.GetEvent(Event))
{
// Window closed
if (Event.Type == sf::Event::Closed)
App.Close();
// Key Pressed
if (Event.Type == sf::Event::KeyPressed){
//Quit
if (Event.Key.Code == sf::Key::Escape)
App.Close();
//Screenshot
if (Event.Key.Code == sf::Key::F12){
sf::Image Screen = App.Capture();
Screen.SaveToFile("screenshot.jpg");
}
//Inventory Toggle
if (Event.Key.Code == sf::Key::I){
if (inventory == false)
inventory = true;
else if (inventory == true)
inventory = false;
}
}
}
const sf::Input& Input = App.GetInput();
int mouseX = Input.GetMouseX();
int mouseY = Input.GetMouseY();
bool leftButtonDown = Input.IsMouseButtonDown(sf::Mouse::Left);
if (inventory == true){
//Position Determination
mousePos = -1;
for (int i=0; i<=15; i++){
if (mouseX >= Slot[i].xMin && mouseX <= Slot[i].xMax && mouseY >= Slot[i].yMin && mouseY <= Slot[i].yMax)
mousePos = i;
}
//Item Placing
//Lift item
if (leftButtonDown == true && itemOnMouse == -1 && mousePos != -1){
dragFromSlot = mousePos;
itemOnMouse = Slot[mousePos].itemNumber;
Slot[mousePos].itemNumber = -1;
}
//Item on drop position to start position
if (leftButtonDown == false && itemOnMouse != -1 && mousePos != -1){
Slot[dragFromSlot].itemNumber = Slot[mousePos].itemNumber;;
}
//Drop item
if (leftButtonDown == false && itemOnMouse != -1){
if (mousePos != -1)
Slot[mousePos].itemNumber = itemOnMouse;
else if (mousePos == -1)
Slot[dragFromSlot].itemNumber = itemOnMouse;
itemOnMouse = -1;
}
}
//Icons Position
for (int i = 0; i<=15; i++){
moveIconsInSlots(Slot[i].itemNumber, Slot[i].xMin, Slot[i].yMin,
inventoryIcon);
}
if (itemOnMouse != -1)
inventoryIcon[itemOnMouse].SetPosition(mouseX, mouseY);
// #################### END OF INVENTORY CODE ####################
// #################### MOVEMENT CODE ####################
//Speed of character
character.speed = 1 * Character.GetPosition().y / screenHeight;
//Mouse on Inventory?
if (inventory == true && mouseX >= inventoryBag.GetPosition().x + 100 &&
mouseY >= inventoryBag.GetPosition().y)
mouseOnInventory = true;
else
mouseOnInventory = false;
// Movement Calculations
//Toggle Movement
if (leftButtonDown == true && mouseOnInventory == false && itemOnMouse == -1){
moveToX = mouseX;
moveToY = mouseY;
}
//Set Center of Character
character.xCenter = character.x + characterWidth / 2;
character.yCenter = character.y + characterHeight / 2;
if (character.xCenter != moveToX || (character.y + characterHeight) != moveToY)
movement = true;
else
movement = false;
if (movement == true){
animationStanding = false;
//Movement Direction Left/Right
if (moveToX < character.xCenter)
moveLeft = true;
else
moveLeft = false;
if (moveToX > character.xCenter)
moveRight = true;
else
moveRight = false;
//Movement Direction Up/Down
if (moveToY < (character.y + characterHeight))
moveUp = true;
else
moveUp = false;
if (moveToY > (character.y + characterHeight))
moveDown = true;
else
moveDown = false;
if (leftButtonDown == true){
//Range to end Pos
if (moveLeft == true)
rangeX = character.xCenter - moveToX;
else if (moveRight == true)
rangeX = moveToX - character.xCenter;
if (moveUp == true)
rangeY = (character.y + characterHeight) - moveToY;
else if (moveDown == true)
rangeY = moveToY - (character.y + characterHeight);
}
//Character Step
character.stepX = rangeX / (rangeX + rangeY) * 16 * character.speed;
character.stepY = rangeY / (rangeX + rangeY) * 16 * character.speed;
}
else
animationStanding = true;
float characterHeightLastFrame = Character.GetSize().y;
//Set Scale
Character.SetScale(character.y / screenHeight, character.y / screenHeight);
characterWidth = Character.GetSize().x;
characterHeight = Character.GetSize().y;
//Adjustment for scaling
if (moveUp == true)
character.y += (characterHeightLastFrame - characterHeight) * 0.0;
else if (moveDown == true)
character.y -= (characterHeight - characterHeightLastFrame) * 1.0;
//From struct to drawable
Character.SetPosition(character.x, character.y);
//Background
App.Draw(background);
//Character
App.Draw(Character);
if (inventory == true){
//Inventory
App.Draw(inventoryBag);
//Icons in slots
for (int i = 0; i<=15; i++){
if (Slot[0].itemNumber == i || Slot[1].itemNumber == i || Slot[2].itemNumber == i || Slot[3].itemNumber == i ||
Slot[4].itemNumber == i || Slot[5].itemNumber == i || Slot[6].itemNumber == i || Slot[7].itemNumber == i ||
Slot[8].itemNumber == i || Slot[9].itemNumber == i || Slot[10].itemNumber == i || Slot[11].itemNumber == i ||
Slot[12].itemNumber == i || Slot[13].itemNumber == i || Slot[14].itemNumber == i || Slot[15].itemNumber == i)
App.Draw(inventoryIcon[i]);
}
}
//Icons on mouse
if (itemOnMouse != -1)
App.Draw(inventoryIcon[itemOnMouse]);
App.Display();
}
return 0;
}