Moving a figure in console C++ - c++

Im writing a program, which is supposed to print "X' made of ASCII chars in the console, change size and allow to move it with keys. I know how to print this X and change a size, but I'm totally stuck and i don't know how to move it.
#include <iostream>
#include <conio.h>
#include <Windows.h>
void Intro();
void Draw();
const int Esc = 27;
int main()
{
Intro();
Draw();
return 0;
}
void Intro()
{
std::cout << "Napisz program rysowania znakiem ponizszej figury:\n";
std::cout << " * * \n";
std::cout << " * * \n";
std::cout << " * \n";
std::cout << " * * \n";
std::cout << " * * \n";
std::cout << std::endl;
std::cout << "Program powinien umozliwiac:\n"
<< " - Wybor znaku kodu ASII,\n"
<< " - Wczytanie poczatkowych rozmiarow figury,\n"
<< " - Zmiane wielkosci figury klawiszami '+' i '-',\n"
<< " - Przesuwanie figury w czterech kierunkach za pomoca kursorow,\n"
<< " - Ograniczenie przesuwania i rozmiarow figury do obszaru ekranu.\n";
_getch();
return;
}
void Draw()
{
int Size;
char AsciiChar;
char Tab[50][80];
int AsciiCharPosX = 0;
int AsciiCharPosY = 0;
char Key;
system("cls");
std::cout << "Enter the size: ";
std::cin >> Size;
std::cout << std::endl;
std::cout << "Enter the ASCII char from the keyboard: ";
std::cin >> AsciiChar;
std::cout << std::endl;
for (int i = 0; i < Size; i++)
{
for (int j = 0; j < Size; j++)
{
Tab[i][j] = 'e'; // e - empty field
}
}
Tab[AsciiCharPosX][AsciiCharPosY] = 'f'; //f - filled
do
{
system("cls");
for (int Rows = 1; Rows <= Size; Rows++)
{
for (int Cols = 1; Cols <= Size; Cols++)
{
if (Rows == Cols || Cols == (Size + 1) - Rows)
{
Tab[Rows][Cols] = 'f';
if (Tab[Rows][Cols] == 'f')
{
std::cout << AsciiChar;
}
}
else
{
Tab[Rows][Cols] = 'e';
if (Tab[Rows][Cols] == 'e')
{
std::cout << " ";
}
}
}
std::cout << std::endl;
}
Key = _getch();
switch (Key)
{
case '+':
{
Size = Size + 2;
break;
}
case '-':
{
Size = Size - 2;
break;
}
case 's':
{
AsciiCharPosY++;
break;
}
case 'w':
{
AsciiCharPosY--;
break;
}
case 'a':
{
AsciiCharPosX--;
break;
}
case 'd':
{
AsciiCharPosX++;
break;
}
}
} while (Key != Esc);
return;
}

To move it you will need to follow one of 2 aproaches:
Console control
Write code that can send special characters that the console picks up to mean special things like move cursor or change color etc. The most common way is tu use a library for this, like libncurses. Please note that this depends greatly on the console you are using, and sxo you need to find which code or library to use based on that.
Faking it
You can fake it by simply rewriting the whole screen-full of text while incorporating the changes you want and hope your victim (user) does not scroll upward to see what is going on.
In both cases, you will need to write out changes in steps (frames) and you will benefit by knowing about animation.
Good luck!

Related

Automate nested Loops in C++

