Clearing the Console in C++ - c++

I am trying to clear the console in C++. I know printing a number of newlines is a bad practice, as it can be slow and is not always reliable to completely clear the console window, but I have researched multiple options and have found almost no other solutions besides system("cls"), which is an even worse option.
Essentially, I have used the line cout << string(100, '\n'); but I am getting a near-unidentifiable error when I try to run the program.
error C2679: binary '<<' : no operator found which takes a right-hand operand of type 'std::basic_string<_Elem,_Traits,_Ax>' (or there is no acceptable conversion)
I have also researched this, and found that most explanations were too complicated for me as a beginning C++ programmer to understand, or completely unrelated to my problem.
My questions are (1) is there a way to fix this error, and (2) could there be a better, cross-platform way of clearing the console other than printing 100 newlines?
I also heard of Console.clear(), but I'm unsure if this is cross-platform. From what I've seen, it looks more like a Windows command. I've also heard of the curses library, which I was willing to research and use, until I read somewhere that it was not recommended to use the functions which I am familiar with coupled with the curses library functions.
Thank you in advance!

About your error... you have to...
#include <iostream>
#include <string>
using namespace std;
If you are using just windows use windows console API.
If you are using a linux\unix terminal, use escape codes.
You can do a #if to choose between the two methods.
On linux\unix use the write function defined in in this way:
write(1,"\E[H\E[2J",7); // we use ANSI escape sequences here.
Here is the microsoft page that explain how to do that.
http://support.microsoft.com/kb/99261
The really bad console api microsoft use for the console always makes me angry :) why 100 lines of code to clear a screen? :)
Now the if... you should create a clearscreen.h file and a clearscreen.cpp file.
In clearscreen.h we just put our function.
void clearconsole();
In clearscreen.cpp we put our code for both operative systems
#ifdef _WIN32 || _WIN64
#include <windows.h>
void clearconsole()
{
...
// 100 lines of codes copied from microsoft article
}
#else
#include <unistd.h>
void clearconsole()
{
write(1,"\E[H\E[2J",7);
}
#endif

At a guess, your immediate problem is probably that you're missing an #include <string>.
Probably the most portable way of dealing with the screen is via ncurses. It's included in POSIX and most POSIX-like systems, and available as a library for most others (e.g., Windows) as well.
Edit: For what it's worth, clearing the screen on Windows doesn't require anywhere close to 100 lines of code.
#include <windows.h>
void clear_screen(char fill = ' ') {
COORD tl = {0,0};
CONSOLE_SCREEN_BUFFER_INFO s;
HANDLE console = GetStdHandle(STD_OUTPUT_HANDLE);
GetConsoleScreenBufferInfo(console, &s);
DWORD written, cells = s.dwSize.X * s.dwSize.Y;
FillConsoleOutputCharacter(console, fill, cells, tl, &written);
FillConsoleOutputAttribute(console, s.wAttributes, cells, tl, &written);
SetConsoleCursorPosition(console, tl);
}
#ifdef TEST
int main(){
clear_screen();
return 0;
}
#endif
I'm the first to say that the code is more verbose than I'd like -- but it's less than ten lines, not to mention a hundred. Even the version in the MS knowledgebase is actually less than 40 lines -- of which many are blank or comments.
In fairness, however, I feel obliged to admit assembly language code writing directly to the hardware (or using the BIOS) does end up quite a bit shorter.

I know this is a complete necro. But I figured out what I feel is a rather neat solution and thought I'd share it just in case someone has this problem in the future.
void clearConsole() {
#ifdef _WIN32
#include <iostream>
static const char* CSI = "\33[";
printf("%s%c%s%c", CSI, 'H', CSI, '2J');
#else
#include <unistd.h>
write(1, "\E[H\E[2J", 7);
#endif
}

Related

What C++ header can I use for these specific functions ? Linux

I am linux user and would like to use these 'keyboard_event' functions, but the header for these functions is 'windows.h' and linux doesn't have any 'windows.h', so can anyone support some alternative header for these functions, or alternative way to simulate key press for linux ?
#include <iostream>
using namespace std;
int main() {
keybd_event(VK_CONTROL,0x9d,0 , 0); //pressing CTRL
keybd_event(VkKeyScan(‘R’),0x93,0 , 0); //pressing 'R'
keybd_event(VkKeyScan(‘R’),0x93,KEYEVENTF_KEYUP,0); //releasing 'R'
keybd_event(VK_CONTROL,0x9d,KEYEVENTF_KEYUP,0); /* releasing CTRL */
return;
}
There's no "equivalent" for windows.h in Linux. You need to fix your errors case by case, or better, rewrite your code for Linux.
Reference: https://ubuntuforums.org/showthread.php?t=533304
The uinput kernel module and libevdev were introduced for exactly this purpose.
I've found a solution, in code I just type:
system("xte 'keydown Control_L' 'key R' 'keyup Control_L'");
and it does the same, but <cstdlib> has to be included.

Simple and portable method for managing console cursors action in C++

