PageRenderTime 53ms CodeModel.GetById 8ms app.highlight 40ms RepoModel.GetById 1ms app.codeStats 0ms

/src/ftk_display_mem.c

http://ftk.googlecode.com/
C | 262 lines | 196 code | 36 blank | 30 comment | 32 complexity | 916d21a152566ba24bcfb2571da8dc9b MD5 | raw file
  1/*
  2 * File: ftk_display_mem.c    
  3 * Author:  Li XianJing <xianjimli@hotmail.com>
  4 * Brief:   memory based display.
  5 *
  6 * Copyright (c) 2009 - 2010  Li XianJing <xianjimli@hotmail.com>
  7 *
  8 * Licensed under the Academic Free License version 2.1
  9 *
 10 * This program is free software; you can redistribute it and/or modify
 11 * it under the terms of the GNU General Public License as published by
 12 * the Free Software Foundation; either version 2 of the License, or
 13 * (at your option) any later version.
 14 *
 15 * This program is distributed in the hope that it will be useful,
 16 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 18 * GNU General Public License for more details.
 19 *
 20 * You should have received a copy of the GNU General Public License
 21 * along with this program; if not, write to the Free Software
 22 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
 23 */
 24
 25/*
 26 * History:
 27 * ================================================================
 28 * 2010-03-21 Li XianJing <xianjimli@hotmail.com> from ftk_display_fb.c
 29 *
 30 */
 31
 32#include "ftk_log.h"
 33#include "ftk_display_mem.h"
 34
 35typedef struct _DisplayMemPrivInfo
 36{
 37	int bpp;
 38	int width;
 39	int height;
 40	void* bits;
 41	FtkDestroy on_destroy;
 42	void* on_destroy_ctx;
 43	FtkPixelFormat format;
 44	FtkBitmapCopyFromData copy_from_data;
 45	FtkBitmapCopyToData   copy_to_data;
 46	FtkDisplaySync sync;
 47	void* sync_ctx;
 48}PrivInfo;
 49
 50static Ret ftk_display_mem_update(FtkDisplay* thiz, FtkBitmap* bitmap, FtkRect* rect, int xoffset, int yoffset)
 51{
 52	Ret ret = RET_OK;
 53	DECL_PRIV(thiz, priv);
 54	int display_width  = priv->width;
 55	int display_height = priv->height;
 56	return_val_if_fail(priv != NULL, RET_FAIL);
 57
 58	ftk_logd("%s: ox=%d oy=%d (%d %d %d %d)\n", __func__, xoffset, yoffset, 
 59		rect->x, rect->y, rect->width, rect->height);
 60	ret = priv->copy_to_data(bitmap, rect, 
 61		priv->bits, xoffset, yoffset, display_width, display_height); 
 62
 63	if(priv->sync != NULL && ret == RET_OK)
 64	{
 65		FtkRect r;
 66		r.x = xoffset;
 67		r.y = yoffset;
 68		r.width = rect->width;
 69		r.height = rect->height;
 70		priv->sync(priv->sync_ctx, &r);
 71	}
 72
 73	return ret;
 74}
 75
 76static int ftk_display_mem_width(FtkDisplay* thiz)
 77{
 78	DECL_PRIV(thiz, priv);
 79	return_val_if_fail(priv != NULL, 0);
 80
 81	return priv->width;
 82}
 83
 84static int ftk_display_mem_height(FtkDisplay* thiz)
 85{
 86	DECL_PRIV(thiz, priv);
 87	return_val_if_fail(priv != NULL, 0);
 88
 89	return priv->height;
 90}
 91
 92static Ret ftk_display_mem_snap(FtkDisplay* thiz, FtkRect* r, FtkBitmap* bitmap)
 93{
 94	FtkRect rect = {0};
 95	DECL_PRIV(thiz, priv);
 96	int w = ftk_display_width(thiz);
 97	int h = ftk_display_height(thiz);
 98	int bw = ftk_bitmap_width(bitmap);
 99	int bh = ftk_bitmap_height(bitmap);
100	return_val_if_fail(priv != NULL, RET_FAIL);
101	
102	rect.x = r->x;
103	rect.y = r->y;
104	rect.width = FTK_MIN(bw, r->width);
105	rect.height = FTK_MIN(bh, r->height);
106
107	return priv->copy_from_data(bitmap, priv->bits, w, h, &rect);
108}
109
110static void ftk_display_mem_destroy(FtkDisplay* thiz)
111{
112	if(thiz != NULL)
113	{
114		DECL_PRIV(thiz, priv);
115		
116		if(priv->on_destroy != NULL)
117		{
118			priv->on_destroy(priv->on_destroy_ctx);
119		}
120
121		FTK_ZFREE(thiz, sizeof(FtkDisplay) + sizeof(PrivInfo));
122	}
123
124	return;
125}
126
127FtkDisplay* ftk_display_mem_create(FtkPixelFormat format, 
128	int width, int height, void* bits, FtkDestroy on_destroy, void* ctx)
129{
130	FtkDisplay* thiz = NULL;
131
132	thiz = (FtkDisplay*)FTK_ZALLOC(sizeof(FtkDisplay) + sizeof(PrivInfo));
133	if(thiz != NULL)
134	{
135		DECL_PRIV(thiz, priv);
136		thiz->update   = ftk_display_mem_update;
137		thiz->width    = ftk_display_mem_width;
138		thiz->height   = ftk_display_mem_height;
139		thiz->snap     = ftk_display_mem_snap;
140		thiz->destroy  = ftk_display_mem_destroy;
141
142		priv->bits = bits;
143		priv->width = width;
144		priv->height = height;
145		priv->format = format;
146		priv->on_destroy = on_destroy;
147		priv->on_destroy_ctx = ctx;
148
149		switch(format)
150		{
151			case FTK_PIXEL_RGB565:
152			{
153				priv->bpp = 2;
154				priv->copy_to_data   = ftk_bitmap_copy_to_data_rgb565;
155				priv->copy_from_data = ftk_bitmap_copy_from_data_rgb565;
156				break;
157			}
158			case FTK_PIXEL_BGR24:
159			{
160				priv->bpp = 3;
161				priv->copy_to_data   = ftk_bitmap_copy_to_data_bgr24;
162				priv->copy_from_data = ftk_bitmap_copy_from_data_bgr24;
163				break;
164			}
165			case FTK_PIXEL_BGRA32:
166			{
167				priv->bpp = 4;
168#ifdef WORDS_BIGENDIAN				
169				priv->copy_to_data   = ftk_bitmap_copy_to_data_argb32;
170				priv->copy_from_data = ftk_bitmap_copy_from_data_argb32;
171#else
172				priv->copy_to_data   = ftk_bitmap_copy_to_data_bgra32;
173				priv->copy_from_data = ftk_bitmap_copy_from_data_bgra32;
174#endif
175				break;
176			}
177			case FTK_PIXEL_RGBA32:
178			{
179				priv->bpp = 4;
180				priv->copy_to_data   = ftk_bitmap_copy_to_data_rgba32;
181				priv->copy_from_data = ftk_bitmap_copy_from_data_rgba32;
182				break;
183			}
184			default:
185			{
186				assert(!"not supported framebuffer format.");
187				break;
188			}
189		}
190	}
191		
192	return thiz;
193}
194
195Ret ftk_display_mem_set_sync_func(FtkDisplay* thiz, FtkDisplaySync sync, void* ctx)
196{
197	DECL_PRIV(thiz, priv);
198	return_val_if_fail(thiz != NULL && thiz->update == ftk_display_mem_update, RET_FAIL);
199
200	priv->sync = sync;
201	priv->sync_ctx = ctx;
202
203	return RET_OK;
204}
205
206int ftk_display_mem_is_active(FtkDisplay* thiz)
207{
208	return (thiz != NULL && thiz->update == ftk_display_mem_update);
209}
210
211FtkPixelFormat ftk_display_mem_get_pixel_format(FtkDisplay* thiz)
212{
213	DECL_PRIV(thiz, priv);
214
215	return priv != NULL ? priv->format : FTK_PIXEL_NONE;
216}
217
218Ret ftk_display_mem_update_directly(FtkDisplay* thiz, FtkPixelFormat format,
219	void* bits, int width, int height, int xoffset, int yoffset)
220{
221	int w = 0;
222	int h = 0;
223	char* src = NULL;
224	char* dst = NULL;
225	DECL_PRIV(thiz, priv);
226	return_val_if_fail(bits != NULL, RET_FAIL);
227	return_val_if_fail(ftk_display_mem_is_active(thiz), RET_FAIL);
228	return_val_if_fail(xoffset < priv->width && yoffset < priv->height, RET_FAIL);
229
230	w = (xoffset + width) < priv->width ? width : priv->width - xoffset;
231	h = (yoffset + height) < priv->height ? height : priv->height - yoffset;
232
233	if(format == priv->format)
234	{
235		src = (char*)bits;
236		dst = (char*)priv->bits + priv->width * priv->bpp + xoffset;
237		for(; h; h--)
238		{
239			memcpy(dst, src, priv->bpp * w);
240			dst += priv->width * priv->bpp;
241			src += width * priv->bpp;
242		}
243	}
244	else
245	{
246		/*TODO*/
247		assert(!"not supprted yet");
248	}
249
250	return RET_OK;
251}
252
253void* ftk_display_bits(FtkDisplay* thiz, int* bpp)
254{
255    DECL_PRIV(thiz, priv);
256    return_val_if_fail(thiz != NULL && priv != NULL && priv->bits != NULL, NULL);
257    return_val_if_fail(bpp != NULL, NULL);
258
259    *bpp = priv->bpp;
260
261    return priv->bits;
262}