I just got started with C++ and I'm currently trying to build an algorith that cracks passwords. I ran into a problem with nested loops for longer passwords. It currently works fine for 4 character passwords, I have to wait for a while, but it works. Is there a way to get rid of the hard coded nested loops, to make the algorithm work for more than for characters without having to copy and paste the if statements over and over again?
#include <iostream>
#include <string>
#include <ctime>
using namespace std;
const char alphanum[] = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789!##$%^&* ";
const string pw = "0000";
bool cracked = false;
int tries = 0;
const int pwLength = pw.length();
string crack();
string guess="0";
const int maxLen = 30;
int main()
{
clock_t begin, end;
double time;
begin = clock();
string crackedPassword = crack();
end = clock();
time = double(end - begin) / (double)CLOCKS_PER_SEC;
cout << "The password is: " << crackedPassword << " The program checked a total of " << tries << " possibilites and took " << time << " seconds to crack the password!";
return 0;
}
string crack() {
int index = 0;
int repeat = 0;
while (!cracked) {
for (int i = 0; i < 71; i++) {
tries++;
guess[index] = alphanum[i];
cout << "Trying: " << guess << endl;
if (repeat > 0) {
for (int i = 0; i < 71; i++) {
tries++;
guess.push_back(alphanum[i]);
cout << "Trying: " << guess << endl;
if (repeat > 1) {
for (int i = 0; i < 71; i++) {
tries++;
guess.push_back(alphanum[i]);
cout << "Trying: " << guess << endl;
if (repeat > 2) {
for (int i = 0; i < 71; i++) {
tries++;
guess.push_back(alphanum[i]);
cout << "Trying: " << guess << endl;
if (guess == pw) {
cracked = true;
break;
}
else {
guess.pop_back();
}
}
}
if (guess == pw) {
cracked = true;
break;
}
else {
guess.pop_back();
}
}
}
if (guess == pw) {
cracked = true;
break;
}
else {
guess.pop_back();
}
}
}
if (guess == pw) {
cracked = true;
break;
}
}
repeat++;
}
return guess;
}

Storing the names and address of people from a file into strings and later on printing them in alphabetic (from the surname)

In the file a1.txt, there are ames of people and their addresses. I am thinking of storing them in strings and then comparing and printing them in alphabetic order. Here is how the information in the file looks:
Kitty Garfield
36 Jon Havey Court, Middle, MO 66222
Bill Lake
21 Ritts, Middletown, MI 48788
...The list continues
I think I have included everything in the my code shown below but the function does not run.
I am using Microsoft Visual Studio and CodeBlocks.
Here is the code:
#include <math.h>
#include <time.h>
#include <string.h>
#include <stdio.h>
#include <stdlib.h>
using namespace std;
struct person
{
string name;
string address;
};
int getWhatTheyWant();
void displayPeople();
void addPerson();
void searchByLastName();
void printAllSearchedAndFoundPeople();
int main()
{
int whatTheyWant;
do
{
whatTheyWant = getWhatTheyWant();
switch (whatTheyWant)
{
case 1:
displayPeople();
break;
case 2:
addPerson();
break;
case 3:
searchByLastName();
break;
case 4:
printAllSearchedAndFoundPeople();
break;
case 5: //just not to print the cout statement after
break;
default:
cout << "Please enter something valid" << endl;
}
} while (whatTheyWant != 5);
cout << endl << endl;
system("PAUSE");
return(0);
}
//display
int getWhatTheyWant()
{
int choice;
cout << "1-Print people in the alphabetic order" << endl;
cout << "2- If you want to add people" << endl;
cout << "3-Search by last name" << endl;
cout << "4-Print all the peope who are searched and found" << endl;
cout << "5- Exit the program" << endl;
cin >> choice;
return(choice);
}
//printing the people
void displayPeople()
{
ifstream theFile("a1.txt");
if (theFile.is_open())
{
person x[6];
string justToGetFromFile;
string *temporary;
temporary = new string[12];
int whereFirstLetterOfSurnameIs[6];
char whatIsTheFirstLetterOfSurname[6];
for (int i = 0; i < 12; i++)
{
getline(theFile, justToGetFromFile);
temporary[i] = justToGetFromFile;
}
theFile.close();
for (int i = 0; i < 6; i++)
{
x[i].name = temporary[2 * i];
x[i].address = temporary[2 * i + 1];
}
for (int i = 0; i < 6; i++)
{
whereFirstLetterOfSurnameIs[i] = x[i].name.find(" ", 0) + 1;
whatIsTheFirstLetterOfSurname[i] = x[i].name.at(whereFirstLetterOfSurnameIs[i]);
}
for (int j = 1; j < 6; j++)
{
for (int k = 0; k < 6; k++)
{
if (whatIsTheFirstLetterOfSurname[j - 1] > whatIsTheFirstLetterOfSurname[j])//comparison as the letters are numbers
{
person temp;
temp = x[j];
x[j] = x[j - 1];
x[j - 1] = temp;
}
}
}
for (int i = 0; i < 6; i++)
{
cout << x[i].name << endl << x[i].address << endl << endl;
}
}
else
{
cout << "you messed it up" << endl;
}
}
void addPerson()
{
}
void searchByLastName()
{
}
void printAllSearchedAndFoundPeople()
{
}