When dealing with console input (stdin,std::cin) is there a portable way in C++ to manage the various actions that a user may perform like:
Backspace/Delete
List item
Left/Right arrow keys (moving cursor back/forth insert text)
For example in windows when using std::cin (eg: std::cin >> s;), it allows for arrow keys, however when using the same bit of code on linux, the arrow keys are assumed as part of the input, the cursor is not moved around.
I know of various TUI frameworks like curses and ncurses that provide such functionality however they are more than what is required.
I'm hoping there's a simple solution based on the standard libraries, or even a lightweight open source library that might have a std::getline like feature that is portable across the more popular OSes.
Things like backspace and delete are typically handled by the
system; when you read from a terminal, you only get the input
when the user presses enter.
What the system does is usually fairly limited. In particular,
I don't know of any that do things like file name completion.
If more than what the system does is desired, I would recommend
looking into the readline library, used by many GNU programs
(bash, gdb, etc.). It's available separately from the
applications which use it. (Two small warnings: I don't know
how good its support is for native Windows, and I'm not sure
which license it is under: GPL or LGPL.)
readline is a good choice for Linux, but it's GPL! I use the following code to compile on Windows and Linux:
#ifdef USE_READLINE
#include <readline/readline.h>
#include <readline/history.h>
#endif
...
void getline(char *buf)
{
#ifdef USE_READLINE
char *tmp;
tmp = readline(PROMPT);
if(strncmp(tmp, buf, MAXLENGTH)) add_history(tmp); // only add new content
strncpy(buf, tmp, MAXLENGTH);
buf[MAXLENGTH]='\0';
free(tmp);
#else
std::cout<<PROMPT;
std::cin.get(buf,MAXLENGTH);
std::cin.ignore(); // delete CR
#endif
}

Windows Unicode C++ Stream Output Failure

I am currently writing an application which requires me to call GetWindowText on arbitrary windows and store that data to a file for later processing. Long story short, I noticed that my tool was failing on Battlefield 3, and I narrowed the problem down to the following character in its window title:
http://www.fileformat.info/info/unicode/char/2122/index.htm
So I created a little test app which just does the following:
std::wcout << L"\u2122";
Low and behold that breaks output to the console window for the remainder of the program.
Why is the MSVC STL choking on this character (and I assume others) when APIs like MessageBoxW etc display it just fine?
How can I get those characters printed to my file?
Tested on both VC10 and VC11 under Windows 7 x64.
Sorry for the poorly constructed post, I'm tearing my hair out here.
Thanks.
EDIT:
Minimal test case
#include <fstream>
#include <iostream>
int main()
{
{
std::wofstream test_file("test.txt");
test_file << L"\u2122";
}
std::wcout << L"\u2122";
}
Expected result: '™' character printed to console and file.
Observed result: File is created but is empty. No output to console.
I have confirmed that the font I"m using for my console is capable of displaying the character in question, and the file is definitely empty (0 bytes in size).
EDIT:
Further debugging shows that the 'failbit' and 'badbit' are set in the stream(s).
EDIT:
I have also tried using Boost.Locale and I am having the same issue even with the new locale imbued globally and explicitly to all standard streams.
To write into a file, you have to set the locale correctly, for example if you want to write them as UTF-8 characters, you have to add
const std::locale utf8_locale
= std::locale(std::locale(), new std::codecvt_utf8<wchar_t>());
test_file.imbue(utf8_locale);
You have to add these 2 include files
#include <codecvt>
#include <locale>
To write to the console you have to set the console in the correct mode (this is windows specific) by adding
_setmode(_fileno(stdout), _O_U8TEXT);
(in case you want to use UTF-8).
For this you have to add these 2 include files:
#include <fcntl.h>
#include <io.h>
Furthermore you have to make sure that your are using a font that supports Unicode (such as for example Lucida Console). You can change the font in the properties of your console window.
The complete program now looks like this:
#include <fstream>
#include <iostream>
#include <codecvt>
#include <locale>
#include <fcntl.h>
#include <io.h>
int main()
{
const std::locale utf8_locale = std::locale(std::locale(),
new std::codecvt_utf8<wchar_t>());
{
std::wofstream test_file("c:\\temp\\test.txt");
test_file.imbue(utf8_locale);
test_file << L"\u2122";
}
_setmode(_fileno(stdout), _O_U8TEXT);
std::wcout << L"\u2122";
}
Are you always using std::wcout or are you sometimes using std::cout? Mixing these won't work. Of course, the error description "choking" doesn't say at all what problem you are observing. I'd suspect that this is a different problem to the one using files, however.
As there is no real description of the problem it takes somewhat of a crystal ball followed by a shot in the dark to hit the problem... Since you want to get Unicode characters from you file make sure that the file stream you are using uses a std::locale whose std::codecvt<...> facet actually converts to a suitable Unicode encoding.
I just tested GCC (versions 4.4 thru 4.7) and MSVC 10, which all exhibit this problem.
Equally broken is wprintf, which does as little as the C++ stream API.
I also tested the raw Win32 API to see if nothing else was causing the failure, and this works:
#include <windows.h>
int main()
{
HANDLE stdout = GetStdHandle(STD_OUTPUT_HANDLE);
DWORD n;
WriteConsoleW( stdout, L"\u03B2", 1, &n, NULL );
}
Which writes β to the console (if you set cmd's font to something like Lucida Console).
Conclusion: wchar_t output is horribly broken in both large C++ Standard library implementations.
Although the wide character streams take Unicode as input, that's not what they produce as output - the characters go through a conversion. If a character can't be represented in the encoding that it's converting to, the output fails.

porting code from Linux to MinGW

I am writing a small class which can create/remove/rename/search for files and directories on the PC.
I successfully wrote the class and run on Linux.
When I was trying to run the same Class Code in MinGW, it was giving an error.
I could narrow down to:
mkdir function in Linux, Cygwin has 2 Arguments (directory name , mode permissions)
but in MinGW has only one argument(directory name).
My query is : a) What is the best way to make the code work on both OSs. b) Though I never used, I heard Preprocessor directives can be put like #ifdefined .....#endif ..or some thing of that sort c) Is using Preprocessor directives a good programming practice. As I learnt, preprocessor directives should be used minimally.
Could some one help me in this:
Here is my Code which works on Linux and Cygwin:
#include "BioDatabase.h"
#include <dirent.h>
#include <sys/stat.h>
#include <stdio.h>
#include <unistd.h>
BioDatabase::BioDatabase() {
string s = getcwd(NULL,0);
changeDirectory(s,"*");
}
BioDatabase::BioDatabase(string directoryName, string extension)
{
changeDirectory(directoryName, extension);
}
bool BioDatabase::createDirectory(string st)
{
if( mkdir(st.c_str(),0755) == -1)
{
cerr <<endl<<"BOSERR-BioDatabase, createDirectory: Path or file function not found or Permission denied\n\n";
return false;
}
flag =1;
return true;
}
You could code something like
#if _POSIX_C_SOURCE
if( mkdir(st.c_str()) == -1)
#else
if ((mkdir(st.c_str(),0755) == -1)
#endif
See also feature_test_macros(7) man page.
1) you can use pre-processors to do one thing on one platform, and something different on another. EG:
#ifdef mingw32
/* windows specific code, like mkdir()... */
#else
/* other platform code, like a different way to call mkdir() */
#endif
2) Yes, you're absolutely right: limit using them as much as you can. but you'll quickly find out you can't avoid them entirely.
3) The best thing to do is to use a script that checks for
functionality rather than do it on a per-operating system basis.
Typically this involves writing a configure script (or
similar), which is a whole other learning curve. Still, it lets
you port to new platforms by checking for functionality rather than
adding the platform to a long list.

