Ejemplo n.º 1
0
Archivo: ui.c Proyecto: draziw-/uTox
/* Draw add a friend window */
static void drawadd(int UNUSED(x), int UNUSED(y), int UNUSED(w), int height)
{
    setcolor(C_TITLE);
    setfont(FONT_SELF_NAME);
    drawstr(LIST_RIGHT + SCALE * 5, SCALE * 10, ADDFRIENDS);

    setcolor(C_TITLE);
    setfont(FONT_TEXT);
    drawstr(LIST_RIGHT + SCALE * 5, LIST_Y + SCALE * 5, TOXID);

    drawstr(LIST_RIGHT + SCALE * 5, LIST_Y + SCALE * 29, MESSAGE);

    if(addfriend_status) {
        setfont(FONT_MISC);
        setcolor(C_RED);

        STRING *str;
        switch(addfriend_status) {
        case ADDF_SENT:
            str = SPTR(REQ_SENT); break;
        case ADDF_DISCOVER:
            str = SPTR(REQ_RESOLVE); break;
        case ADDF_BADNAME:
            str = SPTR(REQ_INVALID_ID); break;
        case ADDF_NONAME:
            str = SPTR(REQ_EMPTY_ID); break;
        case ADDF_TOOLONG: //if message length is too long.
            str = SPTR(REQ_LONG_MSG); break;
        case ADDF_NOMESSAGE: //if no message (message length must be >= 1 byte).
            str = SPTR(REQ_NO_MSG); break;
        case ADDF_OWNKEY: //if user's own key.
            str = SPTR(REQ_SELF_ID); break;
        case ADDF_ALREADYSENT: //if friend request already sent or already a friend.
            str = SPTR(REQ_ALREADY_FRIENDS); break;
        case ADDF_BADCHECKSUM: //if bad checksum in address.
            str = SPTR(REQ_BAD_CHECKSUM); break;
        case ADDF_SETNEWNOSPAM: //if the friend was already there but the nospam was different.
            str = SPTR(REQ_BAD_NOSPAM); break;
        case ADDF_NOMEM: //if increasing the friend list size fails.
            str = SPTR(REQ_NO_MEMORY); break;
        case ADDF_UNKNOWN: //for unknown error.
        case ADDF_NONE: //this case must never be rendered, but if it does, assume it's an error
        default:
            str = SPTR(REQ_UNKNOWN); break;
        }

        drawtextmultiline(LIST_RIGHT + SCALE * 5, utox_window_width - BM_SBUTTON_WIDTH - 5 * SCALE, LIST_Y + SCALE * 83, 0, height, font_small_lineheight, str->str, str->length, 0xFFFF, 0, 1);
    }
}
Ejemplo n.º 2
0
void edit_draw(EDIT *edit, int x, int y, int width, int height)
{
    if((width - 4 * SCALE - SCROLL_WIDTH) < 0) {
        return;
    }

    if(utox_window_baseline && y > utox_window_baseline - font_small_lineheight - 4 * SCALE) {
        y = utox_window_baseline - font_small_lineheight - 4 * SCALE;
    }

    edit->width = width -4 * SCALE - (edit->multiline ? SCROLL_WIDTH : 0);
    edit->height = height - 4 * SCALE;

    if(!edit->noborder) {
        framerect(x, y, x + width, y + height, (edit == active_edit) ? BLUE : (edit->mouseover ? C_GRAY2 : C_GRAY));
    }
    drawrect(x + 1, y + 1, x + width - 1, y + height - 1, WHITE);

    setfont(FONT_TEXT);
    setcolor(COLOR_TEXT);

    int yy = y;

    if(edit->multiline) {
        pushclip(x + 1, y + 1, width - 2, height - 2);

        SCROLLABLE *scroll = edit->scroll;
        scroll->content_height = text_height(width - 4 * SCALE - SCROLL_WIDTH, font_small_lineheight, edit->data, edit->length) + 4 * SCALE;
        scroll_draw(scroll, x, y, width, height);
        yy -= scroll_gety(scroll, height);
    }


    if(!edit->length && maybe_i18nal_string_is_valid(&edit->empty_str)) {
        STRING* empty_str_text = maybe_i18nal_string_get(&edit->empty_str);
        setcolor(C_GRAY2);
        drawtext(x + 2 * SCALE, yy + 2 * SCALE, empty_str_text->str, empty_str_text->length);
    }

    _Bool a = (edit == active_edit);
    drawtextmultiline(x + 2 * SCALE, x + width - 2 * SCALE - (edit->multiline ? SCROLL_WIDTH : 0), yy + 2 * SCALE, y, y + height, font_small_lineheight, edit->data, edit->length,
                      a ? edit_sel.start : STRING_IDX_MAX, a ? edit_sel.length : STRING_IDX_MAX, edit->multiline);

    if(edit->multiline) {
        popclip();
    }
}
Ejemplo n.º 3
0
/** Formats all messages from self and friends, and then call draw functions
 * to write them to the UI.
 *
 * accepts: messages struct *pointer, int x,y positions, int width,height
 */