Visual Studio C++ | Program crashes everytime I try to loop a cout from an array of [80]x[80]

Basically I've been playing a little with C++ and I am doing an exercise from this website called "Graduation".
So far I've been doing good for a beginner but here's my first problem which I have been struggling for the last hours and I can't find a solution online.
I am using 2 strings of arrays, one 80x80 for the map and one 100x20 for all the existing bunnies. I am putting all the data together in one string like SEX|COLOR|AGE|COORDINATES|NAME. So to extract each piece of the grid I always use 2 for functions to run throughout all the array and cut for example the 2nd character so I can know the color of each bunny in the array.
It worked fine when I used it to discover the sex of each bunny in the array but I am trying to do the same for the color and it isn't working. My program keeps crashing with the error screen I left in the screenshot I uploaded.
Heres the code:
Main.cpp
#include <iostream>
#include "Add.h"
#include "GetNames.h"
#include <string>
#include "PlaceOnMap.h"
#include "Colours.h"
using namespace std;
int start = 1;
int main()
{
while (start == 1)
{
Add(5);
PlaceOnMap(bunniestotal);
Colour();
start = 0;
}
system("pause");
return 0;
}
Add.h
#pragma once
#include <iostream>
#include <time.h>
#include <stdlib.h>
#include <string>
#include <windows.h>
#include "GetNames.h"
using namespace std;
int colours;
int cB, rB;
int bunnies = 0;
int bunniestotal = 0;
int sex = 0;
int h = 0;
string listB[10][100];
void Add(int x)
{
srand(time(NULL));
/***********************************************************************************************/
while (h < 1) {
for (int rB = 0; rB < 10; rB++) //DO THE SLOTS FOR THE BUNNIES
{
for (int cB = 0; cB < 100; cB++)
{
listB[rB][cB] = "-";
}
}
h = 1;
}
/***********************************************************************************************/
while (bunnies < x) //CHOOSE RANDOM SLOTS FOR BUNNIES
{
rB = rand() % 10;
cB = rand() % 100;
if (listB[rB][cB] == "-")
{
listB[rB][cB] = "B";
bunnies++;
}
}
bunniestotal = bunniestotal + bunnies;
bunnies = 0;
/***********************************************************************************************/
for (int rB = 0; rB < 10; rB++) //SET SEX AND COLOUR
{
for (int cB = 0; cB < 100; cB++)
{
if (listB[rB][cB] == "B")
{
sex = rand() % 2 + 1;
//cout << sex << endl;
if (sex == 1)
{
colours = rand() % 4 + 1;
switch (colours)
{
case 1: listB[rB][cB] = "mR";
break;
case 2: listB[rB][cB] = "mY";
break;
case 3: listB[rB][cB] = "mC";
break;
case 4: listB[rB][cB] = "mB";
break;
}
listB[rB][cB] = listB[rB][cB] + "0";
//cut = listB[rB][cB].substr(0, 1);
//cout << listB[rB][cB] << "Cut - " << cut << endl;
//listB[rB][cB] = listB[rB][cB] + GetNames("M") + " ";
//cout << listB[rB][cB] << endl;
//listB[rB][cB] = listB[rB][cB] + GetNames("M");
//cout << listB[rB][cB] << endl;
}
else if (sex == 2)
{
colours = rand() % 4 + 1;
switch (colours)
{
case 1: listB[rB][cB] = "fR";
break;
case 2: listB[rB][cB] = "fY";
break;
case 3: listB[rB][cB] = "fC";
break;
case 4: listB[rB][cB] = "fB";
break;
}
listB[rB][cB] = listB[rB][cB] + "0";
//cut = listB[rB][cB].substr(0, 1);
//cout << listB[rB][cB] << "Cut - " << cut << endl;
//cout << rB << " " << cB << endl;
//listB[rB][cB] = listB[rB][cB]+GetNames("F") + " ";
//cout << listB[rB][cB] << endl;
//listB[rB][cB] = listB[rB][cB] + GetNames("F");
//cout << listB[rB][cB] << endl;
}
}
}
}
}
PlaceOnMap.h
#pragma once
#include <iostream>
#include "Add.h"
#include <string>
#include <sstream>
#include <Windows.h>
#include "Colours.h"
using namespace std;
string map[80][80];
string cut;
ostringstream join;
ostringstream join1;
int xB, yB;
int hh = 0;
int capslock;
int y = 0;
int z = 0;
int u, o;
void PlaceOnMap(int bunniesn)
{
HANDLE color = GetStdHandle(STD_OUTPUT_HANDLE);
//cout << "PlaceOnMap " << listB[rB][cB] << endl;
//cout << rB << " " << cB << endl;
//cut = listB[rB][cB].substr(0, 1);
//cout << cut << endl;
/***********************************************************/
while (hh < 1)
{
for (int xB = 0; xB < 80; xB++) // CREATE MAP
{
for (int yB = 0; yB < 80; yB++)
{
map[xB][yB] = "-";
}
}
hh = 1;
}
/***********************************************************/
//cout << bunniesn << endl;
//cout << rB << endl;
//cout << cB << endl;
for (y = 0; y < 10; y++)
{
for (z = 0; z < 100; z++)
{
nextone:
if (listB[y][z].length() < 4) //DOESN'T LET BUNNIES THAT ARE ALREADY PLACED ENTER THIS LOOP
{
//cout << y << " " << z << endl;
cut = listB[y][z].substr(0, 1); //CUTS THE STRING IN ORDER TO KNOW IF IT IS A FEMALE OR A MALE
if (cut == "f" || cut == "m")
{
if (cut == "f")
{
capslock = 1;
}
else if (cut == "m")
{
capslock = 2;
}
generate:
xB = rand() % 80;
yB = rand() % 80;
if (map[xB][yB] == "-")
{
//cout << "Found a slot!" << endl;
//Sleep(2000);
//join << xB;
//join1 << yB;
listB[y][z] += to_string(xB);
listB[y][z] += to_string(yB);
//cout << "Size - " << listB[y][z].length() << endl;
if (listB[y][z].length() == 5)
{
listB[y][z] = listB[y][z] + " ";
listB[y][z] = listB[y][z] + " ";
}
else if (listB[y][z].length() == 6)
{
listB[y][z] = listB[y][z] + " ";
}
cout << listB[y][z] << endl;
//Sleep(6000);
if (capslock == 1)
{
map[xB][yB] = "f";
}
else if (capslock == 2)
{
map[xB][yB] = "m";
}
z++;
x++;
//cout << x << endl;
//Sleep(3000);
if (x < bunniesn)
{
goto nextone;
}
else
{
goto done;
}
}
else
{
goto generate;
}
}
}
}
}
done:
cout << "All done" << endl;
SetConsoleTextAttribute(color, 15);
}
Colours.h (Where the problem is happening!!)
#pragma once
#include <iostream>
#include "PlaceOnMap.h"
#include <string>
#include "Add.h"
using namespace std;
string wordString;
int t, r;
void Colour()
{
for (t = 0; t < 20; t++)
{
for (r = 0; r < 100; r++)
{
wordString = listB[t][r].substr(1, 2); //CUTS THE STRING IN ORDER TO KNOW ITS COLOR
//cout << wordString << " ";
if (wordString == "R")
{
cout << "GOT RED" << endl;
}
else if (wordString == "C")
{
cout << "GOT CYAN" << endl;
}
else if (wordString == "B")
{
cout << "GOT BLUE" << endl;
}
else if (wordString == "Y")
{
cout << "GOT YELLOW" << endl;
}
}
cout << endl;
}
}
If it is something really dumb I am sorry! Kinda noob but just trying to learn more and more! :) If you need any more info feel free to ask for!
Thank you.
In Colours.h, change for (t = 0; t < 20; t++) to for (t = 0; t < 10; t++). You only have 10 subarrays allocated, so you were going outside the bounds of the array.
From quickly looking through your code:
You defined:
string listB[10][100];
And you iterate the first index up to 20 in Colours.h:
for (t = 0; t < 20; t++)
Which works for:
listB[0][r];
listB[1][r];
listB[2][r];
listB[3][r];
listB[4][r];
listB[5][r];
listB[6][r];
listB[7][r];
listB[8][r];
listB[9][r];
And then you try accessing
listB[10][r]
which is the 11th index and not allocated.
If you redefined it somewhere and I missed I am sorry.