How to redirect printf output back into code?

i'm writing a little c++ app to wrap around the opencv haar training function (namely cvCreateTreeCascadeClassifier). The function throws a whole load of output to the console and I wish to parse this output so that I can populate various variables in my code.
The function I wish to use is not part of the actual openCV library; instead it has to be built with my code as part of the project. All of the output from the the function is via printf.
Question: Is it possible to intercept the printf statements before they end up on the console? I've managed to redirect them using freopen but this seems a little clumsy as I then need to parse the file and then delete it when the function call is finished. Also, the function is likely to be running for several hours (and possibly even weeks!) so the size of the file might be an issue if its constantly being appended too.
Requirements: I need this app to be c++ and to run on both windows and linux (but have no problem with conditional compile statements if need be). I would also like to be able to still see my cout and cerr messages on the console (just not the printf).
My googling has removed my will to live! Can anyone help with a solution via either code example or pointers to places I should be looking for an answer?
Thanks
What you can do is:
create a pipe
make the writable end of the pipe the new stdout
read from the readable part of the pipe
Reading and writing should happen in different threads or you risk that your program starves on one end of the pipe.
Here's a sample how to do the redirection in unix & windows:
#include <fcntl.h>
#include <stdlib.h>
#include <stdio.h>
/* gcc defined unix */
#ifdef unix
#include <unistd.h>
#endif
#ifdef WIN32
#include <io.h>
#define pipe(X) _pipe(X,4096,O_BINARY)
#define fileno _fileno
#define dup2 _dup2
#define read _read
#endif
#include <assert.h>
int main()
{
int fds[2];
int res;
char buf[256];
int so;
res=pipe(fds);
assert(res==0);
so=fileno(stdout);
// close stdout handle and make the writable part of fds the new stdout.
res=dup2(fds[1],so);
assert(res!=-1);
printf("Hi there\n");
fflush(stdout);
// reading should happen in a different thread
res=read(fds[0],buf,sizeof(buf)-1);
assert(res>=0 && res<sizeof(buf));
buf[res]=0;
fprintf(stderr,"buf=>%s\n",buf);
return 0;
}
This code should print
buf=>Hi there
(I'm using assert here, because I am too lazy to do real error checking for this example)
Encapsulate the lib into an application, and pipe the application's output to your application. Now write a script so that you don't have to run the apps together every time with a pipe.
Take a look at: http://www.unix.com/programming/136225-reading-stdout-pipe.html it seems promising, but i never tried it.