提交 ca6a1a7e 编写于 作者: B bernard.xiong

fix dc_buffer code in small size mode.

git-svn-id: https://rt-thread.googlecode.com/svn/trunk@595 bbd45198-f89e-11dd-88c7-29a3b14d5316
上级 01149ddd
......@@ -13,6 +13,7 @@
*/
#include <rtgui/rtgui.h>
#include <rtgui/dc.h>
#include <rtgui/dc_hw.h>
#include <rtgui/color.h>
#include <rtgui/rtgui_system.h>
......@@ -251,89 +252,63 @@ static void rtgui_dc_buffer_blit(struct rtgui_dc* self, struct rtgui_point* dc_p
if (dc_point == RT_NULL) dc_point = &rtgui_empty_point;
if (dest->type == RTGUI_DC_HW)
if ((dest->type == RTGUI_DC_HW) && rtgui_dc_get_visible(dest) == RT_TRUE)
{
register int index;
int fb_pitch;
rtgui_rect_t abs_rect;
rtgui_color_t* pixel;
rt_uint8_t *line_ptr;
rt_uint16_t rect_width, rect_height, index;
void (*blit_line)(rtgui_color_t* color, rt_uint8_t* dest, int line);
abs_rect.x1 = hw->owner->extent.x1 + rect->x1;
abs_rect.y1 = hw->owner->extent.y1 + rect->y1;
abs_rect.x2 = abs_rect.x1 + rtgui_rect_width(*rect);
abs_rect.y2 = abs_rect.y1 + rtgui_rect_height(*rect);
/* calculate correct width and height */
if (rtgui_rect_width(*rect) > (dc->width - dc_point->x))
rect_width = dc->width - dc_point->x;
else
rect_width = rtgui_rect_width(*rect);
/* hw fb pitch */
fb_pitch = hw->device->byte_per_pixel * hw->device->width;
/* hardware dc blit */
if (!rtgui_region_not_empty(&dc->clip) ||
dc->clip_sync != hw->owner->clip_sync)
{
/* should re-calculate clip */
rtgui_region_intersect_rect(&(dc->clip),
&(hw->owner->clip), &abs_rect);
}
if (rtgui_rect_height(*rect) > (dc->height - dc_point->y))
rect_height = dc->height - dc_point->y;
else
rect_height = rtgui_rect_height(*rect);
/* get blit line function */
switch (hw->device->byte_per_pixel)
{
case 1:
blit_line = rtgui_blit_line_1;
break;
case 2:
blit_line = rtgui_blit_line_2;
break;
case 3:
case 4:
blit_line = rtgui_blit_line_4;
break;
default:
/* can not blit */
/* not support byte per pixel */
return;
}
/* blit each clip rect */
if (dc->clip.data == RT_NULL)
{
int y;
rtgui_color_t* pixel;
rt_uint8_t* fb;
pixel = (rtgui_color_t*)(dc->pixel + (dc_point->y + dc->clip.extents.y1 - abs_rect.y1) * dc->pitch +
(dc_point->x + dc->clip.extents.x1 - abs_rect.x1) * sizeof(rtgui_color_t));
fb = hw->device->get_framebuffer() + dc->clip.extents.y1 * fb_pitch +
dc->clip.extents.x1 * hw->device->byte_per_pixel;
for (y = dc->clip.extents.y1; y < dc->clip.extents.y2; y ++)
{
blit_line(pixel, fb, dc->clip.extents.x2 - dc->clip.extents.x1);
fb += fb_pitch;
pixel += dc->width;
}
}
else for (index = 0; index < rtgui_region_num_rects(&(dc->clip)); index ++)
{
int y;
rtgui_rect_t* prect;
rtgui_color_t* pixel;
rt_uint8_t* fb;
prect = ((rtgui_rect_t *)(dc->clip.data + index + 1));
/* create line buffer */
line_ptr = (rt_uint8_t*) rtgui_malloc(rect_width * hw->device->byte_per_pixel);
pixel = (rtgui_color_t*)(dc->pixel + (dc_point->y + prect->y1 - abs_rect.y1) * dc->pitch +
(dc_point->x + prect->x1 - abs_rect.x1) * sizeof(rtgui_color_t));
fb = hw->device->get_framebuffer() + prect->y1 * fb_pitch +
prect->x1 * hw->device->byte_per_pixel;
/* prepare pixel line */
pixel = (rtgui_color_t*)(dc->pixel + dc_point->y * dc->pitch + dc_point->x * sizeof(rtgui_color_t));
for (y = prect->y1; y < prect->y2; y ++)
{
blit_line(pixel, fb, prect->x2 - prect->x1);
fb += fb_pitch;
pixel += dc->width;
}
/* draw each line */
for (index = rect->y1; index < rect->y1 + rect_height; index ++)
{
/* blit on line buffer */
blit_line(pixel, line_ptr, rect_width);
pixel += dc->width;
/* draw on hardware dc */
rtgui_dc_hw_draw_raw_hline(hw, line_ptr, rect->x1, rect->x1 + rect_width, index);
}
/* release line buffer */
rtgui_free(line_ptr);
}
}
......
......@@ -12,6 +12,7 @@
* 2009-10-16 Bernard first version
*/
#include <rtgui/dc.h>
#include <rtgui/dc_hw.h>
#include <rtgui/driver.h>
#include <rtgui/rtgui_system.h>
#include <rtgui/widgets/view.h>
......@@ -436,3 +437,51 @@ static void rtgui_dc_hw_get_rect(struct rtgui_dc* self, rtgui_rect_t* rect)
rtgui_widget_get_rect(dc->owner, rect);
}
void rtgui_dc_hw_draw_raw_hline(struct rtgui_dc_hw* dc, rt_uint8_t* raw_ptr, int x1, int x2, int y)
{
register rt_base_t index;
register rt_base_t bpp;
/* convert logic to device */
x1 = x1 + dc->owner->extent.x1;
x2 = x2 + dc->owner->extent.x1;
y = y + dc->owner->extent.y1;
bpp = dc->device->byte_per_pixel;
if (dc->owner->clip.data == RT_NULL)
{
rtgui_rect_t* prect;
prect = &(dc->owner->clip.extents);
/* calculate hline intersect */
if (prect->y1 > y || prect->y2 <= y ) return;
if (prect->x2 <= x1 || prect->x1 > x2) return;
if (prect->x1 > x1) x1 = prect->x1;
if (prect->x2 < x2) x2 = prect->x2;
/* draw raw hline */
dc->device->draw_raw_hline(raw_ptr, x1, x2, y);
}
else for (index = 0; index < rtgui_region_num_rects(&(dc->owner->clip)); index ++)
{
rtgui_rect_t* prect;
register rt_base_t draw_x1, draw_x2;
prect = ((rtgui_rect_t *)(dc->owner->clip.data + index + 1));
draw_x1 = x1;
draw_x2 = x2;
/* calculate hline clip */
if (prect->y1 > y || prect->y2 <= y ) continue;
if (prect->x2 <= x1 || prect->x1 > x2) continue;
if (prect->x1 > x1) draw_x1 = prect->x1;
if (prect->x2 < x2) draw_x2 = prect->x2;
/* draw raw hline */
dc->device->draw_raw_hline(raw_ptr + (draw_x1 - x1) * bpp, draw_x1, draw_x2, y);
}
}
#include <rtthread.h>
#include <rtgui/dc_hw.h>
#include <rtgui/image.h>
#include <rtgui/rtgui_system.h>
......@@ -129,54 +130,6 @@ static void rtgui_image_hdc_unload(struct rtgui_image* image)
}
}
static void rtgui_image_hdc_raw_hline(struct rtgui_dc_hw* dc, rt_uint8_t* raw_ptr, int x1, int x2, int y)
{
register rt_base_t index;
register rt_base_t bpp;
/* convert logic to device */
x1 = x1 + dc->owner->extent.x1;
x2 = x2 + dc->owner->extent.x1;
y = y + dc->owner->extent.y1;
bpp = dc->device->byte_per_pixel;
if (dc->owner->clip.data == RT_NULL)
{
rtgui_rect_t* prect;
prect = &(dc->owner->clip.extents);
/* calculate hline intersect */
if (prect->y1 > y || prect->y2 <= y ) return;
if (prect->x2 <= x1 || prect->x1 > x2) return;
if (prect->x1 > x1) x1 = prect->x1;
if (prect->x2 < x2) x2 = prect->x2;
/* draw raw hline */
dc->device->draw_raw_hline(raw_ptr, x1, x2, y);
}
else for (index = 0; index < rtgui_region_num_rects(&(dc->owner->clip)); index ++)
{
rtgui_rect_t* prect;
register rt_base_t draw_x1, draw_x2;
prect = ((rtgui_rect_t *)(dc->owner->clip.data + index + 1));
draw_x1 = x1;
draw_x2 = x2;
/* calculate hline clip */
if (prect->y1 > y || prect->y2 <= y ) continue;
if (prect->x2 <= x1 || prect->x1 > x2) continue;
if (prect->x1 > x1) draw_x1 = prect->x1;
if (prect->x2 < x2) draw_x2 = prect->x2;
/* draw raw hline */
dc->device->draw_raw_hline(raw_ptr + (draw_x1 - x1) * bpp, draw_x1, draw_x2, y);
}
}
static void rtgui_image_hdc_blit(struct rtgui_image* image, struct rtgui_dc* dc, struct rtgui_rect* dst_rect)
{
rt_uint16_t y, w, h;
......@@ -207,7 +160,7 @@ static void rtgui_image_hdc_blit(struct rtgui_image* image, struct rtgui_dc* dc,
for (y = 0; y < h; y ++)
{
rtgui_image_hdc_raw_hline((struct rtgui_dc_hw*)dc, ptr, dst_rect->x1, dst_rect->x1 + w, dst_rect->y1 + y);
rtgui_dc_hw_draw_raw_hline((struct rtgui_dc_hw*)dc, ptr, dst_rect->x1, dst_rect->x1 + w, dst_rect->y1 + y);
ptr += hdc->pitch;
}
}
......@@ -226,7 +179,7 @@ static void rtgui_image_hdc_blit(struct rtgui_image* image, struct rtgui_dc* dc,
if (rtgui_filerw_read(hdc->filerw, ptr, 1, hdc->pitch) != hdc->pitch)
break; /* read data failed */
rtgui_image_hdc_raw_hline((struct rtgui_dc_hw*)dc, ptr, dst_rect->x1, dst_rect->x1 + w, dst_rect->y1 + y);
rtgui_dc_hw_draw_raw_hline((struct rtgui_dc_hw*)dc, ptr, dst_rect->x1, dst_rect->x1 + w, dst_rect->y1 + y);
}
rtgui_free(ptr);
......
......@@ -23,6 +23,7 @@ enum rtgui_dc_type
{
RTGUI_DC_HW,
RTGUI_DC_BUFFER,
RTGUI_DC_IMLIB2,
};
/* the abstract device context */
......@@ -57,30 +58,10 @@ struct rtgui_dc
rt_bool_t (*fini )(struct rtgui_dc* dc);
};
/* hardware device context */
struct rtgui_dc_hw
{
struct rtgui_dc parent;
/* widget owner */
rtgui_widget_t* owner;
/* visible */
rt_bool_t visible;
/* display driver */
struct rtgui_graphic_driver* device;
};
/* create a buffer dc */
struct rtgui_dc* rtgui_dc_buffer_create(int width, int height);
rt_uint8_t* rtgui_dc_buffer_get_pixel(struct rtgui_dc* dc);
/* create a hardware dc */
struct rtgui_dc* rtgui_dc_hw_create(rtgui_widget_t* owner);
struct rtgui_dc* rtgui_dc_begin_drawing(rtgui_widget_t* owner);
void rtgui_dc_end_drawing(struct rtgui_dc* dc);
/* destroy a dc */
void rtgui_dc_destory(struct rtgui_dc* dc);
......
/*
* File : dc_buffer.h
* This file is part of RT-Thread RTOS
* COPYRIGHT (C) 2006 - 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-04-10 Bernard first version
*/
#ifndef __RTGUI_DC_HW_H__
#define __RTGUI_DC_HW_H__
#include <rtgui/dc.h>
/* hardware device context */
struct rtgui_dc_hw
{
struct rtgui_dc parent;
/* widget owner */
rtgui_widget_t* owner;
/* visible */
rt_bool_t visible;
/* display driver */
struct rtgui_graphic_driver* device;
};
/* create a hardware dc */
struct rtgui_dc* rtgui_dc_hw_create(rtgui_widget_t* owner);
struct rtgui_dc* rtgui_dc_begin_drawing(rtgui_widget_t* owner);
void rtgui_dc_end_drawing(struct rtgui_dc* dc);
/* draw a hline with raw pixel data */
void rtgui_dc_hw_draw_raw_hline(struct rtgui_dc_hw* dc, rt_uint8_t* raw_ptr, int x1, int x2, int y);
#endif
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册