List Info

Thread: display rotation




display rotation
user name
2006-10-14 10:41:46
Hi,

I would like to extend directfb to support Portrait Mode
(rotated TFT screen).

I found some earlier posts, but seems it stalled.

Anyway, attached is a tiny extension (not very complete and
untested, just to give you an idea what I'm up to) to the
nvidia driver to support rotating an image (for now by 270
degrees).

I also had a look at
src/core/layer_region.c:dfb_layer_region_flip_update, but I
don't have enough knowledge yet to "connect it all
together" from here.

If DirectFB always uses a back buffer, the obvious and
least-impact way would be to have the back buffer(s) be for
example 768x1024 and rotate-update the front buffer to
1024x768.

However, most Flippers seem to just set some offset register
on the graphics adapter, so that isn't really possible.

My earlier tries included swapping every x and y in
nvidia_2d.c, which worked kind of, but I guess DirectFB
mostly works over the frame buffer and so not all things
were actually rotated.

What do you think?

cheers,
   Danny

-- 
Der GMX SmartSurfer hilft bis zu 70% Ihrer Onlinekosten zu
sparen! 
Ideal für Modem und ISDN: http://www.gmx.n
et/de/go/smartsurfer
? Q
? nvidia-add-rotated-blit.patch
Index: nvidia_2d.c
============================================================
=======
RCS file:
/cvs/directfb/DirectFB/gfxdrivers/nvidia/nvidia_2d.c,v
retrieving revision 1.19
diff -u -p -u -p -r1.19 nvidia_2d.c
--- nvidia_2d.c	28 Jan 2006 11:36:56 -0000	1.19
+++ nvidia_2d.c	14 Oct 2006 10:30:11 -0000
 -326,6
+326,119  bool nvBlitFromCPU( void *drv, void *dev
      return true;
 }
 
+static void vertical_memcpy( void* destination, void*
source, int count, int pixel_size, int src_pitch)
+{
+     D_ASSUME( pixel_size == 2 || pixel_size == 4);
+
+     if (pixel_size == 2) {
+          src_pitch = src_pitch >> 1;
+          __u16* destination_16 = (__u16*) destination;
+          __u16* source_16 = (__u16*) source;
+
+          for (; count--; ) {
+               *(destination_16++) = *source_16;
+               source_16 += src_pitch;
+          }
+     } else {
+          src_pitch = src_pitch >> 2;
+          __u32* destination_32 = (__u32*) destination;
+          __u32* source_32 = (__u32*) source;
+
+          for (; count--; ) {
+               *(destination_32++) = *source_32;
+               source_32 += src_pitch;
+          }
+     }
+}
+
+bool nvRotatedBlitFromCPU( void *drv, void *dev,
DFBRectangle *rect, int dx, int dy, int rotation_degrees )
+{
+     if (rotation_degrees == 0) {
+          return nvBlitFromCPU( drv, dev, rect, dx, dy);
+     }
+     
+     NVidiaDriverData *nvdrv = (NVidiaDriverData*) drv;
+     NVidiaDeviceData *nvdev = (NVidiaDeviceData*) dev;
+     __u8             *src   = nvdev->src_address;
+     __u32             src_w;
+     __u32             src_h;
+     int               w, h, n;
+     char              real_buffer[256 * 4];
+     char*             buffer;
+     
+     
+     if (!nv_clip_source( rect, nvdev->src_width,
nvdev->src_height ))
+          return true;
+
+     int bytes_per_pixel;
+     bytes_per_pixel =
DFB_BYTES_PER_PIXEL(nvdev->src_format);
+
+     buffer = real_buffer;
+
+     src_w = (DFB_BYTES_PER_PIXEL(nvdev->src_format) ==
2)
+             ? ((rect->w + 1) & ~1) : rect->w;
+     src_h = rect->h;
+
+     nv_begin( SUBC_IMAGEBLT, IBLIT_COLOR_FORMAT, 1 );
+     nv_outr( nvdev->system_format );
+     
+     nv_begin( SUBC_IMAGEBLT, IBLIT_POINT, 3 );
+     nv_outr( (dy      << 16) | (dx      &
0xFFFF) );
+     nv_outr( (rect->h << 16) | (rect->w &
0xFFFF) );
+     nv_outr( (src_h   << 16) | (src_w   &
0xFFFF) );
+
+     n = nvdev->use_dma ? 256 : 128;
+     
+     src += rect->y * nvdev->src_pitch + (rect->x
+ rect->w) * bytes_per_pixel;
+
+     switch (nvdev->src_format) {
+          case DSPF_ARGB1555:
+          case DSPF_RGB16:
+               for (w = rect->w; w--;) {
+                    src -= bytes_per_pixel;
+
+                    __u8 *s2 = src;
+
+                    for (h = rect->h; h >= n * 2; h
-= n * 2) {
+                         vertical_memcpy( (void*) buffer,
s2, n, 4, nvdev->src_pitch);
+
+                         nv_begin( SUBC_IMAGEBLT,
IBLIT_PIXEL0, n );
+                         direct_memcpy(
(void*)nvdev->cmd_ptr, buffer, n * 4 );
+                         s2 += n * 4;
+                    }
+                    if (h > 0) {
+                         vertical_memcpy( (void*) buffer,
s2, h, 4, nvdev->src_pitch);
+                         nv_begin( SUBC_IMAGEBLT,
IBLIT_PIXEL0, (h + 1)>>1 );
+                         nv_copy16( nvdev->cmd_ptr,
buffer, h );
+                    }
+               }
+               break;
+               
+          default:
+               for (w = rect->w; w--;) {
+                    src -= bytes_per_pixel;
+
+                    __u8 *s2 = src;
+
+                    vertical_memcpy( (void*) buffer, s2, n,
bytes_per_pixel, nvdev->src_pitch);
+                    
+                    for (h = rect->h; h >= n; h -= n)
{
+                         vertical_memcpy( (void*) buffer,
s2, n, 4, nvdev->src_pitch);
+                         nv_begin( SUBC_IMAGEBLT,
IBLIT_PIXEL0, n );
+                         direct_memcpy(
(void*)nvdev->cmd_ptr, buffer, h * 4 );
+                         s2 += h * 4;
+                    }
+                    if (h > 0) {
+                         vertical_memcpy( (void*) buffer,
s2, h, 4, nvdev->src_pitch);
+                         nv_begin( SUBC_IMAGEBLT,
IBLIT_PIXEL0, h );
+                         nv_copy32( nvdev->cmd_ptr,
buffer, h );
+                    }
+                    
+               }
+               break;
+     }
+}
+
 bool nvStretchBlit( void *drv, void *dev, DFBRectangle *sr,
DFBRectangle *dr )
 {
      NVidiaDriverData *nvdrv      = (NVidiaDriverData*)
drv;
Index: nvidia_2d.h
============================================================
=======
RCS file:
/cvs/directfb/DirectFB/gfxdrivers/nvidia/nvidia_2d.h,v
retrieving revision 1.5
diff -u -p -u -p -r1.5 nvidia_2d.h
--- nvidia_2d.h	28 Jan 2006 11:36:56 -0000	1.5
+++ nvidia_2d.h	14 Oct 2006 10:30:11 -0000
 -41,6
+41,8  bool nvBlit( void *drv, void *dev, DFBRe
 
 bool nvBlitFromCPU( void *drv, void *dev, DFBRectangle
*rect, int dx, int dy );
 
+bool nvRotatedBlitFromCPU( void *drv, void *dev,
DFBRectangle *rect, int dx, int dy, int rotation_degrees );
+
 bool nvStretchBlit( void *drv, void *dev, DFBRectangle *sr,
DFBRectangle *dr );
 
 bool nvStretchBlitFromCPU( void *drv, void *dev,
DFBRectangle *sr, DFBRectangle *dr );
Index: nvidia_primary.c
============================================================
=======
RCS file:
/cvs/directfb/DirectFB/gfxdrivers/nvidia/nvidia_primary.c,v
retrieving revision 1.14
diff -u -p -u -p -r1.14 nvidia_primary.c
--- nvidia_primary.c	28 Jan 2006 11:36:56 -0000	1.14
+++ nvidia_primary.c	14 Oct 2006 10:30:11 -0000
 -156,6
+156,8  void        *OldPrimaryScreenDriverData;
 
 /*************************** Primary Layer hooks
******************************/
 
+/* TODO dannym rotate if needed */
+
 static DFBResult
 fb0FlipRegion( CoreLayer           *layer,
                void                *driver_data,
_______________________________________________
directfb-dev mailing list
directfb-devdirectfb.org
http://mail.directfb.org/cgi-bin/mailman/listinfo/
directfb-dev
display rotation
user name
2006-10-28 23:27:46
Danny Milosavljevic schrieb:
> Hi,
> 
> I would like to extend directfb to support Portrait
Mode (rotated TFT screen).

Nice, that's really a missing feature!

> I found some earlier posts, but seems it stalled.
> 
> Anyway, attached is a tiny extension (not very complete
and untested, just to give you an idea what I'm up to) to
the nvidia driver to support rotating an image (for now by
270 degrees).

We should be able to use the TMU for that.

> I also had a look at
src/core/layer_region.c:dfb_layer_region_flip_update, but I
don't have enough knowledge yet to "connect it all
together" from here.
> 
> If DirectFB always uses a back buffer, the obvious and
least-impact way would be to have the back buffer(s) be for
example 768x1024 and rotate-update the front buffer to
1024x768.

Right, dfb_layer_region_flip_update() is the central point
where
rotation should happen. However, adding support for
differently
sized buffers in one surface will be difficult.

> However, most Flippers seem to just set some offset
register on the graphics adapter, so that isn't really
possible.

The window stack updates are blitted from back to front
buffer most of
the time, i.e. when only a portion of the screen is
affected.

Fullscreen applications/updates could be forced to do a blit
for
flipping.

> My earlier tries included swapping every x and y in
nvidia_2d.c, which worked kind of, but I guess DirectFB
mostly works over the frame buffer and so not all things
were actually rotated.
> 
> What do you think?

I think limiting the rotation support to blitted flipping is
fine.
PDAs for example would use that mode anyways, because of the
windowing.

-- 
Best regards,
   Denis Oliver Kropp

.------------------------------------------.
| DirectFB - Hardware accelerated graphics |
| http://www.directfb.org/
                |
"------------------------------------------"

_______________________________________________
directfb-dev mailing list
directfb-devdirectfb.org
http://mail.directfb.org/cgi-bin/mailman/listinfo/
directfb-dev
display rotation
user name
2006-10-28 23:27:46
Danny Milosavljevic schrieb:
> Hi,
> 
> I would like to extend directfb to support Portrait
Mode (rotated TFT screen).

Nice, that's really a missing feature!

> I found some earlier posts, but seems it stalled.
> 
> Anyway, attached is a tiny extension (not very complete
and untested, just to give you an idea what I'm up to) to
the nvidia driver to support rotating an image (for now by
270 degrees).

We should be able to use the TMU for that.

> I also had a look at
src/core/layer_region.c:dfb_layer_region_flip_update, but I
don't have enough knowledge yet to "connect it all
together" from here.
> 
> If DirectFB always uses a back buffer, the obvious and
least-impact way would be to have the back buffer(s) be for
example 768x1024 and rotate-update the front buffer to
1024x768.

Right, dfb_layer_region_flip_update() is the central point
where
rotation should happen. However, adding support for
differently
sized buffers in one surface will be difficult.

> However, most Flippers seem to just set some offset
register on the graphics adapter, so that isn't really
possible.

The window stack updates are blitted from back to front
buffer most of
the time, i.e. when only a portion of the screen is
affected.

Fullscreen applications/updates could be forced to do a blit
for
flipping.

> My earlier tries included swapping every x and y in
nvidia_2d.c, which worked kind of, but I guess DirectFB
mostly works over the frame buffer and so not all things
were actually rotated.
> 
> What do you think?

I think limiting the rotation support to blitted flipping is
fine.
PDAs for example would use that mode anyways, because of the
windowing.

-- 
Best regards,
   Denis Oliver Kropp

.------------------------------------------.
| DirectFB - Hardware accelerated graphics |
| http://www.directfb.org/
                |
"------------------------------------------"

_______________________________________________
directfb-dev mailing list
directfb-devdirectfb.org
http://mail.directfb.org/cgi-bin/mailman/listinfo/
directfb-dev
[1-3]

about | contact  Other archives ( Real Estate discussion Medical topics )