diff options
| author | [email protected] <[email protected]> | 2011-03-24 14:00:19 +0000 |
|---|---|---|
| committer | [email protected] <[email protected]> | 2011-03-24 14:00:19 +0000 |
| commit | 0e93e6809c7beac4597148edc1dc09bcdf9a2ab3 (patch) | |
| tree | 113765e7f8351d84226a3de04f13daf86ddd82f9 /components/rtgui_win/widgets | |
| parent | 96c53b49571adadd957df804f4f5e6698c14e3b3 (diff) | |
add rtgui_win subfield,Highlight the ease of use
git-svn-id: https://rt-thread.googlecode.com/svn/trunk@1345 bbd45198-f89e-11dd-88c7-29a3b14d5316
Diffstat (limited to 'components/rtgui_win/widgets')
22 files changed, 8010 insertions, 0 deletions
diff --git a/components/rtgui_win/widgets/button.c b/components/rtgui_win/widgets/button.c new file mode 100644 index 0000000000..93e6863869 --- /dev/null +++ b/components/rtgui_win/widgets/button.c @@ -0,0 +1,238 @@ +/* + * File : button.c + * This file is part of RT-Thread RTOS + * COPYRIGHT (C) 2006 - 2009, RT-Thread Development Team + * + * The license and distribution terms for this file may be + * found in the file LICENSE in this distribution or at + * http://www.rt-thread.org/license/LICENSE + * + * Change Logs: + * Date Author Notes + * 2009-10-16 Bernard first version + */ +#include <rtgui/dc.h> +#include <rtgui/widgets/button.h>
+#include <rtgui/widgets/container.h> +#include <rtgui/rtgui_theme.h>
+ +static rt_bool_t rtgui_button_onunfocus(PVOID wdt, rtgui_event_t* event);
+ +static void _rtgui_button_constructor(rtgui_button_t *button) +{ + /* init widget and set event handler */ + RTGUI_WIDGET_FLAG(button) |= RTGUI_WIDGET_FLAG_FOCUSABLE;
+ + rtgui_widget_set_event_handler(button, rtgui_button_event_handler); + rtgui_widget_set_onunfocus(button, rtgui_button_onunfocus); + /* un-press button */ + button->flag = 0;
+ rtgui_widget_set_style(button,RTGUI_BORDER_UP); + + /* set flag and on_button event handler */ + button->image = RT_NULL; + button->on_button = RT_NULL; + + /* set gc */ + RTGUI_WIDGET_FOREGROUND(button) = default_foreground; + RTGUI_WIDGET_BACKGROUND(button) = default_background;
+ RTGUI_WIDGET_TEXTALIGN(button) = RTGUI_ALIGN_CENTER_HORIZONTAL|RTGUI_ALIGN_CENTER_VERTICAL; +} + +static void _rtgui_button_destructor(rtgui_button_t *button) +{ + if(button->image != RT_NULL) + { + rtgui_image_destroy(button->image); + button->image = RT_NULL; + } +} + +rtgui_type_t *rtgui_button_type_get(void) +{ + static rtgui_type_t *button_type = RT_NULL; + + if(!button_type) + { + button_type = rtgui_type_create("button", RTGUI_LABEL_TYPE, + sizeof(rtgui_button_t), + RTGUI_CONSTRUCTOR(_rtgui_button_constructor), + RTGUI_DESTRUCTOR(_rtgui_button_destructor)); + } + + return button_type; +}
+ +rtgui_button_t* rtgui_button_create(PVOID parent, char* text,int left, int top, int w, int h) +{ + rtgui_button_t* btn;
+ + RT_ASSERT(parent != RT_NULL);
+ + btn = rtgui_widget_create(RTGUI_BUTTON_TYPE); + if(btn != RT_NULL) + { + rtgui_rect_t rect; + /* set default rect */ + rtgui_font_get_string_rect(RTGUI_WIDGET_FONT(btn), text, &rect); +
+ rtgui_label_set_text(RTGUI_LABEL(btn), text);
+
+ rtgui_widget_get_rect(parent, &rect);
+ rtgui_widget_rect_to_device(parent,&rect);
+ rect.x1 += left;
+ rect.y1 += top;
+ rect.x2 = rect.x1+w;
+ rect.y2 = rect.y1+h; + rtgui_widget_set_rect(btn, &rect);
+
+ rtgui_container_add_child(parent, btn); + } + + return btn; +} + +void rtgui_button_destroy(rtgui_button_t* btn) +{ + rtgui_widget_destroy(btn); +}
+ +rt_bool_t rtgui_button_event_handler(PVOID wdt, rtgui_event_t* event) +{ + rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ rtgui_button_t* btn = (rtgui_button_t*) widget;
+ + if(btn == RT_NULL)return RT_FALSE; + + switch (event->type) + { + case RTGUI_EVENT_PAINT: + if(widget->on_draw != RT_NULL )
+ widget->on_draw(widget, event); + else + rtgui_theme_draw_button(btn); + break; + + case RTGUI_EVENT_KBD: + { + rtgui_event_kbd_t* ekbd = (rtgui_event_kbd_t*) event; + + if((ekbd->key == RTGUIK_RETURN) || (ekbd->key == RTGUIK_SPACE)) + { + if(RTGUI_KBD_IS_DOWN(ekbd)) + { + btn->flag |= RTGUI_BUTTON_FLAG_PRESS; + } + else + { + btn->flag &= ~RTGUI_BUTTON_FLAG_PRESS; + } + + /* draw button */ + rtgui_theme_draw_button(btn); + + if((btn->flag & RTGUI_BUTTON_FLAG_PRESS) && (btn->on_button != RT_NULL)) + { + /* call on button handler */ + btn->on_button(widget, event); + } + } + } + break; + + case RTGUI_EVENT_MOUSE_BUTTON: + { + rtgui_event_mouse_t* emouse = (rtgui_event_mouse_t*)event; + + if(emouse->button & RTGUI_MOUSE_BUTTON_LEFT) + {
+ rtgui_widget_focus(widget);
+ /* it's a normal button */ + if(emouse->button & RTGUI_MOUSE_BUTTON_DOWN) + { + btn->flag |= RTGUI_BUTTON_FLAG_PRESS; + } + else + { + btn->flag &= ~RTGUI_BUTTON_FLAG_PRESS; + } + + /* draw button */ + if(widget->on_draw != RT_NULL )
+ widget->on_draw(widget, event); + else
+ { + rtgui_theme_draw_button(btn);
+ } + + /* invokes call back */ + if(widget->on_mouseclick != RT_NULL && emouse->button & RTGUI_MOUSE_BUTTON_UP) + return widget->on_mouseclick(widget, event); + + if(!(btn->flag & RTGUI_BUTTON_FLAG_PRESS) && (btn->on_button != RT_NULL)) + { + /* call on button handler */ + btn->on_button(widget, event); + } + } + + return RT_TRUE; + }
+ default:
+ break; + } + + return RT_FALSE; +} + +void rtgui_button_set_image(rtgui_button_t* btn, rtgui_image_t* image) +{ + if(btn == RT_NULL)return; + + btn->image = image; +} + +void rtgui_button_set_onbutton(rtgui_button_t* btn, rtgui_onbutton_func_t func) +{ + RT_ASSERT(btn != RT_NULL); + + btn->on_button = func; +}
+ +static rt_bool_t rtgui_button_onunfocus(PVOID wdt, rtgui_event_t* event)
+{
+ rtgui_rect_t rect;
+ rtgui_button_t *btn = (rtgui_button_t*)wdt;
+ rtgui_dc_t *dc;
+
+ RT_ASSERT(wdt != RT_NULL);
+
+ dc = rtgui_dc_begin_drawing(wdt);
+ if(dc == RT_NULL)return RT_FALSE;
+ + rtgui_widget_get_rect(btn, &rect);
+
+ if(!RTGUI_WIDGET_IS_FOCUSED(btn)) + {//��������
+ rtgui_color_t color; + rtgui_rect_inflate(&rect, -2);
+ color = RTGUI_DC_FC(dc); + RTGUI_DC_FC(dc) = RTGUI_DC_BC(dc); + rtgui_dc_draw_focus_rect(dc,&rect);
+ RTGUI_DC_FC(dc) = color; + }
+
+ rtgui_dc_end_drawing(dc);
+ + return RT_TRUE;
+}
+
+void rtgui_button_set_text(rtgui_button_t* btn, const char* text) +{ + if(btn == RT_NULL)return;
+
+ rtgui_label_set_text(RTGUI_LABEL(btn), text); + + /* update widget */ + rtgui_theme_draw_button(btn); +} diff --git a/components/rtgui_win/widgets/checkbox.c b/components/rtgui_win/widgets/checkbox.c new file mode 100644 index 0000000000..6b97bf995d --- /dev/null +++ b/components/rtgui_win/widgets/checkbox.c @@ -0,0 +1,211 @@ +#include <rtgui/dc.h>
+#include <rtgui/rtgui_theme.h>
+#include <rtgui/widgets/container.h>
+#include <rtgui/widgets/checkbox.h>
+
+static rt_bool_t rtgui_checkbox_onunfocus(PVOID wdt, rtgui_event_t* event);
+
+static void _rtgui_checkbox_constructor(rtgui_checkbox_t *checkbox)
+{
+ /* init widget and set event handler */
+ RTGUI_WIDGET_FLAG(checkbox) |= RTGUI_WIDGET_FLAG_FOCUSABLE;
+ rtgui_widget_set_event_handler(checkbox, rtgui_checkbox_event_handler);
+ + rtgui_widget_set_onunfocus(checkbox, rtgui_checkbox_onunfocus);
+ /* set status */
+ checkbox->value = 0;
+
+ /* set default gc */
+ RTGUI_WIDGET_TEXTALIGN(checkbox) = RTGUI_ALIGN_LEFT | RTGUI_ALIGN_CENTER_VERTICAL;
+}
+
+static void _rtgui_checkbox_destructor(rtgui_checkbox_t *checkbox)
+{
+
+}
+
+rtgui_type_t *rtgui_checkbox_type_get(void)
+{
+ static rtgui_type_t *checkbox_type = RT_NULL;
+
+ if(!checkbox_type)
+ {
+ checkbox_type = rtgui_type_create("checkbox", RTGUI_LABEL_TYPE,
+ sizeof(rtgui_checkbox_t),
+ RTGUI_CONSTRUCTOR(_rtgui_checkbox_constructor),
+ RTGUI_DESTRUCTOR(_rtgui_checkbox_destructor));
+ }
+
+ return checkbox_type;
+}
+
+rtgui_checkbox_t* rtgui_checkbox_create(PVOID parent,const char* text, rt_bool_t checked,rtgui_color_t fc,int left,int top)
+{
+ rtgui_checkbox_t* box;
+
+ RT_ASSERT(parent != RT_NULL);
+
+ box = rtgui_widget_create (RTGUI_CHECKBOX_TYPE);
+ if(box != RT_NULL)
+ {
+ rtgui_rect_t rect,text_rect;
+
+ rtgui_widget_get_rect(parent, &rect);
+ rtgui_widget_rect_to_device(parent,&rect);
+ /* set default rect */
+ rtgui_font_get_string_rect(RTGUI_WIDGET_FONT(box), text, &text_rect);
+ text_rect.x2 += RTGUI_WIDGET_BORDER(box) + 5 + (RTGUI_WIDGET_BORDER(box) << 1);
+ text_rect.y2 += (RTGUI_WIDGET_BORDER(box) << 1);
+
+ rect.x1 += left;
+ rect.y1 += top;
+ rect.x2 = rect.x1 + CHECK_BOX_W + rtgui_rect_width(text_rect);
+ rect.y2 = rect.y1 + rtgui_rect_height(text_rect);
+
+ rtgui_widget_set_rect(box, &rect);
+
+ rtgui_checkbox_set_text(box, text);
+ RTGUI_WIDGET_FOREGROUND(box) = fc;
+ if(checked == RT_TRUE)
+ box->value = 1;
+ else
+ box->value = 0;
+ rtgui_container_add_child(parent, box);
+ }
+
+ return box;
+}
+
+void rtgui_checkbox_destroy(rtgui_checkbox_t* box)
+{
+ rtgui_widget_destroy(box);
+}
+
+rt_bool_t rtgui_checkbox_event_handler(PVOID wdt, rtgui_event_t* event)
+{
+ rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ rtgui_checkbox_t* box = (rtgui_checkbox_t*)widget;
+
+ switch (event->type)
+ {
+ case RTGUI_EVENT_PAINT:
+ if(widget->on_draw != RT_NULL)
+ {
+ return widget->on_draw(widget, event);
+ }
+ else
+ rtgui_theme_draw_checkbox(box);
+ break;
+
+ case RTGUI_EVENT_MOUSE_BUTTON:
+ if(RTGUI_WIDGET_IS_ENABLE(widget) && !RTGUI_WIDGET_IS_HIDE(widget))
+ {
+ rtgui_event_mouse_t* emouse = (rtgui_event_mouse_t*)event;
+ if(emouse->button & RTGUI_MOUSE_BUTTON_LEFT && emouse->button & RTGUI_MOUSE_BUTTON_UP)
+ {
+ if(box->value)
+ {
+ /* check it */
+ box->value = 0;
+ }
+ else
+ {
+ /* un-check it */
+ box->value = 1;
+ }
+ }
+ else if(emouse->button & RTGUI_MOUSE_BUTTON_LEFT && emouse->button & RTGUI_MOUSE_BUTTON_DOWN)
+ {
+ /* set focus */
+ rtgui_widget_focus(widget);
+ }
+ /* draw checkbox */
+ rtgui_theme_draw_checkbox(box);
+
+ /* call user callback */
+ if(widget->on_mouseclick != RT_NULL)
+ {
+ return widget->on_mouseclick(widget, event);
+ }
+ }
+
+ return RT_TRUE;
+ default:
+ break;
+ }
+
+ return RT_FALSE;
+}
+
+void rtgui_checkbox_set_checked(rtgui_checkbox_t* checkbox, rt_bool_t checked)
+{
+ RT_ASSERT(checkbox != RT_NULL);
+ if(checked == RT_TRUE)
+ checkbox->value = 1;
+ else
+ checkbox->value = 0;
+
+}
+
+rt_bool_t rtgui_checkbox_get_checked(rtgui_checkbox_t* checkbox)
+{
+ RT_ASSERT(checkbox != RT_NULL);
+
+ if(checkbox->value)
+ return RT_TRUE;
+
+ return RT_FALSE;
+} + +static rt_bool_t rtgui_checkbox_onunfocus(PVOID wdt, rtgui_event_t* event) +{
+ rtgui_rect_t rect;
+ rtgui_checkbox_t* box = (rtgui_checkbox_t*)wdt;
+ rtgui_dc_t *dc;
+
+ RT_ASSERT(box != RT_NULL);
+
+ dc = rtgui_dc_begin_drawing(box);
+ if(dc == RT_NULL)return RT_FALSE;
+ + rtgui_widget_get_rect(box, &rect);
+
+ if(!RTGUI_WIDGET_IS_FOCUSED(box)) + {//�������� + rtgui_rect_t tmp_rect;
+ rtgui_color_t color;
+ rtgui_font_get_string_rect(RTGUI_WIDGET_FONT(box), rtgui_label_get_text(RTGUI_LABEL(box)), &tmp_rect);
+
+ rtgui_rect_moveto(&tmp_rect,rect.x1+CHECK_BOX_W+7, rect.y1); + tmp_rect.x1 -= 1;
+ tmp_rect.x2 += 2;
+ tmp_rect.y2 = rect.y2-1;
+
+ /* draw focused border */
+ color = RTGUI_DC_FC(dc); + RTGUI_DC_FC(dc) = RTGUI_DC_BC(dc); + rtgui_dc_draw_focus_rect(dc,&tmp_rect);
+ RTGUI_DC_FC(dc) = color;
+ }
+
+ rtgui_dc_end_drawing(dc);
+ + return RT_TRUE; +}
+
+void rtgui_checkbox_set_text(rtgui_checkbox_t *box, const char* text)
+{
+ RT_ASSERT(box != RT_NULL); + + if(RTGUI_LABEL(box)->text != RT_NULL) + { + /* release old text memory */ + rt_free(RTGUI_LABEL(box)->text);
+ RTGUI_LABEL(box)->text = RT_NULL; + } + + if(text != RT_NULL)
+ RTGUI_LABEL(box)->text = rt_strdup(text); + else
+ RTGUI_LABEL(box)->text = RT_NULL;
+}
diff --git a/components/rtgui_win/widgets/combobox.c b/components/rtgui_win/widgets/combobox.c new file mode 100644 index 0000000000..07805c6d92 --- /dev/null +++ b/components/rtgui_win/widgets/combobox.c @@ -0,0 +1,326 @@ +//��Ͽ�ؼ�
+ +#include <rtgui/dc.h> +#include <rtgui/rtgui_theme.h>
+#include <rtgui/widgets/combobox.h>
+ +static rt_uint32_t rtgui_combo_get_count(rtgui_combo_t* cbo);
+static void rtgui_combo_add_string(rtgui_combo_t* cbo, char* string);
+
+static void _rtgui_combobox_constructor(rtgui_combo_t *cbo) +{ + RTGUI_WIDGET_FLAG(cbo) |= RTGUI_WIDGET_FLAG_FOCUSABLE;
+ cbo->style = RTGUI_COMBO_STYLE_DOWNARROW_UP;
+ cbo->lbox = RT_NULL;
+ cbo->tbox = RT_NULL;
+ + rtgui_widget_set_event_handler(cbo, rtgui_combo_event_handler); + + RTGUI_WIDGET_BACKGROUND(cbo) = white;
+ /* set default text align */ + RTGUI_WIDGET_TEXTALIGN(cbo) = RTGUI_ALIGN_CENTER_VERTICAL;
+ rtgui_widget_set_style(cbo, RTGUI_BORDER_SUNKEN);
+ cbo->on_selected = RT_NULL;
+ cbo->get_count = rtgui_combo_get_count;
+ cbo->add_string = rtgui_combo_add_string; +} + +static void _rtgui_combobox_destructor(rtgui_combo_t *cbo) +{ + +} + +rtgui_type_t *rtgui_combo_type_get(void) +{ + static rtgui_type_t *combo_type = RT_NULL; + + if(!combo_type) + { + combo_type = rtgui_type_create("combobox", RTGUI_CONTAINER_TYPE, + sizeof(rtgui_combo_t), + RTGUI_CONSTRUCTOR(_rtgui_combobox_constructor), + RTGUI_DESTRUCTOR(_rtgui_combobox_destructor)); + } + + return combo_type; +}
+
+rtgui_combo_t* rtgui_combo_create(PVOID parent,const char* text,int left,int top,int w,int h)
+{
+ rtgui_combo_t* cbo;
+ + RT_ASSERT(parent != RT_NULL);
+ + cbo = rtgui_widget_create(RTGUI_COMBOBOX_TYPE); + if(cbo != RT_NULL) + {
+ rtgui_rect_t rect;
+
+ rtgui_widget_get_rect(parent, &rect);
+ rtgui_widget_rect_to_device(parent,&rect);
+ rect.x1 += left;
+ rect.y1 += top;
+ rect.x2 = rect.x1+w;
+ rect.y2 = rect.y1+RTGUI_COMBOBOX_HEIGHT;
+ rtgui_widget_set_rect(cbo,&rect);
+
+ rtgui_container_add_child(parent, cbo);
+
+ if(cbo->tbox == RT_NULL)
+ {
+ cbo->tbox = rtgui_textbox_create(cbo,text,
+ RTGUI_WIDGET_BORDER(cbo),
+ RTGUI_WIDGET_BORDER(cbo),
+ w-RTGUI_COMBOBOX_BUTTON_WIDTH-RTGUI_WIDGET_BORDER(cbo)*2,
+ h-RTGUI_WIDGET_BORDER(cbo)*2,RTGUI_TEXTBOX_NONE);
+
+ if(cbo->tbox == RT_NULL) return RT_NULL;
+ rtgui_widget_set_style(cbo->tbox,RTGUI_BORDER_NONE);
+ cbo->tbox->isedit = RT_FALSE;//ȱʡcombo�ı༭�ɱ༭
+ }
+ if(cbo->lbox == RT_NULL)
+ {//���������������б�
+ rtgui_point_t point;
+ rt_uint32_t mleft,mtop,mwidth;
+
+ rtgui_widget_get_position(cbo, &point);
+ mleft = point.x;
+ mtop = point.y+RTGUI_COMBOBOX_HEIGHT;
+ mwidth = rtgui_widget_get_width(cbo);
+
+ //���������б�
+ cbo->lbox = rtgui_listbox_create(parent,mleft,mtop,mwidth,4,RTGUI_BORDER_SIMPLE);
+ if(cbo->lbox == RT_NULL)return RT_NULL;
+ cbo->lbox->ispopup = RT_TRUE;
+ cbo->lbox->widgetlnk = cbo;
+ rtgui_listbox_set_onitem(cbo->lbox,rtgui_combo_onitem);
+
+ RTGUI_WIDGET_HIDE(cbo->lbox);
+ } + } + + return cbo;
+}
+
+void rtgui_combo_destroy(rtgui_combo_t* cbo) +{ + rtgui_widget_destroy(cbo); +}
+
+void rtgui_combo_set_onitem(rtgui_combo_t* cbo, rtgui_event_handler_ptr func)
+{
+ if(cbo == RT_NULL) return;
+
+ if(cbo->lbox != RT_NULL)
+ {
+ rtgui_listbox_set_onitem(cbo->lbox,func);
+ }
+}
+
+rt_uint32_t rtgui_combo_get_select(rtgui_combo_t* cbo)
+{
+ return cbo->lbox->now_aloc;
+}
+
+char* rtgui_combo_get_string(rtgui_combo_t* cbo)
+{
+ if(cbo->lbox->items != RT_NULL)
+ {
+ return cbo->lbox->items[cbo->lbox->now_aloc].name;
+ }
+
+ return RT_NULL;
+}
+
+//������Ŀ�ı��
+rt_bool_t rtgui_combo_onitem(PVOID wdt, rtgui_event_t* event)
+{
+ rtgui_listbox_t* box = (rtgui_listbox_t*)wdt;
+
+ if(box != RT_NULL && box->ispopup)
+ {
+ char *str;
+ rtgui_combo_t* cbo=box->widgetlnk;
+ if(cbo==RT_NULL)return RT_FALSE;
+
+ str = rtgui_combo_get_string(cbo);
+
+ rtgui_textbox_set_value(cbo->tbox,str);
+ }
+
+ return RT_TRUE;
+}
+
+void rtgui_combo_get_downarrow_rect(rtgui_combo_t* cbo, rtgui_rect_t* rect)
+{
+ rtgui_widget_get_rect(cbo, rect);
+ rect->x1 = rect->x2 - RTGUI_COMBOBOX_BUTTON_WIDTH;
+}
+
+static rt_uint32_t rtgui_combo_get_count(rtgui_combo_t* cbo)
+{
+ if(cbo->lbox)
+ {
+ return cbo->lbox->get_count(cbo->lbox);
+ }
+ return 0;
+}
+
+static void rtgui_combo_add_string(rtgui_combo_t* cbo,char* string)
+{
+ if(cbo->lbox != RT_NULL)
+ {
+ rtgui_listbox_item_t item;
+ rtgui_rect_t rect;
+ rt_uint32_t h,count;
+
+ item.name = string;
+ item.image = RT_NULL;
+ cbo->lbox->add_item(cbo->lbox,&item);
+
+ rtgui_widget_get_rect(cbo->lbox, &rect);
+ count = cbo->get_count(cbo);
+
+ h = 2+(SELECTED_HEIGHT + 2)*count;
+
+ if(h>rtgui_rect_height(rect))//������Ҫ���Ŀؼ���extent
+ {
+ if(cbo->lbox->item_per_page<5)//ÿҳ��ʾ����С��5���Ż����
+ {
+ rect.y2 = rect.y1+h;
+ rtgui_widget_rect_to_device(cbo->lbox,&rect);
+ rtgui_widget_set_rect(cbo->lbox,&rect);//����lbox�Ĵ�С
+ cbo->lbox->item_per_page = rtgui_rect_height(rect) / (SELECTED_HEIGHT+2);
+
+ if(cbo->lbox->sbar != RT_NULL)//ͬʱ����sbar��extent
+ {
+ rtgui_widget_get_rect(cbo->lbox->sbar, &rect);
+ rect.y2 = rect.y1+h-RTGUI_WIDGET_BORDER(cbo->lbox)*2;
+ rtgui_widget_rect_to_device(cbo->lbox->sbar,&rect);
+ rtgui_widget_set_rect(cbo->lbox->sbar,&rect);
+
+ if(cbo->lbox->item_count > cbo->lbox->item_per_page)
+ {
+ RTGUI_WIDGET_UNHIDE(cbo->lbox->sbar);
+ rtgui_scrollbar_set_line_step(cbo->lbox->sbar, 1);
+ rtgui_scrollbar_set_page_step(cbo->lbox->sbar, cbo->lbox->item_per_page);
+ rtgui_scrollbar_set_range(cbo->lbox->sbar, cbo->lbox->item_count);
+ }
+ else
+ {
+ RTGUI_WIDGET_HIDE(cbo->lbox->sbar);
+ }
+ rtgui_widget_update_clip(cbo->lbox);
+ }
+ }
+ }
+ }
+}
+
+void rtgui_combo_set_items(rtgui_combo_t* cbo, rtgui_listbox_item_t* items, rt_uint32_t count)
+{
+ if(cbo != RT_NULL && cbo->lbox != RT_NULL)
+ {
+ rtgui_listbox_set_items(cbo->lbox,items,count);
+ }
+}
+
+rt_bool_t rtgui_combo_event_handler(PVOID wdt, rtgui_event_t* event) +{ + rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ rtgui_combo_t* cbo = (rtgui_combo_t*) widget;
+
+ + RT_ASSERT(widget != RT_NULL); + + switch(event->type) + { + case RTGUI_EVENT_PAINT: + if(widget->on_draw != RT_NULL )
+ widget->on_draw(widget, event); + else + rtgui_theme_draw_combo(cbo); + break;
+ + case RTGUI_EVENT_KBD: + if(widget->on_key != RT_NULL)
+ widget->on_key(widget, event);
+ + return RT_TRUE;
+
+ case RTGUI_EVENT_MOUSE_BUTTON:
+ {
+ rtgui_rect_t rect;
+ rtgui_event_mouse_t* emouse = (rtgui_event_mouse_t*)event;
+ rt_bool_t inclip=RT_EOK;
+
+ if(cbo->tbox->isedit == RT_TRUE)
+ {//�༭��ɱ༭ʱ,ֻ���������ť����
+ inclip = rtgui_region_contains_point(&RTGUI_WIDGET_CLIP(cbo),emouse->x,emouse->y,&rect);
+ }
+ else
+ {//���ȫ������
+ inclip = (rtgui_region_contains_point(&RTGUI_WIDGET_CLIP(cbo),emouse->x,emouse->y,&rect) &&
+ rtgui_region_contains_point(&RTGUI_WIDGET_CLIP(cbo->tbox),emouse->x,emouse->y,&rect));
+ }
+
+ if(inclip == RT_EOK)
+ {
+ rtgui_combo_get_downarrow_rect(cbo,&rect);
+ if(emouse->button & RTGUI_MOUSE_BUTTON_DOWN)
+ {
+ if(rtgui_rect_contains_point(&rect,emouse->x,emouse->y) == RT_EOK)
+ {//��������ť��
+ cbo->style = RTGUI_COMBO_STYLE_DOWNARROW_DOWN;
+ rtgui_theme_draw_combo_downarrow(cbo);
+ }
+
+ if(cbo->lbox != RT_NULL)
+ {
+ if(RTGUI_WIDGET_IS_HIDE(cbo->lbox))
+ {//��ʾ�����б�
+ RTGUI_WIDGET_UNHIDE(cbo->lbox);
+ rtgui_widget_focus(cbo->lbox);
+ rtgui_widget_update_clip_pirate(RTGUI_WIDGET_PARENT(cbo->lbox),cbo->lbox);
+ //�б���λ����Ϊ0
+ cbo->lbox->frist_aloc=0;
+ cbo->lbox->now_aloc = 0;
+ if(cbo->lbox->sbar != RT_NULL)
+ {
+ if(!RTGUI_WIDGET_IS_HIDE(cbo->lbox->sbar))
+ {//��������λ����Ϊ0
+ rtgui_scrollbar_set_value(cbo->lbox->sbar,cbo->lbox->frist_aloc);
+ }
+ }
+ rtgui_widget_update(RTGUI_WIDGET_PARENT(cbo->lbox));
+ }
+ else
+ {//���ص����б�
+ RTGUI_WIDGET_HIDE(cbo->lbox);
+ rtgui_widget_unfocus(cbo->lbox);
+ }
+ }
+ }
+ else if(emouse->button & RTGUI_MOUSE_BUTTON_UP)
+ {
+ if(rtgui_region_contains_point(&RTGUI_WIDGET_CLIP(cbo),emouse->x,emouse->y,&rect) == RT_EOK)
+ {//��������ť��
+ cbo->style = RTGUI_COMBO_STYLE_DOWNARROW_UP;
+ rtgui_theme_draw_combo_downarrow(cbo);
+ }
+ }
+ }
+ else
+ rtgui_view_event_handler(widget,event);
+
+ break;
+ }
+
+ default:
+ return rtgui_view_event_handler(widget,event); + } + + return RT_FALSE; +}
+
+
diff --git a/components/rtgui_win/widgets/container.c b/components/rtgui_win/widgets/container.c new file mode 100644 index 0000000000..61f65a9cd3 --- /dev/null +++ b/components/rtgui_win/widgets/container.c @@ -0,0 +1,321 @@ +/* + * File : box.c + * This file is part of RT-Thread RTOS + * COPYRIGHT (C) 2006 - 2009, RT-Thread Development Team + * + * The license and distribution terms for this file may be + * found in the file LICENSE in this distribution or at + * http://www.rt-thread.org/license/LICENSE + * + * Change Logs: + * Date Author Notes + * 2009-10-16 Bernard first version + */ + +#include <rtgui/widgets/container.h>
+#include <rtgui/widgets/window.h> + +static void _rtgui_container_constructor(rtgui_container_t *container) +{ + /* set event handler and init field */ + rtgui_widget_set_event_handler(container, rtgui_container_event_handler); + rtgui_list_init(&(container->children));
+ + /* set focused widget to itself */ + container->focused = RTGUI_WIDGET(container); + /* set box as focusable widget */ + RTGUI_WIDGET_FLAG(container) |= RTGUI_WIDGET_FLAG_FOCUSABLE; +} + +static void _rtgui_container_destructor(rtgui_container_t *container) +{ + /* destroy child of box */ + rtgui_container_destroy_children(container); +} + +static void _rtgui_container_update_toplevel(rtgui_container_t* container) +{ + rtgui_list_t* node; + + rtgui_list_foreach(node, &(container->children)) + { + rtgui_widget_t* child = rtgui_list_entry(node, rtgui_widget_t, sibling); + /* set child top */ + child->toplevel = RTGUI_WIDGET(rtgui_widget_get_toplevel(container)); + + if(RTGUI_IS_CONTAINER(child)) + { + _rtgui_container_update_toplevel(RTGUI_CONTAINER(child)); + } + } +} + +rtgui_type_t *rtgui_container_type_get(void) +{ + static rtgui_type_t *container_type = RT_NULL; + + if(!container_type) + { + container_type = rtgui_type_create("container", RTGUI_WIDGET_TYPE, + sizeof(rtgui_container_t), + RTGUI_CONSTRUCTOR(_rtgui_container_constructor), + RTGUI_DESTRUCTOR(_rtgui_container_destructor)); + } + + return container_type; +} + +rt_bool_t rtgui_container_dispatch_event(rtgui_container_t *container, rtgui_event_t* event) +{ + /* handle in child widget */ + rtgui_list_t* node; + + rtgui_list_foreach(node, &(container->children)) + { + rtgui_widget_t* w; + w = rtgui_list_entry(node, rtgui_widget_t, sibling); + if(RTGUI_WIDGET_IS_HIDE(w)) continue; //�ؼ������ص�������
+ //if(RTGUI_IS_WIN(w)) continue;
+ if(RTGUI_WIDGET_EVENT_HANDLE(w) != RT_NULL) + RTGUI_WIDGET_EVENT_CALL(w, event); + } + + return RT_FALSE; +} + +rt_bool_t rtgui_container_dispatch_mouse_event(rtgui_container_t *container, rtgui_event_mouse_t* event) +{ + /* handle in child widget */ + rtgui_list_t* node; + rtgui_widget_t *focus; + + /* get focus widget on toplevel */ + focus = RTGUI_CONTAINER(RTGUI_WIDGET(container)->toplevel)->focused; + rtgui_list_foreach(node, &(container->children)) + { + rtgui_widget_t* w; + w = rtgui_list_entry(node, rtgui_widget_t, sibling);
+ if(RTGUI_WIDGET_IS_HIDE(w))continue;//���صĿؼ�������
+ + if(rtgui_rect_contains_point(&(w->extent), event->x, event->y) == RT_EOK) + {//����ǰ����ij���ؼ���
+ if ((focus != w) && RTGUI_WIDGET_IS_FOCUSABLE(w)) + rtgui_widget_focus(w);
+ if(RTGUI_WIDGET_EVENT_HANDLE(w) != RT_NULL)
+ return RTGUI_WIDGET_EVENT_CALL(w,(rtgui_event_t*)event); + } + } + + return RT_FALSE; +} + +rt_bool_t rtgui_container_event_handler(PVOID wdt, rtgui_event_t* event) +{
+ rtgui_widget_t *widget = (rtgui_widget_t*)wdt; + rtgui_container_t *container = RTGUI_CONTAINER(widget); + + switch (event->type) + { + case RTGUI_EVENT_KBD: + if(widget->on_key != RT_NULL) + { + return widget->on_key(widget, event); + } + else + { + /* let parent to handle keyboard event */ + if(widget->parent != RT_NULL && widget->parent != widget->toplevel) + { + if(RTGUI_WIDGET_EVENT_HANDLE(widget->parent) != RT_NULL)
+ return RTGUI_WIDGET_EVENT_CALL(widget->parent, event); + } + } + break; + + case RTGUI_EVENT_MOUSE_BUTTON: + /* handle in child widget */ + if(rtgui_container_dispatch_mouse_event(container,(rtgui_event_mouse_t*)event) == RT_FALSE) + { + /* handle event in current widget */ + if(widget->on_mouseclick != RT_NULL) + { + return widget->on_mouseclick(widget, event); + } + } + else return RT_TRUE; + break; + + case RTGUI_EVENT_MOUSE_MOTION: + if(rtgui_container_dispatch_mouse_event(container,(rtgui_event_mouse_t*)event) == RT_FALSE) + { + #if 0 + /* handle event in current widget */ + if(widget->on_mousemotion != RT_NULL) + { + return widget->on_mousemotion(widget, event); + } + #endif + } + else
+ return RT_TRUE; + break;
+ + case RTGUI_EVENT_TIMER:
+ {
+ rtgui_timer_t* timer;
+ rtgui_event_timer_t* etimer = (rtgui_event_timer_t*) event;
+
+ timer = etimer->timer;
+ if(timer->timeout != RT_NULL)
+ {
+ /* call timeout function */
+ timer->timeout(timer, timer->user_data);
+ }
+ }
+ break;
+ + case RTGUI_EVENT_COMMAND: + if(rtgui_container_dispatch_event(container, event) == RT_FALSE) + { + if(widget->on_command != RT_NULL) + { + return widget->on_command(widget, event); + } + } + else
+ return RT_TRUE; + break; + + case RTGUI_EVENT_RESIZE: + if(rtgui_container_dispatch_event(container, event) == RT_FALSE) + { + if(widget->on_size != RT_NULL) + return widget->on_size(widget, event); + } + else return RT_TRUE; + break; + + default: + /* call parent widget event handler */ + return rtgui_widget_event_handler(widget, event); + } + + return RT_FALSE; +} + +/* + * This function will add a child to a box widget + * Note: this function will not change the widget layout + * the layout is the responsibility of layout widget, such as box. + */ +void rtgui_container_add_child(PVOID cbox, PVOID wdt) +{ + rtgui_container_t *container = (rtgui_container_t*)cbox;
+ rtgui_widget_t* child = (rtgui_widget_t*)wdt;
+
+ RT_ASSERT(container != RT_NULL); + RT_ASSERT(child != RT_NULL);
+ RT_ASSERT(RTGUI_IS_CONTAINER(container));
+ + /* set parent and toplevel widget */ + child->parent = RTGUI_WIDGET(container); + /* put widget to parent's child list */ + rtgui_list_append(&(container->children), &(child->sibling)); + + /* update child toplevel */ + if(RTGUI_WIDGET(container)->toplevel != RT_NULL && RTGUI_IS_CONTAINER(RTGUI_WIDGET(container)->toplevel)) + { + child->toplevel = RTGUI_WIDGET(rtgui_widget_get_toplevel(container)); + + /* update all child toplevel */ + if(RTGUI_IS_CONTAINER(child)) + { + _rtgui_container_update_toplevel(RTGUI_CONTAINER(child)); + } + }
+
+ rtgui_widget_update_clip(child); +} + +/* remove a child to widget */ +void rtgui_container_remove_child(rtgui_container_t *container, PVOID wdt) +{
+ rtgui_widget_t *child = (rtgui_widget_t*)wdt;
+
+ RT_ASSERT(container != RT_NULL); + RT_ASSERT(child != RT_NULL);
+ + if(child == container->focused) + { + /* set focused to itself */ + container->focused = RTGUI_WIDGET(container); + + rtgui_widget_focus(container); + } + + /* remove widget from parent's child list */ + rtgui_list_remove(&(container->children), &(child->sibling)); + + /* set parent and top widget */ + child->parent = RT_NULL; + child->toplevel = RT_NULL;
+ rtgui_widget_update_clip(container); +} + +/* destroy all child of box */ +void rtgui_container_destroy_children(rtgui_container_t *container) +{ + rtgui_list_t* node; + + if(container == RT_NULL) return; + + node = container->children.next; + while(node != RT_NULL) + { + rtgui_widget_t* child = rtgui_list_entry(node, rtgui_widget_t, sibling); + + if(RTGUI_IS_CONTAINER(child)) + { + /* break parent firstly */ + child->parent = RT_NULL; + + /* destroy child of child */ + rtgui_container_destroy_children(RTGUI_CONTAINER(child)); + } + + /* remove widget from parent's child list */ + rtgui_list_remove(&(container->children), &(child->sibling)); + + /* set parent and top widget */ + child->parent = RT_NULL; + + /* destroy object and remove from parent */ + rtgui_object_destroy(RTGUI_OBJECT(child)); + + //node = box->child.next;
+ node = node->next; + } + + container->children.next = RT_NULL; + container->focused = RTGUI_WIDGET(container); + if(RTGUI_WIDGET_PARENT(container) != RT_NULL) + rtgui_widget_focus(container); + + /* update widget clip */ + rtgui_widget_update_clip(RTGUI_WIDGET(container)->toplevel); +} + +rtgui_widget_t* rtgui_container_get_first_child(rtgui_container_t* container) +{ + rtgui_widget_t* child = RT_NULL; + + if(container->children.next != RT_NULL) + { + child = rtgui_list_entry(container->children.next, rtgui_widget_t, sibling); + } + + return child; +}
+
+
+ diff --git a/components/rtgui_win/widgets/file.xpm b/components/rtgui_win/widgets/file.xpm new file mode 100644 index 0000000000..60e323cc82 --- /dev/null +++ b/components/rtgui_win/widgets/file.xpm @@ -0,0 +1,43 @@ +/* XPM */
+static const char *file_xpm[] =
+{
+"16 16 21 1",
+" c None",
+". c #999999",
+"+ c #818181",
+"@ c #FFFFFF",
+"# c #ECECEC",
+"$ c #EAEAEA",
+"% c #EBEBEB",
+"& c #EDEDED",
+"* c #F0F0F0",
+"= c #C4C4C4",
+"- c #C5C5C5",
+"; c #C6C6C6",
+"> c #C7C7C7",
+", c #EEEEEE",
+"' c #EDEDE5",
+") c #EDEDE6",
+"! c #EFEFEF",
+"~ c #C8C8C8",
+"{ c #F1F1F1",
+"] c #F2F2F2",
+"^ c #959595",
+".++++++++++++ ",
+"+@@@@@@@@@@@@+ ",
+"+@#$$%%%##&*@+ ",
+"+@$=--;;;;>*@+ ",
+"+@$%%###&&,*@+ ",
+"+@%-;;;;;;>*@+ ",
+"+@%%##&&'#,*@+ ",
+"+@%;;;;,,),*@+ ",
+"+@##&&,,!!!*@+ ",
+"+@#;;;>>~~~*@+ ",
+"+@#&,,!!*{{{@+ ",
+"+@&;>>~~~{{]@+ ",
+"+@&&,!!**{]]@+ ",
+"+@@@@@@@@@@@@+ ",
+"^++++++++++++^ ",
+" "
+};
+
diff --git a/components/rtgui_win/widgets/file_hdc.h b/components/rtgui_win/widgets/file_hdc.h new file mode 100644 index 0000000000..2bdc0694c5 --- /dev/null +++ b/components/rtgui_win/widgets/file_hdc.h @@ -0,0 +1,155 @@ +#ifndef __FILE_HDC_H__
+#define __FILE_HDC_H__
+
+
+
+//�ļ�ͼ��
+const unsigned char file_hdc[] =
+{ +0x48, 0x44, 0x43, 0x00,//HDC
+0x10, 0x00, 0x00, 0x00,//width
+0x10, 0x00, 0x00, 0x00,//height
+0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, +0xBE, 0xF7, 0xBE, 0xF7, 0xBE, 0xF7, 0xBE, 0xF7,
+0xBE, 0xF7, 0xBE, 0xF7, 0xBE, 0xF7, 0xBE, 0xF7,
+0xBE, 0xF7, 0xBE, 0xF7, 0xBE, 0xF7, 0xBE, 0xF7,
+0xBE, 0xF7, 0xBE, 0xF7, 0xBE, 0xF7, 0xBE, 0xF7,
+0xBE, 0xF7, 0xBE, 0xF7, 0xDF, 0xFF, 0xD7, 0x4C,
+0xFA, 0x4D, 0x52, 0x33, 0x34, 0x3C, 0xFA, 0x4D,
+0xF2, 0x63, 0xFA, 0x4D, 0x70, 0x6B, 0x13, 0x5C,
+0xBA, 0xD6, 0x9E, 0xF7, 0xBE, 0xF7, 0xBE, 0xF7,
+0xBE, 0xF7, 0xBE, 0xF7, 0x59, 0xE6, 0xCF, 0xC3,
+0x57, 0x95, 0x52, 0x33, 0x57, 0x95, 0xD1, 0x6B,
+0xB7, 0xD5, 0x95, 0x6C, 0xB7, 0xBD, 0x13, 0x5C,
+0x14, 0xA5, 0x1C, 0xE7, 0xBE, 0xF7, 0xBE, 0xF7,
+0xBE, 0xF7, 0xBE, 0xF7, 0xCF, 0xC3, 0x38, 0xE6,
+0x50, 0x43, 0xBD, 0xF7, 0x50, 0x43, 0xBD, 0xF7,
+0x50, 0x43, 0xDE, 0xFF, 0x50, 0x43, 0xFF, 0xFF,
+0x8E, 0x73, 0xBA, 0xD6, 0xBE, 0xF7, 0xBE, 0xF7,
+0xBE, 0xF7, 0xBE, 0xF7, 0xCF, 0xC3, 0x77, 0xD6,
+0xBD, 0xF7, 0xBD, 0xF7, 0xBD, 0xF7, 0xBD, 0xF7,
+0xDE, 0xF7, 0xDE, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+0x8E, 0x73, 0xBA, 0xD6, 0xBE, 0xF7, 0xBE, 0xF7,
+0xBE, 0xF7, 0xBE, 0xF7, 0xCF, 0xC3, 0x78, 0xD6,
+0xBD, 0xF7, 0xBD, 0xF7, 0xBD, 0xF7, 0xBD, 0xF7,
+0xDE, 0xF7, 0xDE, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+0x8E, 0x73, 0xBA, 0xD6, 0xBE, 0xF7, 0xBE, 0xF7,
+0xBE, 0xF7, 0xBE, 0xF7, 0xCF, 0xC3, 0x77, 0xD6,
+0xBD, 0xF7, 0x1F, 0x00, 0x1F, 0x00, 0x1F, 0x00,
+0x1F, 0x00, 0xF7, 0xBD, 0xFF, 0xFF, 0xFF, 0xFF,
+0x8E, 0x73, 0xBA, 0xD6, 0xBE, 0xF7, 0xBE, 0xF7,
+0xBE, 0xF7, 0xBE, 0xF7, 0xCF, 0xC3, 0x77, 0xD6,
+0xBD, 0xF7, 0xBD, 0xF7, 0xBD, 0xF7, 0xBD, 0xF7,
+0xDE, 0xF7, 0xDE, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+0x8E, 0x73, 0xBA, 0xD6, 0xBE, 0xF7, 0xBE, 0xF7,
+0xBE, 0xF7, 0xBE, 0xF7, 0xCF, 0xC3, 0x97, 0xD6,
+0xBD, 0xF7, 0x00, 0x04, 0x00, 0x04, 0x00, 0x04,
+0x00, 0x04, 0xF7, 0xBD, 0xFF, 0xFF, 0xFF, 0xFF,
+0x8E, 0x73, 0xBA, 0xD6, 0xBE, 0xF7, 0xBE, 0xF7,
+0xBE, 0xF7, 0xBE, 0xF7, 0xCF, 0xC3, 0x77, 0xD6,
+0xBD, 0xF7, 0xBD, 0xF7, 0xBD, 0xF7, 0xBD, 0xF7,
+0xDE, 0xF7, 0xDE, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+0x8E, 0x73, 0xBA, 0xD6, 0xBE, 0xF7, 0xBE, 0xF7,
+0xBE, 0xF7, 0xBE, 0xF7, 0xCF, 0xC3, 0x57, 0xDE,
+0xBD, 0xF7, 0x00, 0xF8, 0x00, 0xF8, 0x00, 0xF8,
+0x00, 0xF8, 0xF7, 0xBD, 0xFF, 0xFF, 0xFF, 0xFF,
+0x8E, 0x73, 0xBA, 0xD6, 0xBE, 0xF7, 0xBE, 0xF7,
+0xBE, 0xF7, 0xBE, 0xF7, 0xCF, 0xC3, 0x78, 0xDE,
+0xBD, 0xF7, 0xBD, 0xF7, 0xBD, 0xF7, 0xBD, 0xF7,
+0xDE, 0xF7, 0xDE, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+0x8E, 0x73, 0xBA, 0xD6, 0xBE, 0xF7, 0xBE, 0xF7,
+0xBE, 0xF7, 0xBE, 0xF7, 0xCF, 0xC3, 0x77, 0xD6,
+0xBD, 0xF7, 0x1F, 0xF8, 0x1F, 0xF8, 0x1F, 0xF8,
+0x1F, 0xF8, 0xF7, 0xBD, 0xFF, 0xFF, 0xFF, 0xFF,
+0x8E, 0x73, 0xBA, 0xD6, 0xBE, 0xF7, 0xBE, 0xF7,
+0xBE, 0xF7, 0xBE, 0xF7, 0xCF, 0xC3, 0x56, 0xCE,
+0xBD, 0xF7, 0xBD, 0xF7, 0xBD, 0xF7, 0xBD, 0xF7,
+0xBD, 0xF7, 0xBD, 0xF7, 0xBD, 0xF7, 0xBD, 0xF7,
+0x8E, 0x73, 0xDB, 0xDE, 0xBE, 0xF7, 0xBE, 0xF7,
+0xBE, 0xF7, 0xBE, 0xF7, 0xDB, 0xDE, 0xF3, 0x9C,
+0x0F, 0x84, 0x0F, 0x84, 0x6D, 0x6B, 0x4D, 0x6B,
+0x4D, 0x6B, 0x4D, 0x6B, 0x71, 0x8C, 0xF3, 0x9C,
+0xF3, 0x9C, 0x5D, 0xEF, 0xBE, 0xF7, 0xBE, 0xF7,
+0xBE, 0xF7, 0xBE, 0xF7, 0xBE, 0xF7, 0xBE, 0xF7,
+0xBE, 0xF7, 0xBE, 0xF7, 0xBE, 0xF7, 0xBE, 0xF7,
+0xBE, 0xF7, 0xBE, 0xF7, 0xBE, 0xF7, 0xBE, 0xF7,
+0xBE, 0xF7, 0xBE, 0xF7, 0xBE, 0xF7, 0xBE, 0xF7,
+};
+
+//�ļ���ͼ��
+const unsigned char folder_hdc[] =
+{ +0x48, 0x44, 0x43, 0x00,//HDC
+0x10, 0x00, 0x00, 0x00,//width
+0x10, 0x00, 0x00, 0x00,//height
+0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, +0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0xFF, 0x07,
+0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07,
+0xFF, 0x07, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF,
+0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF,
+0xFF, 0xFF, 0x00, 0x00, 0xFF, 0x07, 0xFF, 0x07,
+0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07,
+0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07,
+0xFF, 0x07, 0xFF, 0x07, 0x00, 0x00, 0xFF, 0xFF,
+0xFF, 0xFF, 0x00, 0x00, 0xFF, 0x07, 0xFF, 0x07,
+0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07,
+0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07,
+0xFF, 0x07, 0xFF, 0x07, 0x00, 0x00, 0xFF, 0xFF,
+0xFF, 0xFF, 0x00, 0x00, 0xFF, 0x07, 0xFF, 0x07,
+0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07,
+0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07,
+0xFF, 0x07, 0xFF, 0x07, 0x00, 0x00, 0xFF, 0xFF,
+0xFF, 0xFF, 0x00, 0x00, 0xFF, 0x07, 0xFF, 0x07,
+0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07,
+0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07,
+0xFF, 0x07, 0xFF, 0x07, 0x00, 0x00, 0xFF, 0xFF,
+0xFF, 0xFF, 0x00, 0x00, 0xFF, 0x07, 0xFF, 0x07,
+0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07,
+0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07,
+0xFF, 0x07, 0xFF, 0x07, 0x00, 0x00, 0xFF, 0xFF,
+0xFF, 0xFF, 0x00, 0x00, 0xFF, 0x07, 0xFF, 0x07,
+0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07,
+0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07,
+0xFF, 0x07, 0xFF, 0x07, 0x00, 0x00, 0xFF, 0xFF,
+0xFF, 0xFF, 0x00, 0x00, 0xFF, 0x07, 0xFF, 0x07,
+0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07,
+0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07,
+0xFF, 0x07, 0xFF, 0x07, 0x00, 0x00, 0xFF, 0xFF,
+0xFF, 0xFF, 0x00, 0x00, 0xFF, 0x07, 0xFF, 0x07,
+0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07,
+0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07, 0xFF, 0x07,
+0xFF, 0x07, 0xFF, 0x07, 0x00, 0x00, 0xFF, 0xFF,
+0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF,
+0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+};
+
+#endif
+
diff --git a/components/rtgui_win/widgets/filelist_view.c b/components/rtgui_win/widgets/filelist_view.c new file mode 100644 index 0000000000..8eb9a7db64 --- /dev/null +++ b/components/rtgui_win/widgets/filelist_view.c @@ -0,0 +1,799 @@ +/*
+ * File : fileview.c
+ * This file is part of RTGUI in RT-Thread RTOS
+ * COPYRIGHT (C) 2010, RT-Thread Development Team
+ *
+ * The license and distribution terms for this file may be
+ * found in the file LICENSE in this distribution or at
+ * http://www.rt-thread.org/license/LICENSE
+ *
+ * Change Logs:
+ * Date Author Notes
+ * 2010-01-06 Bernard first version
+ */
+
+#include <rtgui/rtgui.h>
+#include <rtgui/rtgui_object.h>
+#include <rtgui/rtgui_system.h>
+#include <rtgui/rtgui_theme.h>
+
+#include <rtgui/list.h>
+#include <rtgui/image.h>
+#include <rtgui/widgets/view.h>
+#include <rtgui/widgets/filelist_view.h>
+#include <rtgui/widgets/listbox.h>
+#include <rtgui/widgets/window.h>
+#include <rtgui/widgets/dialog.h>
+#include <lcd.h>
+
+#include <uffs/uffs_fd.h>
+#include <uffs_ext.h>
+#include <dfs_posix.h>
+
+//·���ָ��
+#define PATH_SEPARATOR '/'
+
+#include <string.h>
+
+#include "file_hdc.h" //�ļ�ͼ��
+
+/* image for file and folder */
+static rtgui_image_t *file_image = RT_NULL;
+static rtgui_image_t *folder_image = RT_NULL;
+
+static rt_bool_t rtgui_fileview_onunfocus(PVOID wdt, rtgui_event_t* event);
+static rt_bool_t rtgui_fileview_sbar_handle(PVOID wdt, rtgui_event_t* event);
+
+static void _rtgui_fileview_constructor(rtgui_filelist_view_t *fview)
+{
+ /* set default widget rect and set event handler */
+ rtgui_widget_set_event_handler(fview, rtgui_filelist_view_event_handler);
+ rtgui_widget_set_onunfocus(fview, rtgui_fileview_onunfocus);
+
+ RTGUI_WIDGET_FLAG(fview) |= RTGUI_WIDGET_FLAG_FOCUSABLE;
+
+ fview->frist_aloc = 0;
+ fview->now_aloc = 0;
+ fview->item_count = 0;
+ fview->item_per_page = 0;
+
+ fview->current_dir = RT_NULL;
+ fview->pattern = RT_NULL;
+ RTGUI_WIDGET_BACKGROUND(fview) = white;
+ RTGUI_WIDGET_TEXTALIGN(fview) = RTGUI_ALIGN_CENTER_VERTICAL;
+
+ if(file_image==RT_NULL)
+ file_image = rtgui_image_create_from_mem("hdc",file_hdc, sizeof(file_hdc), TRUE);
+ if(folder_image==RT_NULL)
+ folder_image = rtgui_image_create_from_mem("hdc",folder_hdc, sizeof(folder_hdc), TRUE);
+
+}
+
+static void _rtgui_fileview_destructor(rtgui_filelist_view_t *fview)
+{
+ rtgui_filelist_view_destroy(fview);
+}
+
+rtgui_type_t *rtgui_filelist_view_type_get(void)
+{
+ static rtgui_type_t *fileview_type = RT_NULL;
+
+ if(!fileview_type)
+ {
+ fileview_type = rtgui_type_create("fileview", RTGUI_CONTAINER_TYPE,
+ sizeof(rtgui_filelist_view_t),
+ RTGUI_CONSTRUCTOR(_rtgui_fileview_constructor),
+ RTGUI_DESTRUCTOR(_rtgui_fileview_destructor));
+ }
+
+ return fileview_type;
+}
+
+
+rtgui_filelist_view_t* rtgui_filelist_view_create(PVOID parent, const char* directory, const char* pattern, int left, int top, int w, int h)
+{
+ rtgui_filelist_view_t* fview = RT_NULL;
+
+ RT_ASSERT(parent != RT_NULL);
+
+ /* create a new view */
+ fview = rtgui_widget_create(RTGUI_FILELIST_VIEW_TYPE);
+
+ if(fview != RT_NULL)
+ {
+ rtgui_rect_t rect;
+
+ rtgui_widget_get_rect(parent, &rect);
+ rtgui_widget_rect_to_device(parent,&rect);
+ rect.x1 += left;
+ rect.y1 += top;
+ rect.x2 = rect.x1+w;
+ rect.y2 = rect.y1+h;
+
+ fview->items = RT_NULL;
+ fview->pattern = rt_strdup(pattern);
+ fview->item_per_page = rtgui_rect_height(rect) / (1 + SELECTED_HEIGHT);
+
+ rtgui_widget_set_rect(fview,&rect);
+
+ rtgui_container_add_child(parent, fview);
+
+ {//��������ؼ�
+ rt_uint32_t sLeft,sTop,sw=RTGUI_DEFAULT_SB_WIDTH,sLen;
+ sLeft = rtgui_rect_width(rect)-RTGUI_WIDGET_BORDER(fview)-sw;
+ sTop = RTGUI_WIDGET_BORDER(fview);
+
+ sLen = rect.y2-rect.y1-RTGUI_WIDGET_BORDER(fview)*2;
+ fview->sbar = rtgui_scrollbar_create(fview,sLeft,sTop,sw,sLen,RTGUI_VERTICAL);
+ if(fview->sbar != RT_NULL)
+ {
+ fview->sbar->widgetlnk = fview;
+ fview->sbar->on_scroll = rtgui_fileview_sbar_handle;
+ RTGUI_WIDGET_HIDE(fview->sbar);//Ĭ�����ع�����
+ }
+ }
+
+ rtgui_filelist_view_set_directory(fview, directory);
+ }
+
+ return fview;
+}
+
+static void rtgui_filelist_view_clear(rtgui_filelist_view_t* view);
+
+void rtgui_filelist_view_destroy(rtgui_filelist_view_t* fview)
+{
+ /* delete all file items */
+ rtgui_filelist_view_clear(fview);
+
+ /* delete current directory and pattern */
+ if(fview->current_dir != RT_NULL)
+ rt_free(fview->current_dir);
+ fview->current_dir = RT_NULL;
+
+ if(fview->pattern != RT_NULL)
+ rt_free(fview->pattern);
+ fview->pattern = RT_NULL;
+
+ /* delete image */
+ rtgui_image_destroy(file_image);
+ file_image = RT_NULL;
+ rtgui_image_destroy(folder_image);
+ folder_image = RT_NULL;
+}
+
+static void rtgui_filelist_view_on_folder_item(rtgui_filelist_view_t *fview)
+{
+ char* dir_ptr;
+
+ dir_ptr = (char*)rt_malloc(256);
+ if(dir_ptr==RT_NULL)
+ {
+ return;
+ }
+ //û�����ļ��л����ļ������˳�
+ if(fview->items==RT_NULL)return;
+
+ rtgui_filelist_view_get_fullpath(fview, dir_ptr, 256);
+
+ rtgui_filelist_view_set_directory(fview, dir_ptr);
+ rt_free(dir_ptr);
+}
+
+void rtgui_filelist_view_ondraw(rtgui_filelist_view_t* fview)
+{
+ rt_uint16_t frist, i,rx2;
+ rtgui_filelist_view_item_t* item;
+ rtgui_rect_t rect, item_rect, image_rect;
+ rtgui_dc_t* dc;
+
+ RT_ASSERT(fview != RT_NULL);
+
+ /* begin drawing */
+ dc = rtgui_dc_begin_drawing(fview);
+ if(dc == RT_NULL)return;
+
+ rtgui_widget_get_rect(fview, &rect);
+ rtgui_dc_draw_border(dc, &rect,RTGUI_WIDGET_BORDER_STYLE(fview));
+ rtgui_rect_inflate(&rect,-RTGUI_WIDGET_BORDER(fview));
+ RTGUI_DC_BC(dc) = white;
+ rtgui_dc_fill_rect(dc,&rect);
+ rtgui_rect_inflate(&rect,RTGUI_WIDGET_BORDER(fview));
+ if(fview->sbar && !RTGUI_WIDGET_IS_HIDE(fview->sbar))
+ rect.x2 -= rtgui_rect_width(fview->sbar->parent.extent);
+
+ rect.x2 -=1; rect.y2 -= 1;
+
+ /* get item base rect */
+ item_rect = rect;
+ item_rect.x1 += RTGUI_WIDGET_BORDER(fview);
+ item_rect.x2 -= RTGUI_WIDGET_BORDER(fview); rx2 = item_rect.x2;
+ item_rect.y1 += RTGUI_WIDGET_BORDER(fview);
+ item_rect.y2 = item_rect.y1 + (1 + SELECTED_HEIGHT);
+
+ /* get image base rect */
+ image_rect.x1 = RTGUI_WIDGET_DEFAULT_MARGIN;
+ image_rect.y1 = 0;
+ image_rect.x2 = RTGUI_WIDGET_DEFAULT_MARGIN + file_image->w;
+ image_rect.y2 = file_image->h;
+ rtgui_rect_moveto_align(&item_rect, &image_rect, RTGUI_ALIGN_CENTER_VERTICAL);
+
+
+ //ȡ�õ�ǰҳ
+ frist = fview->frist_aloc;
+ for(i = 0; i < fview->item_per_page; i ++)
+ {
+ char str_size[16];
+
+ if(frist + i >= fview->item_count) break;
+
+ item = &(fview->items[frist + i]);
+
+ /* draw item image */
+ if(item->type == RTGUI_FITEM_FILE)
+ rtgui_image_blit(file_image, dc, &image_rect);
+ else
+ rtgui_image_blit(folder_image, dc, &image_rect);
+
+ /* draw text */
+ item_rect.x1 += RTGUI_WIDGET_DEFAULT_MARGIN + file_image->w + 2;
+ item_rect.x2 = item_rect.x1 + rtgui_font_get_string_width(RTGUI_DC_FONT(dc), item->name);
+ if(frist + i == fview->now_aloc)
+ {
+ if(RTGUI_WIDGET_IS_FOCUSED(fview))
+ {
+ RTGUI_DC_BC(dc) = selected_color;
+ RTGUI_DC_FC(dc) = white;
+ }
+ else
+ {
+ RTGUI_DC_BC(dc) = dark_grey;
+ RTGUI_DC_FC(dc) = black;
+ }
+ rtgui_dc_fill_rect(dc, &item_rect);
+ rtgui_dc_draw_text(dc, item->name, &item_rect);
+ }
+ else
+ {
+ /* draw background */
+ RTGUI_DC_BC(dc) = white;
+ RTGUI_DC_FC(dc) = black;
+ rtgui_dc_fill_rect(dc,&item_rect);
+ rtgui_dc_draw_text(dc, item->name, &item_rect);
+ }
+
+
+ {//��ʾ�ļ���С��Ϣ
+ rtgui_rect_t rect=item_rect;
+ rect.x1 += 265;
+ rect.x2 = rect.x1+64;
+ if(item->type == RTGUI_FITEM_FILE)
+ rt_snprintf(str_size, 32, "%d",item->size);
+ else
+ rt_snprintf(str_size, 32, "%s","DIR");
+ RTGUI_DC_FC(dc) = black;
+ rtgui_dc_draw_text(dc, str_size, &rect);
+ }
+
+ item_rect.x1 -= RTGUI_WIDGET_DEFAULT_MARGIN + file_image->w + 2;
+ item_rect.x2 = rx2;
+ /* move to next item position */
+ item_rect.y1 += (SELECTED_HEIGHT + 1);
+ item_rect.y2 += (SELECTED_HEIGHT + 1);
+
+ image_rect.y1 += (SELECTED_HEIGHT + 1);
+ image_rect.y2 += (SELECTED_HEIGHT + 1);
+ }
+
+ if(fview->sbar && !RTGUI_WIDGET_IS_HIDE(fview->sbar))
+ {
+ rtgui_theme_draw_scrollbar(fview->sbar);
+ }
+
+ rtgui_dc_end_drawing(dc);
+}
+
+//����FileView�Ľ���
+void rtgui_filelist_view_update_current(rtgui_filelist_view_t* fview)
+{
+ rtgui_filelist_view_item_t* item;
+ rtgui_rect_t rect, item_rect, image_rect;
+ rtgui_win_t* win;
+ struct OpenDlgSt *dlgst=RT_NULL;
+ rtgui_dc_t* dc;
+
+ RT_ASSERT(fview != RT_NULL);
+
+ /* begin drawing */
+ dc = rtgui_dc_begin_drawing(fview);
+ if(dc == RT_NULL)return;
+
+ win = rtgui_win_get_win_by_widget(fview);
+ if(win == RT_NULL)return;
+ if(win->user_data != RT_NULL)
+ {
+ dlgst = (struct OpenDlgSt*)win->user_data;
+ }
+
+ //���ļ���Ϊ��ʱ��������
+ if(fview->items==RT_NULL)return;
+
+ rtgui_widget_get_rect(fview, &rect);
+ if(fview->sbar && !RTGUI_WIDGET_IS_HIDE(fview->sbar))
+ rect.x2 -= rtgui_rect_width(fview->sbar->parent.extent);
+
+ if((fview->old_aloc >= fview->frist_aloc) &&
+ (fview->old_aloc < fview->frist_aloc+fview->item_per_page) &&
+ (fview->old_aloc != fview->now_aloc))
+ {//��Щ����,��������ȵļ��ٻ�ͼ��˸����
+ //ȡ�þɵ���Ŀ
+ item_rect = rect;
+ item_rect.x1 += RTGUI_WIDGET_BORDER(fview);
+ item_rect.x2 -= RTGUI_WIDGET_BORDER(fview);
+ item_rect.y1 += RTGUI_WIDGET_BORDER(fview);
+ item_rect.y1 += ((fview->old_aloc-fview->frist_aloc) % fview->item_per_page) * (1 + SELECTED_HEIGHT);
+ item_rect.y2 = item_rect.y1 + (1 + SELECTED_HEIGHT);
+
+ //ȡ��ͼ�����
+ image_rect.x1 = RTGUI_WIDGET_DEFAULT_MARGIN; image_rect.y1 = 0;
+ image_rect.x2 = RTGUI_WIDGET_DEFAULT_MARGIN + file_image->w; image_rect.y2 = file_image->h;
+ rtgui_rect_moveto_align(&item_rect, &image_rect, RTGUI_ALIGN_CENTER_VERTICAL);
+
+ //���ƾɵ���Ŀ
+ item = &(fview->items[fview->old_aloc]);
+ if(item->type == RTGUI_FITEM_FILE) /* draw item image */
+ rtgui_image_blit(file_image, dc, &image_rect);
+ else
+ rtgui_image_blit(folder_image, dc, &image_rect);
+
+ item_rect.x1 += RTGUI_WIDGET_DEFAULT_MARGIN + file_image->w + 2;
+ item_rect.x2 = item_rect.x1 + rtgui_font_get_string_width(RTGUI_DC_FONT(dc), item->name);
+ RTGUI_DC_BC(dc) = white;
+ RTGUI_DC_FC(dc) = black;
+ rtgui_dc_fill_rect(dc,&item_rect);
+ rtgui_dc_draw_text(dc, item->name, &item_rect);
+ }
+ //���Ƶ�ǰ��Ŀ
+ item_rect = rect;
+ item_rect.x1 += RTGUI_WIDGET_BORDER(fview);
+ item_rect.x2 -= RTGUI_WIDGET_BORDER(fview);
+ item_rect.y1 += RTGUI_WIDGET_BORDER(fview);
+ item_rect.y1 += ((fview->now_aloc-fview->frist_aloc) % fview->item_per_page) * (1 + SELECTED_HEIGHT);
+ item_rect.y2 = item_rect.y1 + (1 + SELECTED_HEIGHT);
+
+ /* get image base rect */
+ image_rect.x1 = RTGUI_WIDGET_DEFAULT_MARGIN; image_rect.y1 = 0;
+ image_rect.x2 = RTGUI_WIDGET_DEFAULT_MARGIN + file_image->w; image_rect.y2 = file_image->h;
+ rtgui_rect_moveto_align(&item_rect, &image_rect, RTGUI_ALIGN_CENTER_VERTICAL);
+
+ item = &(fview->items[fview->now_aloc]);
+ if(item->type == RTGUI_FITEM_FILE) /* draw item image */
+ rtgui_image_blit(file_image, dc, &image_rect);
+ else
+ rtgui_image_blit(folder_image, dc, &image_rect);
+
+ if(dlgst->filename) rt_free(dlgst->filename);
+ dlgst->filename = rt_strdup(item->name);
+ dlgst->type = item->type;
+ dlgst->size = item->size;
+
+ item_rect.x1 += RTGUI_WIDGET_DEFAULT_MARGIN + file_image->w + 2;
+ item_rect.x2 = item_rect.x1 + rtgui_font_get_string_width(RTGUI_DC_FONT(dc), item->name);
+
+ {
+ if(RTGUI_WIDGET_IS_FOCUSED(fview))
+ {
+ RTGUI_DC_BC(dc) = selected_color;
+ RTGUI_DC_FC(dc) = white;
+ }
+ else
+ {
+ RTGUI_DC_BC(dc) = dark_grey;
+ RTGUI_DC_FC(dc) = black;
+ }
+ rtgui_dc_fill_rect(dc, &item_rect);
+ rtgui_dc_draw_text(dc, item->name, &item_rect);
+ }
+ if(item->type == RTGUI_FITEM_FILE)
+ rtgui_textbox_set_value(dlgst->tbox_filename,dlgst->filename);
+ RTGUI_DC_FC(dc) = black;
+ rtgui_theme_draw_textbox(dlgst->tbox_filename);
+
+ rtgui_dc_end_drawing(dc);
+}
+
+void rtgui_filelist_view_on_enter(rtgui_filelist_view_t* fview)
+{
+ if(fview->items==RT_NULL)return;
+ if(fview->item_count==0)return;
+
+ if(fview->items[fview->now_aloc].type == RTGUI_FITEM_DIR)
+ {//���
+ rtgui_filelist_view_on_folder_item(fview);
+ }
+ else
+ {//�ļ�
+
+ }
+}
+
+rt_bool_t rtgui_filelist_view_event_handler(PVOID wdt, rtgui_event_t* event)
+{
+ rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ rtgui_filelist_view_t* fview = RT_NULL;
+
+ fview = RTGUI_FILELIST_VIEW(widget);
+ switch (event->type)
+ {
+ case RTGUI_EVENT_PAINT:
+ rtgui_filelist_view_ondraw(fview);
+ return FALSE;
+
+ case RTGUI_EVENT_RESIZE:
+ {
+ rtgui_event_resize_t* resize;
+
+ resize = (rtgui_event_resize_t*)event;
+
+ /* recalculate page items */
+ if(file_image != RT_NULL)
+ fview->item_per_page = resize->h / (1 + SELECTED_HEIGHT);
+ else
+ fview->item_per_page = resize->h / (2 + 14);
+ }
+ break;
+
+ case RTGUI_EVENT_MOUSE_BUTTON:
+ {
+ rtgui_rect_t rect;
+ rtgui_event_mouse_t* emouse;
+
+ emouse = (rtgui_event_mouse_t*)event;
+
+ //����ѡ�����Ŀλ��
+
+ rtgui_widget_focus(fview);
+ /* get physical extent information */
+ rtgui_widget_get_rect(fview, &rect);
+ rtgui_widget_rect_to_device(fview, &rect);
+
+ if(fview->sbar && !RTGUI_WIDGET_IS_HIDE(fview->sbar))
+ rect.x2 -= rtgui_rect_width(fview->sbar->parent.extent);
+
+ if((rtgui_rect_contains_point(&rect, emouse->x, emouse->y) == RT_EOK) && fview->item_count>0)
+ {
+ rt_uint16_t i;
+
+ i = (emouse->y - rect.y1) / (2 + SELECTED_HEIGHT);
+
+ /* set focus */
+ rtgui_widget_focus(fview);
+
+ if((i < fview->item_count) && (i < fview->item_per_page))
+ {
+ //����ѡ����
+ if(emouse->button & RTGUI_MOUSE_BUTTON_DOWN)
+ {
+ fview->old_aloc = fview->now_aloc;
+ fview->now_aloc = fview->frist_aloc + i;
+ rtgui_filelist_view_update_current(fview);
+ }
+ else if(emouse->button & RTGUI_MOUSE_BUTTON_UP)
+ {
+ if(fview->now_aloc==fview->old_aloc) return FALSE;
+
+ rtgui_filelist_view_update_current(fview);
+ }
+ if(fview->sbar && !RTGUI_WIDGET_IS_HIDE(fview))
+ {
+ if(!RTGUI_WIDGET_IS_HIDE(fview->sbar))
+ rtgui_scrollbar_set_value(fview->sbar,fview->frist_aloc);
+ }
+ }
+ return TRUE;
+ }
+ }
+ break;
+
+ case RTGUI_EVENT_KBD:
+ {
+ rtgui_event_kbd_t* ekbd = (rtgui_event_kbd_t*)event;
+ if(RTGUI_KBD_IS_DOWN(ekbd))
+ {
+ switch (ekbd->key)
+ {
+ case RTGUIK_UP: //һ���Ϸ�һ��
+ if(fview->now_aloc > 0)
+ {
+ fview->old_aloc = fview->now_aloc;
+ fview->now_aloc --;
+
+ if(fview->now_aloc < fview->frist_aloc)
+ {//���Ϸ�ҳ��
+ fview->frist_aloc = fview->now_aloc;
+ rtgui_filelist_view_ondraw(fview);
+ }
+ else
+ {//��ǰҳ��
+ rtgui_filelist_view_update_current(fview);
+ }
+
+ if(fview->sbar && !RTGUI_WIDGET_IS_HIDE(fview))
+ {
+ if(!RTGUI_WIDGET_IS_HIDE(fview->sbar))
+ rtgui_scrollbar_set_value(fview->sbar,fview->frist_aloc);
+ }
+ }
+ return TRUE;
+
+ case RTGUIK_DOWN: //һ���·�һ��
+ if(fview->now_aloc < fview->item_count-1)
+ {
+ fview->old_aloc = fview->now_aloc;
+ fview->now_aloc ++;
+
+ if(fview->now_aloc >= fview->frist_aloc+fview->item_per_page)
+ {//��ҳ��
+ fview->frist_aloc++;
+ rtgui_filelist_view_ondraw(fview);
+ }
+ else
+ {//�ڵ�ǰҳ��
+ rtgui_filelist_view_update_current(fview);
+ }
+ if(fview->sbar && !RTGUI_WIDGET_IS_HIDE(fview))
+ {
+ if(!RTGUI_WIDGET_IS_HIDE(fview->sbar))
+ rtgui_scrollbar_set_value(fview->sbar,fview->frist_aloc);
+ }
+ }
+ return TRUE;
+
+ case RTGUIK_LEFT:
+ if(fview->item_count==0)return FALSE;
+ fview->old_aloc = fview->now_aloc;
+ fview->now_aloc -= fview->item_per_page;
+
+ if(fview->now_aloc < 0)
+ fview->now_aloc = 0;
+
+ if(fview->now_aloc < fview->frist_aloc)
+ {
+ fview->frist_aloc = fview->now_aloc;
+ rtgui_filelist_view_ondraw(fview);
+ }
+ else
+ {
+ rtgui_filelist_view_update_current(fview);
+ }
+ if(fview->sbar && !RTGUI_WIDGET_IS_HIDE(fview))
+ {
+ if(!RTGUI_WIDGET_IS_HIDE(fview->sbar))
+ rtgui_scrollbar_set_value(fview->sbar,fview->frist_aloc);
+ }
+ return TRUE;
+
+ case RTGUIK_RIGHT:
+ if(fview->item_count==0)return FALSE;
+ fview->old_aloc = fview->now_aloc;
+ fview->now_aloc += fview->item_per_page;
+
+ if(fview->now_aloc > fview->item_count-1)
+ fview->now_aloc = fview->item_count-1;
+
+ if(fview->now_aloc >= fview->frist_aloc+fview->item_per_page)
+ {
+ fview->frist_aloc += fview->item_per_page;
+ if(fview->frist_aloc >fview->item_count-fview->item_per_page)
+ {
+ fview->frist_aloc = fview->item_count-fview->item_per_page;
+ fview->now_aloc = fview->frist_aloc;
+ }
+ rtgui_filelist_view_ondraw(fview);
+ }
+ else
+ {
+ rtgui_filelist_view_update_current(fview);
+ }
+ if(fview->sbar && !RTGUI_WIDGET_IS_HIDE(fview))
+ {
+ if(!RTGUI_WIDGET_IS_HIDE(fview->sbar))
+ rtgui_scrollbar_set_value(fview->sbar,fview->frist_aloc);
+ }
+ return TRUE;
+
+ case RTGUIK_RETURN:
+ //GoToSubFolder(fview,RT_NULL);
+ return TRUE;
+ case RTGUIK_BACKSPACE:
+ //GoToTopFolder(fview,RT_NULL);
+ return TRUE;
+ default:
+ break;
+ }
+ }
+ }
+ return FALSE;
+ default:
+ return rtgui_container_event_handler(widget, event);
+ }
+
+ /* use view event handler */
+ return rtgui_container_event_handler(widget, event);
+}
+
+/* clear all file items */
+static void rtgui_filelist_view_clear(rtgui_filelist_view_t* fview)
+{
+ rt_uint32_t index;
+ rtgui_filelist_view_item_t* item;
+
+ if(fview->items == RT_NULL) return;
+
+ for(index = 0; index < fview->item_count; index ++)
+ {
+ item = &(fview->items[index]);
+
+ /* release item name */
+ if(item->name != RT_NULL)
+ {
+ rt_free(item->name);
+ item->name = RT_NULL;
+ }
+ }
+
+ /* release items */
+ rt_free(fview->items);
+ fview->items = RT_NULL;
+
+ fview->item_count = 0;
+ fview->now_aloc = 0;
+}
+
+void rtgui_filelist_view_set_directory(rtgui_filelist_view_t* fview, const char* directory)
+{
+ char fullpath[256];
+ rtgui_filelist_view_item_t *item;
+ rtgui_win_t* win;
+ struct OpenDlgSt* dlgst=RT_NULL;
+
+ win = rtgui_win_get_win_by_widget(fview);
+ if(win == RT_NULL)return;
+ if(win->user_data != RT_NULL)
+ {
+ dlgst = (struct OpenDlgSt*)win->user_data;
+ }
+
+ fview->frist_aloc = 0;
+
+ //��������ļ���Ŀ
+ rtgui_filelist_view_clear(fview);
+ if(directory != RT_NULL)
+ {
+ DIR* dir;
+ struct stat s;
+ rt_uint32_t i;
+ struct dirent* dirent;
+
+ fview->item_count = 0;
+ //�����
+ dir = opendir(directory);
+ if(dir == RT_NULL) goto __return;
+
+ //���õ�ǰ�ļ���
+ if(fview->current_dir != RT_NULL)
+ rt_free(fview->current_dir);
+ fview->current_dir = rt_strdup(directory);
+
+ if(dlgst->path != RT_NULL) rt_free(dlgst->path);
+ dlgst->path = rt_strdup(fview->current_dir);
+
+ rtgui_textbox_set_value(dlgst->tbox_path,dlgst->path);
+ rtgui_theme_draw_textbox(dlgst->tbox_path);
+
+ do{
+ dirent = readdir(dir);
+ if(dirent == RT_NULL) break;
+ fview->item_count ++;
+ }while (dirent != RT_NULL);
+ closedir(dir);
+
+ if((fview->item_count > fview->item_per_page) && fview->sbar!=RT_NULL)
+ {
+ RTGUI_WIDGET_UNHIDE(fview->sbar);
+ rtgui_scrollbar_set_line_step(fview->sbar,1);
+ rtgui_scrollbar_set_page_step(fview->sbar, fview->item_per_page);
+ rtgui_scrollbar_set_range(fview->sbar, fview->item_count);
+ }
+ else
+ {
+ RTGUI_WIDGET_HIDE(fview->sbar);
+ }
+ rtgui_widget_update_clip(fview);
+
+ //����һ�����Է���������Ŀ�Ŀռ�
+ fview->items = (rtgui_filelist_view_item_t*) rt_malloc(sizeof(rtgui_filelist_view_item_t) * fview->item_count);
+
+ if(fview->items == RT_NULL) goto __return; /*under the folder has not sub files. */
+
+ //���´��ļ���
+ dir = opendir(directory);
+ if(dir == RT_NULL) goto __return;
+
+ for(i=0; i < fview->item_count; i ++)
+ {
+ dirent = readdir(dir);
+ if(dirent == RT_NULL) break;
+
+ item = &(fview->items[i]);
+ item->name = rt_strdup(dirent->d_name);
+
+ rt_memset(&s, 0, sizeof(struct stat));
+
+ //����ÿ���ļ���ȫ·��
+ if(directory[strlen(directory) - 1] != PATH_SEPARATOR)
+ rt_sprintf(fullpath, "%s%c%s", directory, PATH_SEPARATOR, dirent->d_name);
+ else
+ rt_sprintf(fullpath, "%s%s", directory, dirent->d_name);
+
+ stat(fullpath, &s);
+ if( s.st_mode & S_IFDIR )
+ {
+ item->type = RTGUI_FITEM_DIR;
+ item->size = 0;
+ }
+ else
+ {
+ item->type = RTGUI_FITEM_FILE;
+ item->size = s.st_size;
+ }
+ }
+
+ closedir(dir);
+ }
+
+ fview->now_aloc = 0;
+
+__return:
+ /* update view */
+ rtgui_widget_update(fview);
+}
+
+void rtgui_filelist_view_get_fullpath(rtgui_filelist_view_t* view, char* path, rt_size_t len)
+{
+ RT_ASSERT(view != RT_NULL);
+
+ if(view->current_dir[strlen(view->current_dir) - 1] != PATH_SEPARATOR)
+ rt_snprintf(path, len, "%s%c%s",view->current_dir, PATH_SEPARATOR,
+ view->items[view->now_aloc].name);
+ else
+ rt_snprintf(path, len, "%s%s",view->current_dir,
+ view->items[view->now_aloc].name);
+}
+
+static rt_bool_t rtgui_fileview_onunfocus(PVOID wdt, rtgui_event_t* event)
+{
+ rtgui_filelist_view_t *fview = (rtgui_filelist_view_t*)wdt;
+
+ if(fview == RT_NULL) return FALSE;
+ + if(!RTGUI_WIDGET_IS_FOCUSED(fview)) + {//�������� + rtgui_filelist_view_update_current(fview); + }
+ + return TRUE;
+}
+
+static rt_bool_t rtgui_fileview_sbar_handle(PVOID wdt, rtgui_event_t* event)
+{
+ rtgui_filelist_view_t *fview = (rtgui_filelist_view_t*)wdt;
+
+ fview->frist_aloc = fview->sbar->value;
+
+ rtgui_filelist_view_ondraw(fview);
+
+ return TRUE;
+}
+
+
diff --git a/components/rtgui_win/widgets/folder.xpm b/components/rtgui_win/widgets/folder.xpm new file mode 100644 index 0000000000..f5feb65555 --- /dev/null +++ b/components/rtgui_win/widgets/folder.xpm @@ -0,0 +1,142 @@ +/* XPM */
+static const char * folder_xpm[] = {
+"16 16 121 2",
+" c None",
+". c #D9B434",
+"+ c #E1C25E",
+"@ c #E2C360",
+"# c #E2C35F",
+"$ c #DBB63C",
+"% c #DAB336",
+"& c #FEFEFD",
+"* c #FFFFFE",
+"= c #FFFEFE",
+"- c #FFFEFD",
+"; c #FBF7EA",
+"> c #E4C76B",
+", c #E3C76B",
+"' c #E6CD79",
+") c #E5CA74",
+"! c #DAAF35",
+"~ c #FEFCF7",
+"{ c #F8E48E",
+"] c #F5DE91",
+"^ c #F5E09F",
+"/ c #F6E1AC",
+"( c #FEFBEF",
+"_ c #FEFDF4",
+": c #FEFCF3",
+"< c #FEFCF1",
+"[ c #FEFBEE",
+"} c #FFFDFA",
+"| c #DAAF36",
+"1 c #DAAA36",
+"2 c #FDFAF1",
+"3 c #F5DE94",
+"4 c #F4DC93",
+"5 c #F2D581",
+"6 c #EDCA6A",
+"7 c #EACB6C",
+"8 c #EFD385",
+"9 c #EFD280",
+"0 c #EFD07A",
+"a c #EECF76",
+"b c #EECF72",
+"c c #FBF7E9",
+"d c #DAAE34",
+"e c #DAAB35",
+"f c #FBF6E8",
+"g c #EFD494",
+"h c #EECE88",
+"i c #E9C173",
+"j c #F6E9C9",
+"k c #FEFCF2",
+"l c #FEFCF0",
+"m c #DAAB36",
+"n c #DAA637",
+"o c #FFFDF8",
+"p c #FFFDF6",
+"q c #FFFCF5",
+"r c #FCF6D8",
+"s c #F8E694",
+"t c #F7E385",
+"u c #F6DF76",
+"v c #F5DB68",
+"w c #F4D85C",
+"x c #FCF4D7",
+"y c #DAA435",
+"z c #DAA136",
+"A c #FEFCF6",
+"B c #FCF2C8",
+"C c #FBEFB9",
+"D c #FAECAC",
+"E c #F9E89C",
+"F c #F7E38B",
+"G c #F6E07C",
+"H c #F6DC6C",
+"I c #F5D95D",
+"J c #F4D64F",
+"K c #F3D344",
+"L c #FCF3D0",
+"M c #DA9F35",
+"N c #DA9A36",
+"O c #FDFAF2",
+"P c #FAEDB3",
+"Q c #F9E9A4",
+"R c #F8E695",
+"S c #F7E285",
+"T c #F6DE76",
+"U c #F5DB65",
+"V c #F4D757",
+"W c #F3D449",
+"X c #F2D13B",
+"Y c #F1CE30",
+"Z c #FBF2CC",
+"` c #DA9835",
+" . c #DA9435",
+".. c #FEFAEF",
+"+. c #F9E9A1",
+"@. c #F8E591",
+"#. c #F7E181",
+"$. c #F6DE72",
+"%. c #F5DA63",
+"&. c #F4D754",
+"*. c #F3D347",
+"=. c #F2D039",
+"-. c #F1CD2E",
+";. c #F0CB26",
+">. c #FBF2CA",
+",. c #D98E33",
+"'. c #FAF0DC",
+"). c #F4DDA7",
+"!. c #F4DB9E",
+"~. c #F3DA96",
+"{. c #F3D88E",
+"]. c #F3D786",
+"^. c #F2D47F",
+"/. c #F2D379",
+"(. c #F1D272",
+"_. c #F1D06C",
+":. c #F1CF69",
+"<. c #F8EAC2",
+"[. c #D8882D",
+"}. c #D8872D",
+"|. c #D8862C",
+" ",
+" ",
+" ",
+" . + @ @ @ # $ ",
+" % & * = - * ; > , , , ' ) ",
+" ! ~ { ] ^ / ( _ : < ( [ } | ",
+" 1 2 3 4 5 6 7 8 9 0 a b c d ",
+" e f g h i j k : k l ( [ * m ",
+" n * o p q : r s t u v w x y ",
+" z A B C D E F G H I J K L M ",
+" N O P Q R S T U V W X Y Z ` ",
+" ...+.@.#.$.%.&.*.=.-.;.>. . ",
+" ,.'.).!.~.{.].^./.(._.:.<.,. ",
+" [.}.[.[.[.[.[.[.[.[.}.[.|. ",
+" ",
+" "
+};
+
diff --git a/components/rtgui_win/widgets/iconbox.c b/components/rtgui_win/widgets/iconbox.c new file mode 100644 index 0000000000..6040b9b093 --- /dev/null +++ b/components/rtgui_win/widgets/iconbox.c @@ -0,0 +1,221 @@ +/* + * File : iconbox.c + * This file is part of RT-Thread RTOS + * COPYRIGHT (C) 2006 - 2009, RT-Thread Development Team + * + * The license and distribution terms for this file may be + * found in the file LICENSE in this distribution or at + * http://www.rt-thread.org/license/LICENSE + * + * Change Logs: + * Date Author Notes + * 2009-10-16 Bernard first version + */ +#include <rtgui/dc.h>
+ +#include <rtgui/widgets/iconbox.h> +#include <rtgui/rtgui_theme.h>
+#include <rtgui/font.h>
+ +static rt_bool_t rtgui_iconbox_onfocus(PVOID wdt, rtgui_event_t* event);
+static rt_bool_t rtgui_iconbox_onunfocus(PVOID wdt, rtgui_event_t* event);
+ +static void _rtgui_iconbox_constructor(rtgui_iconbox_t *iconbox) +{ + /* init widget and set event handler */ + rtgui_widget_set_event_handler(iconbox, rtgui_iconbox_event_handler); + RTGUI_WIDGET_FLAG(iconbox) |= RTGUI_WIDGET_FLAG_TRANSPARENT; + /* set proper of control */ + iconbox->image = RT_NULL; + iconbox->selected = RT_FALSE; + iconbox->text = RT_NULL; + iconbox->text_position = RTGUI_ICONBOX_TEXT_BELOW;
+ iconbox->call = RT_NULL;
+
+ rtgui_widget_set_onfocus(iconbox,rtgui_iconbox_onfocus);
+ rtgui_widget_set_onunfocus(iconbox,rtgui_iconbox_onunfocus); +} + +static void _rtgui_iconbox_destructor(rtgui_iconbox_t *iconbox) +{ + if(iconbox->image != RT_NULL) + { + rtgui_image_destroy(iconbox->image); + iconbox->image = RT_NULL; + } + if(iconbox->text != RT_NULL)
+ { + rt_free(iconbox->text); + iconbox->text = RT_NULL;
+ } +} + +rtgui_type_t *rtgui_iconbox_type_get(void) +{ + static rtgui_type_t *iconbox_type = RT_NULL; + + if(!iconbox_type) + { + iconbox_type = rtgui_type_create("iconbox", RTGUI_WIDGET_TYPE, + sizeof(rtgui_iconbox_t), RTGUI_CONSTRUCTOR(_rtgui_iconbox_constructor), + RTGUI_DESTRUCTOR(_rtgui_iconbox_destructor)); + } + + return iconbox_type; +} + +rt_bool_t rtgui_iconbox_event_handler(PVOID wdt, rtgui_event_t* event) +{ + rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ rtgui_iconbox_t* iconbox = (rtgui_iconbox_t*)widget; + + switch (event->type) + { + case RTGUI_EVENT_PAINT: + if(widget->on_draw != RT_NULL)
+ widget->on_draw(widget, event); + else + { + rtgui_theme_draw_iconbox(iconbox); + } + + break;
+ case RTGUI_EVENT_MOUSE_BUTTON:
+ rtgui_widget_focus(wdt);
+ if(iconbox->call)
+ iconbox->call();
+ break; + } + + return RT_FALSE; +} + +rtgui_iconbox_t* rtgui_iconbox_create(PVOID parent, rtgui_image_t* image,const char* text,int position) +{ + rtgui_iconbox_t* iconbox;
+ + RT_ASSERT(parent != RT_NULL);
+ + iconbox = rtgui_widget_create(RTGUI_ICONBOX_TYPE); + if(iconbox != RT_NULL) + { + rtgui_rect_t rect, text_rect; +
+ rect.x2 = image->w; + rect.y2 = image->h; + + /* get text rect */ + rtgui_font_get_string_rect(RTGUI_WIDGET_FONT(iconbox), text, &text_rect); + if(position == RTGUI_ICONBOX_TEXT_BELOW) + { + rect.y2 += RTGUI_WIDGET_DEFAULT_MARGIN; + if(text_rect.x2 > rect.x2) + { + rect.x2 = text_rect.x2; + } + rect.y2 += text_rect.y2; + } + else if(position == RTGUI_ICONBOX_TEXT_RIGHT) + { + rect.x2 += RTGUI_WIDGET_DEFAULT_MARGIN; + if(text_rect.y2 > rect.y2) + { + rect.y2 = text_rect.y2; + } + rect.x2 += text_rect.x2; + } + + /* set widget rect */ + rtgui_widget_set_rect(iconbox, &rect); + + /* set image and text position */ + iconbox->image = image; + iconbox->text = rt_strdup(text); + iconbox->text_position = position;
+
+ rtgui_container_add_child(parent, iconbox); + } + + return iconbox; +} + +void rtgui_iconbox_destroy(rtgui_iconbox_t* iconbox) +{ + rtgui_widget_destroy(iconbox); +} + +void rtgui_iconbox_set_text_position(rtgui_iconbox_t* iconbox, int position) +{ + rtgui_rect_t rect = {0, 0, 0, 0}, text_rect; + + RT_ASSERT(iconbox != RT_NULL); + + iconbox->text_position = position; + + /* set mini width and height */ + rect.x2 = iconbox->image->w; + rect.y2 = iconbox->image->h; + + /* get text rect */ + if(iconbox->text != RT_NULL) + { + rtgui_font_get_string_rect(RTGUI_WIDGET_FONT(iconbox), + iconbox->text, &text_rect); + if(position == RTGUI_ICONBOX_TEXT_BELOW) + { + rect.y2 += RTGUI_WIDGET_DEFAULT_MARGIN; + if(text_rect.x2 > rect.x2) + { + rect.x2 = text_rect.x2; + } + rect.y2 += text_rect.y2; + } + else if(position == RTGUI_ICONBOX_TEXT_RIGHT) + { + rect.x2 += RTGUI_WIDGET_DEFAULT_MARGIN; + if(text_rect.y2 > rect.y2) + { + rect.y2 = text_rect.y2; + } + rect.x2 += text_rect.x2; + } + } +}
+ +static rt_bool_t rtgui_iconbox_onfocus(PVOID wdt, rtgui_event_t* event) +{ + rtgui_rect_t rect;
+ rtgui_dc_t *dc;
+
+ RT_ASSERT(wdt != RT_NULL);
+
+ dc = rtgui_dc_begin_drawing(wdt);
+ if(dc == RT_NULL)return RT_FALSE;
+
+ rtgui_widget_get_rect(wdt,&rect); + rtgui_dc_draw_focus_rect(dc,&rect);
+ + rtgui_dc_end_drawing(dc);
+ + return RT_TRUE; +} + +static rt_bool_t rtgui_iconbox_onunfocus(PVOID wdt, rtgui_event_t* event) +{ + rtgui_rect_t rect;
+ rtgui_dc_t *dc;
+
+ RT_ASSERT(wdt != RT_NULL);
+
+ dc = rtgui_dc_begin_drawing(wdt);
+ if(dc == RT_NULL)return RT_FALSE;
+
+ rtgui_widget_get_rect(wdt,&rect);
+ RTGUI_DC_FC(dc) = RTGUI_WIDGET_BACKGROUND(RTGUI_WIDGET(wdt)->parent); + rtgui_dc_draw_focus_rect(dc,&rect);
+ + rtgui_dc_end_drawing(dc);
+ + return RT_TRUE; +}
+
diff --git a/components/rtgui_win/widgets/label.c b/components/rtgui_win/widgets/label.c new file mode 100644 index 0000000000..608252c07a --- /dev/null +++ b/components/rtgui_win/widgets/label.c @@ -0,0 +1,135 @@ +/* + * File : label.c + * This file is part of RT-Thread RTOS + * COPYRIGHT (C) 2006 - 2009, RT-Thread Development Team + * + * The license and distribution terms for this file may be + * found in the file LICENSE in this distribution or at + * http://www.rt-thread.org/license/LICENSE + * + * Change Logs: + * Date Author Notes + * 2009-10-16 Bernard first version + */ +#include <rtgui/dc.h> +#include <rtgui/widgets/label.h> +#include <rtgui/rtgui_system.h> +#include <rtgui/rtgui_theme.h> + +static void _rtgui_label_constructor(rtgui_label_t *label) +{ + /* init widget and set event handler */ + rtgui_widget_set_event_handler(label, rtgui_label_event_handler);
+
+ RTGUI_WIDGET_FOREGROUND(label) = black;
+ RTGUI_WIDGET_BACKGROUND(label) = default_background; + RTGUI_WIDGET_TEXTALIGN(label) = RTGUI_ALIGN_CENTER_VERTICAL; + /* set field */ + label->text = RT_NULL; +} + +static void _rtgui_label_destructor(rtgui_label_t *label) +{ + /* release text memory */ + if(label->text != RT_NULL)
+ {
+ rt_free(label->text); + label->text = RT_NULL;
+ } +} + +rtgui_type_t *rtgui_label_type_get(void) +{ + static rtgui_type_t *label_type = RT_NULL; + + if(!label_type) + { + label_type = rtgui_type_create("label", RTGUI_WIDGET_TYPE, + sizeof(rtgui_label_t), + RTGUI_CONSTRUCTOR(_rtgui_label_constructor), + RTGUI_DESTRUCTOR(_rtgui_label_destructor)); + } + + return label_type; +} + +rt_bool_t rtgui_label_event_handler(PVOID wdt, rtgui_event_t* event) +{ + rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ rtgui_label_t* label; + + RT_ASSERT(widget != RT_NULL); + + label = (rtgui_label_t*) widget; + switch (event->type) + { + case RTGUI_EVENT_PAINT: + rtgui_theme_draw_label(label); + break;
+ default:
+ break; + } + + return RT_FALSE; +}
+ +//parent������һ��������ؼ� +rtgui_label_t* rtgui_label_create(PVOID parent, const char* text,int left, int top, int w, int h) +{ + rtgui_label_t* label;
+
+ RT_ASSERT(parent != RT_NULL);
+ + label = rtgui_widget_create(RTGUI_LABEL_TYPE); + if(label != RT_NULL) + { + rtgui_rect_t rect;
+ rtgui_widget_get_rect(parent, &rect);
+ rtgui_widget_rect_to_device(parent,&rect);
+ rect.x1 += left;
+ rect.y1 += top;
+ rect.x2 = rect.x1+w;
+ rect.y2 = rect.y1+h; + rtgui_widget_set_rect(label, &rect);
+
+ label->text = rt_strdup(text); +
+ rtgui_container_add_child(parent, label); + } + + return label; +} + +void rtgui_label_destroy(rtgui_label_t* label) +{ + rtgui_widget_destroy(label); +} + +char* rtgui_label_get_text(rtgui_label_t* label) +{ + if(label == RT_NULL)return RT_NULL; + + return label->text; +} + +void rtgui_label_set_text(rtgui_label_t* label, const char* text) +{ + if(label == RT_NULL)return;
+ + if(strcmp(text,label->text)==0)return;
+ + if(label->text != RT_NULL) + { + /* release old text memory */ + rt_free(label->text);
+ label->text = RT_NULL; + } + + if(text != RT_NULL)
+ label->text = rt_strdup(text); + else
+ label->text = RT_NULL;
+ + /* update widget */ + rtgui_theme_draw_label(label);//�þ��ƺ��Ƕ����,�������Ͻ�(0,0)����һ���ַ��� +} diff --git a/components/rtgui_win/widgets/list_view.c b/components/rtgui_win/widgets/list_view.c new file mode 100644 index 0000000000..ced1ca157e --- /dev/null +++ b/components/rtgui_win/widgets/list_view.c @@ -0,0 +1,667 @@ +/*
+ * File : list_view.c
+ * This file is part of RTGUI in RT-Thread RTOS
+ * COPYRIGHT (C) 2010, RT-Thread Development Team
+ *
+ * The license and distribution terms for this file may be
+ * found in the file LICENSE in this distribution or at
+ * http://www.rt-thread.org/license/LICENSE
+ *
+ * Change Logs:
+ * Date Author Notes
+ * 2010-01-06 Bernard first version
+ */
+
+#include <rtgui/rtgui_theme.h>
+#include <rtgui/widgets/list_view.h>
+
+static void _rtgui_list_view_constructor(rtgui_list_view_t *view)
+{
+ /* default rect */
+ rtgui_rect_t rect = {0, 0, 200, 200};
+
+ /* set default widget rect and set event handler */
+ rtgui_widget_set_event_handler(view,rtgui_list_view_event_handler);
+ rtgui_widget_set_rect(view, &rect);
+
+ RTGUI_WIDGET_FLAG(view) |= RTGUI_WIDGET_FLAG_FOCUSABLE;
+
+ view->flag = RTGUI_LIST_VIEW_LIST;
+ view->item_current = 0;
+ view->item_count = 0;
+ view->page = 0;
+
+ RTGUI_WIDGET_BACKGROUND(view) = white;
+ RTGUI_WIDGET_TEXTALIGN(view) = RTGUI_ALIGN_CENTER_VERTICAL;
+}
+
+static void _rtgui_list_view_destructor(rtgui_list_view_t *view)
+{
+
+}
+
+rtgui_type_t *rtgui_list_view_type_get(void)
+{
+ static rtgui_type_t *list_view_type = RT_NULL;
+
+ if(!list_view_type)
+ {
+ list_view_type = rtgui_type_create("listview", RTGUI_VIEW_TYPE,
+ sizeof(rtgui_list_view_t),
+ RTGUI_CONSTRUCTOR(_rtgui_list_view_constructor),
+ RTGUI_DESTRUCTOR(_rtgui_list_view_destructor));
+ }
+
+ return list_view_type;
+}
+
+static void rtgui_list_view_onicondraw(rtgui_list_view_t* view)
+{
+ rtgui_rect_t rect, item_rect, drawing_rect;
+ rt_uint32_t c, r, i; /* col and row index */
+ rt_uint32_t item_width, item_height;
+ rtgui_image_t* image;
+ rtgui_dc_t* dc;
+
+ RT_ASSERT(view != RT_NULL);
+
+ /* begin drawing */
+ dc = rtgui_dc_begin_drawing(view);
+ if(dc == RT_NULL)return;
+
+ if(view->item_count == 0) return;
+
+ rtgui_widget_get_rect(view, &rect);
+ i = (view->item_current / view->page) * view->page;
+
+ item_width = (rtgui_rect_width(rect) - 2 * RTGUI_WIDGET_DEFAULT_MARGIN)/view->col_items;
+ item_height = (rtgui_rect_height(rect) - 4)/view->row_items;
+ image = view->items[0].image;
+
+ for(r = 0; r < view->row_items; r ++)
+ {
+ for(c = 0; c < view->col_items; c ++)
+ {
+ if(i < view->item_count)
+ {
+ item_rect.y1 = rect.y1 + RTGUI_WIDGET_DEFAULT_MARGIN + r * item_height;
+ item_rect.x1 = rect.x1 + RTGUI_WIDGET_DEFAULT_MARGIN + c * item_width;
+ item_rect.x2 = item_rect.x1 + item_width;
+ item_rect.y2 = item_rect.y1 + item_height;
+
+ if(i == view->item_current)
+ {
+ RTGUI_DC_BC(dc) = selected_color;
+ rtgui_dc_fill_rect(dc, &item_rect);
+ }
+
+ drawing_rect.x1 = drawing_rect.y1 = 0;
+ drawing_rect.x2 = image->w;
+ drawing_rect.y2 = image->h;
+ rtgui_rect_moveto_align(&item_rect, &drawing_rect, RTGUI_ALIGN_CENTER_HORIZONTAL);
+ drawing_rect.y1 += 3; drawing_rect.y2 += 3;
+ rtgui_image_blit(view->items[i].image, dc, &drawing_rect);
+
+ item_rect.y1 = drawing_rect.y2 + RTGUI_WIDGET_DEFAULT_MARGIN;
+ item_rect.x1 += 3; item_rect.x2 -=3;
+ rtgui_font_get_string_rect(RTGUI_WIDGET_FONT(view), view->items[i].name,
+ &drawing_rect);
+ rtgui_rect_moveto_align(&item_rect, &drawing_rect, RTGUI_ALIGN_CENTER_HORIZONTAL);
+ rtgui_dc_draw_text(dc, view->items[i].name, &drawing_rect);
+
+ i ++;
+ }
+ else break;
+ }
+ }
+ rtgui_dc_end_drawing(dc);
+}
+
+static void rtgui_list_view_update_icon(rtgui_list_view_t* view, rt_uint16_t old_item)
+{
+ rtgui_rect_t rect, item_rect, drawing_rect;
+ rt_uint32_t c, r; /* col and row index */
+ rt_uint32_t item_width, item_height;
+ rtgui_image_t* image;
+ rtgui_dc_t* dc;
+
+ RT_ASSERT(view != RT_NULL);
+
+ /* begin drawing */
+ dc = rtgui_dc_begin_drawing(view);
+ if(dc == RT_NULL)return;
+
+ if((view->item_count == 0) ||
+ (old_item == view->item_current))
+ return;
+
+ if(old_item/view->page != view->item_current/view->page)
+ {
+ /* it's not a same page, update all */
+ rtgui_widget_update(view);
+ return;
+ }
+
+ rtgui_widget_get_rect(view, &rect);
+
+ item_width = (rtgui_rect_width(rect) - 2 * RTGUI_WIDGET_DEFAULT_MARGIN)/view->col_items;
+ item_height = (rtgui_rect_height(rect) - 4)/view->row_items;
+ image = view->items[0].image;
+
+ /* update old item */
+ r = (old_item % view->page)/ view->col_items;
+ c = (old_item % view->page)% view->col_items;
+ item_rect.y1 = rect.y1 + RTGUI_WIDGET_DEFAULT_MARGIN + r * item_height;
+ item_rect.x1 = rect.x1 + RTGUI_WIDGET_DEFAULT_MARGIN + c * item_width;
+ item_rect.x2 = item_rect.x1 + item_width;
+ item_rect.y2 = item_rect.y1 + item_height;
+ rtgui_dc_fill_rect(dc,&item_rect);
+
+ /* draw image */
+ drawing_rect.x1 = drawing_rect.y1 = 0;
+ drawing_rect.x2 = image->w;
+ drawing_rect.y2 = image->h;
+ rtgui_rect_moveto_align(&item_rect, &drawing_rect, RTGUI_ALIGN_CENTER_HORIZONTAL);
+ drawing_rect.y1 += 3; drawing_rect.y2 += 3;
+ rtgui_image_blit(view->items[old_item].image, dc,&drawing_rect);
+
+ /* draw text */
+ item_rect.y1 = drawing_rect.y2 + RTGUI_WIDGET_DEFAULT_MARGIN;
+ item_rect.x1 += 3; item_rect.x2 -=3;
+ rtgui_font_get_string_rect(RTGUI_WIDGET_FONT(view), view->items[old_item].name,
+ &drawing_rect);
+ rtgui_rect_moveto_align(&item_rect, &drawing_rect, RTGUI_ALIGN_CENTER_HORIZONTAL);
+ rtgui_dc_draw_text(dc, view->items[old_item].name, &drawing_rect);
+
+ /* update new item as selected */
+ r = (view->item_current % view->page) / view->col_items;
+ c = (view->item_current % view->page) % view->col_items;
+ item_rect.y1 = rect.y1 + RTGUI_WIDGET_DEFAULT_MARGIN + r * item_height;
+ item_rect.x1 = rect.x1 + RTGUI_WIDGET_DEFAULT_MARGIN + c * item_width;
+ item_rect.x2 = item_rect.x1 + item_width;
+ item_rect.y2 = item_rect.y1 + item_height;
+ RTGUI_DC_BC(dc) = selected_color;
+ rtgui_dc_fill_rect(dc, &item_rect);
+
+ /* draw image */
+ drawing_rect.x1 = 0;
+ drawing_rect.y1 = 3;
+ drawing_rect.x2 = image->w;
+ drawing_rect.y2 = 3 + image->h;
+
+ rtgui_rect_moveto_align(&item_rect, &drawing_rect, RTGUI_ALIGN_CENTER_HORIZONTAL);
+ rtgui_image_blit(view->items[view->item_current].image, dc, &drawing_rect);
+
+ /* draw text */
+ item_rect.y1 = drawing_rect.y2 + RTGUI_WIDGET_DEFAULT_MARGIN;
+ item_rect.x1 += 3; item_rect.x2 -=3;
+ rtgui_font_get_string_rect(RTGUI_WIDGET_FONT(view),
+ view->items[view->item_current].name,
+ &drawing_rect);
+ rtgui_rect_moveto_align(&item_rect, &drawing_rect, RTGUI_ALIGN_CENTER_HORIZONTAL);
+ rtgui_dc_draw_text(dc, view->items[view->item_current].name, &drawing_rect);
+
+ rtgui_dc_end_drawing(dc);
+}
+
+static void rtgui_list_view_onlistdraw(rtgui_list_view_t* view)
+{
+ rt_uint32_t i, page;
+ rtgui_rect_t rect, item_rect, image_rect;
+ const rtgui_list_view_item_t* item;
+ rtgui_dc_t* dc;
+
+ RT_ASSERT(view != RT_NULL);
+
+ /* begin drawing */
+ dc = rtgui_dc_begin_drawing(view);
+ if(dc == RT_NULL)return;
+
+ rtgui_widget_get_rect(view, &rect);
+
+ /* get item base rect */
+ item_rect = rect;
+ item_rect.x1 += 2;
+ item_rect.x2 -= 2;
+ item_rect.y1 += 2;
+ item_rect.y2 = item_rect.y1 + (2 + SELECTED_HEIGHT);
+
+ /* get current page */
+ page = (view->item_current / view->page) * view->page;
+ for(i = 0; i < view->page; i ++)
+ {
+ if(page + i >= view->item_count) break;
+
+ item = &(view->items[page + i]);
+
+ if(page + i == view->item_current)
+ {
+ RTGUI_DC_BC(dc) = selected_color;
+ rtgui_dc_fill_rect(dc, &item_rect);
+ }
+ item_rect.x1 += RTGUI_WIDGET_DEFAULT_MARGIN;
+
+ if(item->image != RT_NULL)
+ {
+ /* blit on center */
+ image_rect.x1 = 0; image_rect.y1 = 0;
+ image_rect.x2 = item->image->w;
+ image_rect.y2 = item->image->h;
+
+ rtgui_rect_moveto_align(&item_rect, &image_rect, RTGUI_ALIGN_CENTER_VERTICAL);
+ rtgui_image_blit(item->image, dc, &image_rect);
+ item_rect.x1 += item->image->w + 2;
+ }
+ /* draw text */
+ rtgui_dc_draw_text(dc, item->name, &item_rect);
+
+ if(item->image != RT_NULL)
+ item_rect.x1 -= (item->image->w + 2);
+ item_rect.x1 -= RTGUI_WIDGET_DEFAULT_MARGIN;
+
+ /* move to next item position */
+ item_rect.y1 += (SELECTED_HEIGHT + 2);
+ item_rect.y2 += (SELECTED_HEIGHT + 2);
+ }
+
+ rtgui_dc_end_drawing(dc);
+}
+
+void rtgui_list_view_update_list(rtgui_list_view_t* view, rt_uint16_t old_item)
+{
+ const rtgui_list_view_item_t* item;
+ rtgui_rect_t rect, item_rect;
+ rtgui_dc_t* dc;
+
+ RT_ASSERT(view != RT_NULL);
+
+ /* begin drawing */
+ dc = rtgui_dc_begin_drawing(view);
+ if(dc == RT_NULL)return;
+
+ if(old_item/view->page != view->item_current/view->page)
+ {
+ /* it's not a same page, update all */
+ rtgui_widget_update(view);
+ return;
+ }
+
+ //������һ����Ŀ
+ rtgui_widget_get_rect(view, &rect);
+ item_rect = rect;
+ item_rect.x1 += 2;
+ item_rect.x2 -= 2;
+ item_rect.y1 += 2;
+ item_rect.y1 += (old_item % view->page) * (2 + SELECTED_HEIGHT);
+ item_rect.y2 = item_rect.y1 + (2 + SELECTED_HEIGHT);
+
+ rtgui_dc_fill_rect(dc,&item_rect);
+
+ item_rect.x1 += RTGUI_WIDGET_DEFAULT_MARGIN;
+
+ item = &(view->items[old_item]);
+ if(item->image != RT_NULL)
+ {
+ rtgui_rect_t image_rect;
+
+ /* blit on center */
+ image_rect.x1 = 0; image_rect.y1 = 0;
+ image_rect.x2 = item->image->w;
+ image_rect.y2 = item->image->h;
+
+ rtgui_rect_moveto_align(&item_rect, &image_rect, RTGUI_ALIGN_CENTER_VERTICAL);
+ rtgui_image_blit(item->image, dc, &image_rect);
+ item_rect.x1 += item->image->w + 2;
+ }
+ rtgui_dc_draw_text(dc, item->name, &item_rect);
+
+ //���Ƶ�ǰ��
+ item_rect = rect;
+ /* get current item's rect */
+ item_rect.x1 += 2;
+ item_rect.x2 -= 2;
+ item_rect.y1 += 2;
+ item_rect.y1 += (view->item_current % view->page) * (2 + SELECTED_HEIGHT);
+ item_rect.y2 = item_rect.y1 + (2 + SELECTED_HEIGHT);
+
+ /* draw current item */
+ RTGUI_DC_BC(dc) = selected_color;
+ rtgui_dc_fill_rect(dc, &item_rect);
+
+ item_rect.x1 += RTGUI_WIDGET_DEFAULT_MARGIN;
+
+ item = &(view->items[view->item_current]);
+ if(item->image != RT_NULL)
+ {
+ rtgui_rect_t image_rect;
+
+ /* blit on center */
+ image_rect.x1 = 0; image_rect.y1 = 0;
+ image_rect.x2 = item->image->w;
+ image_rect.y2 = item->image->h;
+
+ rtgui_rect_moveto_align(&item_rect, &image_rect, RTGUI_ALIGN_CENTER_VERTICAL);
+ rtgui_image_blit(item->image, dc, &image_rect);
+ item_rect.x1 += (item->image->w + 2);
+ }
+
+ RTGUI_DC_FC(dc) = white;
+ rtgui_dc_draw_text(dc, item->name, &item_rect);
+
+ rtgui_dc_end_drawing(dc);
+}
+
+void rtgui_list_view_ondraw(rtgui_list_view_t* view)
+{
+ rtgui_rect_t rect;
+ rtgui_dc_t* dc;
+
+ RT_ASSERT(view != RT_NULL);
+
+ /* begin drawing */
+ dc = rtgui_dc_begin_drawing(view);
+ if(dc == RT_NULL)return;
+
+ rtgui_widget_get_rect(view, &rect);
+ rtgui_dc_fill_rect(dc,&rect);
+
+ switch (view->flag)
+ {
+ case RTGUI_LIST_VIEW_LIST:
+ rtgui_list_view_onlistdraw(view);
+ break;
+
+ case RTGUI_LIST_VIEW_ICON:
+ rtgui_list_view_onicondraw(view);
+ break;
+ }
+
+ rtgui_dc_end_drawing(dc);
+}
+
+static rt_bool_t rtgui_list_view_onmouse(rtgui_list_view_t* view, rtgui_event_mouse_t* emouse)
+{
+ rtgui_rect_t rect;
+
+ /* calculate selected item */
+
+ /* get physical extent information */
+ rtgui_widget_get_rect(view, &rect);
+
+ if(rtgui_rect_contains_point(&rect, emouse->x, emouse->y) == RT_EOK)
+ {
+ rt_uint16_t index;
+ rt_uint16_t old_item;
+
+ /* get old item */
+ old_item = view->item_current;
+
+ switch (view->flag)
+ {
+ case RTGUI_LIST_VIEW_LIST:
+ index = (emouse->y - rect.y1) / (2 + SELECTED_HEIGHT);
+
+ if((index < view->item_count) && (index < view->page))
+ {
+ /* set selected item */
+ view->item_current = (view->item_current/view->page) * view->page + index;
+ if(emouse->button & RTGUI_MOUSE_BUTTON_DOWN)
+ {
+ /* down event */
+ rtgui_list_view_update_list(view, old_item);
+ }
+ else
+ {
+ /* up event */
+ if(view->items[view->item_current].action != RT_NULL)
+ {
+ view->items[view->item_current].action(view->items[view->item_current].parameter);
+ }
+ }
+ }
+ break;
+
+ case RTGUI_LIST_VIEW_ICON:
+ {
+ rt_uint16_t x, y;
+ rt_uint16_t item_height, item_width;
+ rt_uint32_t current_page;
+
+ item_width = (rtgui_rect_width(rect) - 2 * RTGUI_WIDGET_DEFAULT_MARGIN)/view->col_items;
+ item_height = (rtgui_rect_height(rect) - 4)/view->row_items;
+ x = emouse->x - rect.x1;
+ y = emouse->y - rect.y1;
+
+ index = (y / item_height * view->col_items) + x / item_width;
+ current_page = view->item_current / view->page;
+
+ if((index + (current_page * view->page) < view->item_count))
+ {
+ if(emouse->button & RTGUI_MOUSE_BUTTON_DOWN)
+ {
+ view->item_current = index + (current_page * view->page);
+
+ /* down event */
+ rtgui_list_view_update_icon(view, old_item);
+ }
+ else
+ {
+ /* up event */
+ if(view->items[view->item_current].action != RT_NULL)
+ {
+ view->items[view->item_current].action(view->items[view->item_current].parameter);
+ }
+ }
+ }
+ }
+ break;
+
+ case RTGUI_LIST_VIEW_REPORT:
+ break;
+ }
+
+ return RT_TRUE;
+ }
+
+ return RT_FALSE;
+}
+
+rt_bool_t rtgui_list_view_event_handler(PVOID wdt, rtgui_event_t* event)
+{
+ rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ rtgui_list_view_t* view = RT_NULL;
+
+ view = RTGUI_LIST_VIEW(widget);
+ switch (event->type)
+ {
+ case RTGUI_EVENT_PAINT:
+ rtgui_list_view_ondraw(view);
+ return RT_FALSE;
+
+ case RTGUI_EVENT_RESIZE:
+ {
+ rtgui_event_resize_t* resize;
+
+ resize = (rtgui_event_resize_t*)event;
+
+ /* recalculate page items */
+ view->page = resize->h / (2 + SELECTED_HEIGHT);
+ }
+ break;
+
+ case RTGUI_EVENT_MOUSE_BUTTON:
+ {
+ rtgui_event_mouse_t* emouse;
+
+ emouse = (rtgui_event_mouse_t*)event;
+ return rtgui_list_view_onmouse(view, emouse);
+ }
+
+ case RTGUI_EVENT_KBD:
+ {
+ rtgui_event_kbd_t* ekbd = (rtgui_event_kbd_t*)event;
+ if(RTGUI_KBD_IS_DOWN(ekbd))
+ {
+ rt_uint16_t old_item;
+
+ old_item = view->item_current;
+ switch (ekbd->key)
+ {
+ case RTGUIK_LEFT:
+ if(view->flag == RTGUI_LIST_VIEW_LIST)
+ {
+ if(view->item_current - view->page >= 0)
+ view->item_current -= view->page;
+
+ rtgui_list_view_update_list(view, old_item);
+ }
+ else if(view->flag == RTGUI_LIST_VIEW_ICON)
+ {
+ if(view->item_current > 0)
+ view->item_current --;
+ rtgui_list_view_update_icon(view, old_item);
+ }
+ return RT_FALSE;
+
+ case RTGUIK_UP:
+ if(view->flag == RTGUI_LIST_VIEW_LIST)
+ {
+ if(view->item_current > 0)
+ view->item_current --;
+ rtgui_list_view_update_list(view, old_item);
+ }
+ else if(view->flag == RTGUI_LIST_VIEW_ICON)
+ {
+ if(view->item_current >= view->col_items)
+ view->item_current -= view->col_items;
+ else
+ view->item_current = 0;
+
+ rtgui_list_view_update_icon(view, old_item);
+ }
+ return RT_FALSE;
+
+ case RTGUIK_RIGHT:
+ if(view->flag == RTGUI_LIST_VIEW_LIST)
+ {
+ if(view->item_current + view->page < view->item_count - 1)
+ view->item_current += view->page;
+
+ rtgui_list_view_update_list(view, old_item);
+ }
+ else if(view->flag == RTGUI_LIST_VIEW_ICON)
+ {
+ if(view->item_current < view->item_count - 1)
+ view->item_current ++;
+
+ rtgui_list_view_update_icon(view, old_item);
+ }
+ return RT_FALSE;
+
+ case RTGUIK_DOWN:
+ if(view->flag == RTGUI_LIST_VIEW_LIST)
+ {
+ if(view->item_current < view->item_count - 1)
+ view->item_current ++;
+
+ rtgui_list_view_update_list(view, old_item);
+ }
+ else if(view->flag == RTGUI_LIST_VIEW_ICON)
+ {
+ if(view->item_current + view->col_items <= (view->item_count - 1))
+ view->item_current += view->col_items;
+ else
+ view->item_current = view->item_count - 1;
+
+ rtgui_list_view_update_icon(view, old_item);
+ }
+ return RT_FALSE;
+
+ case RTGUIK_RETURN:
+ if(view->items[view->item_current].action != RT_NULL)
+ {
+ view->items[view->item_current].action(view->items[view->item_current].parameter);
+ }
+ return RT_FALSE;
+
+ default:
+ break;
+ }
+ }
+ }
+ return RT_FALSE;
+
+ default:
+ break;
+ }
+
+ /* use view event handler */
+ return rtgui_view_event_handler(widget, event);
+}
+
+static void rtgui_list_view_calc(rtgui_list_view_t* view)
+{
+ /* get image of first item*/
+ rtgui_image_t *image;
+ rtgui_rect_t rect;
+ rt_uint32_t text_width, text_height;
+ rt_uint32_t item_width, item_height;
+
+ if(view->item_count == 0) return;
+
+ image = view->items[0].image;
+ rtgui_font_get_string_rect(RTGUI_WIDGET_FONT(view), "HHHHHH", &rect);
+
+ text_height = rtgui_rect_height(rect);
+ text_width = rtgui_rect_width(rect);
+
+ rtgui_widget_get_rect(view, &rect);
+
+ item_width = image->w + RTGUI_WIDGET_DEFAULT_MARGIN;
+ if(item_width < (text_width + RTGUI_WIDGET_DEFAULT_MARGIN)) item_width = text_width + RTGUI_WIDGET_DEFAULT_MARGIN;
+ item_height = image->h + 3 + text_height + RTGUI_WIDGET_DEFAULT_MARGIN;
+
+ view->row_items = (rtgui_rect_height(rect) - 2 * RTGUI_WIDGET_DEFAULT_MARGIN) / item_height;
+ view->col_items = (rtgui_rect_width(rect) - 2 * RTGUI_WIDGET_DEFAULT_MARGIN) / item_width;
+ view->page = view->row_items * view->col_items;
+}
+
+rtgui_list_view_t* rtgui_list_view_create(PVOID parent,const rtgui_list_view_item_t* items, rt_uint16_t count, int left,int top,int w,int h, rt_uint16_t flag)
+{
+ rtgui_list_view_t* view = RT_NULL;
+
+ RT_ASSERT(parent != RT_NULL);
+
+ view = rtgui_widget_create(RTGUI_LIST_VIEW_TYPE);
+ if(view != RT_NULL)
+ {
+ rtgui_rect_t rect;
+ view->items = items;
+ view->item_count = count;
+
+ view->flag = flag;
+ rtgui_widget_get_rect(view, &rect);
+ rtgui_widget_rect_to_device(parent,&rect);
+ rect.x1 += left;
+ rect.y1 += top;
+ rect.x2 = rect.x1+w;
+ rect.y2 = rect.y1+h;
+ rtgui_widget_set_rect(view, &rect);
+
+ if(flag == RTGUI_LIST_VIEW_LIST)
+ view->page = rtgui_rect_height(rect) / (2 + SELECTED_HEIGHT);
+ else if((flag == RTGUI_LIST_VIEW_ICON) && (count > 0))
+ {
+ rtgui_list_view_calc(view);
+ }
+ rtgui_container_add_child(parent, view);
+ }
+
+ return view;
+}
+
+void rtgui_list_view_destroy(rtgui_list_view_t* view)
+{
+ /* destroy view */
+ rtgui_widget_destroy(view);
+}
diff --git a/components/rtgui_win/widgets/listbox.c b/components/rtgui_win/widgets/listbox.c new file mode 100644 index 0000000000..086a140ca4 --- /dev/null +++ b/components/rtgui_win/widgets/listbox.c @@ -0,0 +1,728 @@ +/*
+ * File : listbox.c
+ * This file is part of RTGUI in RT-Thread RTOS
+ * COPYRIGHT (C) 2010, RT-Thread Development Team
+ *
+ * The license and distribution terms for this file may be
+ * found in the file LICENSE in this distribution or at
+ * http://www.rt-thread.org/license/LICENSE
+ *
+ * Change Logs:
+ * Date Author Notes
+ * 2010-01-06 Bernard first version
+ */
+
+#include <rtgui/rtgui_theme.h>
+#include <rtgui/widgets/listbox.h>
+
+#define RTGUI_WIDGET_DEFAULT_MARGIN 3
+
+static rt_bool_t rtgui_listbox_unfocus(PVOID wdt, rtgui_event_t* event);
+static rt_bool_t rtgui_listbox_sbar_handle(PVOID wdt, rtgui_event_t* event);
+static rt_uint32_t rtgui_listbox_get_item_count(rtgui_listbox_t* box);
+static void rtgui_listbox_add_item(rtgui_listbox_t* box,rtgui_listbox_item_t* item);
+
+static void _rtgui_listbox_constructor(rtgui_listbox_t *box)
+{
+ /* set default widget rect and set event handler */
+ rtgui_widget_set_event_handler(box,rtgui_listbox_event_handler);
+ rtgui_widget_set_onunfocus(box, rtgui_listbox_unfocus);
+ RTGUI_WIDGET_FLAG(box) |= RTGUI_WIDGET_FLAG_FOCUSABLE;
+ box->frist_aloc = 0;
+ box->now_aloc = 0;
+ box->old_aloc = 0;
+ box->item_count = 0;
+ box->item_size = SELECTED_HEIGHT;
+ box->item_per_page = 0;
+ box->ispopup = RT_FALSE;
+ box->widgetlnk = RT_NULL;
+
+ RTGUI_WIDGET_BACKGROUND(box) = white;
+ RTGUI_WIDGET_TEXTALIGN(box) = RTGUI_ALIGN_LEFT|RTGUI_ALIGN_CENTER_VERTICAL;
+
+ box->items = RT_NULL;
+ box->sbar = RT_NULL;
+
+ box->on_item = RT_NULL;
+
+ box->get_count = rtgui_listbox_get_item_count;
+ box->add_item = rtgui_listbox_add_item;
+}
+static void _rtgui_listbox_destructor(rtgui_listbox_t *box)
+{
+
+}
+
+rtgui_type_t *rtgui_listbox_type_get(void)
+{
+ static rtgui_type_t *listbox_type = RT_NULL;
+
+ if(!listbox_type)
+ {
+ listbox_type = rtgui_type_create("listbox", RTGUI_CONTAINER_TYPE,
+ sizeof(rtgui_listbox_t),
+ RTGUI_CONSTRUCTOR(_rtgui_listbox_constructor),
+ RTGUI_DESTRUCTOR(_rtgui_listbox_destructor));
+ }
+
+ return listbox_type;
+}
+
+rtgui_listbox_t* rtgui_listbox_create(PVOID parent, int left,int top,int w,int h,rt_uint32_t style)
+{
+ rtgui_listbox_t* box = RT_NULL;
+
+ RT_ASSERT(parent != RT_NULL);
+
+ box = rtgui_widget_create(RTGUI_LISTBOX_TYPE);
+ if(box != RT_NULL)
+ {
+ rtgui_rect_t rect;
+ rtgui_widget_get_rect(parent,&rect);
+ rtgui_widget_rect_to_device(parent, &rect);
+ rect.x1 += left;
+ rect.y1 += top;
+ rect.x2 = rect.x1+w;
+ rect.y2 = rect.y1+h;
+ rtgui_widget_set_rect(box,&rect);
+ rtgui_container_add_child(parent, box);
+
+ rtgui_widget_set_style(box,style);
+
+ if(box->sbar == RT_NULL)
+ {//��������ؼ�
+ rt_uint32_t sLeft,sTop,sWidth=RTGUI_DEFAULT_SB_WIDTH,sLen;
+ sLeft = rtgui_rect_width(rect)-RTGUI_WIDGET_BORDER(box)-sWidth;
+ sTop = RTGUI_WIDGET_BORDER(box);
+ sLen = rtgui_rect_height(rect)-RTGUI_WIDGET_BORDER(box)*2;
+
+ box->sbar = rtgui_scrollbar_create(box,sLeft,sTop,sWidth,sLen,RTGUI_VERTICAL);
+
+ if(box->sbar != RT_NULL)
+ {
+ box->sbar->widgetlnk = (PVOID)box;
+ box->sbar->on_scroll = rtgui_listbox_sbar_handle;
+ RTGUI_WIDGET_HIDE(box->sbar);//Ĭ�����ع�����
+ }
+ }
+ }
+
+ return box;
+}
+
+void rtgui_listbox_set_items(rtgui_listbox_t* box, rtgui_listbox_item_t* items, rt_uint32_t count)
+{
+ rtgui_rect_t rect;
+ rt_uint32_t i,h;;
+
+ RT_ASSERT(box != RT_NULL);
+
+ if(box->items != RT_NULL)
+ {
+ rt_free(box->items);
+ box->items = RT_NULL;
+ }
+ //֧������/ɾ����Ŀ,��̬�ռ�
+ box->items = (rtgui_listbox_item_t*) rt_malloc(sizeof(rtgui_listbox_item_t)*count);
+ if(box->items == RT_NULL) return;
+
+ for(i=0;i<count;i++)
+ {
+ box->items[i].name = rt_strdup(items[i].name);
+ box->items[i].image = items[i].image;
+ }
+
+ box->item_count = count;
+ box->now_aloc = 0;
+ box->old_aloc = 0;
+
+ rtgui_widget_get_rect(box, &rect);
+
+ box->item_per_page = rtgui_rect_height(rect) / (box->item_size+2);
+
+ if(box->ispopup)//����ʽ�����б�,������combo�ؼ�֮��
+ {
+ if(box->item_count < 5)
+ box->item_per_page = count;
+ else
+ box->item_per_page = 5;
+
+ h = 2+(box->item_size+2)*box->item_per_page;
+ rect.y2 = rect.y1+h;
+ rtgui_widget_rect_to_device(box,&rect);
+ rtgui_widget_set_rect(box,&rect);//����box�Ĵ�С
+
+ if(box->sbar != RT_NULL) //����sbar��extent
+ {
+ rtgui_widget_get_rect(box->sbar,&rect);
+ rect.y2 = rect.y1+h-RTGUI_WIDGET_BORDER(box)*2;
+ rtgui_widget_rect_to_device(box->sbar,&rect);
+ rtgui_widget_set_rect(box->sbar,&rect);
+ }
+ }
+
+ if(box->sbar != RT_NULL)//����sbar�IJ���
+ {
+ if(box->item_count > box->item_per_page)
+ {
+ RTGUI_WIDGET_UNHIDE(box->sbar);
+ rtgui_scrollbar_set_line_step(box->sbar, 1);
+ rtgui_scrollbar_set_page_step(box->sbar, box->item_per_page);
+ rtgui_scrollbar_set_range(box->sbar, box->item_count);
+ }
+ else
+ {
+ RTGUI_WIDGET_HIDE(box->sbar);
+ }
+ rtgui_widget_update_clip(box);
+ }
+
+}
+
+void rtgui_listbox_destroy(rtgui_listbox_t* box)
+{
+ /* destroy box */
+ rtgui_widget_destroy(box);
+}
+
+//����ListBox����,����������
+void rtgui_listbox_ondraw(rtgui_listbox_t* box)
+{
+ rtgui_rect_t rect, item_rect, image_rect;
+ rt_uint16_t frist, i;
+ const rtgui_listbox_item_t* item;
+ rtgui_dc_t* dc;
+
+ RT_ASSERT(box != RT_NULL);
+
+ /* begin drawing */
+ dc = rtgui_dc_begin_drawing(box);
+ if(dc == RT_NULL)return;
+
+ rtgui_widget_get_rect(box, &rect);
+
+ //���Ʊ߿�
+ rtgui_dc_draw_border(dc, &rect,RTGUI_WIDGET_BORDER_STYLE(box));
+ rtgui_rect_inflate(&rect,-RTGUI_WIDGET_BORDER(box));
+ RTGUI_DC_BC(dc) = white;
+ rtgui_dc_fill_rect(dc, &rect);
+ rtgui_rect_inflate(&rect,RTGUI_WIDGET_BORDER(box));
+
+ if(box->items==RT_NULL)return;//û����Ŀ,���ٻ�������
+
+ if(box->sbar && !RTGUI_WIDGET_IS_HIDE(box->sbar))
+ {
+ rect.x2 -= rtgui_rect_width(box->sbar->parent.extent);
+ }
+
+ /* get item base rect */
+ item_rect = rect;
+ item_rect.x1 += RTGUI_WIDGET_BORDER(box);
+ item_rect.x2 -= RTGUI_WIDGET_BORDER(box);
+ item_rect.y1 += RTGUI_WIDGET_BORDER(box);
+ item_rect.y2 = item_rect.y1 + (2+box->item_size);
+
+ /* get frist aloc */
+ frist = box->frist_aloc;
+ for(i = 0; i < box->item_per_page; i ++)
+ {
+ if(frist + i >= box->item_count) break;
+
+ item = &(box->items[frist + i]);
+
+ if(frist + i == box->now_aloc)
+ {//draw current item
+ if(RTGUI_WIDGET_IS_FOCUSED(box))
+ {
+ RTGUI_DC_BC(dc) = selected_color;
+ RTGUI_DC_FC(dc) = white;
+ rtgui_dc_fill_rect(dc, &item_rect);
+ rtgui_dc_draw_focus_rect(dc, &item_rect); //���ƽ����
+ }
+ else
+ {
+ RTGUI_DC_BC(dc) = dark_grey;
+ RTGUI_DC_FC(dc) = black;
+ rtgui_dc_fill_rect(dc, &item_rect);
+ }
+ }
+ item_rect.x1 += RTGUI_WIDGET_DEFAULT_MARGIN;
+
+ if(item->image != RT_NULL)
+ {
+ /* get image base rect */
+ image_rect.x1 = 0;
+ image_rect.y1 = 0;
+ image_rect.x2 = item->image->w;
+ image_rect.y2 = item->image->h;
+ rtgui_rect_moveto_align(&item_rect, &image_rect, RTGUI_ALIGN_CENTER_VERTICAL);
+ rtgui_image_paste(item->image, dc, &image_rect, white);
+ item_rect.x1 += item->image->w + 2;
+ }
+ /* draw text */
+ if(frist + i == box->now_aloc && RTGUI_WIDGET_IS_FOCUSED(box))
+ {
+ RTGUI_DC_FC(dc) = white;
+ rtgui_dc_draw_text(dc, item->name, &item_rect);
+ }
+ else
+ {
+ RTGUI_DC_FC(dc) = black;
+ rtgui_dc_draw_text(dc, item->name, &item_rect);
+ }
+
+ if(item->image != RT_NULL)
+ item_rect.x1 -= (item->image->w + 2);
+ item_rect.x1 -= RTGUI_WIDGET_DEFAULT_MARGIN;
+
+ /* move to next item position */
+ item_rect.y1 += (box->item_size + 2);
+ item_rect.y2 += (box->item_size + 2);
+ }
+
+ if(box->sbar && !RTGUI_WIDGET_IS_HIDE(box->sbar))
+ {
+ rtgui_theme_draw_scrollbar(box->sbar);
+ }
+
+ rtgui_dc_end_drawing(dc);
+}
+
+//����ListBox����,ֻ�����¾ɽ�����
+void rtgui_listbox_update(rtgui_listbox_t* box)
+{
+ const rtgui_listbox_item_t* item;
+ rtgui_rect_t rect, item_rect, image_rect;
+ rtgui_dc_t* dc;
+
+ RT_ASSERT(box != RT_NULL);
+
+ if(RTGUI_WIDGET_IS_HIDE(box))return;
+ if(box->items==RT_NULL)return;
+
+ /* begin drawing */
+ dc = rtgui_dc_begin_drawing(box);
+ if(dc == RT_NULL)return;
+
+ rtgui_widget_get_rect(box, &rect);
+ if(box->sbar && !RTGUI_WIDGET_IS_HIDE(box->sbar))
+ {
+ rect.x2 -= rtgui_rect_width(box->sbar->parent.extent);
+ }
+
+ if((box->old_aloc >= box->frist_aloc) && /* ��֮��ijҳ�� */
+ (box->old_aloc < box->frist_aloc+box->item_per_page) && /* ��֮ǰijҳ�� */
+ (box->old_aloc != box->now_aloc)) /* λ��û�б仯,����Ҫˢ���� */
+ {//��Щ����,��������ȵļ��ٻ�ͼ��˸����
+ item_rect = rect;
+ /* get old item's rect */
+ item_rect.x1 += RTGUI_WIDGET_BORDER(box);
+ item_rect.x2 -= RTGUI_WIDGET_BORDER(box);
+ item_rect.y1 += RTGUI_WIDGET_BORDER(box);
+ item_rect.y1 += ((box->old_aloc-box->frist_aloc) % box->item_per_page) * (2 + box->item_size);
+ item_rect.y2 = item_rect.y1 + (2+box->item_size);
+
+ /* draw old item */
+ RTGUI_DC_BC(dc) = white;
+ RTGUI_DC_FC(dc) = black;
+ rtgui_dc_fill_rect(dc,&item_rect);
+
+ item_rect.x1 += RTGUI_WIDGET_DEFAULT_MARGIN;
+
+ item = &(box->items[box->old_aloc]);
+ if(item->image != RT_NULL)
+ {
+ image_rect.x1 = 0;
+ image_rect.y1 = 0;
+ image_rect.x2 = item->image->w;
+ image_rect.y2 = item->image->h;
+ rtgui_rect_moveto_align(&item_rect, &image_rect, RTGUI_ALIGN_CENTER_VERTICAL);
+ rtgui_image_paste(item->image, dc, &image_rect, white);
+ item_rect.x1 += item->image->w + 2;
+ }
+ rtgui_dc_draw_text(dc, item->name, &item_rect);
+ }
+
+ /* draw now item */
+ item_rect = rect;
+ /* get now item's rect */
+ item_rect.x1 += RTGUI_WIDGET_BORDER(box);
+ item_rect.x2 -= RTGUI_WIDGET_BORDER(box);
+ item_rect.y1 += RTGUI_WIDGET_BORDER(box);
+ item_rect.y1 += ((box->now_aloc-box->frist_aloc) % box->item_per_page) * (2 + box->item_size);
+ item_rect.y2 = item_rect.y1 + (2 + box->item_size);
+
+ /* draw current item */
+ if(RTGUI_WIDGET_IS_FOCUSED(box))
+ {
+ RTGUI_DC_BC(dc) = selected_color;
+ RTGUI_DC_FC(dc) = white;
+ rtgui_dc_fill_rect(dc, &item_rect);
+ rtgui_dc_draw_focus_rect(dc, &item_rect); //���ƽ����
+ }
+ else
+ {
+ RTGUI_DC_BC(dc) = dark_grey;
+ RTGUI_DC_FC(dc) = black;
+ rtgui_dc_fill_rect(dc, &item_rect);
+ }
+
+ item_rect.x1 += RTGUI_WIDGET_DEFAULT_MARGIN;
+
+ item = &(box->items[box->now_aloc]);
+ if(item->image != RT_NULL)
+ {
+ image_rect.x1 = 0;
+ image_rect.y1 = 0;
+ image_rect.x2 = item->image->w;
+ image_rect.y2 = item->image->h;
+ rtgui_rect_moveto_align(&item_rect, &image_rect, RTGUI_ALIGN_CENTER_VERTICAL);
+ rtgui_image_paste(item->image, dc, &image_rect, white);
+ item_rect.x1 += (item->image->w + 2);
+ }
+ if(RTGUI_WIDGET_IS_FOCUSED(box))
+ {
+ RTGUI_DC_FC(dc) = white;
+ rtgui_dc_draw_text(dc, item->name, &item_rect);
+ }
+ else
+ {
+ RTGUI_DC_FC(dc) = black;
+ rtgui_dc_draw_text(dc, item->name, &item_rect);
+ }
+ box->old_aloc = box->now_aloc;
+
+ rtgui_dc_end_drawing(dc);
+}
+
+rt_bool_t rtgui_listbox_event_handler(PVOID wdt, rtgui_event_t* event)
+{
+ rtgui_listbox_t* box = (rtgui_listbox_t*)wdt;
+
+ RT_ASSERT(box != RT_NULL);
+
+ switch (event->type)
+ {
+ case RTGUI_EVENT_PAINT:
+ {
+ rtgui_dc_t *dc;
+
+ dc = rtgui_dc_begin_drawing(box);
+ if(dc == RT_NULL)return RT_FALSE;
+
+ if(!RTGUI_WIDGET_IS_FOCUSED(box))
+ {
+ rtgui_rect_t rect;
+ rtgui_widget_get_rect(box, &rect);
+ rtgui_dc_fill_rect(dc,&rect);
+ }
+
+ rtgui_dc_end_drawing(dc);
+
+ rtgui_listbox_ondraw(box);
+ return RT_FALSE;
+ }
+ case RTGUI_EVENT_RESIZE:
+ {
+ rtgui_event_resize_t* resize;
+
+ resize = (rtgui_event_resize_t*)event;
+
+ /* recalculate page items */
+ box->item_per_page = resize->h / (2 + box->item_size);
+ }
+ break;
+
+ case RTGUI_EVENT_MOUSE_BUTTON:
+ {
+ rtgui_rect_t rect;
+ rtgui_event_mouse_t* emouse;
+
+ emouse = (rtgui_event_mouse_t*)event;
+
+ /* get physical extent information */
+ rtgui_widget_get_rect(box, &rect);
+ if(box->sbar && !RTGUI_WIDGET_IS_HIDE(box->sbar))
+ rect.x2 -= rtgui_rect_width(box->sbar->parent.extent);
+
+ if((rtgui_region_contains_point(&RTGUI_WIDGET_CLIP(box), emouse->x, emouse->y,&rect) == RT_EOK) && (box->item_count > 0))
+ {
+ rt_uint16_t i;
+ i = (emouse->y - rect.y1) / (2 + box->item_size);
+
+ /* set focus */
+ rtgui_widget_focus(box);
+
+ if((i < box->item_count) && (i < box->item_per_page))
+ {
+ if(emouse->button & RTGUI_MOUSE_BUTTON_DOWN)
+ {
+ box->old_aloc = box->now_aloc;
+ /* set selected item */
+ box->now_aloc = box->frist_aloc + i;
+
+ if(box->on_item != RT_NULL)
+ {
+ box->on_item(box, RT_NULL);
+ }
+
+ /* down event */
+ rtgui_listbox_update(box);
+ }
+ else if(emouse->button & RTGUI_MOUSE_BUTTON_UP)
+ {
+ rtgui_listbox_update(box);
+
+ if(box->ispopup && !RTGUI_WIDGET_IS_HIDE(box))
+ {
+ RTGUI_WIDGET_HIDE(box);
+ box->frist_aloc=0;
+ box->now_aloc = 0;
+
+ rtgui_widget_update_clip(RTGUI_WIDGET_PARENT(box));
+ rtgui_widget_update(RTGUI_WIDGET_PARENT(box));
+ return RT_TRUE;
+ }
+ }
+ if(box->sbar && !RTGUI_WIDGET_IS_HIDE(box))
+ {
+ if(!RTGUI_WIDGET_IS_HIDE(box->sbar))
+ rtgui_scrollbar_set_value(box->sbar,box->frist_aloc);
+ }
+ }
+ }
+
+ }
+ break;
+
+ case RTGUI_EVENT_KBD:
+ {
+ rtgui_event_kbd_t* ekbd = (rtgui_event_kbd_t*)event;
+ if((RTGUI_KBD_IS_DOWN(ekbd)) && (box->item_count > 0))
+ {
+ switch (ekbd->key)
+ {
+ case RTGUIK_UP:
+ if(box->now_aloc > 0)
+ {
+ box->old_aloc = box->now_aloc;
+ box->now_aloc --;
+ if(box->now_aloc < box->frist_aloc)
+ {
+ if(box->frist_aloc)box->frist_aloc--;
+ rtgui_listbox_ondraw(box);
+ }
+ else
+ {
+ rtgui_listbox_update(box);
+ }
+
+ if(box->sbar && !RTGUI_WIDGET_IS_HIDE(box))
+ {
+ if(!RTGUI_WIDGET_IS_HIDE(box->sbar))
+ rtgui_scrollbar_set_value(box->sbar,box->frist_aloc);
+ }
+
+ if(box->on_item != RT_NULL)
+ {
+ box->on_item(box, RT_NULL);
+ }
+ }
+ break;
+
+ case RTGUIK_DOWN:
+ if(box->now_aloc < box->item_count - 1)
+ {
+ box->old_aloc = box->now_aloc;
+ box->now_aloc ++;
+ if(box->now_aloc >= box->frist_aloc+box->item_per_page)
+ {
+ box->frist_aloc++;
+ rtgui_listbox_ondraw(box);
+ }
+ else
+ {
+ rtgui_listbox_update(box);
+ }
+ if(box->sbar && !RTGUI_WIDGET_IS_HIDE(box))
+ {
+ if(!RTGUI_WIDGET_IS_HIDE(box->sbar))
+ rtgui_scrollbar_set_value(box->sbar,box->frist_aloc);
+ }
+
+ if(box->on_item != RT_NULL)
+ {
+ box->on_item(box, RT_NULL);
+ }
+ }
+ break;
+
+ case RTGUIK_RETURN:
+ if(box->on_item != RT_NULL)
+ {
+ box->on_item(box, RT_NULL);
+ }
+
+ if(box->ispopup && !RTGUI_WIDGET_IS_HIDE(box))
+ {
+ RTGUI_WIDGET_HIDE(box);
+ box->frist_aloc=0;
+ box->now_aloc = 0;
+ rtgui_widget_update_clip(RTGUI_WIDGET_PARENT(box));
+ rtgui_widget_update(RTGUI_WIDGET_PARENT(box));
+ }
+ break;
+
+ default:
+ break;
+ }
+ }
+ return RT_FALSE;
+ }
+ default:
+ return rtgui_container_event_handler(box, event);
+ }
+
+ /* use box event handler */
+ return rtgui_container_event_handler(box, event);
+}
+
+void rtgui_listbox_set_onitem(rtgui_listbox_t* box, rtgui_event_handler_ptr func)
+{
+ if(box == RT_NULL) return;
+
+ box->on_item = func;
+}
+
+void rtgui_listbox_delete_item(rtgui_listbox_t* box, rt_uint32_t item_num)
+{
+ rtgui_listbox_item_t* _items;
+ rt_base_t i;
+
+ if(box == RT_NULL) return;
+
+ for(i=item_num;i<box->item_count-1;i++)
+ {
+ if(box->items[i].name != RT_NULL)
+ {
+ rt_free(box->items[i].name);
+ box->items[i].name = RT_NULL;
+ }
+ box->items[i].name = box->items[i+1].name;
+ box->items[i].image = box->items[i+1].image;
+ }
+
+ box->item_count -= 1;
+ _items = rt_realloc(box->items,sizeof(rtgui_listbox_item_t)*(box->item_count));
+ if(_items != RT_NULL)
+ {
+ box->items = _items;
+ }
+
+ rtgui_listbox_ondraw(box);
+}
+
+static void rtgui_listbox_add_item(rtgui_listbox_t* box,rtgui_listbox_item_t* item)
+{
+ rtgui_listbox_item_t* _items;
+ RT_ASSERT(box != RT_NULL);
+
+ if(box->item_count==0)
+ {
+ _items = rt_malloc(sizeof(rtgui_listbox_item_t)*(box->item_count+1));
+ }
+ else
+ {
+ _items = rt_realloc(box->items,sizeof(rtgui_listbox_item_t)*(box->item_count+1));
+ }
+
+ if(_items != RT_NULL)
+ {
+ box->items = _items;
+ box->items[box->item_count].name = rt_strdup(item->name);
+ box->items[box->item_count].image= item->image;
+ box->item_count += 1;
+
+ if(box->sbar != RT_NULL)
+ {
+ if(RTGUI_WIDGET_IS_HIDE(box->sbar))
+ {
+ if(box->item_count > box->item_per_page)
+ {
+ RTGUI_WIDGET_UNHIDE(box->sbar);
+ rtgui_scrollbar_set_line_step(box->sbar, 1);
+ rtgui_scrollbar_set_page_step(box->sbar, box->item_per_page);
+ rtgui_scrollbar_set_range(box->sbar, box->item_count);
+ }
+ else
+ {
+ RTGUI_WIDGET_HIDE(box->sbar);
+ }
+ rtgui_widget_update_clip(box);
+ }
+ else
+ {
+ rtgui_scrollbar_set_range(box->sbar, box->item_count);
+ }
+ }
+
+ if(!RTGUI_WIDGET_IS_HIDE(box))
+ rtgui_listbox_ondraw(box);
+ }
+}
+
+static rt_uint32_t rtgui_listbox_get_item_count(rtgui_listbox_t* box)
+{
+ return box->item_count;
+}
+
+static rt_bool_t rtgui_listbox_unfocus(PVOID wdt, rtgui_event_t* event)
+{
+ rtgui_listbox_t *box = (rtgui_listbox_t*)wdt;
+ if(box == RT_NULL)return RT_FALSE;
+
+ if(!RTGUI_WIDGET_IS_FOCUSED(box)) + {//�������� + rtgui_listbox_update(RTGUI_LISTBOX(wdt));
+ }
+
+ if(box->ispopup)
+ {//�ǵ����б�,˵���ǹ���һЩ�ؼ�(����combo)�µ�
+ rtgui_win_t *win;
+
+ RTGUI_WIDGET_HIDE(box);
+ box->frist_aloc=0;
+ box->now_aloc = 0;
+
+ //rtgui_widget_update_clip(RTGUI_WIDGET_PARENT(box));
+ //rtgui_widget_update_clip_pirate(RTGUI_WIDGET_PARENT(box),box);
+ win = rtgui_win_get_win_by_widget(box);
+ if(win != RT_NULL)
+ {//��һ��������
+ if(rtgui_rect_is_intersect(&(RTGUI_WIDGET_EXTENT(win)),
+ &(RTGUI_WIDGET_EXTENT(box))) == RT_EOK)
+ {
+ rtgui_topwin_move(win,RTGUI_WIDGET_EXTENT(win).x1,
+ RTGUI_WIDGET_EXTENT(win).y1);
+ }
+ rtgui_widget_focus(win);
+ rtgui_widget_update_clip(win);
+ }
+ rtgui_panel_redraw(&(RTGUI_WIDGET_EXTENT(box)));
+ }
+ + return RT_TRUE;
+}
+
+static rt_bool_t rtgui_listbox_sbar_handle(PVOID wdt, rtgui_event_t* event)
+{
+ rtgui_listbox_t *box = (rtgui_listbox_t*)wdt;
+
+ //�϶�ʱ���ı��һ��
+ box->frist_aloc = box->sbar->value;
+
+ rtgui_listbox_ondraw(box);
+
+ return RT_TRUE;
+}
+
diff --git a/components/rtgui_win/widgets/menu.c b/components/rtgui_win/widgets/menu.c new file mode 100644 index 0000000000..5dd5662557 --- /dev/null +++ b/components/rtgui_win/widgets/menu.c @@ -0,0 +1,476 @@ +/* + * File : menu.c + * This file is part of RT-Thread RTOS + * COPYRIGHT (C) 2006 - 2009, RT-Thread Development Team + * + * The license and distribution terms for this file may be + * found in the file LICENSE in this distribution or at + * http://www.rt-thread.org/license/LICENSE + * + * Change Logs: + * Date Author Notes + * 2010-07-16 amsl first version + */
+ +#include <rtgui/dc.h> +#include <rtgui/rtgui_system.h>
+#include <rtgui/rtgui_theme.h>
+#include <rtgui/widgets/menu.h>
+
+rt_bool_t rtgui_menu_event_handler(PVOID wdt, rtgui_event_t* event);
+//static rt_bool_t rtgui_menu_onfocus(PVOID wdt, rtgui_event_t* event);
+static rt_bool_t rtgui_menu_onunfocus(PVOID wdt, rtgui_event_t* event);
+ +static void _rtgui_menu_constructor(rtgui_menu_t *menu) +{ + /* init menu */ + rtgui_widget_set_event_handler(menu, rtgui_menu_event_handler);
+ rtgui_widget_set_onunfocus(menu, rtgui_menu_onunfocus); + menu->current_item = RT_NULL; //��ǰ�˵���
+ menu->forego_item = RT_NULL; + menu->name = RT_NULL;
+ RTGUI_WIDGET_FLAG(menu) |= RTGUI_WIDGET_FLAG_FOCUSABLE;
+
+ menu->head = RT_NULL;
+ menu->tail = RT_NULL;
+ menu->farther = RT_NULL;
+
+ //���û��Ʋ˵�ʱҪ�õ��IJ���
+ menu->orient = RTGUI_VERTICAL;
+ menu->item_count = 0;//�˵�������
+ menu->item_size = SELECTED_HEIGHT; +} + +static void _rtgui_menu_destructor(rtgui_menu_t *menu) +{ + if(menu->name != RT_NULL)
+ { + rt_free(menu->name); + menu->name = RT_NULL;
+ } +} + +rtgui_type_t *rtgui_menu_type_get(void) +{ + static rtgui_type_t *menu_type = RT_NULL; + + if(!menu_type) + { + menu_type = rtgui_type_create("menu", RTGUI_WIDGET_TYPE, + sizeof(rtgui_menu_t), + RTGUI_CONSTRUCTOR(_rtgui_menu_constructor), + RTGUI_DESTRUCTOR (_rtgui_menu_destructor )); + } + + return menu_type; +}
+ +void rtgui_menu_set_selected(rtgui_menu_t* menu, int selected)
+{
+ RT_ASSERT(menu != RT_NULL);
+
+ if(selected >= menu->item_count) return;
+
+ if(selected >= 0)
+ {
+ rtgui_menu_item_t* item=menu->head;
+ while(selected--)
+ {
+ item = item->next;
+ }
+ menu->forego_item = menu->current_item;
+ menu->current_item = item;
+ }
+
+ /* update rbox widget */
+ rtgui_theme_draw_menu_item(menu, menu->forego_item);
+ rtgui_theme_draw_menu_item(menu, menu->current_item);
+
+ if(menu->current_item->func_updown)
+ {
+ menu->current_item->func_updown(menu);
+ }
+}
+
+static void rtgui_menu_onmouse(rtgui_menu_t* menu, rtgui_event_mouse_t* event)
+{
+ RT_ASSERT(menu != RT_NULL);
+ RT_ASSERT(event != RT_NULL);
+
+ if(event->button & RTGUI_MOUSE_BUTTON_DOWN && event->button & RTGUI_MOUSE_BUTTON_LEFT)
+ {
+ rtgui_rect_t rect;
+
+ rtgui_widget_focus(menu);
+
+ rtgui_widget_get_rect(menu, &rect);
+ rtgui_widget_rect_to_device(menu, &rect);
+
+ rtgui_rect_inflate(&rect, -RTGUI_WIDGET_BORDER(menu));
+ if(rtgui_rect_contains_point(&rect, event->x, event->y) == RT_EOK)
+ {
+ if(menu->orient == RTGUI_VERTICAL)
+ {
+ int delta_y = event->y - rect.y1;
+ int sel = delta_y/(menu->item_size+1);
+
+ rtgui_menu_set_selected(menu, sel);
+
+ return;
+ }
+ }
+ }
+}
+ +rt_bool_t rtgui_menu_event_handler(PVOID wdt, rtgui_event_t* event) +{ + rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ rtgui_menu_t* menu = (rtgui_menu_t*)widget;
+
+ RT_ASSERT(widget != RT_NULL); + + switch (event->type) + { + case RTGUI_EVENT_PAINT: + if(widget->on_draw != RT_NULL)
+ widget->on_draw(widget, event); + else + { + rtgui_theme_draw_menu(menu); + } + break;
+
+ case RTGUI_EVENT_MOUSE_BUTTON:
+ if(widget->on_mouseclick != RT_NULL)
+ widget->on_mouseclick(widget, event);
+ else
+ {
+ rtgui_menu_onmouse(menu, (rtgui_event_mouse_t*)event);
+ }
+ break;
+ case RTGUI_EVENT_KBD:
+ {
+ rtgui_event_kbd_t* ekbd = (rtgui_event_kbd_t*)event;
+
+ if(RTGUI_KBD_IS_DOWN(ekbd))
+ {
+ rt_uint16_t key = ekbd->key;
+
+ switch(key)
+ {
+ case RTGUIK_UP:
+ //������һ���˵�
+ rtgui_menu_on_up(menu);
+ break;
+
+ case RTGUIK_DOWN:
+ //������һ���˵�
+ rtgui_menu_on_down(menu);
+ break;
+
+ case RTGUIK_LEFT:
+ //������һ���˵�
+ break;
+
+ case RTGUIK_RIGHT:
+ //�����Ӳ˵�
+ break;
+
+ default:
+ break;
+ }
+ }
+ }
+ default:
+ break; + } + + return RT_FALSE; +}
+ +static rt_bool_t rtgui_menu_onunfocus(PVOID wdt, rtgui_event_t* event)
+{
+ rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ rtgui_menu_t* menu = (rtgui_menu_t*)widget;
+
+ rtgui_menu_on_exit(menu);
+ return RT_TRUE;
+}
+ +rtgui_menu_t* rtgui_menu_create(PVOID parent, const char* name) +{ + rtgui_menu_t* menu;
+ + RT_ASSERT(parent != RT_NULL);
+ + /* allocate view */ + menu = rtgui_widget_create (RTGUI_MENU_TYPE); + if(menu != RT_NULL) + { + rtgui_rect_t rect; +
+ rtgui_widget_get_rect(parent, &rect);
+ rtgui_widget_rect_to_device(parent,&rect);
+ rect.x1 += 1;//������ø�ֵ
+ rect.y1 += 1;
+ rect.x2 = rect.x1+10;
+ rect.y2 = rect.y1+10; + rtgui_widget_set_rect(menu, &rect);
+
+ menu->name = rt_strdup(name);
+ RTGUI_WIDGET_BACKGROUND(menu) = white;
+ RTGUI_WIDGET_TEXTALIGN(menu) = RTGUI_ALIGN_CENTER_VERTICAL;
+
+ rtgui_container_add_child(parent, menu); + } + + return menu; +} + +void rtgui_menu_destroy(rtgui_menu_t* menu) +{ + rtgui_widget_destroy(menu); +}
+
+/*
+��һ��POPUP�˵�������������һ���˵���,ͬWindow����
+Input: menu -- Ҫ�ӵIJ˵�
+ flags -- RTGUI_MENU_POPUP:��ʾ�ӵ���ΪPOPUP�˵�,����:��ʾ��Ϊ��ͨ�˵���
+ ID -- ���flagsΪMENU_FLAG_POPUP ,������ʾΪPOPUP�˵���ָ��,���flagsΪ���� ,������ʾΪ�˵����ID
+ name -- �˵�����
+return : TRUE --�ɹ�
+*/
+rt_bool_t rtgui_menu_append(rtgui_menu_t *menu,rt_uint32_t flag,rt_uint32_t ID,char* caption)
+{
+ rtgui_menu_item_t *item,*node,*old;
+
+ if(menu == RT_NULL) return RT_FALSE;
+
+ item = rt_malloc(sizeof(rtgui_menu_item_t));
+ if(item == RT_NULL) return RT_FALSE;
+ rt_memset(item, 0, sizeof(rtgui_menu_item_t));
+
+ item->type = flag;
+
+ item->caption = rt_strdup(caption);
+
+ item->shortcut = 0; /*��ݼ�*/
+ item->bexit = RT_FALSE;//TRUE;
+ item->func_updown = RT_NULL;
+ item->func_enter = RT_NULL;
+
+ if(flag & RTGUI_MENU_POPUP)
+ {//popup�˵�
+ item->item_id = 0;
+ item->sub_menu = (rtgui_menu_t*)ID;
+
+ /*�����ϼ��˵�*/
+ item->sub_menu->farther = item;
+ }
+ else
+ {//��ͨ�˵�
+ item->item_id = ID;
+ item->sub_menu = 0;
+ }
+ item->next = RT_NULL;
+ menu->item_count++;
+
+ node = menu->head;
+ if(!node)
+ {
+ /*û�в˵����ǵ�һ��*/
+ menu->head = item;
+ menu->tail = item;
+ item->prev = RT_NULL;
+ return RT_TRUE;
+ }
+
+ while(node)
+ {
+ old = node;
+ node = node->next;/*��һ���˵��� */
+ }
+
+ /* ��������� */
+ old->next = item;
+ item->prev = old;
+
+ /*���¶���βָ�� */
+ menu->tail = item;
+
+ return RT_TRUE;
+}
+
+/*
+ * �ڲ˵���ɾ��һ���˵���,�����������һ���Ӳ˵�,�����Ӳ˵�ָ��
+ */
+rtgui_menu_t* rtgui_menu_item_delete(rtgui_menu_t* menu,rtgui_menu_item_t* item)
+{
+ rtgui_menu_t* ret;
+
+ if(item->prev == RT_NULL)
+ {
+ if(item->next == RT_NULL)
+ {
+ /*ֻ��һ�� */
+ menu->head = RT_NULL;
+ menu->tail = RT_NULL;
+ }
+ else
+ {
+ /*ɾ����һ�� */
+ item->next->prev = RT_NULL;
+ menu->head = item->next;
+ }
+ }
+ else
+ {
+ if( item->next == RT_NULL)
+ {
+ /*���һ�� */
+ item->prev->next = RT_NULL;
+ menu->tail = item->prev;
+ }
+ else
+ {
+ /* �� */
+ item->prev->next = item->next;
+ item->next->prev = item->prev;
+ }
+ }
+
+ if(item->type & RTGUI_MENU_POPUP)
+ ret = item->sub_menu; /* �����Ӳ˵� */
+ else
+ ret = RT_NULL;
+
+ rt_free(item->caption);
+ rt_free(item);
+
+ return ret;
+}
+
+/*
+�ж��Ƿ�һ���˵�Ϊ�ղ˵���û�в˵���)
+*/
+rt_bool_t rtgui_menu_is_null(rtgui_menu_t* hMenu)
+{
+ if(hMenu->head == RT_NULL)
+ return RT_TRUE;
+ return RT_FALSE;
+}
+
+/* ɾ��һ��Popup�˵� */
+void rtgui_menu_popup_delete(rtgui_menu_t* menu)
+{
+ rtgui_menu_item_t* pItem;
+ rtgui_menu_t* sub_menu;
+
+ if(rtgui_menu_is_null(menu))
+ {
+ /*�˵�Ϊ��,�ͷ�Popup�ռ�*/
+ rt_free(menu );
+ return;
+ }
+
+ pItem = menu->head;
+ while(pItem)
+ {
+ sub_menu = rtgui_menu_item_delete(menu,pItem);
+ if(sub_menu)
+ {
+ /*ʹ�õݹ��ͷ���һ���Ӳ˵� */
+ rtgui_menu_popup_delete(sub_menu);
+ }
+ /*ȡ��һ���� */
+ pItem = menu->head;
+ }
+ /*ȫ���˵����ͷ����,�ͷ�POPUPָ�� */
+
+ rt_free(menu);
+}
+
+/* �����ƶ�һ���˵�,����:��ǰ�˵���� */
+void rtgui_menu_on_down(rtgui_menu_t* menu)
+{
+ RT_ASSERT(menu != RT_NULL);
+
+ /* Popup�˵�û�в˵��� */
+ if(menu->current_item==RT_NULL)
+ {
+ return ; /* �˵��ݴ� */
+ }
+
+ menu->forego_item = menu->current_item;
+ /* ���һ���˵����� */
+ if(menu->current_item->next==RT_NULL)
+ {
+ /* ��,�ƶ�����ͷ��һ�� */
+ menu->current_item = menu->head;
+ }
+ else
+ {
+ /*�Ƶ���һ�� */
+ menu->current_item = menu->current_item->next;
+ }
+
+ rtgui_theme_draw_menu_item(menu, menu->forego_item);
+ rtgui_theme_draw_menu_item(menu, menu->current_item);
+
+ if(menu->current_item->func_updown)
+ {
+ menu->current_item->func_updown(menu);
+ }
+}
+
+/*
+�����ƶ�һ���˵�
+*/
+void rtgui_menu_on_up(rtgui_menu_t* menu)
+{
+ RT_ASSERT(menu != RT_NULL);
+
+ /*Popup�˵�û�в˵���,�˵���ƴ��� */
+ if(menu->current_item==RT_NULL)
+ {
+ return ; /*�˵��ݴ� */
+ }
+
+ menu->forego_item = menu->current_item;
+ /* ��һ���˵����� */
+ if(menu->current_item->prev==RT_NULL)
+ {
+ /* ��,�����ƶ�*/
+ menu->current_item = menu->tail;
+ }
+ else
+ {
+ /* �Ƶ���һ�� */
+ menu->current_item = menu->current_item->prev;
+ }
+
+ rtgui_theme_draw_menu_item(menu, menu->forego_item);
+ rtgui_theme_draw_menu_item(menu, menu->current_item);
+
+ if(menu->current_item->func_updown)
+ {
+ menu->current_item->func_updown(menu);
+ }
+}
+
+/*�����˵�
+*/
+void rtgui_menu_on_exit(rtgui_menu_t* menu)
+{
+ rtgui_widget_unfocus(menu);
+ rtgui_theme_draw_menu(menu);
+
+ if(menu->current_item->bexit)
+ {
+ menu->current_item = RT_NULL;
+ menu->forego_item = RT_NULL;
+ }
+}
+
+
+
diff --git a/components/rtgui_win/widgets/progressbar.c b/components/rtgui_win/widgets/progressbar.c new file mode 100644 index 0000000000..0de2595c53 --- /dev/null +++ b/components/rtgui_win/widgets/progressbar.c @@ -0,0 +1,128 @@ +#include <rtgui/dc.h>
+#include <rtgui/rtgui_theme.h>
+#include <rtgui/widgets/progressbar.h>
+
+#define RTGUI_PROGRESSBAR_DEFAULT_RANGE 100
+
+static void _rtgui_progressbar_constructor(rtgui_progressbar_t *bar)
+{
+ rtgui_rect_t rect = {0, 0, DEFAULT_WIDTH, DEFAULT_HEIGHT};
+
+ rtgui_widget_set_event_handler(bar, rtgui_progressbar_event_handler);
+ rtgui_widget_set_rect(bar, &rect);
+
+ bar->orient = RTGUI_HORIZONTAL;
+ bar->range = RTGUI_PROGRESSBAR_DEFAULT_RANGE;
+ bar->position = 0;
+
+ /* set gc */
+ RTGUI_WIDGET_TEXTALIGN(bar) = RTGUI_ALIGN_CENTER_HORIZONTAL|RTGUI_ALIGN_CENTER_VERTICAL;
+}
+
+static void _rtgui_progressbar_destructor(rtgui_progressbar_t *bar)
+{
+
+}
+
+rtgui_type_t *rtgui_progressbar_type_get(void)
+{
+ static rtgui_type_t *progressbar_type = RT_NULL;
+
+ if(!progressbar_type)
+ {
+ progressbar_type = rtgui_type_create("progressbar", RTGUI_WIDGET_TYPE,
+ sizeof(rtgui_progressbar_t),
+ RTGUI_CONSTRUCTOR(_rtgui_progressbar_constructor),
+ RTGUI_DESTRUCTOR(_rtgui_progressbar_destructor));
+ }
+
+ return progressbar_type;
+}
+
+rt_bool_t rtgui_progressbar_event_handler(PVOID wdt, rtgui_event_t* event)
+{
+ rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ rtgui_progressbar_t* bar = (rtgui_progressbar_t*)widget;
+
+ switch (event->type)
+ {
+ case RTGUI_EVENT_PAINT:
+ if(widget->on_draw != RT_NULL)
+ widget->on_draw(widget, event);
+ else
+ {
+ rtgui_theme_draw_progressbar(bar);
+ }
+
+ break;
+ }
+
+ return RT_FALSE;
+}
+
+rtgui_progressbar_t* rtgui_progressbar_create(PVOID parent, int orient, int range, int left, int top, int w, int h)
+{
+ rtgui_progressbar_t* bar;
+
+ RT_ASSERT(parent != RT_NULL);
+
+ bar = rtgui_widget_create (RTGUI_PROGRESSBAR_TYPE);
+ if(bar != RT_NULL)
+ {
+ rtgui_rect_t rect;
+ rtgui_widget_get_rect(bar, &rect);
+ rtgui_widget_rect_to_device(parent,&rect);
+ rect.x1 += left;
+ rect.y1 += top;
+ rect.x2 = rect.x1+w;
+ rect.y2 = rect.y1+h;
+ rtgui_widget_set_rect(bar, &rect);
+
+ bar->orient = orient;
+ bar->range = range;
+
+ rtgui_container_add_child(parent, bar);
+ }
+
+ return bar;
+}
+
+void rtgui_progressbar_destroy(rtgui_progressbar_t* bar)
+{
+ rtgui_widget_destroy(bar);
+}
+
+void rtgui_progressbar_set_value(rtgui_progressbar_t *bar, int value)
+{
+ RT_ASSERT(bar != RT_NULL);
+
+ bar->position = value;
+
+ rtgui_theme_draw_progressbar(bar);
+ return;
+}
+
+int rtgui_progressbar_get_value(rtgui_progressbar_t *bar)
+{
+ RT_ASSERT(bar != RT_NULL);
+
+ return bar->position;
+}
+
+void rtgui_progressbar_set_range(rtgui_progressbar_t *bar, int range)
+{
+ RT_ASSERT(bar != RT_NULL);
+
+ bar->range = range;
+
+ rtgui_theme_draw_progressbar(bar);
+ return;
+}
+
+int rtgui_progressbar_get_range(rtgui_progressbar_t *bar)
+{
+ RT_ASSERT(bar != RT_NULL);
+
+ return bar->range;
+}
+
diff --git a/components/rtgui_win/widgets/radiobox.c b/components/rtgui_win/widgets/radiobox.c new file mode 100644 index 0000000000..8f71b04faa --- /dev/null +++ b/components/rtgui_win/widgets/radiobox.c @@ -0,0 +1,206 @@ +#include <rtgui/dc.h>
+#include <rtgui/rtgui_theme.h>
+#include <rtgui/widgets/radiobox.h>
+
+#define RTGUI_RADIOBOX_DEFAULT_WIDTH 100
+#define RTGUI_RADIOBOX_DEFAULT_HEIGHT 20
+
+static void _rtgui_radiobox_constructor(rtgui_radiobox_t *rbox)
+{
+ rtgui_rect_t rect = {0, 0, RTGUI_RADIOBOX_DEFAULT_WIDTH, RTGUI_RADIOBOX_DEFAULT_HEIGHT};
+
+ /* init widget and set event handler */
+ RTGUI_WIDGET_FLAG(rbox) |= RTGUI_WIDGET_FLAG_FOCUSABLE;
+ RTGUI_WIDGET_TEXTALIGN(rbox) = RTGUI_ALIGN_LEFT | RTGUI_ALIGN_CENTER_VERTICAL; + rtgui_widget_set_rect(rbox, &rect);
+ rtgui_widget_set_event_handler(rbox, rtgui_radiobox_event_handler);
+
+ /* set proper of control */
+ rbox->items = RT_NULL;
+ rbox->item_count = 0;
+ rbox->item_sel = -1;
+ rbox->orient = RTGUI_HORIZONTAL;
+}
+
+static void _rtgui_radiobox_destructor(rtgui_radiobox_t *rbox)
+{
+ if(rbox->name != RT_NULL)
+ {
+ rt_free(rbox->name);
+ rbox->name = RT_NULL;
+ }
+}
+rtgui_type_t *rtgui_radiobox_type_get(void)
+{
+ static rtgui_type_t *radiobox_type = RT_NULL;
+
+ if(!radiobox_type)
+ {
+ radiobox_type = rtgui_type_create("radiobox", RTGUI_WIDGET_TYPE,
+ sizeof(rtgui_radiobox_t),
+ RTGUI_CONSTRUCTOR(_rtgui_radiobox_constructor),
+ RTGUI_DESTRUCTOR(_rtgui_radiobox_destructor));
+ }
+
+ return radiobox_type;
+}
+
+rtgui_radiobox_t* rtgui_radiobox_create(PVOID parent, const char* name, int orient, char** items, int count,
+ int left, int top, int w, int h)
+{
+ rtgui_radiobox_t* rbox;
+
+ RT_ASSERT(parent != RT_NULL);
+
+ rbox = rtgui_widget_create(RTGUI_RADIOBOX_TYPE);
+ if(rbox != RT_NULL)
+ {
+ rtgui_rect_t rect;
+
+ rtgui_widget_get_rect(parent,&rect);
+ rtgui_widget_rect_to_device(parent,&rect);
+ rect.x1 += left;
+ rect.y1 += top;
+ rect.x2 = rect.x1+w;
+ rect.y2 = rect.y1+h;
+ rtgui_widget_set_rect(rbox,&rect);
+ rtgui_container_add_child(parent, rbox);
+
+ rbox->name = rt_strdup(name);
+ rbox->item_count = count;
+ if(count > 0)
+ {
+ rbox->items = (char**)rt_malloc(sizeof(char**)*count);
+ if(rbox->items == RT_NULL) return RT_NULL;
+ }
+
+ rbox->item_sel = -1;
+ rbox->orient = orient;
+ }
+
+ return rbox;
+}
+
+void rtgui_radiobox_destroy(rtgui_radiobox_t* rbox)
+{
+ rtgui_widget_destroy(rbox);
+}
+
+static void rtgui_radiobox_onmouse(rtgui_radiobox_t* rbox, rtgui_event_mouse_t* event)
+{
+ RT_ASSERT(rbox != RT_NULL);
+ RT_ASSERT(event != RT_NULL);
+
+ if(event->button & RTGUI_MOUSE_BUTTON_DOWN && event->button & RTGUI_MOUSE_BUTTON_LEFT)
+ {
+
+ rtgui_rect_t rect;
+
+ /* focus widgets */
+ rtgui_widget_focus(rbox);
+
+ /* get widget physical rect */
+ rtgui_widget_get_rect(rbox, &rect);
+
+ /* get board size */
+ if(rbox->orient == RTGUI_HORIZONTAL)
+ {//ˮƽ
+ }
+ else if(rbox->orient == RTGUI_VERTICAL)
+ {//��ֱ
+
+ }
+
+ }
+}
+
+rt_bool_t rtgui_radiobox_event_handler(PVOID wdt, rtgui_event_t* event)
+{
+ rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ rtgui_radiobox_t* rbox = (rtgui_radiobox_t*)widget;
+
+ switch (event->type)
+ {
+ case RTGUI_EVENT_PAINT:
+ if(widget->on_draw != RT_NULL)
+ widget->on_draw(widget, event);
+ else
+ {
+ rtgui_theme_draw_radiobox(rbox);
+ }
+
+ break;
+
+ case RTGUI_EVENT_KBD:
+ if(widget->on_key != RT_NULL) widget->on_key(widget, event);
+ else
+ {
+ rtgui_event_kbd_t *e = (rtgui_event_kbd_t*)event;
+
+ /* set focused */
+ rtgui_widget_focus(rbox);
+ if(!(RTGUI_KBD_IS_UP(e))) return RT_FALSE;
+
+ if(rbox->orient == RTGUI_VERTICAL)
+ {
+ if(e->key == RTGUIK_UP)
+ {
+ if(rbox->item_sel > 0)
+ rtgui_radiobox_set_selection(rbox, rbox->item_sel - 1);
+ }
+ else if(e->key == RTGUIK_DOWN)
+ {
+ if(rbox->item_sel < rbox->item_count - 1)
+ rtgui_radiobox_set_selection(rbox, rbox->item_sel + 1);
+ }
+ }
+ else
+ {
+ if(e->key == RTGUIK_LEFT)
+ {
+ if(rbox->item_sel > 0)
+ rtgui_radiobox_set_selection(rbox, rbox->item_sel - 1);
+ }
+ else if(e->key == RTGUIK_RIGHT)
+ {
+ if(rbox->item_sel < rbox->item_count - 1)
+ rtgui_radiobox_set_selection(rbox, rbox->item_sel + 1);
+ }
+ }
+ }
+ break;
+
+ case RTGUI_EVENT_MOUSE_BUTTON:
+ if(widget->on_mouseclick != RT_NULL)
+ widget->on_mouseclick(widget, event);
+ else
+ {
+ rtgui_radiobox_onmouse(rbox, (rtgui_event_mouse_t*)event);
+ }
+ break;
+ }
+
+ return RT_FALSE;
+}
+
+void rtgui_radiobox_set_selection(rtgui_radiobox_t* rbox, int selection)
+{
+ rt_uint16_t old_item;
+
+ if(selection == rbox->item_sel) return;
+
+ old_item = rbox->item_sel;
+ if(selection >= 0 && selection < rbox->item_count)
+ {
+ rbox->item_sel = selection;
+ }
+
+ /* update rbox widget */
+ rtgui_theme_draw_radiobutton(rbox, old_item);
+ rtgui_theme_draw_radiobutton(rbox, rbox->item_sel);
+}
+
+int rtgui_radiobox_get_selection(rtgui_radiobox_t* rbox)
+{
+ return rbox->item_sel;
+}
diff --git a/components/rtgui_win/widgets/scrollbar.c b/components/rtgui_win/widgets/scrollbar.c new file mode 100644 index 0000000000..93d6287ccd --- /dev/null +++ b/components/rtgui_win/widgets/scrollbar.c @@ -0,0 +1,666 @@ +/*
+ * File : scrollbar.c
+ * This file is part of RT-Thread RTOS
+ * COPYRIGHT (C) 2006 - 2009, RT-Thread Development Team
+ *
+ * The license and distribution terms for this file may be
+ * found in the file LICENSE in this distribution or at
+ * http://www.rt-thread.org/license/LICENSE
+ *
+ * Change Logs:
+ * Date Author Notes
+ * 2010-08-09 Bernard first version
+ */
+#include <rtgui/dc.h>
+#include <rtgui/widgets/scrollbar.h>
+#include <rtgui/rtgui_theme.h>
+
+static void _rtgui_scrollbar_constructor(rtgui_scrollbar_t *bar)
+{
+ /* set event handler */
+ rtgui_widget_set_event_handler(bar, rtgui_scrollbar_event_handler);
+
+ bar->status = 0;
+ bar->value = 0;
+
+ bar->thumb_w = 16;
+ bar->thumb_len = 16;
+
+ bar->widgetlnk = RT_NULL;
+ bar->on_scroll = RT_NULL;
+
+ bar->orient = RTGUI_HORIZONTAL;
+ /* set gc */
+ RTGUI_WIDGET_TEXTALIGN(bar) = RTGUI_ALIGN_CENTER_HORIZONTAL|RTGUI_ALIGN_CENTER_VERTICAL;
+}
+
+static void _rtgui_scrollbar_destructor(rtgui_scrollbar_t *bar)
+{
+
+}
+
+rt_inline rt_uint32_t _rtgui_scrollbar_get_length(rtgui_scrollbar_t *bar)
+{
+ rtgui_rect_t rect;
+ rt_uint32_t result;
+
+ rtgui_widget_get_rect(bar, &rect);
+
+ if(bar->orient & RTGUI_VERTICAL)
+ result = rtgui_rect_height(rect) - 2*rtgui_rect_width(rect) - bar->thumb_len;
+ else
+ result = rtgui_rect_width(rect) - 2*rtgui_rect_height(rect) - bar->thumb_len;
+
+ return result;
+}
+
+rt_inline rt_uint32_t get_scrollbar_pos(rtgui_scrollbar_t* bar)
+{
+ double pos,ftmp;
+ rt_uint32_t result;
+
+ /* calculate thumb position */
+ pos = bar->value;
+ ftmp = _rtgui_scrollbar_get_length(bar);
+ pos *= ftmp;
+ ftmp = bar->count;
+ pos /= ftmp;
+
+ result = pos;
+ return result;
+}
+
+rtgui_type_t *rtgui_scrollbar_type_get(void)
+{
+ static rtgui_type_t *scrollbar_type = RT_NULL;
+
+ if(!scrollbar_type)
+ {
+ scrollbar_type = rtgui_type_create("scrollbar", RTGUI_WIDGET_TYPE,
+ sizeof(rtgui_scrollbar_t),
+ RTGUI_CONSTRUCTOR(_rtgui_scrollbar_constructor),
+ RTGUI_DESTRUCTOR(_rtgui_scrollbar_destructor));
+ }
+
+ return scrollbar_type;
+}
+
+
+rtgui_scrollbar_t* rtgui_scrollbar_create(PVOID parent,int left,int top,int w,int len,int orient)
+{
+ rtgui_scrollbar_t* bar;
+
+ RT_ASSERT(parent != RT_NULL);
+
+ bar = rtgui_widget_create (RTGUI_SCROLLBAR_TYPE);
+ if(bar != RT_NULL)
+ {
+ rtgui_rect_t rect;
+
+ rtgui_widget_get_rect(parent, &rect);
+ rtgui_widget_rect_to_device(parent,&rect);
+ rect.x1 += left;
+ rect.y1 += top;
+
+ bar->thumb_w = w;
+ if(orient == RTGUI_VERTICAL)
+ {
+ rect.x2 = rect.x1+w;
+ rect.y2 = rect.y1+len;
+ }
+ else
+ {
+ rect.x2 = rect.x1+len;
+ rect.y2 = rect.y1+w;
+ }
+ + rtgui_widget_set_rect(bar, &rect);
+
+ bar->orient = orient;
+
+ rtgui_container_add_child(parent, bar);
+ }
+
+ return bar;
+}
+
+void rtgui_scrollbar_destroy(rtgui_scrollbar_t* bar)
+{
+ rtgui_widget_destroy(bar);
+}
+
+
+void rtgui_scrollbar_get_thumb_rect(rtgui_scrollbar_t *bar, rtgui_rect_t *erect)
+{
+ rtgui_rect_t rect;
+
+ rtgui_widget_get_rect(bar, &rect);
+ if(bar->orient & RTGUI_VERTICAL)
+ {
+ /* vertical scroll bar */
+ erect->x1 = rect.x1;
+ erect->x2 = rect.x2;
+ erect->y1 = rect.y1 + rtgui_rect_width(rect) + get_scrollbar_pos(bar);
+ erect->y2 = erect->y1 + bar->thumb_len;
+ }
+ else
+ {
+ /* horizontal scroll bar */
+ erect->x1 = rect.x1 + rtgui_rect_height(rect) + get_scrollbar_pos(bar);
+ erect->x2 = erect->x1 + bar->thumb_len;
+ erect->y1 = rect.y1;
+ erect->y2 = rect.y2;
+ }
+}
+
+static rtgui_point_t sbar_mouse_move_size;
+
+static void _rtgui_scrollbar_on_mouseclick(PVOID wdt, rtgui_event_t * event)
+{
+ rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ rtgui_rect_t btn_rect, bar_rect,rect;
+ rt_uint32_t pos;
+ rtgui_scrollbar_t *bar = (rtgui_scrollbar_t*)widget;
+ rtgui_event_mouse_t *mouse = (rtgui_event_mouse_t*)event;
+
+ RT_ASSERT(bar != RT_NULL);
+
+ /* get value */
+ pos = get_scrollbar_pos(bar);
+
+ rtgui_widget_get_rect(bar, &rect);
+ rtgui_widget_rect_to_device(bar,&rect);
+
+ if(bar->orient == RTGUI_VERTICAL)
+ { /* arrange vertical */
+ /* get up arrow button rect */
+ btn_rect.x1 = rect.x1;
+ btn_rect.x2 = rect.x2;
+ btn_rect.y1 = rect.y1;
+ btn_rect.y2 = rect.y1 + rtgui_rect_width(rect);
+
+ if(rtgui_rect_contains_point(&btn_rect, mouse->x, mouse->y) == RT_EOK)
+ {
+ if((mouse->button & RTGUI_MOUSE_BUTTON_LEFT) && (mouse->button & RTGUI_MOUSE_BUTTON_DOWN))
+ {
+ bar->status |= SBAR_UPARROW;
+ if(bar->value==0)
+ {
+ rtgui_theme_draw_scrollbar(bar);
+ return;
+ }
+ /* line step */
+ bar->value -= bar->line_step;
+ if(bar->value < 0) bar->value = 0;
+ }
+ else if(mouse->button & RTGUI_MOUSE_BUTTON_UP)
+ {
+ bar->status = 0;
+ }
+ goto __exit;
+ }
+ /* click on the thumb chunk, be going to dragging */
+ rtgui_scrollbar_get_thumb_rect(bar, &bar_rect);
+ rtgui_widget_rect_to_device(bar,&bar_rect);
+ if(rtgui_rect_contains_point(&bar_rect, mouse->x, mouse->y) == RT_EOK)
+ { /* on thumb */
+ if((mouse->button & RTGUI_MOUSE_BUTTON_LEFT) && (mouse->button & RTGUI_MOUSE_BUTTON_DOWN))
+ { /* changed status into drag */
+ bar->status |= SBAR_VERTTHUMB;
+ sbar_mouse_move_size.x = mouse->x;
+ sbar_mouse_move_size.y = mouse->y;
+ }
+ else if(mouse->button & RTGUI_MOUSE_BUTTON_UP)
+ {
+ bar->status = 0;
+ }
+ goto __exit;
+ }
+ else
+ { /* click on space without thumb */
+ /* get bar rect */
+ bar_rect.y1 = rect.y1 + rtgui_rect_width(rect);
+ bar_rect.y2 = rect.y2 - rtgui_rect_width(rect);
+ if(rtgui_rect_contains_point(&bar_rect, mouse->x, mouse->y) == RT_EOK)
+ {
+ if((mouse->button & RTGUI_MOUSE_BUTTON_LEFT) && (mouse->button & RTGUI_MOUSE_BUTTON_DOWN))
+ {
+ /* page step */
+ if(mouse->y < bar_rect.y1 + pos)
+ {
+ bar->status |= SBAR_UPSPACE;
+ bar->value -= bar->page_step;
+ if(bar->value < 0) bar->value = 0;
+ }
+ else if(mouse->y > pos + bar->thumb_len)
+ {
+ bar->status |= SBAR_DOWNSPACE;
+ bar->value += bar->page_step;
+ if(bar->value > bar->count) bar->value = bar->count;
+ }
+ }
+ goto __exit;
+ }
+ }
+ /* likewise foregoing */
+ /* get down arrow button rect */
+ bar_rect.x1 = rect.x1;
+ bar_rect.x2 = rect.x2;
+ btn_rect.y1 = rect.y2 - rtgui_rect_width(rect);
+ btn_rect.y2 = rect.y2;
+ if(rtgui_rect_contains_point(&btn_rect, mouse->x, mouse->y) == RT_EOK)
+ {
+ if((mouse->button & RTGUI_MOUSE_BUTTON_LEFT) && (mouse->button & RTGUI_MOUSE_BUTTON_DOWN))
+ {
+ bar->status |= SBAR_DOWNARROW;
+ if(bar->value==bar->count)
+ {
+ rtgui_theme_draw_scrollbar(bar);
+ return;
+ }
+ /* line step */
+ bar->value += bar->line_step;
+ if(bar->value > bar->count) bar->value = bar->count;
+ }
+ else if(mouse->button & RTGUI_MOUSE_BUTTON_UP)
+ bar->status = 0;
+ goto __exit;
+ }
+ }
+ else
+ {
+ /* get left arrow button rect */
+ btn_rect.x1 = rect.x1;
+ btn_rect.x2 = rect.x1 + rtgui_rect_height(rect);
+ btn_rect.y1 = rect.y1;
+ btn_rect.y2 = rect.y2;
+ if(rtgui_rect_contains_point(&btn_rect, mouse->x, mouse->y) == RT_EOK)
+ {
+ if((mouse->button & RTGUI_MOUSE_BUTTON_LEFT) && (mouse->button & RTGUI_MOUSE_BUTTON_DOWN))
+ {
+ bar->status |= SBAR_LEFTARROW;
+ if(bar->value==0)
+ {
+ rtgui_theme_draw_scrollbar(bar);
+ return;
+ }
+ /* line step */
+ bar->value -= bar->line_step;
+ if(bar->value < 0) bar->value = 0;
+ }
+ else if(mouse->button & RTGUI_MOUSE_BUTTON_UP)
+ bar->status = 0;
+ goto __exit;
+ }
+
+ rtgui_scrollbar_get_thumb_rect(bar, &bar_rect);
+ rtgui_widget_rect_to_device(bar,&bar_rect);
+ if(rtgui_rect_contains_point(&bar_rect, mouse->x, mouse->y) == RT_EOK)
+ {/* on the thumb */
+ if((mouse->button & RTGUI_MOUSE_BUTTON_LEFT) && (mouse->button & RTGUI_MOUSE_BUTTON_DOWN))
+ {
+ bar->status |= SBAR_HORZTHUMB;
+ sbar_mouse_move_size.x = mouse->x;
+ sbar_mouse_move_size.y = mouse->y;
+ }
+ else if(mouse->button & RTGUI_MOUSE_BUTTON_UP)
+ {
+ bar->status = 0;
+ }
+ goto __exit;
+ }
+ else
+ {
+ /* get bar rect */
+ bar_rect.x1 = rect.x1 + rtgui_rect_height(rect);
+ bar_rect.x2 = rect.x2 - rtgui_rect_height(rect);
+ bar_rect.y1 = rect.y1;
+ bar_rect.y2 = rect.y2;
+ if(rtgui_rect_contains_point(&bar_rect, mouse->x, mouse->y) == RT_EOK)
+ {
+ if((mouse->button & RTGUI_MOUSE_BUTTON_LEFT) && (mouse->button & RTGUI_MOUSE_BUTTON_DOWN))
+ {
+ /* page step */
+ if(mouse->x < bar_rect.x1 + pos)
+ {
+ bar->status |= SBAR_LEFTSPACE;
+ bar->value -= bar->page_step;
+ if(bar->value < 0) bar->value = 0;
+ }
+ else if(mouse->x > pos + bar->thumb_len)
+ {
+ bar->status |= SBAR_RIGHTSPACE;
+ bar->value += bar->page_step;
+ if(bar->value > bar->count) bar->value = bar->count;
+ }
+ }
+ else if(mouse->button & RTGUI_MOUSE_BUTTON_UP)
+ {
+ bar->status = 0;
+ }
+ goto __exit;
+ }
+ }
+ /* get right arrow button rect */
+ btn_rect.x1 = rect.x2 - rtgui_rect_height(rect);
+ btn_rect.x2 = rect.x2;
+ bar_rect.y1 = rect.y1;
+ bar_rect.y2 = rect.y2;
+ if(rtgui_rect_contains_point(&btn_rect, mouse->x, mouse->y) == RT_EOK)
+ {
+ if((mouse->button & RTGUI_MOUSE_BUTTON_LEFT) && (mouse->button & RTGUI_MOUSE_BUTTON_DOWN))
+ {
+ bar->status |= SBAR_RIGHTARROW;
+ if(bar->value==bar->count)
+ {
+ rtgui_theme_draw_scrollbar(bar);
+ return;
+ }
+ /* line step */
+ bar->value += bar->line_step;
+ if(bar->value > bar->count) bar->value = bar->count;
+ }
+ else if(mouse->button & RTGUI_MOUSE_BUTTON_UP)
+ bar->status = 0;
+ goto __exit;
+ }
+ }
+
+__exit:
+ rtgui_theme_draw_scrollbar(bar);
+ if((mouse->button & RTGUI_MOUSE_BUTTON_LEFT) && (mouse->button & RTGUI_MOUSE_BUTTON_DOWN))
+ {
+ if(bar->widgetlnk != RT_NULL && bar->on_scroll != RT_NULL)
+ {
+ rtgui_widget_focus(bar->widgetlnk);
+ bar->on_scroll(bar->widgetlnk, RT_NULL);
+ }
+ }
+
+}
+
+/* thumb chunk activity */
+static void _rtgui_scrollbar_on_mousemotion(PVOID wdt, rtgui_event_t * event)
+{
+ #include <stdlib.h>
+ float tmppos;
+ rt_uint32_t pos;
+ rtgui_scrollbar_t *bar = (rtgui_scrollbar_t*)wdt;
+ rtgui_event_mouse_t *mouse = (rtgui_event_mouse_t*)event;
+
+ tmppos = _rtgui_scrollbar_get_length(bar);
+ tmppos /= bar->count;
+ pos = (rt_uint32_t)tmppos;
+
+ if(bar->orient == RTGUI_VERTICAL)
+ {
+ if(bar->status & SBAR_VERTTHUMB)
+ { /* from then on mouseclick */
+ if((mouse->y-sbar_mouse_move_size.y) > 3)
+ {
+ bar->status |= SBAR_DOWNTHUMB;
+ }
+ else if((mouse->y-sbar_mouse_move_size.y) < -3)
+ {
+ bar->status |= SBAR_UPTHUMB;
+ }
+ else bar->status &= ~(SBAR_UPTHUMB|SBAR_DOWNTHUMB);
+
+ if(abs(mouse->y-sbar_mouse_move_size.y) >= pos)
+ {
+ int step = abs(mouse->y-sbar_mouse_move_size.y)/pos;
+ sbar_mouse_move_size.y = mouse->y;
+
+ if(bar->status & SBAR_UPTHUMB)
+ {
+ bar->value -= step;
+ if(bar->value < 0) bar->value = 0;
+ }
+ else if(bar->status & SBAR_DOWNTHUMB)
+ {
+ bar->value += step;
+ if(bar->value > bar->count) bar->value = bar->count;
+ }
+ goto __exit;
+ }
+ }
+ else if(bar->status & SBAR_UPARROW)
+ { /* on-going push down uparrow button */
+ if(bar->value==0)return;
+ bar->value -= bar->line_step;
+ if(bar->value < 0) bar->value = 0;
+ goto __exit;
+ }
+ else if(bar->status & SBAR_DOWNARROW)
+ { /* on-going push down downarrow button */
+ if(bar->value==bar->count)return;
+ bar->value += bar->line_step;
+ if(bar->value > bar->count) bar->value = bar->count;
+ goto __exit;
+ }
+ /*else if(bar->status & SBAR_UPSPACE)
+ {
+ bar->value -= bar->page_step;
+ if(bar->value < 0) bar->value = 0;
+ goto __exit;
+ }
+ else if(bar->status & SBAR_DOWNSPACE)
+ {
+ bar->value += bar->page_step;
+ if(bar->value > bar->count) bar->value = bar->count;
+ goto __exit;
+ }*/
+ return;
+ }
+ else
+ { /* ˮƽ���� */
+ if(bar->status & SBAR_HORZTHUMB)
+ {
+ if((mouse->x-sbar_mouse_move_size.x) > 5)
+ {
+ bar->status |= SBAR_RIGHTTHUMB;
+ }
+ else if((mouse->x-sbar_mouse_move_size.x) < -5)
+ {
+ bar->status |= SBAR_LEFTTHUMB;
+ }
+ if(abs(mouse->x-sbar_mouse_move_size.x) > pos)
+ {
+ int step = abs(mouse->x-sbar_mouse_move_size.x)/pos;
+ sbar_mouse_move_size.x = mouse->x;
+ if(bar->status & SBAR_LEFTTHUMB)
+ {
+ bar->value -= step;
+ if(bar->value < 0) bar->value = 0;
+ }
+ else if(bar->status & SBAR_RIGHTTHUMB)
+ {
+ bar->value += step;
+ if(bar->value > bar->count) bar->value = bar->count;
+ }
+ goto __exit;
+ }
+ }
+ else if(bar->status & SBAR_LEFTARROW)
+ {
+ if(bar->value==0)return;
+ bar->value -= bar->line_step;
+ if(bar->value < 0) bar->value = 0;
+ goto __exit;
+ }
+ else if(bar->status & SBAR_RIGHTARROW)
+ {
+ if(bar->value==bar->count)return;
+ bar->value += bar->line_step;
+ if(bar->value > bar->count) bar->value = bar->count;
+ goto __exit;
+ }
+ /*else if(bar->status & SBAR_LEFTSPACE)
+ {
+ bar->value -= bar->page_step;
+ if(bar->value < bar->min) bar->value = bar->min;
+ goto __exit;
+ }
+ else if(bar->status & SBAR_RIGHTSPACE)
+ {
+ bar->value += bar->page_step;
+ if(bar->value > bar->count-1) bar->value = bar->count-1;
+ goto __exit;
+ }*/
+ return;
+ }
+
+__exit:
+ rtgui_theme_draw_scrollbar(bar);
+ if(bar->widgetlnk != RT_NULL && bar->on_scroll != RT_NULL)
+ {
+ rtgui_widget_focus(bar->widgetlnk);
+ bar->on_scroll(bar->widgetlnk, RT_NULL);
+ }
+}
+
+
+rt_bool_t rtgui_scrollbar_event_handler(PVOID wdt, rtgui_event_t *event)
+{
+ rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ rtgui_scrollbar_t* bar = (rtgui_scrollbar_t*)widget;
+
+ if(RTGUI_WIDGET_IS_HIDE(bar))return RT_FALSE;
+
+ switch (event->type)
+ {
+ case RTGUI_EVENT_PAINT:
+ if(widget->on_draw != RT_NULL)
+ widget->on_draw(widget, event);
+ else
+ {
+ if(!RTGUI_WIDGET_IS_HIDE(bar))
+ rtgui_theme_draw_scrollbar(bar);
+ }
+
+ break;
+
+ case RTGUI_EVENT_MOUSE_BUTTON:
+ if(RTGUI_WIDGET_IS_ENABLE(widget))
+ {
+ if(widget->on_mouseclick != RT_NULL)
+ {
+ widget->on_mouseclick(widget, event);
+ }
+ else
+ {
+ _rtgui_scrollbar_on_mouseclick(bar, event);
+ }
+ }
+ break;
+ case RTGUI_EVENT_MOUSE_MOTION:
+ if(RTGUI_WIDGET_IS_ENABLE(widget))
+ {
+ _rtgui_scrollbar_on_mousemotion(bar, event);
+ }
+
+ default:
+ break;
+ }
+
+ return RT_FALSE;
+}
+
+void rtgui_scrollbar_set_orientation(rtgui_scrollbar_t* bar, int orient)
+{
+ RT_ASSERT(bar != RT_NULL);
+
+ bar->orient = orient;
+}
+
+//ȡ�û���Ŀɻ����ij���
+rt_uint32_t get_sbar_active_len(rtgui_scrollbar_t *bar)
+{
+ rtgui_rect_t rect;
+
+ rtgui_widget_get_rect(bar, &rect);
+
+ if(bar->orient & RTGUI_VERTICAL)
+ return rtgui_rect_height(rect) - 2*rtgui_rect_width(rect);
+ else
+ return rtgui_rect_width(rect) - 2*rtgui_rect_height(rect);
+}
+
+void rtgui_scrollbar_set_thumbbar_len(rtgui_scrollbar_t* bar)
+{
+ double size=0;
+ rt_uint32_t len,w;
+
+ RT_ASSERT(bar != RT_NULL);
+
+ //Make sure called rtgui_scrollbar_set_range(),before you use under code.
+ //������ߴ�ķ���:
+ //��һҳ��Ŀ����/�ܼ��������ı�ֵ,��ȷ������ڿɻ�����еı���,
+ //�������ܶ���,ʹ�û����ĵ�һ����Ϊ��С�ߴ�.
+
+ size = bar->page_step;
+ size /= bar->count+bar->page_step;
+ size *= get_sbar_active_len(bar);
+ len = (rt_uint32_t)size ;
+
+ w = bar->thumb_w;
+
+ if(len < w/2) len = w/2;
+
+ bar->thumb_len = len;
+}
+
+//�������������ĵ���˳��:
+//1.SetLineStep();2.SetPageStep();3.SetRange();
+
+void rtgui_scrollbar_set_line_step(rtgui_scrollbar_t* bar, int step)
+{
+ RT_ASSERT(bar != RT_NULL);
+
+ bar->line_step = step;
+}
+
+void rtgui_scrollbar_set_page_step(rtgui_scrollbar_t* bar, int step)
+{
+ RT_ASSERT(bar != RT_NULL);
+
+ bar->page_step = step;
+}
+
+void rtgui_scrollbar_set_range(rtgui_scrollbar_t* bar, int count)
+{
+ RT_ASSERT(bar != RT_NULL);
+
+ /* disable or enable scrollbar */
+ if(bar->page_step >= count)
+ { /* disable bar */
+ RTGUI_WIDGET_DISABLE(bar);
+ }
+ else
+ { /* enable bar */
+ RTGUI_WIDGET_ENABLE(bar);
+ }
+
+ //���������� = �ܸ��� - һ������
+ bar->count = (rt_int16_t)(count-bar->page_step);
+ rtgui_scrollbar_set_thumbbar_len(bar);
+}
+
+//value��ֵ�DZ��ؼ�������ֵfrist_aloc
+void rtgui_scrollbar_set_value(rtgui_scrollbar_t* bar, rt_int16_t value)
+{
+ RT_ASSERT(bar != RT_NULL);
+
+ bar->value = value;
+
+ if(bar->value < 0) bar->value = 0;
+
+ rtgui_widget_update(bar);
+}
+
+void rtgui_scrollbar_set_onscroll(rtgui_scrollbar_t* bar, rtgui_event_handler_ptr handler)
+{
+ if(bar == RT_NULL || handler == RT_NULL) return;
+
+ bar->on_scroll = handler;
+}
diff --git a/components/rtgui_win/widgets/slider.c b/components/rtgui_win/widgets/slider.c new file mode 100644 index 0000000000..f29653945f --- /dev/null +++ b/components/rtgui_win/widgets/slider.c @@ -0,0 +1,229 @@ +#include <rtgui/dc.h>
+#include <rtgui/rtgui_theme.h>
+#include <rtgui/widgets/slider.h>
+
+#define RTGUI_SLIDER_DEFAULT_WIDTH 100
+#define RTGUI_SLIDER_DEFAULT_HEIGHT 20
+#define RTGUI_SLIDER_DEFAULT_MIN 0
+#define RTGUI_SLIDER_DEFAULT_MAX 100
+
+static void _rtgui_slider_constructor(rtgui_slider_t *slider)
+{
+ rtgui_rect_t rect = {0, 0, RTGUI_SLIDER_DEFAULT_WIDTH, RTGUI_SLIDER_DEFAULT_HEIGHT};
+
+ /* init widget and set event handler */
+ RTGUI_WIDGET_FLAG(slider) |= RTGUI_WIDGET_FLAG_FOCUSABLE;
+ rtgui_widget_set_rect(slider, &rect);
+ rtgui_widget_set_event_handler(slider, rtgui_slider_event_handler);
+
+ /* set proper of control */
+ slider->min = RTGUI_SLIDER_DEFAULT_MIN;
+ slider->max = RTGUI_SLIDER_DEFAULT_MAX;
+ slider->value = RTGUI_SLIDER_DEFAULT_MIN;
+ slider->orient = RTGUI_HORIZONTAL;
+
+ slider->ticks = 10;
+ slider->thumb_width = 6;
+}
+
+static void _rtgui_slider_destructor(rtgui_slider_t *slider)
+{
+
+}
+
+rtgui_type_t *rtgui_slider_type_get(void)
+{
+ static rtgui_type_t *slider_type = RT_NULL;
+
+ if(!slider_type)
+ {
+ slider_type = rtgui_type_create("slider", RTGUI_WIDGET_TYPE,
+ sizeof(rtgui_slider_t),
+ RTGUI_CONSTRUCTOR(_rtgui_slider_constructor),
+ RTGUI_DESTRUCTOR(_rtgui_slider_destructor));
+ }
+
+ return slider_type;
+}
+
+static void rtgui_slider_onmouse(rtgui_slider_t* slider, rtgui_event_mouse_t* event)
+{
+ RT_ASSERT(slider != RT_NULL);
+ RT_ASSERT(event != RT_NULL);
+
+ if(event->button & RTGUI_MOUSE_BUTTON_DOWN &&
+ event->button & RTGUI_MOUSE_BUTTON_LEFT)
+ {
+ int sel;
+ int range = slider->max - slider->min;
+ int x0, xsize;
+ int x;
+ x0 = 1 + slider->thumb_width/2;
+
+ if(slider->orient == RTGUI_VERTICAL)
+ {
+ x = event->y - RTGUI_WIDGET(slider)->extent.y1;
+ x -= x0;
+ xsize = rtgui_rect_height(RTGUI_WIDGET(slider)->extent) - 2 * x0;
+ }
+ else
+ {
+ x = event->x - RTGUI_WIDGET(slider)->extent.x1;
+ x -= x0;
+ xsize = rtgui_rect_width(RTGUI_WIDGET(slider)->extent) - 2 * x0;
+ }
+
+ if(x <= 0)
+ {
+ sel = slider->min;
+ }
+ else if(x >= xsize)
+ {
+ sel = slider->max;
+ }
+ else
+ {
+ sel = ((range * x) + xsize/2) / xsize;
+ sel += slider->min;
+ }
+
+ rtgui_widget_focus(slider);
+ rtgui_slider_set_value(slider, sel);
+ }
+}
+
+static void rtgui_slider_onkey(rtgui_slider_t* slider, rtgui_event_kbd_t *event)
+{
+ RT_ASSERT(slider != RT_NULL);
+ RT_ASSERT(event != RT_NULL);
+
+ if(!(RTGUI_KBD_IS_UP(event))) return;
+
+ if(event->key == RTGUIK_LEFT)
+ {
+ if(slider->value > slider->min)
+ slider->value ++;
+ }
+
+ if(event->key == RTGUIK_RIGHT)
+ {
+ if(slider->value < slider->max)
+ slider->value --;
+ }
+
+ /* update widget */
+ rtgui_widget_update(slider);
+}
+
+rt_bool_t rtgui_slider_event_handler(PVOID wdt, rtgui_event_t* event)
+{
+ rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ rtgui_slider_t* slider = (rtgui_slider_t*)widget;
+
+ switch (event->type)
+ {
+ case RTGUI_EVENT_PAINT:
+ if(widget->on_draw != RT_NULL) widget->on_draw(widget, event);
+ else
+ {
+ rtgui_theme_draw_slider(slider);
+ }
+
+ break;
+
+ case RTGUI_EVENT_KBD:
+ if(widget->on_key != RT_NULL) widget->on_key(widget, event);
+ else
+ {
+ rtgui_slider_onkey(slider, (rtgui_event_kbd_t *)event);
+ }
+ break;
+
+ case RTGUI_EVENT_MOUSE_BUTTON:
+ if(widget->on_mouseclick != RT_NULL) widget->on_mouseclick(widget, event);
+ else
+ {
+ rtgui_slider_onmouse(slider, (rtgui_event_mouse_t*)event);
+ }
+ break;
+ }
+
+ return RT_FALSE;
+}
+
+//����һ��������ؼ�
+rtgui_slider_t* rtgui_slider_create(PVOID parent, rt_size_t min, rt_size_t max, int left, int top, int w, int h, int orient)
+{
+ rtgui_slider_t* slider;
+
+ RT_ASSERT(parent != RT_NULL);
+
+ slider = rtgui_widget_create (RTGUI_SLIDER_TYPE);
+ if(slider != RT_NULL)
+ {
+ rtgui_rect_t rect;
+
+ /* set proper of control */
+ slider->min = min;
+ slider->max = max;
+ slider->value = min;
+
+ slider->ticks = 10;
+ slider->thumb_width = 6;//�����߿���
+
+ rtgui_slider_set_orientation(slider, orient);
+
+ rtgui_widget_get_rect(parent, &rect);
+ rtgui_widget_rect_to_device(parent,&rect);
+ rect.x1 += left;
+ rect.y1 += top;
+ rect.x2 = rect.x1+w;
+ rect.y2 = rect.y1+h;
+ rtgui_widget_set_rect(slider, &rect);
+ }
+
+ return slider;
+}
+
+void rtgui_slider_destroy(rtgui_slider_t* slider)
+{
+ rtgui_widget_destroy(slider);
+}
+
+void rtgui_slider_set_range(rtgui_slider_t* slider, rt_size_t min, rt_size_t max)
+{
+ RT_ASSERT(slider != RT_NULL);
+
+ slider->max = max;
+ slider->min = min;
+}
+
+void rtgui_slider_set_value(rtgui_slider_t* slider, rt_size_t value)
+{
+ RT_ASSERT(slider != RT_NULL);
+
+ if(value < slider->min) value = slider->min;
+ if(value > slider->max) value = slider->max;
+
+ if(slider->value != value)
+ {
+ slider->value = value;
+ rtgui_theme_draw_slider(slider);
+ }
+}
+
+//����Ŀ�귽��
+void rtgui_slider_set_orientation(rtgui_slider_t* slider, int orient)
+{
+ RT_ASSERT(slider != RT_NULL);
+
+ /* set orient */
+ slider->orient = orient;
+}
+
+rt_size_t rtgui_slider_get_value(rtgui_slider_t* slider)
+{
+ RT_ASSERT(slider != RT_NULL);
+
+ return slider->value;
+}
diff --git a/components/rtgui_win/widgets/staticline.c b/components/rtgui_win/widgets/staticline.c new file mode 100644 index 0000000000..a63dbe7c62 --- /dev/null +++ b/components/rtgui_win/widgets/staticline.c @@ -0,0 +1,96 @@ +#include <rtgui/dc.h>
+#include <rtgui/rtgui_theme.h>
+#include <rtgui/widgets/staticline.h>
+
+static void _rtgui_static_constructor(rtgui_staticline_t *sline)
+{
+ /* init widget and set event handler */
+ rtgui_rect_t rect = {0, 0, 100, 2};
+
+ rtgui_widget_set_rect(sline, &rect);
+ sline->orient= RTGUI_HORIZONTAL;
+
+ rtgui_widget_set_event_handler(sline, rtgui_staticline_event_handler);
+}
+
+static void _rtgui_static_destructor(rtgui_staticline_t *sline)
+{
+
+}
+
+rtgui_type_t *rtgui_staticline_type_get(void)
+{
+ static rtgui_type_t *staticline_type = RT_NULL;
+
+ if(!staticline_type)
+ {
+ staticline_type = rtgui_type_create("staticline", RTGUI_WIDGET_TYPE,
+ sizeof(rtgui_staticline_t),
+ RTGUI_CONSTRUCTOR(_rtgui_static_constructor),
+ RTGUI_DESTRUCTOR(_rtgui_static_destructor));
+ }
+
+ return staticline_type;
+}
+
+rt_bool_t rtgui_staticline_event_handler(PVOID wdt, rtgui_event_t* event)
+{
+ rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ rtgui_staticline_t* sline;
+ RT_ASSERT(widget != RT_NULL);
+
+ sline = (rtgui_staticline_t*) widget;
+ switch (event->type)
+ {
+ case RTGUI_EVENT_PAINT:
+ if(widget->on_draw != RT_NULL) widget->on_draw(widget, event);
+ else
+ rtgui_theme_draw_staticline(sline);
+ break;
+ }
+
+ return RT_FALSE;
+}
+
+rtgui_staticline_t * rtgui_staticline_create(PVOID parent,int left,int top,int w,int len,int orient)
+{
+ rtgui_staticline_t* sline;
+
+ RT_ASSERT(parent != RT_NULL);
+
+ sline = rtgui_widget_create(RTGUI_STATICLINE_TYPE);
+ if(sline!= RT_NULL)
+ {
+ rtgui_rect_t rect;
+
+ rtgui_widget_get_rect(parent, &rect);
+ rtgui_widget_rect_to_device(parent,&rect);
+ rect.x1 += left;
+ rect.y1 += top;
+
+ sline->orient = orient;
+
+ if(orient == RTGUI_HORIZONTAL)
+ {
+ rect.x2 = rect.x1+len;
+ rect.y2 = rect.y1+w;
+ }
+ else
+ {
+ rect.x2 = rect.x1+w;
+ rect.y2 = rect.y1+len;
+ }
+
+ rtgui_widget_set_rect(sline,&rect);
+
+ rtgui_container_add_child(parent, sline);
+ }
+
+ return sline;
+}
+
+void rtgui_staticline_destroy(rtgui_staticline_t* sline)
+{
+ rtgui_widget_destroy(sline);
+}
+
diff --git a/components/rtgui_win/widgets/textbox.c b/components/rtgui_win/widgets/textbox.c new file mode 100644 index 0000000000..f3f77e908a --- /dev/null +++ b/components/rtgui_win/widgets/textbox.c @@ -0,0 +1,547 @@ +/* + * File : textbox.c + * This file is part of RT-Thread RTOS + * COPYRIGHT (C) 2006 - 2009, RT-Thread Development Team + * + * The license and distribution terms for this file may be + * found in the file LICENSE in this distribution or at + * http://www.rt-thread.org/license/LICENSE + * + * Change Logs: + * Date Author Notes + * 2009-10-16 Bernard first version + */
+#include <rtgui/rtgui.h> +#include <rtgui/dc.h> +#include <rtgui/rtgui_theme.h> +#include <rtgui/rtgui_system.h> +#include <rtgui/widgets/textbox.h>
+#include <rtgui/widgets/widget.h>
+ +#include <ctype.h>
+ +static void rtgui_textbox_timeout(rtgui_timer_t* timer, void* parameter);
+static rt_bool_t rtgui_textbox_onkey(PVOID wdt, rtgui_event_t* event); +static rt_bool_t rtgui_textbox_onfocus(PVOID wdt, rtgui_event_t* event); +static rt_bool_t rtgui_textbox_onunfocus(PVOID wdt, rtgui_event_t* event);
+
+ +void _rtgui_textbox_constructor(rtgui_textbox_t *box) +{ + rtgui_rect_t rect; + + RTGUI_WIDGET_FLAG(box) |= RTGUI_WIDGET_FLAG_FOCUSABLE;
+ + rtgui_widget_set_event_handler(box, rtgui_textbox_event_handler); + rtgui_widget_set_onfocus(box, rtgui_textbox_onfocus); + rtgui_widget_set_onunfocus(box, rtgui_textbox_onunfocus);
+ rtgui_widget_set_onkey(box,rtgui_textbox_onkey);
+ + RTGUI_WIDGET_BACKGROUND(box) = white;
+ /* set default text align */ + RTGUI_WIDGET_TEXTALIGN(box) = RTGUI_ALIGN_CENTER_VERTICAL; + rtgui_widget_set_style(box, RTGUI_BORDER_SUNKEN); + /* set proper of control ����һ�������͵Ŀ��ƶ�ʱ��*/ + box->caret_timer = rtgui_timer_create(100, RT_TIMER_FLAG_PERIODIC,rtgui_textbox_timeout, box);
+ + //��ʼ��...��ǰ��,��ʼ��,�ڵ�ǰ���е�λ�� + box->line = box->line_begin = box->position = 0;
+ box->flag = RTGUI_TEXTBOX_NONE; //����(Ĭ��) + box->isedit = RT_TRUE;//Ĭ���ǿ��Ա༭�� + /* allocate default line buffer ����Ĭ�ϵ��л��� */ + box->text = RT_NULL; + + rtgui_font_get_string_rect(RTGUI_WIDGET_FONT(box), "h", &rect); + box->font_width = rtgui_rect_width(rect);
+ box->on_change = RT_NULL;
+ box->on_enter = RT_NULL; +} + +void _rtgui_textbox_deconstructor(rtgui_textbox_t *textbox) +{ + if(textbox->text != RT_NULL) + { + rt_free(textbox->text); + textbox->text = RT_NULL; + } + if(textbox->caret_timer != RT_NULL) + rtgui_timer_destory(textbox->caret_timer); + textbox->caret_timer = RT_NULL;
+ +} + +rtgui_type_t *rtgui_textbox_type_get(void) +{ + static rtgui_type_t *textbox_type = RT_NULL; + + if(!textbox_type) + { + textbox_type = rtgui_type_create("textbox", RTGUI_WIDGET_TYPE, + sizeof(rtgui_textbox_t), + RTGUI_CONSTRUCTOR(_rtgui_textbox_constructor), + RTGUI_DESTRUCTOR(_rtgui_textbox_deconstructor)); + } + + return textbox_type; +}
+
+//#include <rthw.h>
+//���Ʊ༭����
+void rtgui_textbox_draw_caret(rtgui_textbox_t* box, rt_uint16_t position)
+{
+ int x,y;
+// rtgui_color_t color;
+ rtgui_rect_t rect;
+ int font_h,box_h;
+ rtgui_dc_t *dc;
+
+ RT_ASSERT(box != RT_NULL);
+
+ dc = rtgui_dc_begin_drawing(box);
+ if(dc == RT_NULL)return;
+ + rtgui_widget_get_rect(box, &rect);
+
+ font_h = rtgui_font_get_font_height(RTGUI_WIDGET_FONT(box));
+ box_h = rtgui_rect_height(rect);
+
+ rect.x1 += position * box->font_width+2; + rect.x2 = rect.x1+2; + rect.y1 += (box_h-font_h)/2;
+ rect.y2 = rect.y1 + font_h;
+
+ for(x=rect.x1;x<rect.x2;x++)
+ {
+ for(y=rect.y1;y<rect.y2;y++)
+ {
+// rt_hw_lcd_get_pixel(color,x,y);
+// color ^= white;
+// rtgui_dc_draw_point(box, color,x,y);
+
+ if(box->flag & RTGUI_TEXTBOX_CARET_SHOW)
+ {
+ RTGUI_DC_FC(dc) = black;
+ rtgui_dc_draw_point(dc, x,y);
+ }
+ else
+ {
+ RTGUI_DC_FC(dc) = white;
+ rtgui_dc_draw_point(dc, x,y);
+ }
+ }
+ }
+
+ rtgui_dc_end_drawing(dc);
+}
+ +static void rtgui_textbox_timeout(rtgui_timer_t* timer, void* parameter) +{ + rtgui_textbox_t* box; + + box = (rtgui_textbox_t*)parameter; + /* set caret flag */ + if(box->flag & RTGUI_TEXTBOX_CARET_SHOW) + box->flag &= ~RTGUI_TEXTBOX_CARET_SHOW; + else + box->flag |= RTGUI_TEXTBOX_CARET_SHOW;
+ + rtgui_textbox_draw_caret(box,box->position);
+ + return ; +}
+ +static void rtgui_textbox_onmouse(rtgui_textbox_t* box, rtgui_event_mouse_t* event) +{ + rt_size_t length;
+ rt_uint16_t posbak = box->position; + + RT_ASSERT(box != RT_NULL); + RT_ASSERT(event != RT_NULL);
+
+ if(box->isedit == RT_FALSE)return;
+ + length = rt_strlen(box->text); + + if(event->button & RTGUI_MOUSE_BUTTON_LEFT && event->button & RTGUI_MOUSE_BUTTON_DOWN) + { + rt_int32_t x;
+ if(!box->isedit)return; + if(box->flag & RTGUI_TEXTBOX_MULTI)
+ {//�����ı�
+ /* set widget focus */ + rtgui_widget_focus(box);
+
+ //add codes at here.
+ //...
+
+ box->position = 0;
+ box->flag |= RTGUI_TEXTBOX_CARET_SHOW;
+ rtgui_textbox_draw_caret(box,box->position);
+ }
+ else
+ {//�����ı� + /* set caret position */ + x = event->x - RTGUI_WIDGET(box)->extent.x1; + if(x < 0) + { + box->position = 0; + } + else if(x > length * box->font_width) + { + box->position = length; + } + else + { + box->position = x / box->font_width; + }
+
+ //�ı���λ��,�����һ��λ����ʾ�˱༭����,�����֮. + if(box->flag & RTGUI_TEXTBOX_CARET_SHOW)
+ {
+ rtgui_timer_stop(box->caret_timer);
+
+ box->flag &= ~RTGUI_TEXTBOX_CARET_SHOW;
+ rtgui_textbox_draw_caret(box, posbak);//��ˢ�����±༭����,�������ʾ״̬
+
+ rtgui_timer_start(box->caret_timer);
+ }
+
+ /* set widget focus */ + rtgui_widget_focus(box); + + /* draw caret ���Ʊ༭���� */ + rtgui_textbox_draw_caret(box,box->position);
+ } + } +}
+ +static rt_bool_t rtgui_textbox_onkey(PVOID wdt, rtgui_event_t* event) +{ + rtgui_textbox_t* box = (rtgui_textbox_t*)wdt;
+ rtgui_event_kbd_t* ekbd = (rtgui_event_kbd_t*)event;
+ rt_size_t length;
+ rt_uint16_t posbak = box->position; + + RT_ASSERT(box != RT_NULL); + RT_ASSERT(ekbd != RT_NULL); + + length = rt_strlen(box->text); + if(ekbd->key == RTGUIK_DELETE) + {//ɾ����������ַ� + if(box->position == length - 1) + { + box->text[box->position] = '\0'; + } + else + { + char *c; + + /* remove character */ + for(c = &box->text[box->position]; c[1] != '\0'; c++) + *c = c[1]; + *c = '\0'; + }
+
+ if(box->on_change)box->on_change(box,RT_NULL); + } + else if(ekbd->key == RTGUIK_BACKSPACE) + {//ɾ�����ǰ����ַ�
+ + if(box->position == length - 1) + { + box->text[box->position] = '\0'; + box->position --; + } + else if(box->position != 0) + { + /* remove current character */ + if(box->position != 0) + { + char *c; + + /* remove character */ + for(c = &box->text[box->position - 1]; c[1] != '\0'; c++) + *c = c[1]; + *c = '\0'; + }
+ box->position --; + }
+
+ if(box->on_change)box->on_change(box,RT_NULL); + } + else if(ekbd->key == RTGUIK_LEFT) + {//��������ƶ�һ���ַ�λ + if(box->position > 0)
+ {
+ box->position --;
+ } + } + else if(ekbd->key == RTGUIK_RIGHT) + {//��������ƶ�һ���ַ�λ + if(box->position < length)
+ {
+ box->position ++;
+ } + } + else if(ekbd->key == RTGUIK_HOME) + {//����ƶ������� + box->position = 0; + } + else if(ekbd->key == RTGUIK_END) + {//����ƶ�����β
+ box->position = length; + } + else if(ekbd->key == RTGUIK_RETURN) + { + if(box->on_enter != RT_NULL) + { + box->on_enter(box, RT_NULL); + } + }
+ else if(ekbd->key == RTGUIK_NUMLOCK)//���ּ���Ч
+ {
+ /* change numlock state */
+ } + else + { + if(isprint(ekbd->key)) + {//�ǿɴ�ӡ�ַ������� + /* no buffer on this line */
+ if(box->flag & RTGUI_TEXTBOX_DIGIT)
+ {//������������
+ if(!isdigit(ekbd->key))
+ {//����'.'��'-'
+ if(ekbd->key != '.' && ekbd->key !='-')return RT_FALSE;
+ if(ekbd->key == '.' && strchr(box->text,'.'))return RT_FALSE;
+
+ if(ekbd->key == '-')
+ {//������ģʽ��,������������
+ if(length+1 > box->line_length) return RT_FALSE; + if(length+1 > box->dis_length) return RT_FALSE;
+
+ if(strchr(box->text,'-'))
+ {//��ǰ�Ѿ���Ϊ����
+ char* c; + for(c = &box->text[0]; c != &box->text[length]; c++) + *c = *(c+1); + box->text[length] = '\0';
+ box->position --;
+ goto _exit;
+ }
+ else
+ {
+ char* c; + for(c = &box->text[length]; c != &box->text[0]; c--) + *c = *(c-1);
+ box->text[0] = '-'; + box->text[length+1] = '\0';
+ box->position ++;
+ goto _exit;
+ }
+ }
+ }
+ //rt_kprintf("%c ",ekbd->key);//debug printf
+ } + if(length+1 > box->line_length) return RT_FALSE; + if(length+1 > box->dis_length) return RT_FALSE;
+ + if(box->position <= length-1) + { + char* c; + + for(c = &box->text[length]; c != &box->text[box->position]; c--) + *c = *(c-1); + box->text[length+1] = '\0'; + }
+ + box->text[box->position] = ekbd->key;
+ box->position ++;
+
+ if(box->on_change)box->on_change(box,RT_NULL); + } + }
+
+_exit: + //�ı���λ��,�����һ��λ����ʾ�˱༭����,�����֮. + if(box->flag & RTGUI_TEXTBOX_CARET_SHOW)
+ {
+ rtgui_timer_stop(box->caret_timer);
+
+ box->flag &= ~RTGUI_TEXTBOX_CARET_SHOW;
+ rtgui_textbox_draw_caret(box, posbak);//��ˢ��һ�±༭����,�������ʾ״̬
+
+ rtgui_timer_start(box->caret_timer);
+ }
+ /* set widget focus */ + rtgui_widget_focus(box); + /* set caret to show */ + box->flag |= RTGUI_TEXTBOX_CARET_SHOW;
+ /* re-draw text box */ + rtgui_theme_draw_textbox(box); + /* draw caret ���Ʊ༭���� */ + rtgui_textbox_draw_caret(box,box->position);
+ + return RT_TRUE; +} + +static rt_bool_t rtgui_textbox_onfocus(PVOID wdt, rtgui_event_t* event) +{ + rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ rtgui_textbox_t* box = (rtgui_textbox_t*)widget; + + /* set caret to show */ + box->flag |= RTGUI_TEXTBOX_CARET_SHOW;//�༭���� + /* start caret timer */ + rtgui_timer_start(box->caret_timer); + + return RT_TRUE; +} + +static rt_bool_t rtgui_textbox_onunfocus(PVOID wdt, rtgui_event_t* event) +{ + rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ rtgui_textbox_t* box = (rtgui_textbox_t*)widget; + + /* stop caret timer */ + rtgui_timer_stop(box->caret_timer);
+ + /* set caret to hide */ + box->flag &= ~RTGUI_TEXTBOX_CARET_SHOW;
+ rtgui_textbox_draw_caret(box,box->position);
+
+ if(box->on_enter)box->on_enter(box,event);
+
+ rtgui_theme_draw_textbox(box);
+ + return RT_TRUE; +} + +rt_bool_t rtgui_textbox_event_handler(PVOID wdt, rtgui_event_t* event) +{ + rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ rtgui_textbox_t* box = (rtgui_textbox_t*)widget; + + switch (event->type) + { + case RTGUI_EVENT_PAINT: + if(widget->on_draw != RT_NULL) widget->on_draw(widget, event); + else + rtgui_theme_draw_textbox(box); + break; + + case RTGUI_EVENT_MOUSE_BUTTON: + if(widget->on_mouseclick != RT_NULL) widget->on_mouseclick(widget, event); + else + rtgui_textbox_onmouse(box, (rtgui_event_mouse_t*)event); + return RT_TRUE; + + case RTGUI_EVENT_KBD: + if(widget->on_key != RT_NULL)
+ widget->on_key(widget, event); + + return RT_TRUE;
+ default:
+ return rtgui_widget_event_handler(widget,event);
+ + } + + return RT_FALSE; +} + +rtgui_textbox_t* rtgui_textbox_create(PVOID parent,const char* text,int left,int top,int w,int h, rt_uint32_t flag) +{ + rtgui_textbox_t* box;
+ + RT_ASSERT(parent != RT_NULL);
+ + box = rtgui_widget_create(RTGUI_TEXTBOX_TYPE); + if(box != RT_NULL) + { + rtgui_rect_t rect;
+ rtgui_widget_get_rect(parent, &rect);
+ rtgui_widget_rect_to_device(parent,&rect);
+ rect.x1 += left;
+ rect.y1 += top;
+ rect.x2 = rect.x1+w;
+ rect.y2 = rect.y1+h;
+ rtgui_widget_set_rect(box,&rect);
+
+ /* allocate default line buffer */ + rtgui_textbox_set_value(box, text);
+ + box->flag = flag;
+ //�趨����ʾ�ַ�����
+ box->dis_length = (w-5)/rtgui_font_get_font_width(RTGUI_WIDGET_FONT(box));
+
+ rtgui_container_add_child(parent, box); + } + + return box; +} + +void rtgui_textbox_destroy(rtgui_textbox_t* box) +{ + rtgui_widget_destroy(box); +}
+ +//��һ���ı���������һ��textbox�ؼ�
+void rtgui_textbox_set_value(rtgui_textbox_t* box, const char* text) +{ + if(box->text != RT_NULL) + {//�Ѿ������� + /* free the old text */ + rt_free(box->text); + box->text = RT_NULL; + }
+ + //ԭ��û������ + box->line_length = ((rt_strlen(text)+1)/RTGUI_TEXTBOX_LINE_MAX+1)*RTGUI_TEXTBOX_LINE_MAX; + + /* allocate line buffer */ + box->text = rt_malloc(box->line_length); + rt_memset(box->text, 0, box->line_length); + + /* copy text */ + rt_memcpy(box->text, text, rt_strlen(text) + 1); + + /* set current position */ + box->position = rt_strlen(text); +} + +const char* rtgui_textbox_get_value(rtgui_textbox_t* box) +{ + return (const char*)box->text; +} + +void rtgui_textbox_set_line_length(rtgui_textbox_t* box, rt_size_t length) +{ + rt_uint8_t* new_line; + + RT_ASSERT(box != RT_NULL); + + /* invalid length */ + if(length <= 0) return; + + new_line = rt_malloc(length); + if(length < box->line_length) + { + rt_memcpy(new_line, box->text, length - 1); + new_line[length] = '\0'; + } + else + { + rt_memcpy(new_line, (const char*)box->text, rt_strlen((const char*)box->text)); + } + + /* set line length */ + box->line_length = length; +}
+ +//ȡ��textbox�ؼ����ı���ʾ����
+void rtgui_textbox_get_edit_rect(rtgui_textbox_t *box,rtgui_rect_t *rect)
+{
+ rtgui_widget_get_rect(box, rect);
+ rtgui_rect_inflate(rect,-1);
+}
+
+ diff --git a/components/rtgui_win/widgets/view.c b/components/rtgui_win/widgets/view.c new file mode 100644 index 0000000000..2b4d529feb --- /dev/null +++ b/components/rtgui_win/widgets/view.c @@ -0,0 +1,193 @@ +/*
+ * File : view.c
+ * This file is part of RT-Thread RTOS
+ * COPYRIGHT (C) 2006 - 2009, RT-Thread Development Team
+ *
+ * The license and distribution terms for this file may be
+ * found in the file LICENSE in this distribution or at
+ * http://www.rt-thread.org/license/LICENSE
+ *
+ * Change Logs:
+ * Date Author Notes
+ * 2009-10-16 Bernard first version
+ */
+#include <rtgui/dc.h>
+#include <rtgui/rtgui_system.h>
+#include <rtgui/widgets/view.h>
+ +static void _rtgui_view_constructor(rtgui_view_t *view)
+{
+ /* init view */
+ rtgui_widget_set_event_handler(view,rtgui_view_event_handler);
+
+ RTGUI_WIDGET_BORDER_STYLE(view) = RTGUI_BORDER_NONE;
+ view->title = RT_NULL;
+}
+
+static void _rtgui_view_destructor(rtgui_view_t *view)
+{
+ rt_free(view->title);
+}
+
+rtgui_type_t *rtgui_view_type_get(void)
+{
+ static rtgui_type_t *view_type = RT_NULL;
+
+ if(!view_type)
+ {
+ view_type = rtgui_type_create("view", RTGUI_CONTAINER_TYPE,
+ sizeof(rtgui_view_t),
+ RTGUI_CONSTRUCTOR(_rtgui_view_constructor),
+ RTGUI_DESTRUCTOR(_rtgui_view_destructor));
+ }
+
+ return view_type;
+}
+
+rtgui_view_t* rtgui_view_create(PVOID parent,const char* title,int left,int top,int w,int h)
+{
+ rtgui_view_t* view;
+
+ RT_ASSERT(parent != RT_NULL);
+
+ /* allocate view */
+ view = rtgui_widget_create (RTGUI_VIEW_TYPE);
+ if(view != RT_NULL)
+ {
+ rtgui_rect_t rect;
+ rtgui_widget_get_rect(parent,&rect);
+ rtgui_widget_rect_to_device(parent, &rect);
+ rect.x1 += left;
+ rect.y1 += top;
+ rect.x2 = rect.x1+w;
+ rect.y2 = rect.y1+h;
+ rtgui_widget_set_rect(view,&rect);
+
+ if(title != RT_NULL)
+ view->title = rt_strdup(title);
+
+ rtgui_container_add_child(parent, view);
+ }
+
+ return view;
+}
+
+void rtgui_view_destroy(rtgui_view_t* view)
+{
+ rtgui_widget_destroy(view);
+}
+
+rt_bool_t rtgui_view_event_handler(PVOID wdt, rtgui_event_t* event)
+{
+ rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ rtgui_view_t* view = (rtgui_view_t*) widget;
+
+ RT_ASSERT(wdt != RT_NULL);
+
+ switch (event->type)
+ {
+ case RTGUI_EVENT_PAINT:
+ if(widget->on_draw != RT_NULL)
+ widget->on_draw(widget, event);
+ else
+ {
+ rtgui_rect_t rect;
+ rtgui_dc_t* dc;
+
+ /* begin drawing */
+ dc = rtgui_dc_begin_drawing(view);
+ if(dc == RT_NULL)return RT_FALSE;
+
+ rtgui_widget_get_rect(view, &rect);
+ /* fill view with background */
+ rtgui_dc_fill_rect(dc, &rect);
+
+ if(RTGUI_WIDGET_BORDER(view)>0)
+ rtgui_dc_draw_border(dc,&rect,RTGUI_WIDGET_BORDER_STYLE(view));
+
+ rtgui_dc_end_drawing(dc);
+
+ /* paint on each child */
+ rtgui_container_dispatch_event(RTGUI_CONTAINER(view), event);
+ }
+ break;
+
+ default:
+ return rtgui_container_event_handler(widget, event);
+ }
+
+ return RT_FALSE;
+}
+
+rt_bool_t rtgui_view_show(rtgui_view_t* view)
+{
+ /* parameter check */
+ if(view == RT_NULL) return RT_FALSE;
+
+ //�þ���ں���
+ rtgui_widget_show(view);
+
+ /* no modal mode, always return modal_ok */
+ return RT_TRUE;
+}
+
+ +void rtgui_view_hide(rtgui_view_t* view)
+{
+ if(view == RT_NULL) return;
+
+ if(RTGUI_WIDGET_PARENT(view) == RT_NULL)
+ {
+ RTGUI_WIDGET_HIDE(view);
+ return;
+ }
+
+ rtgui_widget_hide(view);
+}
+
+char* rtgui_view_get_title(rtgui_view_t* view)
+{
+ RT_ASSERT(view != RT_NULL);
+
+ return view->title;
+}
+
+void rtgui_view_set_title(rtgui_view_t* view, const char *title)
+{
+ RT_ASSERT(view != RT_NULL);
+
+ rt_free(view->title);
+
+ if(title != RT_NULL)
+ view->title = rt_strdup(title);
+ else
+ view->title = RT_NULL;
+}
+
+//��ʾһ����ͼ��ָ�����Ƶ�����ͼ
+void rtgui_view_show_child(PVOID wdt,const char* name)
+{
+ rtgui_list_t* node;
+ rtgui_container_t *container = (rtgui_container_t*)wdt;
+ + rtgui_list_foreach(node, &(container->children)) + { + rtgui_widget_t* child = rtgui_list_entry(node, rtgui_widget_t, sibling);
+ if(RTGUI_IS_VIEW(child))
+ {
+ if(strcmp(RTGUI_VIEW(child)->title,name)==0)
+ {
+ RTGUI_WIDGET_UNHIDE(child);
+ }
+ else
+ {
+ RTGUI_WIDGET_HIDE(child);
+ }
+ } + }
+ rtgui_widget_update_clip(wdt);
+ rtgui_widget_update(wdt);
+}
+
+
+
diff --git a/components/rtgui_win/widgets/widget.c b/components/rtgui_win/widgets/widget.c new file mode 100644 index 0000000000..e8556cebfe --- /dev/null +++ b/components/rtgui_win/widgets/widget.c @@ -0,0 +1,757 @@ +/* + * File : widget.c + * This file is part of RTGUI in RT-Thread RTOS + * COPYRIGHT (C) 2006 - 2009, RT-Thread Development Team + * + * The license and distribution terms for this file may be + * found in the file LICENSE in this distribution or at + * http://www.rt-thread.org/license/LICENSE + * + * Change Logs: + * Date Author Notes + * 2009-10-04 Bernard first version + */ +#include <rtgui/dc_client.h>
+#include <rtgui/widgets/widget.h>
+#include <rtgui/widgets/label.h> +#include <rtgui/widgets/window.h>
+#include <rtgui/widgets/combobox.h> +#include <rtgui/widgets/view.h>
+#include <rtgui/widgets/listbox.h>
+#include <panel.h>
+#include <rtgui/dc.h>
+#include <topwin.h>
+ + +static void _rtgui_widget_constructor(PVOID wdt) +{ + rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ if(!widget) return; + + /* set default flag */ + widget->flag = RTGUI_WIDGET_FLAG_DEFAULT; + + /* init list */ + rtgui_list_init(&(widget->sibling)); + + /* init gc */ + widget->gc.foreground = default_foreground; + widget->gc.background = default_background; + widget->gc.font = rtgui_font_default();
+ widget->gc.textstyle = RTGUI_TEXTSTYLE_NORMAL; + widget->gc.textalign = RTGUI_ALIGN_CENTER_HORIZONTAL|RTGUI_ALIGN_CENTER_VERTICAL;
+#ifndef RTGUI_USING_SMALL_SIZE
+ widget->align = RTGUI_ALIGN_CENTER_VERTICAL;
+#endif
+ rtgui_widget_set_style(widget,RTGUI_BORDER_SUNKEN);
+ + widget->tab_index = 0;
+ widget->tab_stop = RT_FALSE; + /* set parent and toplevel */ + widget->parent = RT_NULL; + widget->toplevel = RT_NULL;
+ + /* some common event handler */ + widget->on_focus_in = RT_NULL; + widget->on_focus_out = RT_NULL; + widget->on_draw = RT_NULL; + widget->on_mouseclick = RT_NULL; + widget->on_key = RT_NULL; + widget->on_size = RT_NULL; + widget->on_command = RT_NULL;
+ + /* set default event handler */ + rtgui_widget_set_event_handler(widget,rtgui_widget_event_handler);
+ + /* init user data private to 0 */ + widget->user_data = 0;
+ + /* init clip information */ + rtgui_region_init(&(widget->clip));
+
+ /* init hardware dc */ + rtgui_dc_client_init(widget); +} + +/* Destroys the widget */ +static void _rtgui_widget_destructor(PVOID wdt) +{ + rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ if(widget == RT_NULL) return; + + if(widget->parent != RT_NULL) + { + /* remove widget from parent's child list */ + rtgui_list_remove(&(RTGUI_CONTAINER(widget->parent)->children), &(widget->sibling)); + + widget->parent = RT_NULL; + } + + /* fini clip region */ + rtgui_region_fini(&(widget->clip)); +} + +rtgui_type_t *rtgui_widget_type_get(void) +{ + static rtgui_type_t *widget_type = RT_NULL; + + if(!widget_type) + { + widget_type = rtgui_type_create("rtgui_widget", RTGUI_OBJECT_TYPE, + sizeof(rtgui_widget_t),
+ RTGUI_CONSTRUCTOR(_rtgui_widget_constructor), + RTGUI_DESTRUCTOR(_rtgui_widget_destructor)); + } + + return widget_type; +} + +PVOID rtgui_widget_create(rtgui_type_t *widget_type) +{ + PVOID widget; + + widget = rtgui_object_create(widget_type); + + return widget; +} + +void rtgui_widget_destroy(PVOID wdt) +{ + rtgui_object_destroy(RTGUI_OBJECT(wdt)); +}
+ +void rtgui_widget_set_rect(PVOID wht, rtgui_rect_t* rect) +{ + rtgui_widget_t *widget = (rtgui_widget_t*)wht;
+ if(widget == RT_NULL || rect == RT_NULL) return; + + widget->extent = *rect; + + /* it's not empty, fini it */ + if(rtgui_region_not_empty(&(widget->clip))) + { + rtgui_region_fini(&(widget->clip)); + } + + /* reset clip info */ + rtgui_region_init_with_extents(&(widget->clip), rect);
+ if((widget->parent != RT_NULL) && (widget->toplevel != RT_NULL)) + { + /* update widget clip */ + rtgui_widget_update_clip(widget->parent); + } +} + +//���ÿؼ��������ʽ
+void rtgui_widget_set_style(PVOID wdt, rt_uint32_t style)
+{
+ rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ RT_ASSERT(widget != RT_NULL);
+
+ widget->border_style = style;
+ switch(style)
+ {
+ case RTGUI_BORDER_NONE:
+ widget->border = 0;
+ break;
+
+ case RTGUI_BORDER_STATIC: + case RTGUI_BORDER_SIMPLE:
+ case RTGUI_BORDER_UP: + case RTGUI_BORDER_DOWN:
+ widget->border = 1;
+ break;
+
+ case RTGUI_BORDER_RAISE: + case RTGUI_BORDER_SUNKEN: + case RTGUI_BORDER_BOX: + case RTGUI_BORDER_EXTRA:
+ widget->border = 2; + break; + + default:
+ widget->border = 2; + break;
+ }
+}
+ +/* + * ��������ƶ��ؼ��������ӿؼ���һ������ + */ +void rtgui_widget_move_to_logic(PVOID wdt, int dx, int dy) +{ + rtgui_list_t* node; + rtgui_widget_t* child;
+ rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ + if(widget == RT_NULL) return; + + rtgui_rect_moveto(&(widget->extent), dx, dy); + + /* move each child */ + if(RTGUI_IS_CONTAINER(widget)) + { + rtgui_list_foreach(node, &(RTGUI_CONTAINER(widget)->children)) + { + child = rtgui_list_entry(node, rtgui_widget_t, sibling); + rtgui_widget_move_to_logic(child, dx, dy); + } + } +} + +void rtgui_widget_set_event_handler(PVOID wdt, rtgui_event_handler_ptr handler) +{ + rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ RT_ASSERT(widget != RT_NULL); + + RTGUI_WIDGET_EVENT_HANDLE(widget) = handler; +} +//���ؾ��������rect���� +void rtgui_widget_get_rect(PVOID wdt, rtgui_rect_t *rect) +{ + rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ RT_ASSERT(widget != RT_NULL);
+
+ if (rect != RT_NULL) + { + rect->x1 = rect->y1 = 0; + rect->x2 = widget->extent.x2 - widget->extent.x1; + rect->y2 = widget->extent.y2 - widget->extent.y1; + } +}
+
+void rtgui_widget_get_position(PVOID wdt, rtgui_point_t *p)
+{
+ rtgui_rect_t rect,parent_rect;
+ RT_ASSERT(wdt != RT_NULL && RTGUI_WIDGET_PARENT(wdt) != RT_NULL);
+
+ rtgui_widget_get_rect(wdt, &rect);
+ rtgui_widget_rect_to_device(wdt,&rect);
+ rtgui_widget_get_rect(RTGUI_WIDGET_PARENT(wdt), &parent_rect);
+ rtgui_widget_rect_to_device(RTGUI_WIDGET_PARENT(wdt),&parent_rect);
+
+ p->x = rect.x1 - parent_rect.x1;
+ p->y = rect.y1 - parent_rect.y1;
+}
+ +rt_uint16_t rtgui_widget_get_width(PVOID wdt)
+{
+ rtgui_rect_t rect={0};
+ RT_ASSERT(wdt != RT_NULL);
+
+ rtgui_widget_get_rect(wdt, &rect);
+ return rtgui_rect_width(rect);
+}
+
+rt_uint16_t rtgui_widget_get_height(PVOID wdt)
+{
+ rtgui_rect_t rect={0};
+ RT_ASSERT(wdt != RT_NULL);
+
+ rtgui_widget_get_rect(wdt, &rect);
+ return rtgui_rect_height(rect);
+}
+ +void rtgui_widget_set_onfocus(PVOID wdt, rtgui_event_handler_ptr handler) +{ + rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ RT_ASSERT(widget != RT_NULL); + + widget->on_focus_in = handler; +} + +void rtgui_widget_set_onunfocus(PVOID wdt, rtgui_event_handler_ptr handler) +{ + rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ RT_ASSERT(widget != RT_NULL); + + widget->on_focus_out = handler; +} + +void rtgui_widget_set_ondraw(PVOID wdt, rtgui_event_handler_ptr handler) +{ + rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ RT_ASSERT(widget != RT_NULL); + + widget->on_draw = handler; +} + +void rtgui_widget_set_onmouseclick(PVOID wdt, rtgui_event_handler_ptr handler) +{ + rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ RT_ASSERT(widget != RT_NULL); + + widget->on_mouseclick = handler; +} + +void rtgui_widget_set_onkey(PVOID wdt, rtgui_event_handler_ptr handler) +{ + rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ RT_ASSERT(widget != RT_NULL); + + widget->on_key = handler; +} + +void rtgui_widget_set_onsize(PVOID wdt, rtgui_event_handler_ptr handler) +{ + rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ RT_ASSERT(widget != RT_NULL); + + widget->on_size = handler; +} + +void rtgui_widget_set_oncommand(PVOID wdt, rtgui_event_handler_ptr handler) +{ + rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ RT_ASSERT(widget != RT_NULL); + + widget->on_command = handler; +}
+
+/**
+ * find wdt's toplevel widget and return toplevel focused
+ */
+PVOID rtgui_widget_get_focus(PVOID wdt)
+{
+ rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ rtgui_widget_t *top;
+
+ if(widget == RT_NULL)return RT_NULL;
+
+ top = rtgui_widget_get_toplevel(widget);
+
+ if(RTGUI_IS_CONTAINER(top))
+ return RTGUI_CONTAINER(top)->focused;
+
+ return RT_NULL;
+}
+ +/** + * @brief Focuses the widget. The focused widget is the widget which can receive the keyboard events + * @param widget a widget + * @note The widget has to be attached to a top widget, otherwise it will have no effect + */ +void rtgui_widget_focus(PVOID wdt) +{ + rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ rtgui_container_t *parent;
+ + if(widget == RT_NULL)return;
+
+ if(!widget->parent || !widget->toplevel) return;
+ if(!RTGUI_WIDGET_IS_FOCUSABLE(widget) || !RTGUI_WIDGET_IS_ENABLE(widget))
+ return;
+
+ /* set widget as focused */
+ widget->flag |= RTGUI_WIDGET_FLAG_FOCUS;
+
+ /* ȡ�þɵĸ��ؼ��ͽ���ؼ� */
+ parent = RTGUI_CONTAINER(widget->toplevel);
+ if(parent->focused == widget) return; /* it's the same focused widget */
+
+ /* unfocused the old widget */
+ if((parent->focused != RT_NULL) && !RTGUI_IS_WIN(parent->focused))
+ rtgui_widget_unfocus(parent->focused);
+
+ /* set widget as focused widget in parent link */
+ parent = RTGUI_CONTAINER(widget->parent);
+ do
+ {
+ parent->focused = widget;
+ parent = RTGUI_CONTAINER(RTGUI_WIDGET_PARENT(parent));
+ } while((parent != RT_NULL) && !RTGUI_WIDGET_IS_HIDE(parent));
+
+ /* invoke on focus in call back */
+ if(widget->on_focus_in != RT_NULL)
+ widget->on_focus_in(widget, RT_NULL); +}
+ +/** + * @brief Unfocused the widget + * @param widget a widget + */ +void rtgui_widget_unfocus(PVOID wdt) +{ + rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ if(widget == RT_NULL)return; + + if(!widget->toplevel || !RTGUI_WIDGET_IS_FOCUSED(widget)) + return; + + widget->flag &= ~RTGUI_WIDGET_FLAG_FOCUS;
+ + if(widget->on_focus_out != RT_NULL) + widget->on_focus_out(widget, RT_NULL);
+
+ if(RTGUI_IS_CONTAINER(widget))
+ {
+ rtgui_list_t *node;
+ rtgui_list_foreach(node,&(RTGUI_CONTAINER(widget)->children))
+ {
+ rtgui_widget_t *child = rtgui_list_entry(node, rtgui_widget_t, sibling);
+ if(RTGUI_WIDGET_IS_HIDE(child))continue;
+ rtgui_widget_unfocus(child);
+ }
+ }
+
+ /* refresh widget ˢ�¿ؼ� */ + //rtgui_widget_update(widget);//Ҫ��ȥ�þ�,�����ظ�ˢ�� +} + +void rtgui_widget_point_to_device(PVOID wdt, rtgui_point_t* point) +{ + rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ RT_ASSERT(widget != RT_NULL); + + if(point != RT_NULL) + { + point->x += widget->extent.x1; + point->y += widget->extent.y1; + } +} + +void rtgui_widget_rect_to_device(PVOID wdt, rtgui_rect_t* rect) +{ + rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ RT_ASSERT(widget != RT_NULL); + + if(rect != RT_NULL) + { + rect->x1 += widget->extent.x1; + rect->x2 += widget->extent.x1; + + rect->y1 += widget->extent.y1; + rect->y2 += widget->extent.y1; + } +} + +void rtgui_widget_point_to_logic(PVOID wdt, rtgui_point_t* point) +{
+ rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ RT_ASSERT(widget != RT_NULL); + + if(point != RT_NULL) + { + point->x -= widget->extent.x1; + point->y -= widget->extent.y1; + } +} + +void rtgui_widget_rect_to_logic(PVOID wdt, rtgui_rect_t* rect) +{ + rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ RT_ASSERT(widget != RT_NULL); + + if(rect != RT_NULL) + { + rect->x1 -= widget->extent.x1; + rect->x2 -= widget->extent.x1; + + rect->y1 -= widget->extent.y1; + rect->y2 -= widget->extent.y1; + } +} + +PVOID rtgui_widget_get_toplevel(PVOID wdt) +{ + rtgui_widget_t *top;
+ rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ + RT_ASSERT(widget != RT_NULL); + + if(widget->toplevel)
+ return (PVOID)(widget->toplevel); + + top = widget; + /* get the top widget */ + while(top->parent != RT_NULL) top = top->parent; + + /* set top */ + widget->toplevel = top; + + return top; +} + +rt_bool_t rtgui_widget_event_handler(PVOID wdt, rtgui_event_t* event) +{
+ rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ + switch (event->type) + { + case RTGUI_EVENT_PAINT: + if(widget->on_draw != RT_NULL) return widget->on_draw(widget, event); + break; + + case RTGUI_EVENT_KBD: + if(widget->on_key != RT_NULL) return widget->on_key(widget, event); + break; + + case RTGUI_EVENT_MOUSE_BUTTON: + if(widget->on_mouseclick != RT_NULL) return widget->on_mouseclick(widget, event); + break; + + case RTGUI_EVENT_COMMAND: + if(widget->on_command != RT_NULL) return widget->on_command(widget, event); + break; + + case RTGUI_EVENT_RESIZE: + if(widget->on_size != RT_NULL) return widget->on_size(widget, event); + break; + } + + return RT_FALSE; +}
+ +/* + * This function updates the clip info of widget + */ +void rtgui_widget_update_clip(PVOID wdt) +{ + rtgui_list_t *node; + rtgui_widget_t *parent;
+ rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ + /* no widget or widget is hide, no update clip */ + if(widget == RT_NULL || RTGUI_WIDGET_IS_HIDE(widget)) return; + + parent = widget->parent;
+ + /* if there is no parent, do not update clip (please use toplevel widget API) */ + if(parent == RT_NULL)
+ {
+ rtgui_panel_t *panel = rtgui_panel_get();
+ rtgui_panel_update_clip(panel);
+ return;
+ } + + /* reset clip to extent */ + rtgui_region_reset(&(widget->clip), &(widget->extent));
+
+ /* limit widget extent in screen extent */
+ //rtgui_region_intersect(&(widget->clip), &(widget->clip), &(parent->clip));
+ { + rtgui_rect_t screen_rect;
+ rtgui_graphic_driver_get_rect(rtgui_graphic_driver_get_default(),&screen_rect);
+ //rtgui_region_intersect_rect(&(widget->clip), &(widget->clip), &(parent->clip.extents));
+ rtgui_region_intersect_rect(&(widget->clip), &(widget->clip), &screen_rect);
+ }
+
+ /* get the no transparent parent */
+ while (parent != RT_NULL && parent->flag & RTGUI_WIDGET_FLAG_TRANSPARENT) + { + parent = parent->parent; + }
+ + if (parent != RT_NULL) + {
+ /* subtract widget clip in parent clip */
+ if (!(widget->flag & RTGUI_WIDGET_FLAG_TRANSPARENT))
+ {
+ rtgui_region_subtract_rect(&(parent->clip), &(parent->clip),
+ &(widget->extent));
+ } + } + + /* + * note: since the layout widget introduction, the sibling widget will not + * intersect. + */ + + /* if it's a container object, update the clip info of children */ + if (RTGUI_IS_CONTAINER(widget)) + { + rtgui_widget_t* child;
+ rtgui_list_foreach(node, &(RTGUI_CONTAINER(widget)->children))
+ {
+ child = rtgui_list_entry(node, rtgui_widget_t, sibling);
+ if (RTGUI_WIDGET_IS_HIDE(child)) continue; + rtgui_widget_update_clip(child);
+ } + } +}
+
+/*
+ * ���¶���ؼ��ص�ʱ��clip�������,���ӿؼ�topwdt��Ϊ��˿ؼ�,
+ * �����ֵܿؼ�����Ӧ�ļ��е�topwdt����,ʹ���Ǵ�λ���ϱ�topwdt����
+ * ���øú���ʱ,Ӧ�ñ�֤topwdt�ؼ���wdt�ؼ��µ�һ���ӿؼ�.
+ */ +void rtgui_widget_update_clip_pirate(PVOID wdt,PVOID topwdt) +{ + rtgui_list_t *node;
+ rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ rtgui_rect_t wdt_rect;
+
+ if(widget == RT_NULL || RTGUI_WIDGET_IS_HIDE(widget)) return;
+
+ wdt_rect = widget->extent;
+
+ if(wdt == topwdt)
+ { /* the same as oneself */
+ rtgui_widget_update_clip(widget);
+ return;
+ }
+ else
+ { /* different widget */
+ if(rtgui_rect_is_intersect(&RTGUI_WIDGET_EXTENT(topwdt), &wdt_rect) == RT_EOK)
+ {
+ rtgui_rect_intersect(&RTGUI_WIDGET_EXTENT(topwdt), &wdt_rect);/* calculate overlap */
+ rtgui_region_reset(&(widget->clip), &(widget->extent));
+ rtgui_region_subtract_rect(&(widget->clip), &(widget->clip),&wdt_rect);/* subtract overlap area */
+ }
+ else
+ {
+ rtgui_region_reset(&(widget->clip), &(widget->extent));
+ }
+ }
+
+ { + rtgui_rect_t screen_rect;
+ rtgui_graphic_driver_get_rect(rtgui_graphic_driver_get_default(),&screen_rect);
+ rtgui_region_intersect_rect(&(widget->clip), &(widget->clip), &screen_rect);
+ }
+ + if(RTGUI_IS_CONTAINER(widget))
+ { /* update all child widget */
+ rtgui_list_foreach(node, &(RTGUI_CONTAINER(widget)->children)) + { + rtgui_widget_t *child = rtgui_list_entry(node, rtgui_widget_t, sibling); + if(RTGUI_WIDGET_IS_HIDE(child))continue;
+ if(RTGUI_IS_WIN(child))continue; /* no dispose windows */
+ + rtgui_region_subtract_rect(&(widget->clip), &(widget->clip),&(child->extent));
+ rtgui_widget_update_clip_pirate(child,topwdt); + }
+ } +}
+ +void rtgui_widget_show(PVOID wdt) +{ + /* there is no parent or the parent is hide, no show at all */ + if(RTGUI_WIDGET_PARENT(wdt) == RT_NULL ||RTGUI_WIDGET_IS_HIDE(RTGUI_WIDGET_PARENT(wdt))) return; + + /* update the clip info of widget */ + RTGUI_WIDGET_UNHIDE(wdt); + rtgui_widget_update_clip(wdt); +} + +void rtgui_widget_hide(PVOID wdt) +{ + rtgui_rect_t rect; + rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ + /* hide this widget */ + RTGUI_WIDGET_HIDE(widget); + + if (widget->parent != RT_NULL) + { + int index; + rtgui_widget_t *parent; + + rect = widget->extent; + parent = widget->parent; + /* get the no transparent parent */ + while (parent != RT_NULL && parent->flag & RTGUI_WIDGET_FLAG_TRANSPARENT) + { + parent = parent->parent; + } + + /* union widget rect */ + rtgui_region_union_rect(&(widget->parent->clip), &(widget->parent->clip), &rect); + + /* subtract the external rect */ + for (index = 0; index < external_clip_size; index ++) + { + rtgui_region_subtract_rect(&(widget->parent->clip), &(widget->parent->clip), + &(external_clip_rect[index])); + } + } +} + +rtgui_color_t rtgui_widget_get_parent_foreground(PVOID wdt) +{ + rtgui_widget_t* parent;
+ rtgui_widget_t *widget = (rtgui_widget_t*)wdt; + + /* get parent widget */ + parent = widget->parent; + while (parent->parent != RT_NULL && (RTGUI_WIDGET_FLAG(parent) & RTGUI_WIDGET_FLAG_TRANSPARENT)) + parent = parent->parent; + + /* get parent's color */ + if (parent != RT_NULL) + return RTGUI_WIDGET_FOREGROUND(parent); + + return RTGUI_WIDGET_FOREGROUND(widget); +} + +rtgui_color_t rtgui_widget_get_parent_background(PVOID wdt) +{ + rtgui_widget_t* parent;
+ rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ + /* get parent widget */ + parent = widget->parent; + while (parent->parent != RT_NULL && (RTGUI_WIDGET_FLAG(parent) & RTGUI_WIDGET_FLAG_TRANSPARENT)) + parent = parent->parent; + + /* get parent's color */ + if (parent != RT_NULL) + return RTGUI_WIDGET_BACKGROUND(parent); + + return RTGUI_WIDGET_BACKGROUND(widget); +} + +void rtgui_widget_update(PVOID wdt) +{ + rtgui_event_paint_t paint;
+
+ if(RTGUI_WIDGET_IS_HIDE(wdt)) return;
+ + RTGUI_EVENT_PAINT_INIT(&paint); + paint.wid = RT_NULL; + + RT_ASSERT(wdt != RT_NULL); + + if(RTGUI_WIDGET_EVENT_HANDLE(wdt) != RT_NULL) + { + RTGUI_WIDGET_EVENT_CALL(wdt, &paint.parent); + } +}
+ +//�����һ���ֵܿؼ� +rtgui_widget_t* rtgui_widget_get_next_sibling(PVOID wdt) +{ + rtgui_widget_t* sibling = RT_NULL;
+ rtgui_widget_t* widget = wdt;
+ + if(widget->sibling.next != RT_NULL) + { + sibling = rtgui_list_entry(widget->sibling.next, rtgui_widget_t, sibling); + } + + return sibling; +}
+ +//�����һ���ֵܿؼ� +rtgui_widget_t* rtgui_widget_get_prev_sibling(PVOID wdt) +{ + rtgui_list_t* node; + rtgui_widget_t *sibling, *parent;
+ rtgui_widget_t *widget = (rtgui_widget_t*)wdt; + + node = RT_NULL; sibling = RT_NULL; + parent = widget->parent; + if(parent != RT_NULL) + { + rtgui_list_foreach(node, &(RTGUI_CONTAINER(parent)->children)) + { + if(node->next == &(widget->sibling)) + break; + } + } + + if(node != RT_NULL) + sibling = rtgui_list_entry(node, rtgui_widget_t, sibling); + + return sibling; +} diff --git a/components/rtgui_win/widgets/window.c b/components/rtgui_win/widgets/window.c new file mode 100644 index 0000000000..4a11c1e5b0 --- /dev/null +++ b/components/rtgui_win/widgets/window.c @@ -0,0 +1,726 @@ +/*
+ * File : window.c
+ * This file is part of RTGUI in RT-Thread RTOS
+ * COPYRIGHT (C) 2006 - 2009, RT-Thread Development Team
+ *
+ * The license and distribution terms for this file may be
+ * found in the file LICENSE in this distribution or at
+ * http://www.rt-thread.org/license/LICENSE
+ *
+ * Change Logs:
+ * Date Author Notes
+ * 2009-10-04 Bernard first version
+ */
+#include <rtgui/dc.h>
+#include <rtgui/color.h>
+#include <rtgui/image.h>
+#include <rtgui/rtgui_system.h>
+#include <panel.h>
+#include <rtgui/widgets/window.h>
+#include <rtgui/widgets/button.h>
+#include <rtgui/rtgui_theme.h>
+
+
+static void _rtgui_win_constructor(rtgui_win_t *win)
+{
+ /* init window attribute */
+ win->title = RT_NULL;
+ win->on_activate = RT_NULL;
+ win->on_deactivate = RT_NULL;
+ win->on_close = RT_NULL;
+
+ win->modal_widget = RT_NULL;
+ win->tid = RT_NULL;
+
+ /* set window hide */
+ RTGUI_WIDGET_HIDE(win);
+
+ RTGUI_WIDGET_FLAG(win) |= RTGUI_WIDGET_FLAG_FOCUSABLE; + RTGUI_WIDGET_BACKGROUND(win) = default_background;
+
+ /* set window status and style */
+ win->status = 0;
+ win->style = RTGUI_WIN_DEFAULT;
+ rtgui_widget_set_event_handler(win, rtgui_win_event_handler);
+
+ /* init user data */
+ win->user_data = RT_NULL;
+}
+
+static void _rtgui_win_destructor(rtgui_win_t* win)
+{
+ rtgui_event_win_t ewin;
+
+ /* remove win from box */
+ if(RTGUI_WIDGET_PARENT(win) != RT_NULL)
+ {
+ rtgui_container_t *box;
+
+ box = RTGUI_CONTAINER(RTGUI_WIDGET_PARENT(win));
+ rtgui_container_remove_child(box, win);
+ }
+
+ /* destroy in server */
+ RTGUI_EVENT_WIN_DESTROY_INIT(&ewin);
+ ewin.wid = win;
+ if(rtgui_thread_send_sync(rtgui_thread_get_server(), RTGUI_EVENT(&ewin),sizeof(rtgui_event_win_t)) != RT_EOK)
+ {
+ return; /* destroy in server failed */
+ }
+
+ /* release field */
+ rt_free(win->title);
+}
+
+rtgui_type_t *rtgui_win_type_get(void)
+{
+ static rtgui_type_t *win_type = RT_NULL;
+
+ if(!win_type)
+ {
+ win_type = rtgui_type_create("win", RTGUI_CONTAINER_TYPE,
+ sizeof(rtgui_win_t),
+ RTGUI_CONSTRUCTOR(_rtgui_win_constructor),
+ RTGUI_DESTRUCTOR(_rtgui_win_destructor));
+ }
+
+ return win_type;
+}
+
+rtgui_win_t* rtgui_win_create(PVOID parent, const char* title, rtgui_rect_t *rect, rt_uint32_t style)
+{
+ rtgui_win_t* win;
+ //ȡ��GUI�������߳�
+ struct rt_thread* server = rtgui_thread_get_server();
+ rtgui_thread_t* thread;
+
+ if(parent == RT_NULL) parent = RTGUI_CONTAINER(rtgui_panel_get());
+
+ RT_ASSERT(parent != RT_NULL);
+ if(server == RT_NULL) return RT_NULL;
+
+ win = rtgui_widget_create(RTGUI_WIN_TYPE);
+
+ if(win != RT_NULL)
+ {//������ʽ,����һЩ�ߴ����
+ /* set window title */
+ if(title != RT_NULL)
+ win->title = rt_strdup(title);
+ else
+ win->title = RT_NULL;
+
+ win->style = style;
+
+ //����Ĭ�ϵijߴ����
+ win->title_height = RTGUI_WIN_TITLE_HEIGHT;
+ win->status_height= RTGUI_WIN_STATUS_HEIGHT;
+ win->menu_height = RTGUI_WIN_MENU_HEIGHT;
+ win->border_size = RTGUI_BORDER_DEFAULT_WIDTH;
+
+
+ RTGUI_WIDGET(win)->toplevel = RTGUI_WIDGET(win); //����������Ϊ�����ؼ�
+ /* set extent of win */
+ rtgui_widget_set_rect(win, rect);
+ rtgui_container_add_child(parent, win);
+
+ thread = rtgui_thread_self();
+ win->tid = thread->tid;//�����ڹ��ڵ�ǰ�߳���
+
+ rtgui_thread_set_widget(RTGUI_WIDGET(win));/* �������win����һ��thread */
+
+ {//����һ��������Ϣ
+ rtgui_event_win_t ewin;
+ RTGUI_EVENT_WIN_CREATE_INIT(&ewin);
+ ewin.wid = win;
+
+ if(rtgui_thread_send_sync(server, RTGUI_EVENT(&ewin),sizeof(rtgui_event_win_t)) != RT_EOK)
+ {
+ rt_kprintf("create win: %s failed\n", win->title);
+ return RT_FALSE;
+ }
+ }
+ }
+
+ return win;
+}
+
+void rtgui_win_destroy(rtgui_win_t* win)
+{
+ if(RTGUI_WIN_IS_MODAL_MODE(win))
+ {
+ /* end modal */
+ rtgui_win_end_modal(win);
+ }
+
+ rtgui_widget_destroy(win);
+}
+
+//��ÿؼ�����������
+rtgui_win_t* rtgui_win_get_win_by_widget(PVOID wdt)
+{
+ rtgui_widget_t *parent=(rtgui_widget_t*)wdt;
+
+ if(RTGUI_IS_WIN(parent))
+ return (rtgui_win_t*)parent;
+
+ while(parent->parent != RT_NULL)
+ {
+ if(RTGUI_IS_WIN(parent))break;
+ parent = parent->parent;
+ }
+ if(RTGUI_IS_WIN(parent))
+ return (rtgui_win_t*)parent;
+
+ return RT_NULL;
+}
+
+//���ڹر�ʱ���¼�����
+void rtgui_win_close(PVOID wdt, rtgui_event_t *event)
+{
+ rtgui_win_t* win = RT_NULL;
+
+ if(RTGUI_IS_WIN(wdt))
+ win = RTGUI_WIN(wdt);
+ else
+ win = rtgui_win_get_win_by_widget(wdt);
+
+ if(win != RT_NULL)
+ {
+ rtgui_panel_t *panel=rtgui_panel_get();
+ //�ô���״̬Ϊ�ر�״̬
+ win->status |= RTGUI_WIN_STATUS_CLOSED;
+ RTGUI_CONTAINER(panel)->focused = RT_NULL;
+
+ rtgui_win_destroy(win);
+ }
+}
+
+void rtgui_win_show(rtgui_win_t* win, rt_bool_t modal)
+{
+
+ RT_ASSERT(win != RT_NULL);
+
+ if(RTGUI_WIDGET_IS_HIDE(win))
+ {
+ /* send show message to server */
+ rtgui_event_win_t ewin;
+ RTGUI_EVENT_WIN_SHOW_INIT(&ewin);
+ ewin.wid = win;
+
+ if(rtgui_thread_send_sync(rtgui_thread_get_server(), RTGUI_EVENT(&ewin),sizeof(rtgui_event_win_t)) != RT_EOK)
+ {
+ return;
+ }
+ }
+ else rtgui_widget_update(win);
+
+ if(modal == RT_TRUE) + {//��ģʽ��ʽ��ʾ + rtgui_widget_t *parent_widget = RTGUI_WIDGET_PARENT(win);
+
+ if(parent_widget != RT_NULL) + { + /* set style */ + win->status |= RTGUI_WIN_STATUS_MODAL;
+ //win->modal_widget = win;//��ʱû��ָ��ģʽ�ؼ�,��ָ������ + + if(RTGUI_IS_PANEL(parent_widget)) + { + rtgui_panel_t* panel; + panel = RTGUI_PANEL(parent_widget); + panel->status |= RTGUI_PANEL_STATUS_MODAL; + panel->modal_widget = win; + } + else if(RTGUI_IS_WIN(parent_widget)) + { + rtgui_win_t* pwin; + pwin = RTGUI_WIN(parent_widget); + pwin->status |= RTGUI_WIN_STATUS_MODAL; + pwin->modal_widget = win; + } + } + else + { + /* which is a top window */ + win->status |= RTGUI_WIN_STATUS_MODAL; + rtgui_win_event_loop(win); + + win->status &= ~RTGUI_WIN_STATUS_MODAL; + } + }
+}
+
+void rtgui_win_end_modal(rtgui_win_t* win)
+{
+ rtgui_widget_t* parent_widget;
+
+ RT_ASSERT(win != RT_NULL);
+
+ parent_widget = RTGUI_WIDGET_PARENT(win);
+
+ if(parent_widget != RT_NULL)
+ {
+ if(RTGUI_IS_PANEL(parent_widget)) + { + rtgui_panel_t* panel; + + /* which is shown under workbench */ + panel = RTGUI_PANEL(parent_widget); + panel->status &= ~RTGUI_PANEL_STATUS_MODAL;
+ panel->modal_widget = RT_NULL; + } + else if(RTGUI_IS_WIN(parent_widget))
+ {
+ rtgui_win_t* pwin;
+
+ /* which is shown under win */
+ pwin = RTGUI_WIN(parent_widget);
+ pwin->status &= ~RTGUI_WIN_STATUS_MODAL;
+ pwin->modal_widget = RT_NULL;
+ }
+ }
+ else
+ {
+ /* which is a stand alone window */
+ }
+
+ /* remove modal mode */
+ win->status &= ~RTGUI_WIN_STATUS_MODAL;
+}
+
+void rtgui_win_hiden(rtgui_win_t* win)
+{
+ RT_ASSERT(win != RT_NULL);
+
+ if(!RTGUI_WIDGET_IS_HIDE(win) && rtgui_thread_get_server() != RT_NULL)
+ {
+ /* send hidden message to server */
+ rtgui_event_win_t ewin;
+ RTGUI_EVENT_WIN_HIDE_INIT(&ewin);
+ ewin.wid = win;
+
+ if(rtgui_thread_send_sync(rtgui_thread_get_server(), RTGUI_EVENT(&ewin),sizeof(rtgui_event_win_t)) != RT_EOK)
+ {
+ rt_kprintf("hide win: %s failed\n", win->title);
+ return;
+ }
+
+ /* set window hide and deactivated */
+ RTGUI_WIDGET_HIDE(win);
+ win->status &= ~RTGUI_WIN_STATUS_ACTIVATE;
+ }
+}
+
+rt_bool_t rtgui_win_is_activated(rtgui_win_t* win)
+{
+ RT_ASSERT(win != RT_NULL);
+
+ return win->status & RTGUI_WIN_STATUS_ACTIVATE;
+}
+
+void rtgui_win_move(rtgui_win_t* win, int x, int y)
+{
+ rtgui_event_win_move_t emove; + RTGUI_EVENT_WIN_MOVE_INIT(&emove); + + if (win == RT_NULL) return; + + /* set win hide firstly */ +// RTGUI_WIDGET_HIDE(RTGUI_WIDGET(win)); + + emove.wid = win; + emove.x = x; + emove.y = y; + if (rtgui_thread_send_sync(rtgui_thread_get_server(), RTGUI_EVENT(&emove),
+ sizeof(rtgui_event_win_move_t)) != RT_EOK) + { + return; + } + +// /* move window to logic position */ +// rtgui_widget_move_to_logic(win, +// x - RTGUI_WIDGET(win)->extent.x1, +// y - RTGUI_WIDGET(win)->extent.y1); +// +// /* set window visible */ +// RTGUI_WIDGET_UNHIDE(win); + return;
+
+}
+
+rt_bool_t rtgui_win_ondraw(rtgui_win_t* win)
+{
+ rtgui_event_paint_t event;
+
+ rtgui_theme_draw_win(win);
+
+ /* paint each widget */
+ RTGUI_EVENT_PAINT_INIT(&event);
+ event.wid = RT_NULL;
+ rtgui_container_dispatch_event(RTGUI_CONTAINER(win), (rtgui_event_t*)&event);
+
+ return RT_FALSE;
+}
+
+rt_bool_t rtgui_win_event_handler(PVOID wdt, rtgui_event_t* event)
+{
+ rtgui_widget_t *widget = (rtgui_widget_t*)wdt;
+ rtgui_win_t* win = (rtgui_win_t*)widget;
+
+ RT_ASSERT((win != RT_NULL) && (event != RT_NULL));
+
+ switch (event->type)
+ {
+ case RTGUI_EVENT_WIN_CLOSE:
+ if(win->on_close != RT_NULL)
+ {
+ if(win->on_close(widget, event) == RT_FALSE) return RT_TRUE;
+ }
+
+ if(RTGUI_WIN_IS_MODAL_MODE(win))
+ {
+ rtgui_win_destroy(win);
+ }
+ else
+ {
+ rtgui_win_close(win,RT_NULL);
+ }
+
+ /* exit event loop */
+ return RT_TRUE;
+
+ case RTGUI_EVENT_WIN_MAX: //�����
+ // TODO: Place code here.
+ break;
+
+ case RTGUI_EVENT_WIN_MIN: //��С������,(���ش���)
+ // TODO: Place code here.
+ break;
+
+ case RTGUI_EVENT_WIN_MOVE:
+ {
+ rtgui_event_win_move_t* emove = (rtgui_event_win_move_t*)event;
+ /* move window */
+ rtgui_win_move(win, emove->x, emove->y);
+ }
+ break;
+
+ case RTGUI_EVENT_WIN_ACTIVATE: + if(RTGUI_WIDGET_IS_HIDE(win)) + { + rt_kprintf("activate window, but window is hide!\n"); + } + + win->status |= RTGUI_WIN_STATUS_ACTIVATE;
+ + if(widget->on_draw != RT_NULL)
+ widget->on_draw(widget, event); + else + rtgui_widget_update(win); + + if (win->on_activate != RT_NULL) + { + win->on_activate(widget, event); + } + break; + + case RTGUI_EVENT_WIN_DEACTIVATE: + if(RTGUI_WIN_IS_MODAL_MODE(win)) + { + /* do not deactivate a modal win, re-send win-show event */ + rtgui_event_win_t eshow; + RTGUI_EVENT_WIN_SHOW_INIT(&eshow); + eshow.wid = win; + + rtgui_thread_send(rtgui_thread_get_server(), RTGUI_EVENT(&eshow),sizeof(rtgui_event_win_t)); + } + else + { + win->status &= ~RTGUI_WIN_STATUS_ACTIVATE; + + if(widget->on_draw != RT_NULL)
+ widget->on_draw(widget, event); + else + rtgui_win_ondraw(win); + + if (win->on_deactivate != RT_NULL) + { + win->on_deactivate(widget, event); + } + } + break;
+ case RTGUI_EVENT_PAINT:
+ if(widget->on_draw != RT_NULL) widget->on_draw(widget, event);
+ else
+ rtgui_win_ondraw(win);
+ break;
+
+ case RTGUI_EVENT_MOUSE_BUTTON:
+ if(RTGUI_WIN_IS_MODAL_MODE(win)) + { + if(win->modal_widget != RT_NULL) + return RTGUI_WIDGET_EVENT_CALL(win->modal_widget, event); + } +
+ if(rtgui_container_dispatch_mouse_event(RTGUI_CONTAINER(win),(rtgui_event_mouse_t*)event) == RT_FALSE)
+ {//�ɷ���Ϣ
+ if(widget->on_mouseclick != RT_NULL)
+ {
+ return widget->on_mouseclick(widget, event);
+ }
+ }
+ break;
+
+ case RTGUI_EVENT_MOUSE_MOTION:
+ if (RTGUI_WIN_IS_MODAL_MODE(win)) + { + if (win->modal_widget != RT_NULL) + return RTGUI_WIDGET_EVENT_CALL(win->modal_widget, event); + } +
+ rtgui_container_dispatch_mouse_event(RTGUI_CONTAINER(win),(rtgui_event_mouse_t*)event);
+ break;
+
+ case RTGUI_EVENT_KBD:
+ if(RTGUI_WIN_IS_MODAL_MODE(win))
+ {
+ if(win->modal_widget != RT_NULL) + return RTGUI_WIDGET_EVENT_CALL(win->modal_widget, event);
+ }
+
+ if(RTGUI_CONTAINER(win)->focused != widget)
+ {
+ RTGUI_WIDGET_EVENT_CALL(RTGUI_CONTAINER(win)->focused, event);
+ }
+ break;
+
+ default:
+ //call parent widget event
+ return rtgui_container_event_handler(wdt,event);
+ }
+
+ return RT_FALSE;
+}
+
+/* windows event loop */
+void rtgui_win_event_loop(rtgui_win_t* win)
+{
+ rt_err_t result;
+ rtgui_thread_t* tid;
+ rtgui_event_t* event;
+
+ tid = rtgui_thread_self();
+ RT_ASSERT(tid != RT_NULL);
+
+ /* point to event buffer */
+ event = (rtgui_event_t*)tid->event_buffer;
+
+ if(RTGUI_WIN_IS_MODAL_MODE(win))
+ {
+ while(RTGUI_WIN_IS_MODAL_MODE(win))
+ {
+ if (tid->on_idle != RT_NULL) + { + result = rtgui_thread_recv_nosuspend(event, RTGUI_EVENT_BUFFER_SIZE); + if (result == RT_EOK) + { + /* perform event handler */ + RTGUI_WIDGET_EVENT_CALL(win, event); + } + else if (result == -RT_ETIMEOUT) + { + tid->on_idle(win, RT_NULL); + } + }
+ else
+ {
+ result = rtgui_thread_recv(event, RTGUI_EVENT_BUFFER_SIZE); + if (result == RT_EOK) + { + /* perform event handler */ + RTGUI_WIDGET_EVENT_CALL(win, event); + }
+ }
+ }
+ }
+ else
+ {
+ while(!(win->status & RTGUI_WIN_STATUS_CLOSED))
+ {
+ if (tid->on_idle != RT_NULL) + { + result = rtgui_thread_recv_nosuspend(event, RTGUI_EVENT_BUFFER_SIZE); + if (result == RT_EOK) + { + /* perform event handler */ + RTGUI_WIDGET_EVENT_CALL(win, event); + } + else if (result == -RT_ETIMEOUT) + { + tid->on_idle(win, RT_NULL); + } + }
+ else
+ {
+ result = rtgui_thread_recv(event, RTGUI_EVENT_BUFFER_SIZE); + if (result == RT_EOK) + { + /* perform event handler */ + RTGUI_WIDGET_EVENT_CALL(win, event); + }
+ }
+ }
+ }
+}
+
+void rtgui_win_set_rect(rtgui_win_t* win, rtgui_rect_t* rect)
+{
+ rtgui_event_win_resize_t event;
+
+ if(win == RT_NULL || rect == RT_NULL) return;
+
+ RTGUI_WIDGET(win)->extent = *rect;
+
+ if(rtgui_thread_get_server() != RT_NULL)
+ {
+ /* set window resize event to server */
+ RTGUI_EVENT_WIN_RESIZE_INIT(&event);
+ event.wid = win;
+ event.rect = *rect;
+
+ rtgui_thread_send(rtgui_thread_get_server(), &(event.parent), sizeof(rtgui_event_win_resize_t));
+ }
+}
+
+void rtgui_win_set_onactivate(rtgui_win_t* win, rtgui_event_handler_ptr handler)
+{
+ if(win != RT_NULL)
+ {
+ win->on_activate = handler;
+ }
+}
+
+void rtgui_win_set_ondeactivate(rtgui_win_t* win, rtgui_event_handler_ptr handler)
+{
+ if(win != RT_NULL)
+ {
+ win->on_deactivate = handler;
+ }
+}
+
+void rtgui_win_set_onclose(rtgui_win_t* win, rtgui_event_handler_ptr handler)
+{
+ if(win != RT_NULL)
+ {
+ win->on_close = handler;
+ }
+}
+
+void rtgui_win_set_title(rtgui_win_t* win, const char *title)
+{
+ /* modify in local side */
+ rt_free(win->title);
+
+ if(title != RT_NULL)
+ win->title = rt_strdup(title);
+ else
+ win->title = RT_NULL;
+}
+
+char* rtgui_win_get_title(rtgui_win_t* win)
+{
+ RT_ASSERT(win != RT_NULL);
+
+ return win->title;
+}
+
+rtgui_point_t rtgui_win_get_client_zero(rtgui_win_t *win)
+{
+ rtgui_point_t p={0};
+ rtgui_rect_t r1,r2;
+
+ rtgui_win_get_client_rect(win, &r1);
+ rtgui_widget_get_rect(win, &r2);
+ p.x = r1.x1-r2.x1;
+ p.y = r1.y1-r2.y1;
+
+ return p;
+}
+
+//���ش��ڿͻ�������
+void rtgui_win_get_client_rect(rtgui_win_t *win, rtgui_rect_t *rect)
+{
+ rtgui_widget_get_rect(win, rect);
+
+ if(win->style & RTGUI_WIN_BORDER)
+ rtgui_rect_inflate(rect, -win->border_size);
+
+ if(win->style & RTGUI_WIN_TITLE)//�б��������ȥ�������ĸ߶�
+ rect->y1 += win->title_height;
+
+ if(win->style & RTGUI_WIN_MENU)
+ rect->y1 += win->menu_height;
+
+ if(win->style & RTGUI_WIN_STATUS)//��״̬�����ȥ״̬���ĸ߶�
+ rect->y2 -= win->status_height;
+
+}
+
+//���ش��ڵı���������
+void rtgui_win_get_title_rect(rtgui_win_t *win, rtgui_rect_t *rect)
+{
+ rtgui_widget_get_rect(win, rect);
+
+ if(win->style & RTGUI_WIN_TITLE)
+ {
+ if(win->style & RTGUI_WIN_BORDER)
+ {
+ rtgui_rect_inflate(rect, -win->border_size);
+ }
+ rect->y2 = rect->y1 + win->title_height;
+ }
+ else
+ {
+ rect->x1=rect->x2=rect->y1=rect->y2 = 0;
+ }
+}
+
+//���ش��ڵĹرհ�ť����
+void rtgui_win_get_closebox_rect(rtgui_win_t *win, rtgui_rect_t *rect)
+{
+ rtgui_win_get_title_rect(win,rect);
+ if(win->style & RTGUI_WIN_CLOSEBOX)
+ {
+ /* get close button rect (device value) */
+ rect->x2 = rect->x2 - 2;
+ rect->x1 = rect->x2 - RTGUI_WIN_CLOSEBOX_WIDTH;
+ rect->y1 = rect->y1 + (rtgui_rect_height(*rect)-RTGUI_WIN_CLOSEBOX_HEIGHT)/2;
+ rect->y2 = rect->y1 + RTGUI_WIN_CLOSEBOX_HEIGHT;
+ }
+}
+
+//���ش��ڵ����ť����
+void rtgui_win_get_maxbox_rect(rtgui_win_t *win, rtgui_rect_t *rect)
+{
+ rtgui_win_get_closebox_rect(win,rect);
+ if(win->style & RTGUI_WIN_CLOSEBOX)
+ {
+ rtgui_rect_moveto(rect,-2-RTGUI_WIN_CLOSEBOX_WIDTH,0);
+ }
+}
+
+//���ش��ڵ���С����ť����
+void rtgui_win_get_minbox_rect(rtgui_win_t *win, rtgui_rect_t *rect)
+{
+ rtgui_win_get_closebox_rect(win,rect);
+ if(win->style & RTGUI_WIN_CLOSEBOX)
+ {
+ rtgui_rect_moveto(rect,-2-RTGUI_WIN_CLOSEBOX_WIDTH,0);
+ }
+ if(win->style &RTGUI_WIN_MAXBOX)
+ {
+ rtgui_rect_moveto(rect,-2-RTGUI_WIN_CLOSEBOX_WIDTH,0);
+ }
+}
+
+
|
