简体   繁体   中英

printw (ncurses) not displaying correct char in c

I'm using ncurses to do a sort of sim city simulator.

I have ascii map in a .txt and I need to load it on the terminal.

The loading is good but it doesn't display the right caracters(for some caracters only).

for example:

in .txt -> in terminal

│ -> ~T~B

═ -> ~U~P

( -> (

I'm using http://www.theasciicode.com.ar/ for the ascii map

bellow is the code to display the map in terminal

nt setUpMap(){

FILE *fp;
int c;

fp = fopen("./files/map.txt", "r+");

cbreak();

// Read and display data 

while ((c = fgetc(fp)) != EOF)
{
    switch(c){
        case 'p' :
            // todo : emoji
        break;
        default:
            printw("%c", c);
        break;
    }    
}

fclose(fp);

return 0;
}

example of the content of the .txt :

┌───────────────────────┐
│   []   []   []   []   │
│ []  []   []   []   [] │
│   []   []   []   []   │
│                       │
│   ┌──┐       ┌──┐     │
└───┘  └───────┘  └─────┘

output in terminal :

�~T~L�~T~@�~T~@�~T~@�~T~@�~T~@�~T~@�~T~@�~T~@�~T~@�~T~@�~T~@�~T~@�~T~@    �~T~@�~T~@�~T~@�~T~@�~T~@�~T~@�~T~@�~T~@�~T~@�~T~@�~T~P
�~T~B   []   []   []   []   �~T~B
�~T~B []  []   []   []   [] �~T~B
�~T~B   []   []   []   []   �~T~B
�~T~B                       �~T~B
�~T~B   �~T~L�~T~@�~T~@�~T~P       �~T~L�~T~@�~T~@�~T~P     �~T~B
�~T~T�~T~@�~T~@�~T~@�~T~X       �~T~T�~T~@�~T~@�~T~@�~T~@�~T~@�~T~@�~T~@�~T~X      �~T~T�~T~@�~T~@�~T~@�~T~@�~T~@�~T~X

thanks for any ideas

Generally speaking, curses will display POSIX character set printable characters as you intended. For anything else, there are additional steps (and limitations).

For ncurses , you'll have to initialize the locale to get it to print codes 160-255 as characters. That is mentioned in the ncurses manual's section on initialization .

But if your locale uses UTF-8 encoding (as the typical out-of-the-box "desktop" system does), then ncurses will expect the application to supply the bytes for UTF-8, eg, using addch or addstr . printw might work in that case, although no one's commented on success (or failure) for that special case.

If the value is 128-159, some of those bytes (referring to addch ) could be part of a UTF-8 encoded character, and depending on whether you initialized the locale in ncurses, you would get different results.

Either way (128-159 or 160-255), you'll get behavior as shown when ncurses prints those values in a terminal which displays UTF-8.

Other values in the 0-255 range are control characters.

Since your example uses fgetc , we need not consider values above 255.

Assuming that your example is in UTF-8, this program (linked with ncursesw , the wide-character library ) would display the text as intended:

#include <curses.h>
#include <locale.h>

int
main(void)
{
    FILE *fp;
    int c;

    setlocale(LC_ALL, "");

    fp = fopen("./files/map.txt", "r");
    if (fp == 0)
        return 1;

    initscr();
    cbreak();
    noecho();

    // Read and display data 

    while ((c = fgetc(fp)) != EOF) {
        switch (c) {
        case 'p':
            // todo : emoji
            break;
        default:
            printw("%c", c);
            break;
        }
    }
    getch();
    endwin();

    fclose(fp);

    return 0;
}

To use the extended ascii caracters, you need to use nursesw and not ncurses

you will need to apt-get ncursesw to use it

the include in your main still remains #<ncurses.h>

when you compile, you put -lncursesw

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM