I'm writing a game where I create a map using ncurses. What I want to try and do(if possible) is make the map the size of the terminal, in other words in the main program I have:

// Create a game on an 80x30 map
  Game gameInstance( 80, 30 ) ;
  //run game
  gameInstance.run() ;

But what I want to try and do is detect the size of the terminal window the user already has. Then pass those x and y values to the gameInstance() function.

Dani AI

Generated

Nice work by — the ioctl/winsize approach is a reliable POSIX solution. ’s suggestion of using shell variables can work in simple scripts but is brittle (different shells, remote sessions, or missing env vars). For an ncurses-based game the cleanest, portable-in-the-Unix-world way is to let ncurses tell you the size after it initializes the terminal.

A minimal ncurses detection pattern (different from the ioctl example already posted) is:

initscr();
int rows, cols;
getmaxyx(stdscr, rows, cols);   // rows then cols
endwin();

Game gameInstance(cols, rows);   // pass width, height if Game expects that order

Notes: getmaxyx returns rows first, then columns — be careful to match your Game constructor’s parameter order. If your Game already calls initscr() internally, move the detection there or allow a constructor like Game(int w=0, int h=0) where 0 means “auto-detect”.

To handle terminal resizes while the game is running, catch SIGWINCH and update ncurses’ idea of the screen, then notify the game:

void handle_winch(int) {
  endwin();
  refresh();
  clear();
  int rows, cols;
  getmaxyx(stdscr, rows, cols);
  gameInstance.resize(cols, rows);  // implement a resize method in Game
}

// install with sigaction or signal()

For portability: ioctl and the above ncurses approach are for POSIX systems. On Windows use the Win32 API (GetConsoleScreenBufferInfo) or a curses port such as PDCurses. Always validate the reported size (reject zero or tiny values), provide sensible minimums, and prefer letting the module that owns the terminal (your Game class) initialize curses and manage resizing so you avoid double initialization and race conditions.

Recommended Answers

All 2 Replies

Since this is a non-native c++ thing, I would recommend using system() to call the appropriate system command to get the terminal size (I don't know what it is, but I'm sure one exists). Include in the command writing this result to a file. Then read the file in your c++ program.

In bash it is:

system("echo $COLUMNS $LINES > file.txt");

Hope this helps.

Dave

I got it to work using this code which basically does what you said.

#include <iostream>
#include <stdlib.h>
#include <ncurses.h>
#include <sys/ioctl.h>
#include <string.h>
#include <errno.h>
#include "game.h"

using namespace std;

int main() {

  struct winsize ws;

  if( ioctl( 0, TIOCGWINSZ, &ws ) != 0 ){
    fprintf(stderr, "TIOCGWINSZ:%s\n", strerror(errno));
    exit(1);
  }
  // Create a game on a map with  current terminal size
  Game gameInstance( ws.ws_col, ws.ws_row ) ;

  gameInstance.run() ;

  return 0 ;

}
Be a part of the DaniWeb community

We're a friendly, industry-focused community of developers, IT pros, digital marketers, and technology enthusiasts meeting, networking, learning, and sharing knowledge.