void messages_draw(MESSAGES *m, int x, int y, int width, int height)
{

    // Do not draw author name next to every message
    uint8_t lastauthor = 0xFF;

    // Message iterator
    void **p = m->data->data;
    MSG_IDX i, n = m->data->n;

    // Go through messages
    for(i = 0; i != n; i++) {
        MESSAGE *msg = *p++;

        // Empty message
        if(msg->height == 0) {
            return;
        }

        //! NOTE: should not be constant 0
        if(y + msg->height <= 0) {
            y += msg->height;
            continue;
        }

        //! NOTE: should not be constant 100
        if(y >= height + 50 * SCALE) {
            break;
        }

        // Draw timestamps
        {
            char timestr[6];
            STRING_IDX len;
            len = snprintf(timestr, sizeof(timestr), "%u:%.2u", msg->time / 60, msg->time % 60);
            if (len >= sizeof(timestr)) {
                len = sizeof(timestr) - 1;
            }

            setcolor(COLOR_MAIN_SUBTEXT);
            setfont(FONT_MISC);
            drawtext(x + width - TIME_WIDTH, y, (char_t*)timestr, len);
        }

        // Draw the names for groups or friends
        if(m->type) {
            // Group message authors are all the same colour
            setcolor(COLOR_MAIN_CHATTEXT);
            setfont(FONT_TEXT);
            drawtextwidth_right(x, MESSAGES_X - NAME_OFFSET, y, &msg->msg[msg->length] + 1, msg->msg[msg->length]);
        } else {
            FRIEND *f = &friend[m->data->id];

            // Always draw name next to action message
            if(msg->msg_type == MSG_TYPE_ACTION_TEXT)
                lastauthor = 0xFF;

            if(msg->author != lastauthor) {
                // Draw author name
                // If author is current user
                setfont(FONT_TEXT);
                if(msg->msg_type == MSG_TYPE_ACTION_TEXT)
                    setcolor(COLOR_MAIN_ACTIONTEXT);
                else
                    if(msg->author)
                        setcolor(COLOR_MAIN_SUBTEXT);
                    else
                        setcolor(COLOR_MAIN_CHATTEXT);
                if(msg->author)
                    drawtextwidth_right(x, MESSAGES_X - NAME_OFFSET, y, self.name, self.name_length);
                else
                    drawtextwidth_right(x, MESSAGES_X - NAME_OFFSET, y, f->name, f->name_length);
                lastauthor = msg->author;
            }
        }

        // Draw message contents
        switch(msg->msg_type) {
        case MSG_TYPE_TEXT:
        case MSG_TYPE_ACTION_TEXT: {
            // Normal message
            STRING_IDX h1 = STRING_IDX_MAX, h2 = STRING_IDX_MAX;
            if(i == m->data->istart) {
                h1 = m->data->start;
                h2 = ((i == m->data->iend) ? m->data->end : msg->length);
            } else if(i == m->data->iend) {
                h1 = 0;
                h2 = m->data->end;
            } else if(i > m->data->istart && i < m->data->iend) {
                h1 = 0;
                h2 = msg->length;
            }

            if((m->data->istart == m->data->iend && m->data->start == m->data->end) || h1 == h2) {
                h1 = STRING_IDX_MAX;
                h2 = STRING_IDX_MAX;
            }

            if(msg->author) {
                setcolor(COLOR_MAIN_SUBTEXT);
            } else {
                setcolor(COLOR_MAIN_CHATTEXT);
            }

            if (msg->msg_type == MSG_TYPE_ACTION_TEXT) {
                setcolor(COLOR_MAIN_ACTIONTEXT);
            }

            setfont(FONT_TEXT);
            int ny = drawtextmultiline(x + MESSAGES_X, x + width - TIME_WIDTH, y, y, y + msg->height, font_small_lineheight, msg->msg, msg->length, h1, h2 - h1, 1);
            if(ny < y || (uint32_t)(ny - y) + MESSAGES_SPACING != msg->height) {
                debug("error101 %u %u\n", ny -y, msg->height - MESSAGES_SPACING);
            }
            y = ny;

            break;
        }

        // Draw image
        case MSG_TYPE_IMAGE: {
            MSG_IMG *img = (void*)msg;
            int maxwidth = width - MESSAGES_X - TIME_WIDTH;
            draw_message_image(img->image, x + MESSAGES_X, y, img->w, img->h, maxwidth, img->zoom, img->position);
            y += (img->zoom || img->w <= maxwidth) ? img->h : img->h * maxwidth / img->w;
            break;
        }

        // Draw file transfer
        case MSG_TYPE_FILE: {
            MSG_FILE *file = (void*)msg;
            int dx = MESSAGES_X;
            /* Mouse Positions */
            _Bool mo = (m->iover == i);
            _Bool mouse_over = (mo && m->over) ? 1 : 0;
            _Bool mouse_tbtn = (mo && m->over == 1) ? 1 : 0;
            _Bool mouse_bbtn = (mo && m->over == 2) ? 1 : 0;

            /* Old var kept for bug hunting
            int xx = x + dx;
            int xxx = xx + BM_FTM_WIDTH + SCALE; */

            /* File transfer bar */
            int ftbar_x  = x + dx;
            int ftbar_y  = y;
            int ftbar_w  = BM_FT_WIDTH;
            int ftbar_sw = BM_FTM_WIDTH;
            int ftbar_h  = BM_FT_HEIGHT;
            /* Button Background */
            int btn_bg_x  = ftbar_x + BM_FTM_WIDTH + SCALE;
            int btn_bg_w  = BM_FTB_WIDTH;
            /* Button Background heights */
            int tbtn_bg_y = y;
            int bbtn_bg_y = y + BM_FTB_HEIGHT + SCALE * 2;
            int tbtn_bg_h  = BM_FTB_HEIGHT + SCALE;
            int bbtn_bg_h  = BM_FTB_HEIGHT;
            /* Top button info */
            int btnx    = ((x + dx) + BM_FTM_WIDTH + SCALE) + (BM_FTB_WIDTH - BM_FB_WIDTH) / 2;
            int tbtn_y    = y + SCALE * 4;
            int bbtn_y    = y + BM_FTB_HEIGHT + SCALE * 5;
            int btnw    = BM_FB_WIDTH;
            int btnh    = BM_FB_HEIGHT;

            char_t size[16];
            STRING_IDX sizelen = sprint_bytes(size, sizeof(size), file->size);
            uint64_t progress = file->progress;
            if(progress > file->size) {
                progress = file->size;
            }
            char_t size_text[16];
            STRING_IDX size_text_len = sprint_bytes(size_text, sizeof(size_text), file->speed);
            size_text[size_text_len++] = '/';
            size_text[size_text_len++] = 's';
            uint64_t etasec = 0;
            if(file->speed) {
                etasec = (file->size - progress) / file->speed;
            }

            char_t text2[16];
            STRING_IDX len2 = snprintf((char*)text2, sizeof(text2), "%us", (uint32_t)etasec);
            if (len2 >= sizeof(text2)) {
                len2 = sizeof(text2) - 1;
            }

            // progress rectangle
            uint32_t w = (file->size == 0) ? 0 : (progress * (uint64_t)106 * SCALE) / file->size;

            setfont(FONT_MISC);
            setcolor(COLOR_MAIN_BACKGROUND);

            switch (file->status){
            case FILE_TRANSFER_STATUS_COMPLETED: {
                /* If mouse over use hover color */
                setcolor((mouse_over) ? COLOR_BUTTON_SUCCESS_HOVER_TEXT : COLOR_BUTTON_SUCCESS_TEXT);

                drawalpha(BM_FT, ftbar_x, ftbar_y, ftbar_w, ftbar_h, (mouse_over) ? COLOR_BUTTON_SUCCESS_HOVER_BACKGROUND : COLOR_BUTTON_SUCCESS_BACKGROUND);
                drawalpha(BM_YES, btnx, tbtn_y, btnw, btnh, (mouse_over) ? COLOR_BUTTON_SUCCESS_HOVER_TEXT : COLOR_BUTTON_SUCCESS_TEXT);
                if(file->inline_png){
                    drawstr(x + dx + 5 * SCALE, y + 17 * SCALE, CLICKTOSAVE);
                } else {
                    drawstr(x + dx + 5 * SCALE, y + 17 * SCALE, CLICKTOOPEN);
                }
                break;
            }
            case FILE_TRANSFER_STATUS_KILLED:{
                setcolor(COLOR_BUTTON_DANGER_TEXT);

                drawalpha(BM_FT, ftbar_x, ftbar_y, ftbar_w, ftbar_h, COLOR_BUTTON_DANGER_BACKGROUND);
                drawalpha(BM_NO, btnx, tbtn_y, btnw, btnh, COLOR_BUTTON_DANGER_TEXT);

                drawstr(x + dx + 5 * SCALE, y + 17 * SCALE, TRANSFER_CANCELLED);
                break;
            }
            case FILE_TRANSFER_STATUS_BROKEN: {
                setcolor(COLOR_BUTTON_DANGER_TEXT);

                drawalpha(BM_FT, ftbar_x, ftbar_y, ftbar_w, ftbar_h, COLOR_BUTTON_DANGER_BACKGROUND);
                drawalpha(BM_NO, btnx, tbtn_y, btnw, btnh, COLOR_BUTTON_DANGER_TEXT);

                drawstr(x + dx + 5 * SCALE, y + 17 * SCALE, TRANSFER_BROKEN);
                break;
            }
            case FILE_TRANSFER_STATUS_NONE: {
                /* ↑ used for incoming transfers */
                setcolor(COLOR_BUTTON_DISABLED_TRANSFER);

                drawalpha(BM_FTM, ftbar_x, ftbar_y, ftbar_sw, ftbar_h, COLOR_BUTTON_DISABLED_BACKGROUND);

                drawalpha(BM_FTB1, btn_bg_x, tbtn_bg_y, btn_bg_w, tbtn_bg_h, (mouse_tbtn ? COLOR_BUTTON_SUCCESS_HOVER_BACKGROUND : COLOR_BUTTON_SUCCESS_BACKGROUND));
                drawalpha(BM_NO, btnx, tbtn_y, btnw, btnh, (mouse_tbtn ? COLOR_BUTTON_SUCCESS_HOVER_TEXT : COLOR_BUTTON_SUCCESS_TEXT));

                drawalpha(BM_FTB2, btn_bg_x, bbtn_bg_y, btn_bg_w, bbtn_bg_h, (mouse_bbtn ? COLOR_BUTTON_SUCCESS_HOVER_BACKGROUND : COLOR_BUTTON_SUCCESS_BACKGROUND));
                drawalpha(BM_YES, btnx, bbtn_y, btnw, btnh, (mouse_bbtn ? COLOR_BUTTON_SUCCESS_HOVER_TEXT : COLOR_BUTTON_SUCCESS_TEXT));

                framerect((x + dx) + 5 * SCALE, y + 17 * SCALE, (x + dx) + 111 * SCALE, y + 24 * SCALE, COLOR_BUTTON_DISABLED_TRANSFER);
                drawrectw((x + dx) + 5 * SCALE, y + 17 * SCALE, w, 7 * SCALE, COLOR_BUTTON_DISABLED_TRANSFER);
                break;
            }
            case FILE_TRANSFER_STATUS_ACTIVE: {
                setcolor(COLOR_BUTTON_INPROGRESS_TEXT);

                drawalpha(BM_FTM, ftbar_x, ftbar_y, ftbar_sw, ftbar_h, COLOR_BUTTON_INPROGRESS_BACKGROUND);

                drawalpha(BM_FTB1, btn_bg_x, tbtn_bg_y, btn_bg_w, tbtn_bg_h, (mouse_tbtn ? COLOR_BUTTON_SUCCESS_HOVER_BACKGROUND : COLOR_BUTTON_SUCCESS_BACKGROUND));
                drawalpha(BM_NO, btnx, tbtn_y, btnw, btnh, (mouse_tbtn ? COLOR_BUTTON_SUCCESS_HOVER_TEXT : COLOR_BUTTON_SUCCESS_TEXT));

                drawalpha(BM_FTB2, btn_bg_x, bbtn_bg_y, btn_bg_w, bbtn_bg_h, (mouse_bbtn ? COLOR_BUTTON_SUCCESS_HOVER_BACKGROUND : COLOR_BUTTON_SUCCESS_BACKGROUND));
                drawalpha(BM_PAUSE, btnx, bbtn_y, btnw, btnh, (mouse_bbtn ? COLOR_BUTTON_SUCCESS_HOVER_TEXT : COLOR_BUTTON_SUCCESS_TEXT));

                drawtext(x + dx + 5 * SCALE + 53 * SCALE - textwidth(size_text, size_text_len) / 2, y + 10 * SCALE, size_text, size_text_len);
                drawtext(x + dx + 5 * SCALE + 106 * SCALE - textwidth(text2, len2), y + 10 * SCALE, text2, len2);

                framerect((x + dx) + 5 * SCALE, y + 17 * SCALE, (x + dx) + 111 * SCALE, y + 24 * SCALE, COLOR_BUTTON_INPROGRESS_TEXT);
                drawrectw((x + dx) + 5 * SCALE, y + 17 * SCALE, w, 7 * SCALE, COLOR_BUTTON_INPROGRESS_TEXT);
                break;
            }
            case FILE_TRANSFER_STATUS_PAUSED_US:
            case FILE_TRANSFER_STATUS_PAUSED_BOTH:
            case FILE_TRANSFER_STATUS_PAUSED_THEM: {
                setcolor(COLOR_BUTTON_DISABLED_TRANSFER);

                drawalpha(BM_FTM, ftbar_x, ftbar_y, ftbar_sw, ftbar_h, COLOR_BUTTON_DISABLED_BACKGROUND);

                drawalpha(BM_FTB1, btn_bg_x, tbtn_bg_y, btn_bg_w, tbtn_bg_h, (mouse_tbtn ? COLOR_BUTTON_SUCCESS_HOVER_BACKGROUND : COLOR_BUTTON_SUCCESS_BACKGROUND));
                drawalpha(BM_NO, btnx, tbtn_y, btnw, btnh, (mouse_tbtn ? COLOR_BUTTON_SUCCESS_HOVER_TEXT : COLOR_BUTTON_SUCCESS_TEXT));

                if(file->status <= FILE_TRANSFER_STATUS_PAUSED_BOTH){
                    /* Paused by at least us */
                    drawalpha(BM_FTB2, btn_bg_x, bbtn_bg_y, btn_bg_w, bbtn_bg_h, (mouse_bbtn ? COLOR_BUTTON_SUCCESS_HOVER_BACKGROUND : COLOR_BUTTON_SUCCESS_BACKGROUND));
                    drawalpha(BM_RESUME, btnx, bbtn_y, btnw, btnh, (mouse_bbtn ? COLOR_BUTTON_SUCCESS_HOVER_TEXT : COLOR_BUTTON_SUCCESS_TEXT));
                } else {
                    /* Paused only by them */
                    drawalpha(BM_FTB2, btn_bg_x, bbtn_bg_y, btn_bg_w, bbtn_bg_h, COLOR_BUTTON_DISABLED_BACKGROUND);
                    drawalpha(BM_PAUSE, btnx, bbtn_y, btnw, btnh, COLOR_BUTTON_DISABLED_TRANSFER);
                }

                framerect((x + dx) + 5 * SCALE, y + 17 * SCALE, (x + dx) + 111 * SCALE, y + 24 * SCALE, COLOR_BUTTON_DISABLED_TRANSFER);
                drawrectw((x + dx) + 5 * SCALE, y + 17 * SCALE, w, 7 * SCALE, COLOR_BUTTON_DISABLED_TRANSFER);
                break;
            }
            }

            drawtext(x + dx + 5 * SCALE, y + 10 * SCALE, size, sizelen);
            drawtextwidth(x + dx + 5 * SCALE, 106 * SCALE, y + 3 * SCALE, file->name, file->name_length);

            y += BM_FT_HEIGHT;
            break;

        }
        }

        y += MESSAGES_SPACING;
    }

    if(i == n) {
        // Last message is visible. Append typing notifications, if needed.
        FRIEND *f = get_typers(m);
        if(f) {
            setfont(FONT_TEXT);
            // @TODO: separate these colours if needed
            setcolor(COLOR_MAIN_HINTTEXT);
            drawtextwidth_right(x, MESSAGES_X - NAME_OFFSET, y, f->name, f->name_length);
            drawtextwidth(x + MESSAGES_X, x + width, y, S(IS_TYPING), SLEN(IS_TYPING));
        }
    }
}