summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/video_out/video_out_directfb.c157
1 files changed, 81 insertions, 76 deletions
diff --git a/src/video_out/video_out_directfb.c b/src/video_out/video_out_directfb.c
index ef962f46d..db05c1ea7 100644
--- a/src/video_out/video_out_directfb.c
+++ b/src/video_out/video_out_directfb.c
@@ -67,7 +67,7 @@ typedef struct directfb_driver_s {
xine_t *xine;
- directfb_frame_t *recent_frames[VO_NUM_RECENT_FRAMES];
+ directfb_frame_t *cur_frame;
/* DirectFB related stuff */
IDirectFB *dfb;
@@ -207,7 +207,7 @@ static void directfb_update_frame_format (vo_driver_t *this_gen,
dsc.flags = DSDESC_CAPS | DSDESC_WIDTH |
DSDESC_HEIGHT | DSDESC_PIXELFORMAT;
- dsc.caps = DSCAPS_SYSTEMONLY;
+ dsc.caps = DSCAPS_SYSTEMONLY | DSCAPS_INTERLACED;
dsc.width = (width + 7) & ~7;
dsc.height = (height + 1) & ~1;
dsc.pixelformat = format;
@@ -336,11 +336,25 @@ static void directfb_overlay_blend (vo_driver_t *this_gen,
static int directfb_redraw_needed (vo_driver_t *this_gen) {
directfb_driver_t *this = (directfb_driver_t *) this_gen;
-
+ directfb_frame_t *frame = this->cur_frame;
+
+ if (!frame)
+ return 1;
+
+ this->sc.delivered_width = frame->width;
+ this->sc.delivered_height = frame->height;
+ this->sc.delivered_ratio = frame->ratio;
+ this->sc.crop_left = frame->vo_frame.crop_left;
+ this->sc.crop_right = frame->vo_frame.crop_right;
+ this->sc.crop_top = frame->vo_frame.crop_top;
+ this->sc.crop_bottom = frame->vo_frame.crop_bottom;
+
+ _x_vo_scale_compute_ideal_size (&this->sc);
+
if (_x_vo_scale_redraw_needed (&this->sc)) {
_x_vo_scale_compute_output_size (&this->sc);
-
- if (this->caps & DLCAPS_SCREEN_LOCATION) {
+
+ if (this->caps & DLCAPS_SCREEN_LOCATION) {
this->layer->SetSourceRectangle (this->layer,
this->sc.displayed_xoffset,
this->sc.displayed_yoffset,
@@ -352,33 +366,24 @@ static int directfb_redraw_needed (vo_driver_t *this_gen) {
this->sc.output_width,
this->sc.output_height);
}
-
+
directfb_clean_output_area (this);
+
+ return 1;
}
return 0;
}
-static void directfb_add_recent_frame (directfb_driver_t *this, directfb_frame_t *frame) {
- int i;
-
- i = VO_NUM_RECENT_FRAMES-1;
- if (this->recent_frames[i])
- this->recent_frames[i]->vo_frame.free (&this->recent_frames[i]->vo_frame);
-
- for (; i; i--)
- this->recent_frames[i] = this->recent_frames[i-1];
-
- this->recent_frames[0] = frame;
-}
-
/* directfb_display_frame(): output to overlay */
static void directfb_display_frame (vo_driver_t *this_gen, vo_frame_t *frame_gen) {
directfb_driver_t *this = (directfb_driver_t *) this_gen;
directfb_frame_t *frame = (directfb_frame_t *) frame_gen;
DFBResult ret;
-
- directfb_add_recent_frame (this, frame);
+
+ if (this->cur_frame)
+ this->cur_frame->vo_frame.free (&this->cur_frame->vo_frame);
+ this->cur_frame = frame;
this->config.flags = DLCONF_NONE;
@@ -425,15 +430,7 @@ static void directfb_display_frame (vo_driver_t *this_gen, vo_frame_t *frame_gen
this->sc.delivered_height != frame->height ||
this->sc.delivered_ratio != frame->ratio)
{
- this->sc.delivered_width = frame->width;
- this->sc.delivered_height = frame->height;
- this->sc.delivered_ratio = frame->ratio;
- this->sc.crop_left = frame->vo_frame.crop_left;
- this->sc.crop_right = frame->vo_frame.crop_right;
- this->sc.crop_top = frame->vo_frame.crop_top;
- this->sc.crop_bottom = frame->vo_frame.crop_bottom;
-
- _x_vo_scale_compute_ideal_size (&this->sc);
+ lprintf ("forcing redraw\n");
this->sc.force_redraw = 1;
}
@@ -450,10 +447,18 @@ static void directfb_display_frame (vo_driver_t *this_gen, vo_frame_t *frame_gen
}
if (this->deinterlace) {
- if (!(this->config.options & DLOP_DEINTERLACING))
+ if (!(this->config.options & DLOP_DEINTERLACING)) {
+ frame->surface->SetField (frame->surface,
+ frame->vo_frame.top_field_first ? 0 : 1);
this->surface->SetBlittingFlags (this->surface, DSBLIT_DEINTERLACE);
- } else
+ }
+ else {
+ this->surface->SetField (this->surface,
+ frame->vo_frame.top_field_first ? 0 : 1);
+ }
+ } else {
this->surface->SetBlittingFlags (this->surface, DSBLIT_NOFX);
+ }
this->surface->Blit (this->surface, frame->surface, NULL, 0, 0);
this->surface->Flip (this->surface, NULL,
@@ -474,7 +479,9 @@ static void directfb_display_frame2 (vo_driver_t *this_gen, vo_frame_t *frame_ge
DFBRectangle s, d;
DFBResult ret;
- directfb_add_recent_frame (this, frame);
+ if (this->cur_frame)
+ this->cur_frame->vo_frame.free (&this->cur_frame->vo_frame);
+ this->cur_frame = frame;
/* TODO: try to change video mode when frame size changes */
@@ -504,7 +511,9 @@ static void directfb_display_frame2 (vo_driver_t *this_gen, vo_frame_t *frame_ge
this->temp->Release (this->temp);
this->temp = NULL;
- dsc.flags = DSDESC_WIDTH | DSDESC_HEIGHT | DSDESC_PIXELFORMAT;
+ dsc.flags = DSDESC_CAPS | DSDESC_WIDTH |
+ DSDESC_HEIGHT | DSDESC_PIXELFORMAT;
+ dsc.caps = DSCAPS_INTERLACED;
dsc.width = frame->width;
dsc.height = frame->height;
dsc.pixelformat = frame->format;
@@ -523,15 +532,7 @@ static void directfb_display_frame2 (vo_driver_t *this_gen, vo_frame_t *frame_ge
this->sc.delivered_height != frame->height ||
this->sc.delivered_ratio != frame->ratio)
{
- this->sc.delivered_width = frame->width;
- this->sc.delivered_height = frame->height;
- this->sc.delivered_ratio = frame->ratio;
- this->sc.crop_left = frame->vo_frame.crop_left;
- this->sc.crop_right = frame->vo_frame.crop_right;
- this->sc.crop_top = frame->vo_frame.crop_top;
- this->sc.crop_bottom = frame->vo_frame.crop_bottom;
-
- _x_vo_scale_compute_ideal_size (&this->sc);
+ lprintf ("forcing redraw\n");
this->sc.force_redraw = 1;
}
@@ -562,16 +563,24 @@ static void directfb_display_frame2 (vo_driver_t *this_gen, vo_frame_t *frame_ge
flags = (this->deinterlace) ? DSBLIT_DEINTERLACE : DSBLIT_NOFX;
if (this->temp) {
- if (this->hw_deinterlace)
+ if (this->hw_deinterlace) {
+ this->temp->SetField (this->temp,
+ frame->vo_frame.top_field_first ? 0 : 1);
this->surface->SetBlittingFlags (this->surface, flags);
- else
- this->temp->SetBlittingFlags (this->temp, flags);
+ }
+ else {
+ frame->surface->SetField (frame->surface,
+ frame->vo_frame.top_field_first ? 0 : 1);
+ this->temp->SetBlittingFlags (this->temp, flags);
+ }
this->temp->Blit (this->temp, frame->surface, &s, 0, 0);
s.x = 0; s.y = 0;
this->surface->StretchBlit (this->surface, this->temp, &s, &d);
}
else {
+ frame->surface->SetField (frame->surface,
+ frame->vo_frame.top_field_first ? 0 : 1);
this->surface->SetBlittingFlags (this->surface, flags);
this->surface->StretchBlit (this->surface, frame->surface, &s, &d);
}
@@ -862,42 +871,35 @@ static int directfb_gui_data_exchange (vo_driver_t *this_gen,
static void directfb_dispose (vo_driver_t *this_gen) {
directfb_driver_t *this = (directfb_driver_t *) this_gen;
-
- if (this) {
- int i;
-
- for (i = 0; i < VO_NUM_RECENT_FRAMES; i++) {
- directfb_frame_t *frame = this->recent_frames[i];
- if (frame)
- frame->vo_frame.free (&frame->vo_frame);
- }
+
+ if (this->cur_frame)
+ this->cur_frame->vo_frame.dispose (&this->cur_frame->vo_frame);
#ifdef HAVE_X11
- if (this->visual_type == XINE_VISUAL_TYPE_X11) {
- XLockDisplay (this->display);
- XFreeGC (this->display, this->gc);
- XUnlockDisplay (this->display);
- }
+ if (this->visual_type == XINE_VISUAL_TYPE_X11) {
+ XLockDisplay (this->display);
+ XFreeGC (this->display, this->gc);
+ XUnlockDisplay (this->display);
+ }
#endif
- if (this->temp)
- this->temp->Release (this->temp);
+ if (this->temp)
+ this->temp->Release (this->temp);
- if (this->surface)
- this->surface->Release (this->surface);
+ if (this->surface)
+ this->surface->Release (this->surface);
- if (this->layer) {
- this->layer->SetColorAdjustment (this->layer, &this->default_cadj);
- this->layer->Release (this->layer);
- }
+ if (this->layer) {
+ this->layer->SetColorAdjustment (this->layer, &this->default_cadj);
+ this->layer->Release (this->layer);
+ }
- if (this->dfb)
- this->dfb->Release (this->dfb);
+ if (this->dfb)
+ this->dfb->Release (this->dfb);
- _x_alphablend_free (&this->alphablend_extra_data);
+ _x_alphablend_free (&this->alphablend_extra_data);
- free (this);
- }
+ free (this);
}
/*** misc functions ****/
@@ -1213,7 +1215,9 @@ static DFBResult init_device (directfb_driver_t *this) {
DFBSurfaceDescription dsc;
DFBAccelerationMask mask = DFXL_NONE;
- dsc.flags = DSDESC_WIDTH | DSDESC_HEIGHT | DSDESC_PIXELFORMAT;
+ dsc.flags = DSDESC_CAPS | DSDESC_WIDTH |
+ DSDESC_HEIGHT | DSDESC_PIXELFORMAT;
+ dsc.caps = DSCAPS_INTERLACED;
dsc.width = 320;
dsc.height = 240;
dsc.pixelformat = DSPF_YV12;
@@ -1303,7 +1307,8 @@ static void directfb_frame_output_cb (void *user_data, int video_width, int vide
*dest_y = 0;
*dest_width = this->screen_width;
*dest_height = this->screen_height;
- *dest_pixel_aspect = video_pixel_aspect ? : 1.0;
+ *dest_pixel_aspect = video_pixel_aspect ? :
+ (double)this->screen_width/(double)this->screen_height;
*win_x = 0;
*win_y = 0;
}
@@ -1583,7 +1588,7 @@ static vo_driver_t *open_plugin_x11 (video_driver_class_t *class_gen, const void
_x_alphablend_init (&this->alphablend_extra_data, this->xine);
- _x_vo_scale_init (&this->sc, 0, 0, this->xine->config);
+ _x_vo_scale_init (&this->sc, 1, 0, this->xine->config);
this->sc.user_ratio = XINE_VO_ASPECT_AUTO;
this->sc.gui_width = attrs.width;
this->sc.gui_height = attrs.height;