libfreerdp-core: added pointer object

This commit is contained in:
Marc-André Moreau
2011-10-20 18:18:45 -04:00
parent b7e7067176
commit dbdbea9285
10 changed files with 209 additions and 134 deletions

View File

@@ -17,10 +17,19 @@
* limitations under the License.
*/
#include <X11/Xlib.h>
#include <X11/Xutil.h>
#ifdef WITH_XCURSOR
#include <X11/Xcursor/Xcursor.h>
#endif
#include <freerdp/codec/bitmap.h>
#include "xf_graphics.h"
/* Bitmap Class */
void xf_Bitmap_New(rdpContext* context, rdpBitmap* bitmap)
{
uint8* data;
@@ -105,9 +114,70 @@ void xf_Bitmap_Decompress(rdpContext* context, rdpBitmap* bitmap,
bitmap->bpp = bpp;
}
void xf_Bitmap_SetSurface(rdpContext* context, rdpBitmap* bitmap, boolean primary)
{
xfInfo* xfi = ((xfContext*) context)->xfi;
if (primary)
xfi->drawing = xfi->primary;
else
xfi->drawing = ((xfBitmap*) bitmap)->pixmap;
}
/* Pointer Class */
void xf_Pointer_New(rdpContext* context, rdpPointer* pointer)
{
XcursorImage ci;
xfInfo* xfi = ((xfContext*) context)->xfi;
memset(&ci, 0, sizeof(ci));
ci.version = XCURSOR_IMAGE_VERSION;
ci.size = sizeof(ci);
ci.width = pointer->width;
ci.height = pointer->height;
ci.xhot = pointer->xPos;
ci.yhot = pointer->yPos;
ci.pixels = (XcursorPixel*) malloc(ci.width * ci.height * 4);
memset(ci.pixels, 0, ci.width * ci.height * 4);
if ((pointer->andMaskData != 0) && (pointer->xorMaskData != 0))
{
freerdp_alpha_cursor_convert((uint8*) (ci.pixels), pointer->xorMaskData, pointer->andMaskData,
pointer->width, pointer->height, pointer->xorBpp, xfi->clrconv);
}
if (pointer->xorBpp > 24)
{
freerdp_image_swap_color_order((uint8*) ci.pixels, ci.width, ci.height);
}
((xfPointer*) pointer)->cursor = XcursorImageLoadCursor(xfi->display, &ci);
xfree(ci.pixels);
}
void xf_Pointer_Free(rdpContext* context, rdpPointer* pointer)
{
xfInfo* xfi = ((xfContext*) context)->xfi;
if (((xfPointer*) pointer)->cursor != 0)
XFreeCursor(xfi->display, ((xfPointer*) pointer)->cursor);
}
void xf_Pointer_Set(rdpContext* context, rdpPointer* pointer)
{
xfInfo* xfi = ((xfContext*) context)->xfi;
if (xfi->remote_app != True)
XDefineCursor(xfi->display, xfi->window->handle, ((xfPointer*) pointer)->cursor);
}
/* Graphics Module */
void xf_register_graphics(rdpGraphics* graphics)
{
rdpBitmap bitmap;
rdpPointer pointer;
memset(&bitmap, 0, sizeof(rdpBitmap));
bitmap.size = sizeof(xfBitmap);
@@ -116,6 +186,14 @@ void xf_register_graphics(rdpGraphics* graphics)
bitmap.Free = xf_Bitmap_Free;
bitmap.Paint = xf_Bitmap_Paint;
bitmap.Decompress = xf_Bitmap_Decompress;
bitmap.SetSurface = xf_Bitmap_SetSurface;
memset(&pointer, 0, sizeof(rdpPointer));
pointer.size = sizeof(xfPointer);
pointer.New = xf_Pointer_New;
pointer.Free = xf_Pointer_Free;
pointer.Set = xf_Pointer_Set;
graphics_register_bitmap(graphics, &bitmap);
graphics_register_pointer(graphics, &pointer);
}

View File

@@ -254,71 +254,6 @@ void xf_hw_desktop_resize(rdpUpdate* update)
}
}
void xf_set_surface(rdpUpdate* update, xfBitmap* bitmap, boolean primary)
{
xfInfo* xfi = ((xfContext*) update->context)->xfi;
if (primary)
xfi->drawing = xfi->primary;
else
xfi->drawing = bitmap->pixmap;
}
void xf_pointer_size(rdpUpdate* update, uint32* size)
{
*size = sizeof(xfPointer);
}
void xf_pointer_set(rdpUpdate* update, xfPointer* pointer)
{
xfInfo* xfi = ((xfContext*) update->context)->xfi;
if (xfi->remote_app != True)
XDefineCursor(xfi->display, xfi->window->handle, pointer->cursor);
}
void xf_pointer_new(rdpUpdate* update, xfPointer* pointer)
{
xfInfo* xfi;
XcursorImage ci;
rdpPointer* _pointer;
xfi = ((xfContext*) update->context)->xfi;
_pointer = (rdpPointer*) &pointer->pointer;
memset(&ci, 0, sizeof(ci));
ci.version = XCURSOR_IMAGE_VERSION;
ci.size = sizeof(ci);
ci.width = _pointer->width;
ci.height = _pointer->height;
ci.xhot = _pointer->xPos;
ci.yhot = _pointer->yPos;
ci.pixels = (XcursorPixel*) malloc(ci.width * ci.height * 4);
memset(ci.pixels, 0, ci.width * ci.height * 4);
if ((_pointer->andMaskData != 0) && (_pointer->xorMaskData != 0))
{
freerdp_alpha_cursor_convert((uint8*) (ci.pixels), _pointer->xorMaskData, _pointer->andMaskData,
_pointer->width, _pointer->height, _pointer->xorBpp, xfi->clrconv);
}
if (_pointer->xorBpp > 24)
{
freerdp_image_swap_color_order((uint8*) ci.pixels, ci.width, ci.height);
}
pointer->cursor = XcursorImageLoadCursor(xfi->display, &ci);
xfree(ci.pixels);
}
void xf_pointer_free(rdpUpdate* update, xfPointer* pointer)
{
xfInfo* xfi = ((xfContext*) update->context)->xfi;
if (pointer->cursor != 0)
XFreeCursor(xfi->display, pointer->cursor);
}
boolean xf_get_fds(freerdp* instance, void** rfds, int* rcount, void** wfds, int* wcount)
{
xfInfo* xfi = ((xfContext*) instance->context)->xfi;
@@ -599,6 +534,8 @@ boolean xf_post_connect(freerdp* instance)
if (xf_get_pixmap_info(xfi) != True)
return False;
xf_register_graphics(instance->context->graphics);
if (xfi->sw_gdi)
{
rdpGdi* gdi;
@@ -682,18 +619,11 @@ boolean xf_post_connect(freerdp* instance)
}
pointer_cache_register_callbacks(instance->update);
cache->pointer->PointerSize = (cbPointerSize) xf_pointer_size;
cache->pointer->PointerSet = (cbPointerSet) xf_pointer_set;
cache->pointer->PointerNew = (cbPointerNew) xf_pointer_new;
cache->pointer->PointerFree = (cbPointerFree) xf_pointer_free;
if (xfi->sw_gdi != True)
{
bitmap_cache_register_callbacks(instance->update);
offscreen_cache_register_callbacks(instance->update);
cache->offscreen->SetSurface = (cbSetSurface) xf_set_surface;
xf_register_graphics(instance->context->graphics);
}
instance->context->rail = rail_new(instance->settings);

View File

@@ -27,14 +27,11 @@
#include <freerdp/utils/stream.h>
typedef struct rdp_offscreen_cache rdpOffscreenCache;
typedef void (*cbSetSurface)(rdpUpdate* update, rdpBitmap* bitmap, boolean primary);
#include <freerdp/cache/cache.h>
struct rdp_offscreen_cache
{
cbSetSurface SetSurface;
uint16 currentSurface;
uint16 maxSize;
uint16 maxEntries;

View File

@@ -24,38 +24,15 @@
#include <freerdp/types.h>
#include <freerdp/update.h>
#include <freerdp/freerdp.h>
#include <freerdp/graphics.h>
#include <freerdp/utils/stream.h>
typedef struct rdp_pointer rdpPointer;
typedef struct rdp_pointer_cache rdpPointerCache;
#include <freerdp/cache/cache.h>
struct rdp_pointer
{
uint16 xPos;
uint16 yPos;
uint16 width;
uint16 height;
uint16 xorBpp;
uint16 lengthAndMask;
uint16 lengthXorMask;
uint8* xorMaskData;
uint8* andMaskData;
};
typedef void (*cbPointerSize)(rdpUpdate* update, uint32* size);
typedef void (*cbPointerSet)(rdpUpdate* update, rdpPointer* pointer);
typedef void (*cbPointerNew)(rdpUpdate* update, rdpPointer* pointer);
typedef void (*cbPointerFree)(rdpUpdate* update, rdpPointer* pointer);
struct rdp_pointer_cache
{
cbPointerSize PointerSize;
cbPointerNew PointerSet;
cbPointerNew PointerNew;
cbPointerFree PointerFree;
uint16 cacheSize;
rdpUpdate* update;
rdpSettings* settings;

View File

@@ -21,17 +21,21 @@
#define __GRAPHICS_H
typedef struct rdp_bitmap rdpBitmap;
typedef struct rdp_pointer rdpPointer;
#include <stdlib.h>
#include <freerdp/api.h>
#include <freerdp/types.h>
#include <freerdp/freerdp.h>
/* Bitmap Class */
typedef void (*pBitmap_New)(rdpContext* context, rdpBitmap* bitmap);
typedef void (*pBitmap_Free)(rdpContext* context, rdpBitmap* bitmap);
typedef void (*pBitmap_Paint)(rdpContext* context, rdpBitmap* bitmap, int x, int y);
typedef void (*pBitmap_Decompress)(rdpContext* context, rdpBitmap* bitmap,
uint8* data, int width, int height, int bpp, int length, boolean compressed);
typedef void (*pBitmap_SetSurface)(rdpContext* context, rdpBitmap* bitmap, boolean primary);
struct rdp_bitmap
{
@@ -41,6 +45,7 @@ struct rdp_bitmap
pBitmap_Free Free;
pBitmap_Paint Paint;
pBitmap_Decompress Decompress;
pBitmap_SetSurface SetSurface;
uint16 left;
uint16 top;
@@ -62,14 +67,49 @@ FREERDP_API void Bitmap_Free(rdpContext* context, rdpBitmap* bitmap);
FREERDP_API void Bitmap_Register(rdpContext* context, rdpBitmap* bitmap);
FREERDP_API void Bitmap_Decompress(rdpContext* context, rdpBitmap* bitmap,
uint8* data, int width, int height, int bpp, int length, boolean compressed);
FREERDP_API void Bitmap_SetSurface(rdpContext* context, rdpBitmap* bitmap, boolean primary);
/* Pointer Class */
typedef void (*pPointer_New)(rdpContext* context, rdpPointer* pointer);
typedef void (*pPointer_Free)(rdpContext* context, rdpPointer* pointer);
typedef void (*pPointer_Set)(rdpContext* context, rdpPointer* pointer);
struct rdp_pointer
{
size_t size;
pPointer_New New;
pPointer_Free Free;
pPointer_Set Set;
uint16 xPos;
uint16 yPos;
uint16 width;
uint16 height;
uint16 xorBpp;
uint16 lengthAndMask;
uint16 lengthXorMask;
uint8* xorMaskData;
uint8* andMaskData;
};
FREERDP_API rdpPointer* Pointer_Alloc(rdpContext* context);
FREERDP_API void Pointer_New(rdpContext* context, rdpPointer* pointer);
FREERDP_API void Pointer_Free(rdpContext* context, rdpPointer* pointer);
FREERDP_API void Pointer_Set(rdpContext* context, rdpPointer* pointer);
/* Graphics Module */
struct rdp_graphics
{
rdpContext* context;
rdpBitmap* Bitmap_Prototype;
rdpPointer* Pointer_Prototype;
};
FREERDP_API void graphics_register_bitmap(rdpGraphics* graphics, rdpBitmap* bitmap);
FREERDP_API void graphics_register_pointer(rdpGraphics* graphics, rdpPointer* pointer);
FREERDP_API rdpGraphics* graphics_new(rdpContext* context);
FREERDP_API void graphics_free(rdpGraphics* graphics);

View File

@@ -43,7 +43,7 @@ void update_gdi_create_offscreen_bitmap(rdpUpdate* update, CREATE_OFFSCREEN_BITM
offscreen_cache_put(cache->offscreen, create_offscreen_bitmap->id, bitmap);
if(cache->offscreen->currentSurface == create_offscreen_bitmap->id)
IFCALL(cache->offscreen->SetSurface, update, bitmap, False);
Bitmap_SetSurface(update->context, bitmap, False);
}
void update_gdi_switch_surface(rdpUpdate* update, SWITCH_SURFACE_ORDER* switch_surface)
@@ -52,14 +52,15 @@ void update_gdi_switch_surface(rdpUpdate* update, SWITCH_SURFACE_ORDER* switch_s
if (switch_surface->bitmapId == SCREEN_BITMAP_SURFACE)
{
IFCALL(cache->offscreen->SetSurface, update, NULL, True);
Bitmap_SetSurface(update->context, NULL, True);
}
else
{
rdpBitmap* bitmap;
bitmap = offscreen_cache_get(cache->offscreen, switch_surface->bitmapId);
IFCALL(cache->offscreen->SetSurface, update, bitmap, False);
Bitmap_SetSurface(update->context, bitmap, False);
}
cache->offscreen->currentSurface = switch_surface->bitmapId;
}

View File

@@ -40,12 +40,9 @@ void update_pointer_color(rdpUpdate* update, POINTER_COLOR_UPDATE* pointer_color
void update_pointer_new(rdpUpdate* update, POINTER_NEW_UPDATE* pointer_new)
{
rdpPointer* pointer;
uint32 size = sizeof(rdpPointer);
rdpCache* cache = (rdpCache*) update->context->cache;
IFCALL(cache->pointer->PointerSize, update, &size);
pointer = (rdpPointer*) xzalloc(size);
pointer = Pointer_Alloc(update->context);
if (pointer != NULL)
{
@@ -59,9 +56,9 @@ void update_pointer_new(rdpUpdate* update, POINTER_NEW_UPDATE* pointer_new)
pointer->xorMaskData = pointer_new->colorPtrAttr.xorMaskData;
pointer->andMaskData = pointer_new->colorPtrAttr.andMaskData;
IFCALL(cache->pointer->PointerNew, update, pointer);
pointer->New(update->context, pointer);
pointer_cache_put(cache->pointer, pointer_new->colorPtrAttr.cacheIndex, pointer);
IFCALL(cache->pointer->PointerSet, update, pointer);
Pointer_Set(update->context, pointer);
}
}
@@ -71,7 +68,7 @@ void update_pointer_cached(rdpUpdate* update, POINTER_CACHED_UPDATE* pointer_cac
rdpCache* cache = (rdpCache*) update->context->cache;
pointer = pointer_cache_get(cache->pointer, pointer_cached->cacheIndex);
IFCALL(cache->pointer->PointerSet, update, pointer);
Pointer_Set(update->context, pointer);
}
rdpPointer* pointer_cache_get(rdpPointerCache* pointer_cache, uint16 index)
@@ -139,7 +136,7 @@ void pointer_cache_free(rdpPointerCache* pointer_cache)
if (pointer != NULL)
{
pointer_cache->PointerFree(pointer_cache->update, pointer);
pointer->Free(pointer_cache->update->context, pointer);
if (pointer->xorMaskData != NULL)
xfree(pointer->xorMaskData);

View File

@@ -21,6 +21,8 @@
#include <freerdp/graphics.h>
/* Bitmap Class */
rdpBitmap* Bitmap_Alloc(rdpContext* context)
{
rdpBitmap* bitmap;
@@ -42,17 +44,6 @@ void Bitmap_New(rdpContext* context, rdpBitmap* bitmap)
}
void Bitmap_Decompress(rdpContext* context, rdpBitmap* bitmap,
uint8* data, int width, int height, int bpp, int length, boolean compressed)
{
bitmap->Decompress(context, bitmap, data, width, height, bpp, length, compressed);
}
void Bitmap_Paint(rdpContext* context, rdpBitmap* bitmap, int x, int y)
{
bitmap->Paint(context, bitmap, x, y);
}
void Bitmap_Free(rdpContext* context, rdpBitmap* bitmap)
{
if (bitmap != NULL)
@@ -64,11 +55,69 @@ void Bitmap_Free(rdpContext* context, rdpBitmap* bitmap)
}
}
void Bitmap_Paint(rdpContext* context, rdpBitmap* bitmap, int x, int y)
{
bitmap->Paint(context, bitmap, x, y);
}
void Bitmap_Decompress(rdpContext* context, rdpBitmap* bitmap,
uint8* data, int width, int height, int bpp, int length, boolean compressed)
{
bitmap->Decompress(context, bitmap, data, width, height, bpp, length, compressed);
}
/* static method */
void Bitmap_SetSurface(rdpContext* context, rdpBitmap* bitmap, boolean primary)
{
context->graphics->Bitmap_Prototype->SetSurface(context, bitmap, primary);
}
void graphics_register_bitmap(rdpGraphics* graphics, rdpBitmap* bitmap)
{
memcpy(graphics->Bitmap_Prototype, bitmap, sizeof(rdpBitmap));
}
/* Pointer Class */
rdpPointer* Pointer_Alloc(rdpContext* context)
{
rdpPointer* pointer;
rdpGraphics* graphics;
graphics = context->graphics;
pointer = (rdpPointer*) xmalloc(graphics->Pointer_Prototype->size);
if (pointer != NULL)
{
memcpy(pointer, context->graphics->Pointer_Prototype, sizeof(rdpPointer));
}
return pointer;
}
void Pointer_New(rdpContext* context, rdpPointer* pointer)
{
}
void Pointer_Free(rdpContext* context, rdpPointer* pointer)
{
}
/* static method */
void Pointer_Set(rdpContext* context, rdpPointer* pointer)
{
context->graphics->Pointer_Prototype->Set(context, pointer);
}
void graphics_register_pointer(rdpGraphics* graphics, rdpPointer* pointer)
{
memcpy(graphics->Pointer_Prototype, pointer, sizeof(rdpPointer));
}
/* Graphics Module */
rdpGraphics* graphics_new(rdpContext* context)
{
rdpGraphics* graphics;
@@ -81,6 +130,11 @@ rdpGraphics* graphics_new(rdpContext* context)
graphics->Bitmap_Prototype->size = sizeof(rdpBitmap);
graphics->Bitmap_Prototype->New = Bitmap_New;
graphics->Bitmap_Prototype->Free = Bitmap_Free;
graphics->Pointer_Prototype = (rdpPointer*) xmalloc(sizeof(rdpPointer));
graphics->Pointer_Prototype->size = sizeof(rdpPointer);
graphics->Pointer_Prototype->New = Pointer_New;
graphics->Pointer_Prototype->Free = Pointer_Free;
}
return graphics;
@@ -91,6 +145,7 @@ void graphics_free(rdpGraphics* graphics)
if (graphics != NULL)
{
xfree(graphics->Bitmap_Prototype);
xfree(graphics->Pointer_Prototype);
xfree(graphics);
}
}

View File

@@ -366,16 +366,6 @@ INLINE int gdi_is_mono_pixel_set(uint8* data, int x, int y, int width)
return (data[byte] & (0x80 >> shift)) != 0;
}
void gdi_set_surface(rdpUpdate* update, gdiBitmap* bitmap, boolean primary)
{
rdpGdi* gdi = update->context->gdi;
if (primary)
gdi->drawing = gdi->primary;
else
gdi->drawing = bitmap;
}
gdiBitmap* gdi_glyph_new(rdpGdi* gdi, GLYPH_DATA* glyph)
{
uint8* extra;
@@ -1072,10 +1062,9 @@ int gdi_init(freerdp* instance, uint32 flags, uint8* buffer)
gdi_register_update_callbacks(instance->update);
bitmap_cache_register_callbacks(instance->update);
gdi_register_graphics(instance->context->graphics);
offscreen_cache_register_callbacks(instance->update);
cache->offscreen->SetSurface = (cbSetSurface) gdi_set_surface;
gdi_register_graphics(instance->context->graphics);
gdi->rfx_context = rfx_context_new();
gdi->nsc_context = nsc_context_new();

View File

@@ -111,6 +111,16 @@ void gdi_Bitmap_Decompress(rdpContext* context, rdpBitmap* bitmap,
bitmap->bpp = bpp;
}
void gdi_Bitmap_SetSurface(rdpContext* context, rdpBitmap* bitmap, boolean primary)
{
rdpGdi* gdi = context->gdi;
if (primary)
gdi->drawing = gdi->primary;
else
gdi->drawing = (gdiBitmap*) bitmap;
}
void gdi_register_graphics(rdpGraphics* graphics)
{
rdpBitmap bitmap;
@@ -122,6 +132,7 @@ void gdi_register_graphics(rdpGraphics* graphics)
bitmap.Free = gdi_Bitmap_Free;
bitmap.Paint = gdi_Bitmap_Paint;
bitmap.Decompress = gdi_Bitmap_Decompress;
bitmap.SetSurface = gdi_Bitmap_SetSurface;
graphics_register_bitmap(graphics, &bitmap);
}