Easy C++ = array length and reverse WITHOUT <string>

I can't seem to get my array's length or to print backwards! ANY HELP PLEASE?!
the functions on the bottom for void GetStringLenght and Print Backwards aren't working
#include <iostream>
void ReadString(char* c, int maxLength);
void GetStringLength(char* c, int* length);
void PrintString(char* const c);
void PrintStringBackwards(char* const c);
int main()
{
const int SIZE = 50;
char ca[SIZE];
char* pc = ca;
int fPrints = 0;
int bPrints = 0;
int lengthChecks = 0;
char selection = 'z';
while (selection != 'Q') {
std::cout << "\n[ 1] Test ReadString\n";
std::cout << "[ 2] Test GetStringLength\n";
std::cout << "[ 3] Test PrintString\n";
std::cout << "[ 4] Test PrintStringBackwards\n";
std::cout << "[Q] Quit\n";
std::cout << "Selection: ";
std::cin >> selection;
std::cin.ignore();
std::cout << std::endl;
switch (selection) {
//Test ReadString
case '1':
ReadString(pc, SIZE);
break;
//Test GetStringLength
case '2': {
lengthChecks += 1;
int length = 0;
GetStringLength(pc, &length);
std::cout << "Length[" << lengthChecks << "]=" << length << std::endl;
break;
}
//Test PrintString
case '3':
fPrints += 1;
std::cout << "Foward[" << fPrints << "]=";
PrintString(pc);
std::cout << std::endl;
break;
//[ 4] Test PrintStringBackwards
case '4':
bPrints += 1;
std::cout << "Backwards[" << bPrints << "]=";
PrintStringBackwards(pc);
std::cout << std::endl;
break;
case 'Q':
break;
default:
break;
} //end switch
} //end while
std::cout << "Press ENTER";
std::cin.get();
return 0;
}
void ReadString(char* c, int maxLength)
{
std::cout << "Enter a string less than " << maxLength << " characters." << std::endl;
std::cin.getline(c, maxLength, '\n');
}
//BELOW THIS DOESNT WORK EITHER///
//////////////////////////////////////////
void GetStringLength(char* c, int* length)
{
for (int i = 0; i < *length; i++) {
if (c[i] == '\0')
*length = i - 1;
}
}
void PrintString(char* const c)
{
int counter = 0;
for (int i = 0; i < 100; i++) {
if (c[i] == '\0') {
counter = i;
break;
} //end if
} //end for
for (int j = 0; j < counter; j++) {
std::cout << c[j];
if (j == counter)
std::cout << '\0';
} //end for
std::cout << std::endl;
} //end void
void PrintStringBackwards(char* const c)
{
//this is where I’m lost! I’ve tried 25 different ways and everything is error.
}
Consider for (int i = 0; i < *length; i++) where both i and *length are 0, as in your case... will that loop ever execute? Nope... Consider a loop that starts with x set to 0 and return x; when str[x] is '\0'. i.e. the loop in strlen does this.
As for printing backwards, start at the highest index (returned by strlen or your function once fixed) and decrement until you reach 0, printing the characters at those offsets as you go.
strlen is available in <cstring>, by the way, not just <string>... and as it is a mandatory function it'll always be part of any C++ implementation. You should probably just use strlen...
To get a C string (char*)'s length you can use strlen(...).
To print backwards, do:
for(int i = strlen(str) - 1; i >= 0; --i)
std::cout << str[i];

