]> git.sesse.net Git - vlc/blob - modules/codec/ffmpeg/chroma.c
* modules/codec/ffmpeg/*: added chroma conversion capabilities to the ffmpeg plugin...
[vlc] / modules / codec / ffmpeg / chroma.c
1 /*****************************************************************************
2  * chroma.c: chroma conversion using ffmpeg library
3  *****************************************************************************
4  * Copyright (C) 1999-2001 VideoLAN
5  * $Id: chroma.c,v 1.1 2003/04/27 15:25:11 gbazin Exp $
6  *
7  * Authors: Gildas Bazin <gbazin@netcourrier.com>
8  *
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.
13  *
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.
18  *
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  *****************************************************************************/
23
24 /*****************************************************************************
25  * Preamble
26  *****************************************************************************/
27 #include <stdlib.h>                                      /* malloc(), free() */
28
29 #include <vlc/vlc.h>
30 #include <vlc/vout.h>
31
32 /* ffmpeg header */
33 #ifdef HAVE_FFMPEG_AVCODEC_H
34 #   include <ffmpeg/avcodec.h>
35 #else
36 #   include <avcodec.h>
37 #endif
38
39 #include "ffmpeg.h"
40
41 void ChromaConversion( vout_thread_t *, picture_t *, picture_t * );
42
43 /*****************************************************************************
44  * chroma_sys_t: chroma method descriptor
45  *****************************************************************************
46  * This structure is part of the chroma transformation descriptor, it
47  * describes the chroma plugin specific properties.
48  *****************************************************************************/
49 struct chroma_sys_t
50 {
51     int i_src_vlc_chroma;
52     int i_src_ffmpeg_chroma;
53     int i_dst_vlc_chroma;
54     int i_dst_ffmpeg_chroma;
55 };
56
57 /*****************************************************************************
58  * OpenChroma: allocate a chroma function
59  *****************************************************************************
60  * This function allocates and initializes a chroma function
61  *****************************************************************************/
62 int E_(OpenChroma)( vlc_object_t *p_this )
63 {
64     vout_thread_t *p_vout = (vout_thread_t *)p_this;
65     int i_ffmpeg_chroma[2], i_vlc_chroma[2], i;
66
67     /*
68      * Check the source chroma first, then the destination chroma
69      */
70     i_vlc_chroma[0] = p_vout->render.i_chroma;
71     i_vlc_chroma[1] = p_vout->output.i_chroma;
72     for( i = 0; i < 2; i++ )
73     {
74         switch( i_vlc_chroma[i] )
75         {
76
77         /* Planar YUV formats */
78         case VLC_FOURCC('I','4','4','4'):
79             i_ffmpeg_chroma[i] = PIX_FMT_YUV444P;
80             break;
81
82         case VLC_FOURCC('I','4','2','2'):
83             i_ffmpeg_chroma[i] = PIX_FMT_YUV422P;
84             break;
85
86         case VLC_FOURCC('Y','V','1','2'):
87         case VLC_FOURCC('I','4','2','0'):
88         case VLC_FOURCC('I','Y','U','V'):
89             i_ffmpeg_chroma[i] = PIX_FMT_YUV420P;
90             break;
91
92         case VLC_FOURCC('I','4','1','1'):
93             i_ffmpeg_chroma[i] = PIX_FMT_YUV411P;
94             break;
95
96         case VLC_FOURCC('I','4','1','0'):
97             i_ffmpeg_chroma[i] = PIX_FMT_YUV410P;
98             break;
99
100         /* Packed YUV formats */
101
102         case VLC_FOURCC('Y','U','Y','2'):
103         case VLC_FOURCC('U','Y','V','Y'):
104             i_ffmpeg_chroma[i] = PIX_FMT_YUV422;
105             break;
106            
107         /* Packed RGB formats */
108
109         case VLC_FOURCC('R','V','3','2'):
110             i_ffmpeg_chroma[i] = PIX_FMT_RGBA32;
111             break;
112
113         case VLC_FOURCC('R','V','2','4'):
114             i_ffmpeg_chroma[i] = PIX_FMT_RGB24;
115             //i_ffmpeg_chroma[i] = PIX_FMT_BGR24;
116             break;
117
118         case VLC_FOURCC('R','V','1','6'):
119             i_ffmpeg_chroma[i] = PIX_FMT_RGB565;
120             break;
121
122         case VLC_FOURCC('R','V','1','5'):
123             i_ffmpeg_chroma[i] = PIX_FMT_RGB555;
124             break;
125
126         case VLC_FOURCC('R','G','B','2'):
127             i_ffmpeg_chroma[i] = PIX_FMT_GRAY8;
128             break;
129
130         default:
131             return VLC_EGENERIC;
132             break;
133         }
134     }
135
136     p_vout->chroma.pf_convert = ChromaConversion;
137
138     p_vout->chroma.p_sys = malloc( sizeof( chroma_sys_t ) );
139     if( p_vout->chroma.p_sys == NULL )
140     {
141         return VLC_EGENERIC;
142     }
143
144     p_vout->chroma.p_sys->i_src_vlc_chroma = p_vout->render.i_chroma;
145     p_vout->chroma.p_sys->i_dst_vlc_chroma = p_vout->output.i_chroma;
146     p_vout->chroma.p_sys->i_src_ffmpeg_chroma = i_ffmpeg_chroma[0];
147     p_vout->chroma.p_sys->i_dst_ffmpeg_chroma = i_ffmpeg_chroma[1];
148
149     return VLC_SUCCESS;
150 }
151
152 /*****************************************************************************
153  * ChromaConversion: actual chroma conversion function
154  *****************************************************************************/
155 void ChromaConversion( vout_thread_t *p_vout,
156                        picture_t *p_src, picture_t *p_dest )
157 {
158     AVPicture src_pic;
159     AVPicture dest_pic;
160     int i;
161
162     /* Prepare the AVPictures for converion */
163     for( i = 0; i < p_src->i_planes; i++ )
164     {
165         src_pic.data[i] = p_src->p[i].p_pixels;
166         src_pic.linesize[i] = p_src->p[i].i_pitch;
167     }
168     for( i = 0; i < p_dest->i_planes; i++ )
169     {
170         dest_pic.data[i] = p_dest->p[i].p_pixels;
171         dest_pic.linesize[i] = p_dest->p[i].i_pitch;
172     }
173
174     /* Special cases */
175     if( p_vout->chroma.p_sys->i_src_vlc_chroma == VLC_FOURCC('Y','V','1','2') )
176     {
177         /* Invert U and V */
178         src_pic.data[1] = p_src->p[2].p_pixels;
179         src_pic.data[2] = p_src->p[1].p_pixels;
180     }
181     if( p_vout->chroma.p_sys->i_dst_vlc_chroma == VLC_FOURCC('Y','V','1','2') )
182     {
183         /* Invert U and V */
184         dest_pic.data[1] = p_dest->p[2].p_pixels;
185         dest_pic.data[2] = p_dest->p[1].p_pixels;
186     }
187
188     img_convert( &dest_pic, p_vout->chroma.p_sys->i_dst_ffmpeg_chroma,
189                  &src_pic, p_vout->chroma.p_sys->i_src_ffmpeg_chroma,
190                  p_vout->render.i_width, p_vout->render.i_height );
191 }