1 /*****************************************************************************
2 * yv12_rgb16.c : YUV to paletted RGB16 conversion module for vlc
3 *****************************************************************************
4 * Copyright (C) 2000 VideoLAN
5 * $Id: yv12_rgb16.c,v 1.3 2002/01/02 14:37:42 sam Exp $
7 * Authors: Samuel Hocevar <sam@zoy.org>
9 * This program is free software; you can redistribute it and/or modify
10 * it under the terms of the GNU General Public License as published by
11 * the Free Software Foundation; either version 2 of the License, or
12 * (at your option) any later version.
14 * This program is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 * GNU General Public License for more details.
19 * You should have received a copy of the GNU General Public License
20 * along with this program; if not, write to the Free Software
21 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111, USA.
22 *****************************************************************************/
24 /*****************************************************************************
26 *****************************************************************************/
27 #include <math.h> /* exp(), pow() */
28 #include <errno.h> /* ENOMEM */
29 #include <string.h> /* strerror() */
30 #include <stdlib.h> /* malloc(), free() */
32 #include <videolan/vlc.h>
35 #include "video_output.h"
37 #include "chroma_common.h"
38 #include "transforms.h"
40 /*****************************************************************************
41 * chroma_sys_t: chroma method descriptor
42 *****************************************************************************
43 * This structure is part of the chroma transformation descriptor, it
44 * describes the yuv2rgb16 specific properties.
45 *****************************************************************************/
46 typedef struct chroma_sys_s
53 /*****************************************************************************
54 * Local and extern prototypes.
55 *****************************************************************************/
56 static void chroma_getfunctions ( function_list_t * p_function_list );
58 static int chroma_Probe ( probedata_t *p_data );
59 static int chroma_Init ( vout_thread_t *p_vout );
60 static void chroma_End ( vout_thread_t *p_vout );
62 static void ConvertYUV420RGB16 ( vout_thread_t *, picture_t *, picture_t * );
64 /*****************************************************************************
65 * Build configuration tree.
66 *****************************************************************************/
71 SET_DESCRIPTION( "YV12 to RGB16 conversion module" )
72 ADD_CAPABILITY( CHROMA, 80 )
76 _M( chroma_getfunctions )( &p_module->p_functions->chroma );
79 MODULE_DEACTIVATE_START
80 MODULE_DEACTIVATE_STOP
82 /*****************************************************************************
84 *****************************************************************************/
85 /*****************************************************************************
86 * Functions exported as capabilities. They are declared as static so that
87 * we don't pollute the namespace too much.
88 *****************************************************************************/
89 void _M( chroma_getfunctions )( function_list_t * p_function_list )
91 p_function_list->pf_probe = chroma_Probe;
92 p_function_list->functions.chroma.pf_init = chroma_Init;
93 p_function_list->functions.chroma.pf_end = chroma_End;
96 /*****************************************************************************
97 * chroma_Probe: return a score
98 *****************************************************************************
99 * This function checks that we can handle the required data
100 *****************************************************************************/
101 static int chroma_Probe( probedata_t *p_data )
103 switch( p_data->chroma.p_render->i_chroma )
108 switch( ONLY_FOURCC( p_data->chroma.p_output->i_chroma ) )
110 case FOURCC_BI_BITFIELDS:
125 /*****************************************************************************
126 * chroma_Init: allocate a chroma function
127 *****************************************************************************
128 * This function allocates and initializes a chroma function
129 *****************************************************************************/
130 static int chroma_Init( vout_thread_t *p_vout )
132 switch( p_vout->render.i_chroma )
137 switch( ONLY_FOURCC( p_vout->output.i_chroma ) )
139 case FOURCC_BI_BITFIELDS:
140 switch( ONLY_EXTRA( p_vout->output.i_chroma ) )
143 p_vout->chroma.pf_convert = ConvertYUV420RGB16;
161 p_vout->chroma.p_sys = malloc( sizeof( chroma_sys_t ) );
162 if( p_vout->chroma.p_sys == NULL )
168 /* FIXME: this is really suboptimal ! */
173 /*****************************************************************************
174 * chroma_End: free the chroma function
175 *****************************************************************************
176 * This function frees the previously allocated chroma function
177 *****************************************************************************/
178 static void chroma_End( vout_thread_t *p_vout )
181 free( p_vout->chroma.p_sys );
187 /* Following functions are local */
189 /*****************************************************************************
190 * ConvertYUV420RGB16: color YUV 4:2:0 to RGB 8 bpp
191 *****************************************************************************/
192 static void ConvertYUV420RGB16( vout_thread_t *p_vout, picture_t *p_source,
195 /**********************************************************************
196 * XXX XXX FIXME FIXME XXX XXX XXX *
197 * XXX XXX XXX TODO TODO XXX XXX XXX TODO *
198 * XXX XXX XXX XXX XXX XXX XXX XXX *
199 * XXX FIXME XXX FIXME XXX FIXME XXX *
200 * XXX XXX XXX XXX XXX XXX XXX XXX *
201 * XXX XXX XXX XXX TODO XXX XXX XXX *
202 * XXX XXX XXX XXX FIXME XXX XXX XXX *
203 **********************************************************************/
205 pixel_data_t *p_in, *p_in_end, *p_out, *p_out_end;
207 p_in = p_source->P_Y;
208 p_in_end = p_in + p_source->planes[ Y_PLANE ].i_bytes;
210 p_out = p_dest->P_MAIN;
211 p_out_end = p_out + p_dest->planes[ MAIN_PLANE ].i_bytes;
213 while( p_in < p_in_end && p_out < p_out_end )
215 int i_src = p_source->planes[ Y_PLANE ].i_line_bytes;
216 int i_dst = p_dest->planes[ MAIN_PLANE ].i_line_bytes / 2;
218 /* Masks: 0xf800 0x07e0 0x001f */
219 #define RED ((u16*)p_out)[--i_dst] = (u16)(p_in[--i_src]>>3) << 11;
220 #define GREEN ((u16*)p_out)[--i_dst] = (u16)(p_in[--i_src]>>2) << 5;
221 #define BLUE ((u16*)p_out)[--i_dst] = (u16)(p_in[--i_src]>>3) << 0;
222 #define WHITE ((u16*)p_out)[--i_dst] = ((u16)(p_in[i_src]>>3) << 11) | ((u16)(p_in[i_src]>>2) << 5) | ((u16)(p_in[i_src]>>3) << 0); --i_src;
223 #define BLACK ((u16*)p_out)[--i_dst] = 0; --i_src;
225 while( i_src && i_dst )
227 WHITE; WHITE; WHITE; WHITE; WHITE; WHITE; WHITE; WHITE;
228 //BLACK; BLUE; GREEN; RED; GREEN; BLUE; WHITE; RED;
231 p_in += p_source->planes[ Y_PLANE ].i_line_bytes;
232 p_out += p_dest->planes[ MAIN_PLANE ].i_line_bytes;
234 if( p_in >= p_in_end || p_out >= p_out_end )
239 i_src = p_source->planes[ Y_PLANE ].i_line_bytes;
240 i_dst = p_dest->planes[ MAIN_PLANE ].i_line_bytes / 2;
242 while( i_src && i_dst )
244 WHITE; WHITE; WHITE; WHITE; WHITE; WHITE; WHITE; WHITE;
245 //GREEN; RED; WHITE; BLUE; BLACK; RED; GREEN; BLUE;
248 p_in += p_source->planes[ Y_PLANE ].i_line_bytes;
249 p_out += p_dest->planes[ MAIN_PLANE ].i_line_bytes;
252 /**********************************************************************
253 * XXX XXX XXX XXX FIXME XXX XXX XXX *
254 * XXX XXX XXX XXX TODO XXX XXX XXX TODO *
255 * XXX XXX XXX XXX XXX XXX XXX XXX *
256 * TODO XXX XXX XXX FIXME XXX *
257 * TODO XXX XXX XXX XXX XXX XXX *
258 * XXX TODO XXX TODO XXX XXX XXX *
259 * XXX FIXME FIXME XXX XXX XXX *
260 **********************************************************************/