Ignore:
File:
1 edited

Legend:

Unmodified
Added
Removed
  • uspace/lib/gui/terminal.c

    ra35b458 r5a6cc679  
    4747#include <atomic.h>
    4848#include <stdarg.h>
    49 #include <str.h>
    5049#include "window.h"
    5150#include "terminal.h"
     
    118117        [COLOR_YELLOW]      = PIXEL(255, 240, 240, 0),
    119118        [COLOR_WHITE]       = PIXEL(255, 240, 240, 240),
    120 
     119       
    121120        [COLOR_BLACK + 8]   = PIXEL(255, 0, 0, 0),
    122121        [COLOR_BLUE + 8]    = PIXEL(255, 0, 0, 255),
     
    170169        charfield_t *field =
    171170            chargrid_charfield_at(term->backbuf, col, row);
    172 
     171       
    173172        bool inverted = chargrid_cursor_at(term->backbuf, col, row);
    174 
     173       
    175174        sysarg_t bx = sx + (col * FONT_WIDTH);
    176175        sysarg_t by = sy + (row * FONT_SCANLINES);
    177 
     176       
    178177        pixel_t bgcolor = 0;
    179178        pixel_t fgcolor = 0;
    180 
     179       
    181180        if (inverted)
    182181                attrs_rgb(field->attrs, &fgcolor, &bgcolor);
    183182        else
    184183                attrs_rgb(field->attrs, &bgcolor, &fgcolor);
    185 
     184       
    186185        // FIXME: Glyph type should be actually uint32_t
    187186        //        for full UTF-32 coverage.
    188 
     187       
    189188        uint16_t glyph = fb_font_glyph(field->ch, NULL);
    190 
     189       
    191190        for (unsigned int y = 0; y < FONT_SCANLINES; y++) {
    192191                pixel_t *dst = pixelmap_pixel_at(
     
    207206{
    208207        sysarg_t top_row = chargrid_get_top_row(term->frontbuf);
    209 
     208       
    210209        if (term->top_row == top_row)
    211210                return false;
    212 
     211       
    213212        term->top_row = top_row;
    214 
     213       
    215214        for (sysarg_t row = 0; row < term->rows; row++) {
    216215                for (sysarg_t col = 0; col < term->cols; col++) {
     
    220219                            chargrid_charfield_at(term->backbuf, col, row);
    221220                        bool update = false;
    222 
     221                       
    223222                        if (front_field->ch != back_field->ch) {
    224223                                back_field->ch = front_field->ch;
    225224                                update = true;
    226225                        }
    227 
     226                       
    228227                        if (!attrs_same(front_field->attrs, back_field->attrs)) {
    229228                                back_field->attrs = front_field->attrs;
    230229                                update = true;
    231230                        }
    232 
     231                       
    233232                        front_field->flags &= ~CHAR_FLAG_DIRTY;
    234 
     233                       
    235234                        if (update)
    236235                                term_update_char(term, surface, sx, sy, col, row);
    237236                }
    238237        }
    239 
     238       
    240239        return true;
    241240}
     
    245244{
    246245        bool damage = false;
    247 
     246       
    248247        sysarg_t front_col;
    249248        sysarg_t front_row;
    250249        chargrid_get_cursor(term->frontbuf, &front_col, &front_row);
    251 
     250       
    252251        sysarg_t back_col;
    253252        sysarg_t back_row;
    254253        chargrid_get_cursor(term->backbuf, &back_col, &back_row);
    255 
     254       
    256255        bool front_visibility =
    257256            chargrid_get_cursor_visibility(term->frontbuf) &&
     
    259258        bool back_visibility =
    260259            chargrid_get_cursor_visibility(term->backbuf);
    261 
     260       
    262261        if (front_visibility != back_visibility) {
    263262                chargrid_set_cursor_visibility(term->backbuf,
     
    266265                damage = true;
    267266        }
    268 
     267       
    269268        if ((front_col != back_col) || (front_row != back_row)) {
    270269                chargrid_set_cursor(term->backbuf, front_col, front_row);
     
    273272                damage = true;
    274273        }
    275 
     274       
    276275        return damage;
    277276}
     
    280279{
    281280        fibril_mutex_lock(&term->mtx);
    282 
     281       
    283282        surface_t *surface = window_claim(term->widget.window);
    284283        if (!surface) {
     
    287286                return;
    288287        }
    289 
     288       
    290289        bool damage = false;
    291290        sysarg_t sx = term->widget.hpos;
    292291        sysarg_t sy = term->widget.vpos;
    293 
     292       
    294293        if (term_update_scroll(term, surface, sx, sy)) {
    295294                damage = true;
     
    302301                                    chargrid_charfield_at(term->backbuf, x, y);
    303302                                bool update = false;
    304 
     303                               
    305304                                if ((front_field->flags & CHAR_FLAG_DIRTY) ==
    306305                                    CHAR_FLAG_DIRTY) {
     
    309308                                                update = true;
    310309                                        }
    311 
     310                                       
    312311                                        if (!attrs_same(front_field->attrs,
    313312                                            back_field->attrs)) {
     
    315314                                                update = true;
    316315                                        }
    317 
     316                                       
    318317                                        front_field->flags &= ~CHAR_FLAG_DIRTY;
    319318                                }
    320 
     319                               
    321320                                if (update) {
    322321                                        term_update_char(term, surface, sx, sy, x, y);
     
    326325                }
    327326        }
    328 
     327       
    329328        if (term_update_cursor(term, surface, sx, sy))
    330329                damage = true;
    331 
     330       
    332331        window_yield(term->widget.window);
    333 
     332       
    334333        if (damage)
    335334                window_damage(term->widget.window);
    336 
     335       
    337336        fibril_mutex_unlock(&term->mtx);
    338337}
     
    341340{
    342341        fibril_mutex_lock(&term->mtx);
    343 
     342       
    344343        surface_t *surface = window_claim(term->widget.window);
    345344        if (!surface) {
     
    348347                return;
    349348        }
    350 
     349       
    351350        sysarg_t sx = term->widget.hpos;
    352351        sysarg_t sy = term->widget.vpos;
    353 
     352       
    354353        if (!term_update_scroll(term, surface, sx, sy)) {
    355354                for (sysarg_t y = 0; y < term->rows; y++) {
     
    359358                                charfield_t *back_field =
    360359                                    chargrid_charfield_at(term->backbuf, x, y);
    361 
     360                               
    362361                                back_field->ch = front_field->ch;
    363362                                back_field->attrs = front_field->attrs;
    364363                                front_field->flags &= ~CHAR_FLAG_DIRTY;
    365 
     364                               
    366365                                term_update_char(term, surface, sx, sy, x, y);
    367366                        }
    368367                }
    369368        }
    370 
     369       
    371370        term_update_cursor(term, surface, sx, sy);
    372 
     371       
    373372        window_yield(term->widget.window);
    374373        window_damage(term->widget.window);
    375 
     374       
    376375        fibril_mutex_unlock(&term->mtx);
    377376}
     
    392391        uint8_t *bbuf = buf;
    393392        size_t pos = 0;
    394 
     393       
    395394        /*
    396395         * Read input from keyboard and copy it to the buffer.
     
    403402                        bbuf[pos] = term->char_remains[0];
    404403                        pos++;
    405 
     404                       
    406405                        /* Unshift the array. */
    407406                        for (size_t i = 1; i < term->char_remains_len; i++)
    408407                                term->char_remains[i - 1] = term->char_remains[i];
    409 
     408                       
    410409                        term->char_remains_len--;
    411410                }
    412 
     411               
    413412                /* Still not enough? Then get another key from the queue. */
    414413                if (pos < size) {
    415414                        link_t *link = prodcons_consume(&term->input_pc);
    416415                        cons_event_t *event = list_get_instance(link, cons_event_t, link);
    417 
     416                       
    418417                        /* Accept key presses of printable chars only. */
    419418                        if (event->type == CEV_KEY && event->ev.key.type == KEY_PRESS &&
     
    423422                                        0
    424423                                };
    425 
     424                               
    426425                                wstr_to_str(term->char_remains, UTF8_CHAR_BUFFER_SIZE, tmp);
    427426                                term->char_remains_len = str_size(term->char_remains);
    428427                        }
    429 
     428                       
    430429                        free(event);
    431430                }
    432431        }
    433 
     432       
    434433        *nread = size;
    435434        return EOK;
     
    439438{
    440439        sysarg_t updated = 0;
    441 
    442         fibril_mutex_lock(&term->mtx);
    443 
     440       
     441        fibril_mutex_lock(&term->mtx);
     442       
    444443        switch (ch) {
    445444        case '\n':
     
    457456                updated = chargrid_putchar(term->frontbuf, ch, true);
    458457        }
    459 
    460         fibril_mutex_unlock(&term->mtx);
    461 
     458       
     459        fibril_mutex_unlock(&term->mtx);
     460       
    462461        if (updated > 1)
    463462                term_update(term);
     
    467466{
    468467        terminal_t *term = srv_to_terminal(srv);
    469 
     468       
    470469        size_t off = 0;
    471470        while (off < size)
    472471                term_write_char(term, str_decode(data, &off, size));
    473 
     472       
    474473        *nwritten = size;
    475474        return EOK;
     
    479478{
    480479        terminal_t *term = srv_to_terminal(srv);
    481 
     480       
    482481        term_update(term);
    483482}
     
    486485{
    487486        terminal_t *term = srv_to_terminal(srv);
    488 
     487       
    489488        fibril_mutex_lock(&term->mtx);
    490489        chargrid_clear(term->frontbuf);
    491490        fibril_mutex_unlock(&term->mtx);
    492 
     491       
    493492        term_update(term);
    494493}
     
    497496{
    498497        terminal_t *term = srv_to_terminal(srv);
    499 
     498       
    500499        fibril_mutex_lock(&term->mtx);
    501500        chargrid_set_cursor(term->frontbuf, col, row);
    502501        fibril_mutex_unlock(&term->mtx);
    503 
     502       
    504503        term_update(term);
    505504}
     
    508507{
    509508        terminal_t *term = srv_to_terminal(srv);
    510 
     509       
    511510        fibril_mutex_lock(&term->mtx);
    512511        chargrid_get_cursor(term->frontbuf, col, row);
    513512        fibril_mutex_unlock(&term->mtx);
    514 
     513       
    515514        return EOK;
    516515}
     
    519518{
    520519        terminal_t *term = srv_to_terminal(srv);
    521 
     520       
    522521        fibril_mutex_lock(&term->mtx);
    523522        *cols = term->cols;
    524523        *rows = term->rows;
    525524        fibril_mutex_unlock(&term->mtx);
    526 
     525       
    527526        return EOK;
    528527}
     
    532531        (void) srv;
    533532        *caps = TERM_CAPS;
    534 
     533       
    535534        return EOK;
    536535}
     
    539538{
    540539        terminal_t *term = srv_to_terminal(srv);
    541 
     540       
    542541        fibril_mutex_lock(&term->mtx);
    543542        chargrid_set_style(term->frontbuf, style);
     
    549548{
    550549        terminal_t *term = srv_to_terminal(srv);
    551 
     550       
    552551        fibril_mutex_lock(&term->mtx);
    553552        chargrid_set_color(term->frontbuf, bgcolor, fgcolor, attr);
     
    559558{
    560559        terminal_t *term = srv_to_terminal(srv);
    561 
     560       
    562561        fibril_mutex_lock(&term->mtx);
    563562        chargrid_set_rgb_color(term->frontbuf, bgcolor, fgcolor);
     
    568567{
    569568        terminal_t *term = srv_to_terminal(srv);
    570 
     569       
    571570        fibril_mutex_lock(&term->mtx);
    572571        chargrid_set_cursor_visibility(term->frontbuf, visible);
    573572        fibril_mutex_unlock(&term->mtx);
    574 
     573       
    575574        term_update(term);
    576575}
     
    581580        link_t *link = prodcons_consume(&term->input_pc);
    582581        cons_event_t *ev = list_get_instance(link, cons_event_t, link);
    583 
     582       
    584583        *event = *ev;
    585584        free(ev);
     
    591590        list_remove(&term->link);
    592591        widget_deinit(&term->widget);
    593 
     592       
    594593        if (term->frontbuf)
    595594                chargrid_destroy(term->frontbuf);
    596 
     595       
    597596        if (term->backbuf)
    598597                chargrid_destroy(term->backbuf);
     
    602601{
    603602        terminal_t *term = (terminal_t *) widget;
    604 
     603       
    605604        deinit_terminal(term);
    606605        free(term);
     
    616615{
    617616        terminal_t *term = (terminal_t *) widget;
    618 
     617       
    619618        widget_modify(widget, hpos, vpos, width, height);
    620619        widget->width_ideal = width;
    621620        widget->height_ideal = height;
    622 
     621       
    623622        term_damage(term);
    624623}
     
    627626{
    628627        terminal_t *term = (terminal_t *) widget;
    629 
     628       
    630629        term_damage(term);
    631630}
     
    638637        if (event == NULL)
    639638                return;
    640 
     639       
    641640        *event = *ev;
    642641        link_initialize(&event->link);
    643 
     642       
    644643        prodcons_produce(&term->input_pc, &event->link);
    645644}
     
    651650        terminal_t *term = (terminal_t *) widget;
    652651        cons_event_t event;
    653 
     652       
    654653        event.type = CEV_KEY;
    655654        event.ev.key = kbd_event;
    656 
     655       
    657656        terminal_queue_cons_event(term, &event);
    658657}
     
    680679{
    681680        terminal_t *term = NULL;
    682 
     681       
    683682        list_foreach(terms, link, terminal_t, cur) {
    684683                if (cur->dsid == (service_id_t) IPC_GET_ARG2(*icall)) {
     
    687686                }
    688687        }
    689 
     688       
    690689        if (term == NULL) {
    691690                async_answer_0(iid, ENOENT);
    692691                return;
    693692        }
    694 
     693       
    695694        if (atomic_postinc(&term->refcnt) == 0)
    696695                chargrid_set_cursor_visibility(term->frontbuf, true);
    697 
     696       
    698697        con_conn(iid, icall, &term->srvs);
    699698}
     
    703702{
    704703        widget_init(&term->widget, parent, data);
    705 
     704       
    706705        link_initialize(&term->link);
    707706        fibril_mutex_initialize(&term->mtx);
    708707        atomic_set(&term->refcnt, 0);
    709 
     708       
    710709        prodcons_initialize(&term->input_pc);
    711710        term->char_remains_len = 0;
    712 
     711       
    713712        term->widget.width = width;
    714713        term->widget.height = height;
    715714        term->widget.width_ideal = width;
    716715        term->widget.height_ideal = height;
    717 
     716       
    718717        term->widget.destroy = terminal_destroy;
    719718        term->widget.reconfigure = terminal_reconfigure;
     
    722721        term->widget.handle_keyboard_event = terminal_handle_keyboard_event;
    723722        term->widget.handle_position_event = terminal_handle_position_event;
    724 
     723       
    725724        term->cols = width / FONT_WIDTH;
    726725        term->rows = height / FONT_SCANLINES;
    727 
     726       
    728727        term->frontbuf = NULL;
    729728        term->backbuf = NULL;
    730 
     729       
    731730        term->frontbuf = chargrid_create(term->cols, term->rows,
    732731            CHARGRID_FLAG_NONE);
     
    735734                return false;
    736735        }
    737 
     736       
    738737        term->backbuf = chargrid_create(term->cols, term->rows,
    739738            CHARGRID_FLAG_NONE);
     
    742741                return false;
    743742        }
    744 
     743       
    745744        chargrid_clear(term->frontbuf);
    746745        chargrid_clear(term->backbuf);
    747746        term->top_row = 0;
    748 
     747       
    749748        async_set_fallback_port_handler(term_connection, NULL);
    750749        con_srvs_init(&term->srvs);
    751750        term->srvs.ops = &con_ops;
    752751        term->srvs.sarg = term;
    753 
     752       
    754753        errno_t rc = loc_server_register(NAME);
    755754        if (rc != EOK) {
     
    757756                return false;
    758757        }
    759 
     758       
    760759        char vc[LOC_NAME_MAXLEN + 1];
    761760        snprintf(vc, LOC_NAME_MAXLEN, "%s/%" PRIu64, NAMESPACE,
    762761            task_get_id());
    763 
     762       
    764763        rc = loc_service_register(vc, &term->dsid);
    765764        if (rc != EOK) {
     
    767766                return false;
    768767        }
    769 
     768       
    770769        list_append(&term->link, &terms);
    771770        getterm(vc, "/app/bdsh");
    772 
     771       
    773772        return true;
    774773}
     
    780779        if (!term)
    781780                return NULL;
    782 
     781       
    783782        bool ret = init_terminal(term, parent, data, width, height);
    784783        if (!ret) {
     
    786785                return NULL;
    787786        }
    788 
     787       
    789788        return term;
    790789}
Note: See TracChangeset for help on using the changeset viewer.