Reputation: 201
I'm using ncurses for a typing game I'm making. Letters fall down the screen and you must type them before they reach the bottom. It's working great, save one problem. Clearing the window (with clear()) makes the output flicker. I put clear() at the very beginning of the loop and wrefresh() at the very end. Shouldn't it be waiting 'til wrefresh to show anything, thus not flashing?
#include <iostream>
#include <string>
#include <cstdlib>
#include <ctime>
#include <curses.h>
#include <fstream>
using namespace std;
int main(){
initscr();
cbreak();
noecho();
keypad(stdscr, TRUE);
nodelay(stdscr, TRUE);
srand(time(NULL));
//input character integer (ASCII)
int ch = 1;
//int to store the last time the character positions were updated
int lastupdate = time(NULL);
//x,y,char arrays for falling characters and initialization
int chars[10], x[10], y[10];
for(int i = 0; i < 10; i++){
chars[i] = rand()%25 + 97;
x[i] = rand()%30;
y[i] = 0;
//y[i] = -(rand()%4);
}
while (true){
clear();
ch = wgetch(stdscr);
for (int i = 0; i < 10; i++){
mvwdelch(stdscr,y[i]-1,x[i]);//delete char's prev. position
mvwaddch(stdscr, y[i], x[i], chars[i]);//add char's current position
if (ch == chars[i]){
mvwdelch(stdscr, y[i], x[i]);
chars[i] = rand()%25 + 97;
x[i] = rand()%30;
y[i] = 0;
}
}
if(time(0) >= (lastupdate + 1)){
for (int i = 0; i < 10; i++){
y[i]++;
}
lastupdate = time(NULL);
}
wmove(stdscr, 20, 0);
printw("your score is NULL. press ESC to exit");
scrollok(stdscr, TRUE);
wrefresh(stdscr);
}
endwin();
return 0;
}
edit: added code
edit2: removed some irrelevant debug code
Upvotes: 6
Views: 7124
Reputation: 336
I suggest to Just use erase() instead of clear() clear also calls clearok() automatically.
Upvotes: 16
Reputation: 54515
The clear
manual page is the place to start:
The
clear
andwclear
routines are likeerase
andwerase
, but they also call clearok, so that the screen is cleared completely on the next call towrefresh
for that window and repainted from scratch.
The wgetch
call does that wrefresh
, which causes the repainting:
If the window is not a pad, and it has been moved or modified since the last call to
wrefresh
,wrefresh
will be called before another character is read.
The description of wrefresh
is not nearly so succinct, but "repainting from scratch" will cause flickering since there is a moment when the screen is empty, followed by it being non-empty. Those alternate rapidly due to this call:
nodelay(stdscr, TRUE);
Upvotes: 7
Reputation: 2256
The wgetch()
just after the clear()
does an implicit wrefresh()
. From the wgetch()
man page:
If the window is not a pad, and it has been moved or modified
since the last call to wrefresh, wrefresh will be called before
another character is read.
Upvotes: 4