add combobox widget
git-svn-id: https://rt-thread.googlecode.com/svn/trunk@1174 bbd45198-f89e-11dd-88c7-29a3b14d5316
This commit is contained in:
parent
80af4ee98e
commit
3f5623a8ee
|
@ -156,7 +156,7 @@ static void rtgui_bitmap_font_get_metrics(struct rtgui_font* font, const char* t
|
|||
if (bmp_font->char_width != NULL)
|
||||
{
|
||||
/* get width for each character */
|
||||
while (*text < 0x80)
|
||||
while (*text && (*text < 0x80))
|
||||
{
|
||||
rect->x2 += bmp_font->char_width[*text - bmp_font->first_char];
|
||||
text ++;
|
||||
|
|
|
@ -2,8 +2,8 @@
|
|||
|
||||
#ifdef RTGUI_USING_TTF
|
||||
#include <ft2build.h>
|
||||
#include <freetype/freetype.h>
|
||||
#include <freetype/ftglyph.h>
|
||||
#include <freetype/freetype.h>
|
||||
#include <freetype/ftglyph.h>
|
||||
|
||||
static void rtgui_freetype_font_draw_text(struct rtgui_font* font, struct rtgui_dc* dc, const char* text, rt_ubase_t len, struct rtgui_rect* rect);
|
||||
static void rtgui_freetype_font_get_metrics(struct rtgui_font* font, const char* text, rtgui_rect_t* rect);
|
||||
|
|
|
@ -1,10 +1,11 @@
|
|||
#include <rtthread.h>
|
||||
#include <rtgui/rtgui.h>
|
||||
|
||||
#ifdef RTGUI_USING_JPEG
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include "jpeg/jpeglib.h"
|
||||
|
||||
#include <rtthread.h>
|
||||
#include <rtgui/rtgui.h>
|
||||
#include <rtgui/rtgui_system.h>
|
||||
#include <rtgui/filerw.h>
|
||||
#include <rtgui/image_jpeg.h>
|
||||
|
@ -476,3 +477,4 @@ static rt_bool_t rtgui_image_jpeg_check(struct rtgui_filerw* file)
|
|||
return is_JPG;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
|
|
@ -1,8 +1,10 @@
|
|||
#include "libpng/png.h"
|
||||
#include <rtthread.h>
|
||||
#include <rtgui/image_png.h>
|
||||
#include <rtgui/rtgui_system.h>
|
||||
|
||||
#ifdef RTGUI_USING_PNG
|
||||
#include "libpng/png.h"
|
||||
#include <rtgui/image_png.h>
|
||||
|
||||
#define PNG_MAGIC_LEN 8
|
||||
|
||||
struct rtgui_image_png
|
||||
|
@ -328,3 +330,4 @@ void rtgui_image_png_init()
|
|||
/* register png on image system */
|
||||
rtgui_image_register_engine(&rtgui_image_png_engine);
|
||||
}
|
||||
#endif
|
||||
|
|
|
@ -403,7 +403,6 @@ rt_err_t rtgui_thread_send_urgent(rt_thread_t tid, rtgui_event_t* event, rt_size
|
|||
struct rtgui_thread* thread;
|
||||
|
||||
rtgui_event_dump(tid, event);
|
||||
rt_kprintf("event size: %d\n", event_size);
|
||||
|
||||
/* find rtgui_thread */
|
||||
thread = (struct rtgui_thread*) (tid->user_data);
|
||||
|
@ -424,7 +423,6 @@ rt_err_t rtgui_thread_send_sync(rt_thread_t tid, rtgui_event_t* event, rt_size_t
|
|||
struct rt_mailbox ack_mb;
|
||||
|
||||
rtgui_event_dump(tid, event);
|
||||
rt_kprintf("event size: %d\n", event_size);
|
||||
|
||||
/* init ack mailbox */
|
||||
r = rt_mb_init(&ack_mb, "ack", &ack_buffer, 1, 0);
|
||||
|
|
|
@ -68,7 +68,7 @@ struct rtgui_dc
|
|||
|
||||
/* create a buffer dc */
|
||||
struct rtgui_dc* rtgui_dc_buffer_create(int width, int height);
|
||||
rt_uint8_t* rtgui_dc_buffer_get_pixel(struct rtgui_dc* dc);
|
||||
rt_uint8_t* rtgui_dc_buffer_get_pixel(struct rtgui_dc* dc);
|
||||
|
||||
/* begin and end a drawing */
|
||||
struct rtgui_dc* rtgui_dc_begin_drawing(rtgui_widget_t* owner);
|
||||
|
|
|
@ -26,7 +26,7 @@
|
|||
/* support Chinese font */
|
||||
#define RTGUI_USING_FONTHZ
|
||||
/* support FreeType TTF font */
|
||||
#define RTGUI_USING_TTF
|
||||
// #define RTGUI_USING_TTF
|
||||
/* use small size in RTGUI */
|
||||
#define RTGUI_USING_SMALL_SIZE
|
||||
/* use mouse cursor */
|
||||
|
@ -36,8 +36,8 @@
|
|||
|
||||
#define RTGUI_USING_STDIO_FILERW
|
||||
#define RTGUI_IMAGE_BMP
|
||||
#define RTGUI_IMAGE_PNG
|
||||
#define RTGUI_IMAGE_JPEG
|
||||
// #define RTGUI_IMAGE_PNG
|
||||
// #define RTGUI_IMAGE_JPEG
|
||||
#define RTGUI_USING_FONT12
|
||||
#define RTGUI_USING_HZ_BMP
|
||||
#define RTGUI_MEM_TRACE
|
||||
|
|
|
@ -0,0 +1,53 @@
|
|||
#ifndef __RTGUI_COMBOBOX_H__
|
||||
#define __RTGUI_COMBOBOX_H__
|
||||
|
||||
#include <rtgui/rtgui.h>
|
||||
#include <rtgui/image.h>
|
||||
#include <rtgui/widgets/window.h>
|
||||
|
||||
/* combobox item */
|
||||
struct rtgui_combobox_item
|
||||
{
|
||||
char* name;
|
||||
rtgui_image_t *image;
|
||||
};
|
||||
|
||||
/** Gets the type of a combobox */
|
||||
#define RTGUI_COMBOBOX_TYPE (rtgui_combobox_type_get())
|
||||
/** Casts the object to a rtgui_combobox */
|
||||
#define RTGUI_COMBOBOX(obj) (RTGUI_OBJECT_CAST((obj), RTGUI_COMBOBOX_TYPE, rtgui_combobox_t))
|
||||
/** Checks if the object is a rtgui_combobox */
|
||||
#define RTGUI_IS_COMBOBOX(obj) (RTGUI_OBJECT_CHECK_TYPE((obj), RTGUI_COMBOBOX_TYPE))
|
||||
|
||||
#define RTGUI_COMBOBOX_WIDTH 75
|
||||
#define RTGUI_COMBOBOX_HEIGHT 20
|
||||
#define RTGUI_COMBOBOX_BUTTON_WIDTH 18
|
||||
|
||||
struct rtgui_combobox
|
||||
{
|
||||
struct rtgui_widget parent;
|
||||
|
||||
/* widget private data */
|
||||
|
||||
/* pull down window */
|
||||
struct rtgui_win* pd_win;
|
||||
rt_bool_t pd_pressed;
|
||||
|
||||
/* combobox items */
|
||||
struct rtgui_combobox_item* items;
|
||||
rt_uint16_t items_count;
|
||||
rt_uint16_t current_item;
|
||||
|
||||
/* call back */
|
||||
rt_bool_t (*on_selected) (struct rtgui_widget* widget, struct rtgui_event* event);
|
||||
};
|
||||
typedef struct rtgui_combobox rtgui_combobox_t;
|
||||
|
||||
rtgui_type_t *rtgui_combobox_type_get(void);
|
||||
rtgui_combobox_t *rtgui_combobox_create();
|
||||
void rtgui_combobox_destroy(rtgui_combobox_t* box);
|
||||
|
||||
rt_bool_t rtgui_combobox_event_handler(struct rtgui_widget* widget, struct rtgui_event* event);
|
||||
struct rtgui_item* rtgui_combox_get_select(struct rtgui_combobox* box);
|
||||
|
||||
#endif
|
|
@ -0,0 +1,237 @@
|
|||
#include <rtgui/dc.h>
|
||||
#include <rtgui/widgets/combobox.h>
|
||||
|
||||
static rt_bool_t rtgui_combobox_pulldown_hide(struct rtgui_widget* widget, struct rtgui_event* event);
|
||||
|
||||
static void _rtgui_combobox_constructor(rtgui_combobox_t *box)
|
||||
{
|
||||
rtgui_rect_t rect = {0, 0, RTGUI_COMBOBOX_WIDTH, RTGUI_COMBOBOX_HEIGHT};
|
||||
|
||||
/* init widget and set event handler */
|
||||
rtgui_widget_set_event_handler(RTGUI_WIDGET(box), rtgui_combobox_event_handler);
|
||||
rtgui_widget_set_rect(RTGUI_WIDGET(box), &rect);
|
||||
|
||||
RTGUI_WIDGET_TEXTALIGN(RTGUI_WIDGET(box)) = RTGUI_ALIGN_CENTER_VERTICAL;
|
||||
|
||||
box->pd_pressed = RT_FALSE;
|
||||
box->current_item = 0;
|
||||
box->on_selected = RT_NULL;
|
||||
|
||||
box->pd_win = rtgui_win_create(RT_NULL, "combo", &rect, RTGUI_WIN_STYLE_NO_TITLE);
|
||||
box->pd_win->user_data = (rt_uint32_t)box;
|
||||
rtgui_win_set_ondeactivate(RTGUI_WIN(box->pd_win), rtgui_combobox_pulldown_hide);
|
||||
}
|
||||
|
||||
static void _rtgui_combobox_destructor(rtgui_combobox_t *box)
|
||||
{
|
||||
/* destroy pull down window */
|
||||
rtgui_win_destroy(box->pd_win);
|
||||
|
||||
/* reset box field */
|
||||
box->pd_win = RT_NULL;
|
||||
}
|
||||
|
||||
rtgui_type_t *rtgui_combobox_type_get(void)
|
||||
{
|
||||
static rtgui_type_t *combobox_type = RT_NULL;
|
||||
|
||||
if (!combobox_type)
|
||||
{
|
||||
combobox_type = rtgui_type_create("combobox", RTGUI_WIDGET_TYPE,
|
||||
sizeof(rtgui_combobox_t),
|
||||
RTGUI_CONSTRUCTOR(_rtgui_combobox_constructor),
|
||||
RTGUI_DESTRUCTOR(_rtgui_combobox_destructor));
|
||||
}
|
||||
|
||||
return combobox_type;
|
||||
}
|
||||
|
||||
rtgui_combobox_t *rtgui_combobox_create()
|
||||
{
|
||||
rtgui_combobox_t* box;
|
||||
|
||||
box = (rtgui_combobox_t*)rtgui_widget_create(RTGUI_COMBOBOX_TYPE);
|
||||
|
||||
return box;
|
||||
}
|
||||
|
||||
void rtgui_combobox_destroy(rtgui_combobox_t* box)
|
||||
{
|
||||
rtgui_widget_destroy(RTGUI_WIDGET(box));
|
||||
}
|
||||
|
||||
static void rtgui_combobox_ondraw(struct rtgui_combobox* box)
|
||||
{
|
||||
/* draw button */
|
||||
struct rtgui_dc* dc;
|
||||
struct rtgui_rect rect;
|
||||
|
||||
/* begin drawing */
|
||||
dc = rtgui_dc_begin_drawing(RTGUI_WIDGET(box));
|
||||
if (dc == RT_NULL) return;
|
||||
|
||||
/* get widget rect */
|
||||
rtgui_widget_get_rect(RTGUI_WIDGET(box), &rect);
|
||||
/* fill widget rect with background color */
|
||||
rtgui_dc_fill_rect(dc, &rect);
|
||||
rtgui_dc_draw_border(dc, &rect, RTGUI_BORDER_RAISE);
|
||||
|
||||
/* draw current item */
|
||||
if (box->current_item < box->items_count)
|
||||
{
|
||||
rect.x1 += 5;
|
||||
rtgui_dc_draw_text(dc, box->items[box->current_item].name, &rect);
|
||||
}
|
||||
|
||||
/* draw pull down button */
|
||||
rect.x1 = rect.x2 - RTGUI_COMBOBOX_BUTTON_WIDTH;
|
||||
rtgui_rect_inflate(&rect, -1);
|
||||
if (box->pd_pressed == RT_TRUE) rtgui_dc_draw_border(dc, &rect, RTGUI_BORDER_SUNKEN);
|
||||
else rtgui_dc_draw_border(dc, &rect, RTGUI_BORDER_RAISE);
|
||||
rtgui_dc_draw_arraw(dc, &rect, RTGUI_ARRAW_DOWN);
|
||||
|
||||
/* end drawing */
|
||||
rtgui_dc_end_drawing(dc);
|
||||
return;
|
||||
}
|
||||
|
||||
static rt_bool_t rtgui_combobox_onmouse_button(struct rtgui_combobox* box, struct rtgui_event_mouse* event)
|
||||
{
|
||||
struct rtgui_rect rect;
|
||||
|
||||
/* get widget rect */
|
||||
rect = RTGUI_WIDGET(box)->extent;
|
||||
|
||||
/* move to the pull down button */
|
||||
rect.x1 = rect.x2 - RTGUI_COMBOBOX_BUTTON_WIDTH;
|
||||
if (rtgui_rect_contains_point(&rect, event->x, event->y) == RT_EOK)
|
||||
{
|
||||
/* handle mouse button on pull down button */
|
||||
if (event->button & RTGUI_MOUSE_BUTTON_LEFT &&
|
||||
event->button & RTGUI_MOUSE_BUTTON_DOWN)
|
||||
{
|
||||
box->pd_pressed = RT_TRUE;
|
||||
rtgui_widget_update(RTGUI_WIDGET(box));
|
||||
}
|
||||
else if (event->button & RTGUI_MOUSE_BUTTON_LEFT &&
|
||||
event->button & RTGUI_MOUSE_BUTTON_UP)
|
||||
{
|
||||
box->pd_pressed = RT_FALSE;
|
||||
rtgui_widget_update(RTGUI_WIDGET(box));
|
||||
|
||||
/* pop pull down window */
|
||||
if (box->pd_win != RT_NULL)
|
||||
{
|
||||
struct rtgui_rect r;
|
||||
rtgui_box_t* pd_win_box;
|
||||
|
||||
r.x1 = RTGUI_WIDGET(box)->extent.x1;
|
||||
r.y1 = RTGUI_WIDGET(box)->extent.y2 + 2;
|
||||
r.x2 = RTGUI_WIDGET(box)->extent.x2;
|
||||
r.y2 = r.y1 + box->pd_win_height;
|
||||
|
||||
rtgui_win_set_rect(RTGUI_WIN(box->pd_win), &r);
|
||||
pd_win_box = (rtgui_box_t*) rtgui_container_get_first_child(RTGUI_CONTAINER(box->pd_win));
|
||||
if (pd_win_box != RT_NULL)
|
||||
{
|
||||
RTGUI_WIDGET(pd_win_box)->extent = RTGUI_WIDGET(box->pd_win)->extent;
|
||||
rtgui_box_layout(pd_win_box);
|
||||
}
|
||||
|
||||
/* show combo box pull down window */
|
||||
rtgui_win_show(RTGUI_WIN(box->pd_win), RT_FALSE);
|
||||
}
|
||||
}
|
||||
|
||||
return RT_TRUE;
|
||||
}
|
||||
|
||||
return RT_FALSE;
|
||||
}
|
||||
|
||||
rt_bool_t rtgui_combobox_event_handler(struct rtgui_widget* widget, struct rtgui_event* event)
|
||||
{
|
||||
struct rtgui_combobox* box = (struct rtgui_combobox*)widget;
|
||||
|
||||
switch (event->type)
|
||||
{
|
||||
case RTGUI_EVENT_PAINT:
|
||||
#ifndef RTGUI_USING_SMALL_SIZE
|
||||
if (widget->on_draw != RT_NULL) widget->on_draw(widget, event);
|
||||
else
|
||||
#endif
|
||||
rtgui_combobox_ondraw(box);
|
||||
|
||||
break;
|
||||
|
||||
case RTGUI_EVENT_MOUSE_BUTTON:
|
||||
return rtgui_combobox_onmouse_button(box, (struct rtgui_event_mouse*)event);
|
||||
|
||||
case RTGUI_EVENT_FOCUSED:
|
||||
{
|
||||
/* item focused */
|
||||
struct rtgui_item* item;
|
||||
struct rtgui_event_focused* focused;
|
||||
|
||||
focused = (struct rtgui_event_focused*) event;
|
||||
|
||||
item = (struct rtgui_item*) (focused->widget);
|
||||
if (item != RT_NULL)
|
||||
{
|
||||
if (box->pd_select != RT_NULL)
|
||||
{
|
||||
/* un-select old item */
|
||||
rtgui_item_selected(box->pd_select, RT_FALSE);
|
||||
}
|
||||
|
||||
box->pd_select = item;
|
||||
if (box->on_selected != RT_NULL)
|
||||
{
|
||||
box->on_selected(RTGUI_WIDGET(box), RT_NULL);
|
||||
}
|
||||
|
||||
/* hide pull down window */
|
||||
rtgui_win_hiden(RTGUI_WIN(box->pd_win));
|
||||
rtgui_combobox_ondraw(box);
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
return RT_FALSE;
|
||||
}
|
||||
|
||||
static rt_bool_t rtgui_combobox_pulldown_hide(struct rtgui_widget* widget, struct rtgui_event* event)
|
||||
{
|
||||
struct rtgui_combobox* box;
|
||||
|
||||
if (widget == RT_NULL) return RT_TRUE;
|
||||
|
||||
box = (struct rtgui_combobox*) (((struct rtgui_win*)widget)->user_data);
|
||||
if (box == RT_NULL) return RT_TRUE;
|
||||
|
||||
/* clear select item */
|
||||
if (box->pd_select != RT_NULL)
|
||||
{
|
||||
rtgui_item_selected(box->pd_select, RT_FALSE);
|
||||
}
|
||||
|
||||
/* hide pull down window */
|
||||
rtgui_win_hiden(RTGUI_WIN(box->pd_win));
|
||||
|
||||
/* clear pull down button state */
|
||||
box->pd_pressed = RT_FALSE;
|
||||
rtgui_widget_update(RTGUI_WIDGET(box));
|
||||
|
||||
return RT_TRUE;
|
||||
}
|
||||
|
||||
struct rtgui_item* rtgui_combox_get_select(struct rtgui_combobox* box)
|
||||
{
|
||||
if ((box != RT_NULL) && (box->current_item < box->items_count))
|
||||
{
|
||||
return &(box->items[box->current_item]);
|
||||
}
|
||||
|
||||
return RT_NULL;
|
||||
}
|
Loading…
Reference in New Issue