Mastermind string cout issue

Ok I have been struggling with this code and I think I have it written out right but here is the rules from my teacher
1 = implies right Number, Right Place.
2 = implies right Number, Wrong Place.
0 = implies Wrong Number.
So the computer decides on 12345; the user guesses 11235; the computer should respond with 10221. Hint: Watch out for a double number like 11 when there is only one.
I have it where it does all of that except I can not get it to show a 0 when it is wrong can you please help me every single part is written except that part here is my code
// Programming 2
// Mastermind
#include "stdafx.h"
#include <iostream>
#include <ctime>
#include <cstdlib>
#include <string>
using namespace std;
struct fields{//the list of variables used in my program
int size = 5;;
int range = 9;
char lowest = '0';
string guess;
string answer;
int number;
int correct;
int position;
bool gameover = false;
};
void gameplay(fields & info);//declaring the function
int main()
{
fields game;
gameplay(game);//calling the function
system("pause");
return 0;
}
void gameplay(fields & info){//calling the structure into the function
srand(time(0));//to randomize number
info.answer = "";//getting the number
for (int i = 0; i < info.size; i++)
{
char ch = info.lowest + rand() % info.range;
info.answer += ch;
}
info.number = 1;
info.correct = 0;
info.position = 0;
while (!info.gameover)//using a while loop to let them go until they guess it
{
cout << "Guess #" << info.number << ": Enter 5 numbers that are '0' through '9': ";//asking them to guess
cout << info.answer;
cout << "\n";
cin >> info.guess;
if (info.guess == info.answer)//if the guess is right this will end the game
{
cout << "Right! It took you " << info.number << " move";
if (info.number != 1) cout << "s";
cout << "." << endl;
info.gameover = true;
}
int correctNumbers = 0;
for (char const &ch : info.guess) //seeing if there are numebrs in the guess that is in the answer
{
if (info.answer.find(ch) != string::npos)
{
++correctNumbers;
}
}
int const digits = 5;
int correctPositions = 0;
int correctPosition[digits];
int test = 0;
for (int i = 0; i < digits; ++i)//telling which numbers is correct and displaying the 2 or 0 for number is correct or number is wrong
{
if (info.answer[i] == info.guess[i])
{
++correctPositions;
}
if (info.answer[i] == info.guess[i]){
correctPosition[i] = 2;
cout << correctPosition[i];
}
if (correctPosition[i] != 2){
correctPosition[i] = 1;
cout << correctPosition[i];
}
if (correctPosition[i] != 2 && correctPosition[i] != 1)){
correctPosition[i] = 0;
cout << correctPosition[i];
}
}
cout << "\nYou have " << correctPositions << " numbers in the correct position " <<endl;
cout << "You have " << correctNumbers <<" correct numbers in the wrong position"<< endl;
}
cout << "GAME OVER\n\n";
}