Changeset 9805cde in mainline for uspace/srv/fb/fb.c


Ignore:
Timestamp:
2009-01-01T13:31:23Z (16 years ago)
Author:
Jiri Svoboda <jirik.svoboda@…>
Branches:
lfn, master, serial, ticket/834-toolchain-update, topic/msim-upgrade, topic/simplify-dev-export
Children:
7122bc7
Parents:
666773c
Message:

Console color support overhaul. Create C library console interface.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • uspace/srv/fb/fb.c

    r666773c r9805cde  
    5252#include <kernel/errno.h>
    5353#include <kernel/genarch/fb/visuals.h>
     54#include <console/color.h>
     55#include <console/style.h>
    5456#include <async.h>
    5557#include <bool.h>
     
    9395        rgb_conv_t rgb_conv;
    9496} screen;
     97
     98/** Backbuffer character cell. */
     99typedef struct {
     100        uint8_t glyph;
     101        uint32_t fg_color;
     102        uint32_t bg_color;
     103} bb_cell_t;
    95104
    96105typedef struct {
     
    109118         */
    110119
    111         /** Current style. */
    112         style_t style;
     120        /** Current attributes. */
     121        attr_rgb_t attr;
    113122
    114123        /** Pre-rendered mask for rendering glyphs. Different viewports
     
    129138       
    130139        /* Back buffer */
     140        bb_cell_t *backbuf;
    131141        unsigned int bbsize;
    132         uint8_t *backbuf;
    133142} viewport_t;
    134143
     
    156165
    157166static bool client_connected = false;  /**< Allow only 1 connection */
     167
     168static uint32_t color_table[16] = {
     169        [COLOR_BLACK]           = 0x000000,
     170        [COLOR_BLUE]            = 0x0000f0,
     171        [COLOR_GREEN]           = 0x00f000,
     172        [COLOR_CYAN]            = 0x00f0f0,
     173        [COLOR_RED]             = 0xf00000,
     174        [COLOR_MAGENTA]         = 0xf000f0,
     175        [COLOR_YELLOW]          = 0xf0f000,
     176        [COLOR_WHITE]           = 0xf0f0f0,
     177
     178        [8 + COLOR_BLACK]       = 0x000000,
     179        [8 + COLOR_BLUE]        = 0x0000ff,
     180        [8 + COLOR_GREEN]       = 0x00ff00,
     181        [8 + COLOR_CYAN]        = 0x00ffff,
     182        [8 + COLOR_RED]         = 0xff0000,
     183        [8 + COLOR_MAGENTA]     = 0xff00ff,
     184        [8 + COLOR_YELLOW]      = 0xffff00,
     185        [8 + COLOR_WHITE]       = 0xffffff,
     186};
     187
     188static int rgb_from_style(attr_rgb_t *rgb, int style);
     189static int rgb_from_idx(attr_rgb_t *rgb, ipcarg_t fg_color,
     190    ipcarg_t bg_color, ipcarg_t flags);
     191
     192static int fb_set_color(viewport_t *vport, ipcarg_t fg_color,
     193    ipcarg_t bg_color, ipcarg_t attr);
    158194
    159195static void draw_glyph_aligned(unsigned int x, unsigned int y, bool cursor,
     
    300336                    vport->x + COL2X(vport->cols), vport->y,
    301337                    vport->x + vport->width, vport->y + vport->height,
    302                     vport->style.bg_color);
     338                    vport->attr.bg_color);
    303339        }
    304340
     
    307343                    vport->x, vport->y + ROW2Y(vport->rows),
    308344                    vport->x + vport->width, vport->y + vport->height,
    309                     vport->style.bg_color);
    310         }
    311 }
    312 
     345                    vport->attr.bg_color);
     346        }
     347}
     348
     349static void backbuf_clear(bb_cell_t *backbuf, size_t len, uint32_t fg_color,
     350    uint32_t bg_color)
     351{
     352        unsigned i;
     353
     354        for (i = 0; i < len; i++) {
     355                backbuf[i].glyph = 0;
     356                backbuf[i].fg_color = fg_color;
     357                backbuf[i].bg_color = bg_color;
     358        }
     359}
    313360
    314361/** Clear viewport.
     
    319366static void vport_clear(viewport_t *vport)
    320367{
    321         memset(vport->backbuf, 0, vport->bbsize);
     368        backbuf_clear(vport->backbuf, vport->cols * vport->rows,
     369            vport->attr.fg_color, vport->attr.bg_color);
    322370        vport_redraw(vport);
    323371}
     
    334382        unsigned int x, y;
    335383        uint8_t glyph;
     384        uint32_t fg_color;
     385        uint32_t bg_color;
     386        bb_cell_t *bbp, *xbp;
    336387
    337388        /*
     
    344395                for (col = 0; col < vport->cols; col++) {
    345396                        if ((row + lines >= 0) && (row + lines < vport->rows)) {
    346                                 glyph = vport->backbuf[BB_POS(vport, col, row + lines)];
    347 
    348                                 if (vport->backbuf[BB_POS(vport, col, row)] == glyph) {
     397                                xbp = &vport->backbuf[BB_POS(vport, col, row + lines)];
     398                                bbp = &vport->backbuf[BB_POS(vport, col, row)];
     399
     400                                glyph = xbp->glyph;
     401                                fg_color = xbp->fg_color;
     402                                bg_color = xbp->bg_color;
     403
     404                                if (bbp->glyph == glyph &&
     405                                    bbp->fg_color == xbp->fg_color &&
     406                                    bbp->bg_color == xbp->bg_color) {
    349407                                        x += FONT_WIDTH;
    350408                                        continue;
     
    352410                        } else {
    353411                                glyph = 0;
     412                                fg_color = vport->attr.fg_color;
     413                                bg_color = vport->attr.bg_color;
    354414                        }
    355415
    356416                        (*vport->dglyph)(x, y, false, vport->glyphs, glyph,
    357                             vport->style.fg_color, vport->style.bg_color);
     417                            fg_color, bg_color);
    358418                        x += FONT_WIDTH;
    359419                }
     
    367427        if (lines > 0) {
    368428                memmove(vport->backbuf, vport->backbuf + vport->cols * lines,
    369                     vport->cols * (vport->rows - lines));
    370                 memset(&vport->backbuf[BB_POS(vport, 0, vport->rows - lines)],
    371                     0, vport->cols * lines);
     429                    vport->cols * (vport->rows - lines) * sizeof(bb_cell_t));
     430                backbuf_clear(&vport->backbuf[BB_POS(vport, 0, vport->rows - lines)],
     431                    vport->cols * lines, vport->attr.fg_color, vport->attr.bg_color);
    372432        } else {
    373433                memmove(vport->backbuf - vport->cols * lines, vport->backbuf,
    374                     vport->cols * (vport->rows + lines));
    375                 memset(vport->backbuf, 0, - vport->cols * lines);
     434                    vport->cols * (vport->rows + lines) * sizeof(bb_cell_t));
     435                backbuf_clear(vport->backbuf, - vport->cols * lines,
     436                    vport->attr.fg_color, vport->attr.bg_color);
    376437        }
    377438}
     
    407468        }
    408469       
    409         screen.rgb_conv(vport->bgpixel, vport->style.bg_color);
     470        screen.rgb_conv(vport->bgpixel, vport->attr.bg_color);
    410471}
    411472
     
    435496        unsigned int cols = width / FONT_WIDTH;
    436497        unsigned int rows = height / FONT_SCANLINES;
    437         unsigned int bbsize = cols * rows;
     498        unsigned int bbsize = cols * rows * sizeof(bb_cell_t);
    438499        unsigned int glyphsize = 2 * FONT_GLYPHS * screen.glyphbytes;
    439500        unsigned int word_size = sizeof(unsigned long);
    440501       
    441         uint8_t *backbuf = (uint8_t *) malloc(bbsize);
     502        bb_cell_t *backbuf = (bb_cell_t *) malloc(bbsize);
    442503        if (!backbuf)
    443504                return ENOMEM;
     
    455516                return ENOMEM;
    456517        }
    457        
    458         memset(backbuf, 0, bbsize);
     518
     519        backbuf_clear(backbuf, cols * rows, DEFAULT_FGCOLOR, DEFAULT_BGCOLOR);
    459520        memset(glyphs, 0, glyphsize);
    460521        memset(bgpixel, 0, screen.pixelbytes);
     
    468529        viewports[i].rows = rows;
    469530       
    470         viewports[i].style.bg_color = DEFAULT_BGCOLOR;
    471         viewports[i].style.fg_color = DEFAULT_FGCOLOR;
     531        viewports[i].attr.bg_color = DEFAULT_BGCOLOR;
     532        viewports[i].attr.fg_color = DEFAULT_FGCOLOR;
    472533       
    473534        viewports[i].glyphs = glyphs;
     
    708769        unsigned int x = vport->x + COL2X(col);
    709770        unsigned int y = vport->y + ROW2Y(row);
     771
    710772        uint8_t glyph;
    711        
    712         glyph = vport->backbuf[BB_POS(vport, col, row)];
     773        uint32_t fg_color;
     774        uint32_t bg_color;
     775       
     776        glyph = vport->backbuf[BB_POS(vport, col, row)].glyph;
     777        fg_color = vport->backbuf[BB_POS(vport, col, row)].fg_color;
     778        bg_color = vport->backbuf[BB_POS(vport, col, row)].bg_color;
    713779
    714780        (*vport->dglyph)(x, y, cursor, vport->glyphs, glyph,
    715             vport->style.fg_color, vport->style.bg_color);
     781            fg_color, bg_color);
    716782}
    717783
     
    763829static void draw_char(viewport_t *vport, uint8_t c, unsigned int col, unsigned int row)
    764830{
     831        bb_cell_t *bbp;
     832
    765833        /* Do not hide cursor if we are going to overwrite it */
    766834        if ((vport->cursor_active) && (vport->cursor_shown) &&
    767835            ((vport->cur_col != col) || (vport->cur_row != row)))
    768836                cursor_hide(vport);
    769        
    770         vport->backbuf[BB_POS(vport, col, row)] = c;
     837
     838        bbp = &vport->backbuf[BB_POS(vport, col, row)];
     839        bbp->glyph = c;
     840        bbp->fg_color = vport->attr.fg_color;
     841        bbp->bg_color = vport->attr.bg_color;
     842
    771843        draw_vp_glyph(vport, false, col, row);
    772844       
     
    795867{
    796868        unsigned int i;
     869        bb_cell_t *bbp;
     870        attrs_t *a;
     871        attr_rgb_t rgb;
    797872       
    798873        for (i = 0; i < vport->cols * vport->rows; i++) {
     
    800875                unsigned int row = i / vport->cols;
    801876               
    802                 uint8_t glyph = vport->backbuf[BB_POS(vport, col, row)];
    803                
    804                 // TODO: use data[i].style
    805                
     877                bbp = &vport->backbuf[BB_POS(vport, col, row)];
     878                uint8_t glyph = bbp->glyph;
     879
    806880                if (glyph != data[i].character) {
    807                         vport->backbuf[BB_POS(vport, col, row)] = data[i].character;
     881                        bbp->glyph = data[i].character;
     882                        a = &data[i].attrs;
     883
     884                        switch (a->t) {
     885                        case at_style:
     886                                rgb_from_style(&rgb, a->a.s.style);
     887                                break;
     888                        case at_idx:
     889                                rgb_from_idx(&rgb, a->a.i.fg_color,
     890                                    a->a.i.bg_color, a->a.i.flags);
     891                                break;
     892                        case at_rgb:
     893                                rgb = a->a.r;
     894                                break;
     895                        }
     896
     897                        bbp->fg_color = rgb.fg_color;
     898                        bbp->bg_color = rgb.bg_color;
     899
    808900                        draw_vp_glyph(vport, false, col, row);
    809901                }
     
    13211413        return handled;
    13221414       
     1415}
     1416
     1417static int rgb_from_style(attr_rgb_t *rgb, int style)
     1418{
     1419        switch (style) {
     1420        case STYLE_NORMAL:
     1421                rgb->fg_color = color_table[COLOR_BLACK];
     1422                rgb->bg_color = color_table[COLOR_WHITE];
     1423                break;
     1424        case STYLE_EMPHASIS:
     1425                rgb->fg_color = color_table[COLOR_RED];
     1426                rgb->bg_color = color_table[COLOR_WHITE];
     1427                break;
     1428        default:
     1429                return EINVAL;
     1430        }
     1431
     1432        return EOK;
     1433}
     1434
     1435static int rgb_from_idx(attr_rgb_t *rgb, ipcarg_t fg_color,
     1436    ipcarg_t bg_color, ipcarg_t flags)
     1437{
     1438        fg_color = (fg_color & 7) | ((flags & CATTR_BRIGHT) ? 8 : 0);
     1439        bg_color = (bg_color & 7) | ((flags & CATTR_BRIGHT) ? 8 : 0);
     1440
     1441        rgb->fg_color = color_table[fg_color];
     1442        rgb->bg_color = color_table[bg_color];
     1443
     1444        return EOK;
     1445}
     1446
     1447static int fb_set_style(viewport_t *vport, ipcarg_t style)
     1448{
     1449        return rgb_from_style(&vport->attr, (int) style);
     1450}
     1451
     1452static int fb_set_color(viewport_t *vport, ipcarg_t fg_color,
     1453    ipcarg_t bg_color, ipcarg_t flags)
     1454{
     1455        return rgb_from_idx(&vport->attr, fg_color, bg_color, flags);
    13231456}
    13241457
     
    14791612                        break;
    14801613                case FB_SET_STYLE:
    1481                         vport->style.fg_color = IPC_GET_ARG1(call);
    1482                         vport->style.bg_color = IPC_GET_ARG2(call);
     1614                        retval = fb_set_style(vport, IPC_GET_ARG1(call));
     1615                        break;
     1616                case FB_SET_COLOR:
     1617                        retval = fb_set_color(vport, IPC_GET_ARG1(call),
     1618                            IPC_GET_ARG2(call), IPC_GET_ARG3(call));
     1619                        break;
     1620                case FB_SET_RGB_COLOR:
     1621                        vport->attr.fg_color = IPC_GET_ARG1(call);
     1622                        vport->attr.bg_color = IPC_GET_ARG2(call);
    14831623                        retval = EOK;
    14841624                        break;
Note: See TracChangeset for help on using the changeset viewer.