1 /***************************************************************************
2                           ADM_vidChromaShift.cpp  -  description
3                              -------------------
4 	Try to remove the blue-to-theleft & red to the right effect by shifting chroma
5 
6     begin                : Sun Aug 14 2003
7     copyright            : (C) 2002 by mean
8     email                : fixounet@free.fr
9  ***************************************************************************/
10 
11 /***************************************************************************
12  *                                                                         *
13  *   This program is free software; you can redistribute it and/or modify  *
14  *   it under the terms of the GNU General Public License as published by  *
15  *   the Free Software Foundation; either version 2 of the License, or     *
16  *   (at your option) any later version.                                   *
17  *                                                                         *
18  ***************************************************************************/
19 #include "ADM_default.h"
20 #include "ADM_coreVideoFilter.h"
21 #include "ADM_default.h"
22 #include "ADM_coreVideoFilterInternal.h"
23 #include "DIA_factory.h"
24 
25 #include "ADM_vidChromaShift.h"
26 #include "chromashift_desc.cpp"
27 
28 
29 // Add the hook to make it valid plugin
30 DECLARE_VIDEO_FILTER_PARTIALIZABLE(   ADMVideoChromaShift,   // Class
31                         1,0,0,              // Version
32                         ADM_UI_TYPE_BUILD,         // UI
33                         VF_COLORS,            // Category
34                         "chromashift",            // internal name (must be uniq!)
35                         QT_TRANSLATE_NOOP("chromashift","ChromaShift"),            // Display name
36                         QT_TRANSLATE_NOOP("chromashift","Shift chroma U/V to fix badly synced luma/chroma.") // Description
37                     );
38 /**
39     \fn
40     \brief
41 */
getConfiguration(void)42 const char   *ADMVideoChromaShift::getConfiguration(void)
43 {
44     static char s[256];
45     snprintf(s,255,"Chroma shift U:%d  V:%d",  _param.u,_param.v);
46     return s;
47 }
48 /**
49     \fn
50     \brief
51 */
ADMVideoChromaShift(ADM_coreVideoFilter * in,CONFcouple * couples)52 ADMVideoChromaShift::ADMVideoChromaShift(ADM_coreVideoFilter *in,CONFcouple *couples) : ADM_coreVideoFilter(in,couples)
53 {
54         if(!couples || !ADM_paramLoad(couples,chromashift_param,&_param))
55 		{
56             // Default value
57             _param.u=0;
58             _param.v=0;
59         }
60         _uncompressed=new ADMImageDefault(info.width,info.height);
61         ADM_assert(_uncompressed);
62 
63 }
64 /**
65     \fn
66     \brief
67 */
getCoupledConf(CONFcouple ** couples)68 bool         ADMVideoChromaShift::getCoupledConf(CONFcouple **couples)
69 {
70     return ADM_paramSave(couples, chromashift_param,&_param);
71 }
72 
setCoupledConf(CONFcouple * couples)73 void ADMVideoChromaShift::setCoupledConf(CONFcouple *couples)
74 {
75     ADM_paramLoad(couples, chromashift_param, &_param);
76 }
77 
78 /**
79     \fn
80     \brief
81 */
82 
~ADMVideoChromaShift()83 ADMVideoChromaShift::~ADMVideoChromaShift()
84 {
85 	if(_uncompressed)
86  		delete _uncompressed;
87 	_uncompressed=NULL;
88 
89 }
90 
91 /**
92     \fn     fixup
93     \brief   blacken column with no chroma info
94 */
fixup(ADMImage * target,int32_t val)95 bool ADMVideoChromaShift::fixup(ADMImage *target,int32_t val)
96 {
97 uint32_t line,page;
98 uint8_t *zero;
99 uint8_t *zerochromaU,*zerochromaV;
100 int pitch,pitchU,pitchV;
101 int width=target->GetWidth(PLANAR_Y);
102 int height=target->GetHeight(PLANAR_Y);
103 /*
104 	If val is >0
105 		Source  ++++++++
106 		Target   __++++++
107 */
108 
109 	if(val>0)
110 		{
111 			line=val;
112             // luma
113 			zero=target->GetWritePtr(PLANAR_Y);
114 			pitch=target->GetPitch(PLANAR_Y);
115 			for(uint32_t h=height;h>0;h--)
116 			{
117 				memset(zero,0,val);
118 				zero+=pitch;
119 			}
120             // chroma u
121             zerochromaU=target->GetWritePtr(PLANAR_U);
122             zerochromaV=target->GetWritePtr(PLANAR_V);
123             pitchU=target->GetPitch(PLANAR_U);
124             pitchV=target->GetPitch(PLANAR_V);
125 			val>>=1;
126 			for(uint32_t h=height>>1;h>0;h--)
127 			{
128 				memset(zerochromaU,128,val);
129 				memset(zerochromaV,128,val);
130 				zerochromaU+=pitchU;
131                 zerochromaV+=pitchV;
132 			}
133 		}
134 /*
135 	if val is <0
136 		Source ++++++
137 		Target  ++++__
138 
139 */
140 
141 		else
142 		{
143 			val=-val;
144 
145             zero=target->GetWritePtr(PLANAR_Y)+width-val;
146 			pitch=target->GetPitch(PLANAR_Y);
147 
148             zerochromaU=target->GetWritePtr(PLANAR_U)+(width-val)/2;
149             zerochromaV=target->GetWritePtr(PLANAR_V)+(width-val)/2;
150             pitchU=target->GetPitch(PLANAR_U);
151             pitchV=target->GetPitch(PLANAR_V);
152 
153 
154 			for(uint32_t h=height;h>0;h--)
155 			{
156 				memset(zero,0,val);
157 				zero+=pitch;
158 			}
159 
160 			val>>=1;
161 			for(uint32_t h=height>>1;h>0;h--)
162 			{
163 				memset(zerochromaU,128,val);
164 				memset(zerochromaV,128,val);
165 				zerochromaU+=pitchU;
166                 zerochromaV+=pitchV;
167 			}
168 		}
169     return true;
170 }
171 /**
172     \fn     shift
173     \brief
174 */
shiftPlane(ADM_PLANE plane,ADMImage * s,ADMImage * d,int32_t val)175 bool ADMVideoChromaShift::shiftPlane(ADM_PLANE plane,ADMImage *s,ADMImage *d,int32_t val)
176 {
177 
178         return shift(d->GetWritePtr(plane),s->GetReadPtr(plane),s->GetPitch(plane),
179                         d->GetPitch(plane),s->GetWidth(plane),s->GetHeight(plane),val);
180 }
shift(uint8_t * target,uint8_t * source,uint32_t source_pitch,uint32_t dest_pitch,uint32_t width,uint32_t height,int32_t val)181 bool ADMVideoChromaShift::shift(uint8_t *target,uint8_t *source,
182                                     uint32_t source_pitch,uint32_t dest_pitch,
183                                     uint32_t width, uint32_t height,int32_t val)
184 {
185 uint32_t line;
186 
187 /*
188 	If val is >0
189 		Source  ++++++++
190 		Target   __++++++
191 */
192 	if(val>0)
193 		{
194 			line=width-val;
195 			target+=val;
196 			for(uint32_t h=height;h>0;h--)
197 			{
198 			memcpy(target,source,line);
199 			target+=dest_pitch;
200 			source+=source_pitch;
201 			}
202 		}
203 /*
204 	if val is <0
205 		Source ++++++
206 		Target  ++++__
207 
208 */
209 
210 		else
211 		{
212 			val=-val;
213 			line=width-val;
214 			source+=val;
215 
216 			for(uint32_t h=height;h>0;h--)
217 			{
218 			memcpy(target,source,line);
219 			target+=dest_pitch;
220 			source+=source_pitch;
221 			}
222 		}
223 	return true;
224 }
225 // UI
226 bool DIA_getChromaShift( ADM_coreVideoFilter *instream,chromashift    *param );
configure()227 bool ADMVideoChromaShift::configure( )
228 
229 {
230     return DIA_getChromaShift(previousFilter,&_param);
231 
232 }
233 
234 /**
235     \fn getNextFrame
236     \brief
237 */
getNextFrame(uint32_t * fn,ADMImage * image)238 bool         ADMVideoChromaShift::getNextFrame(uint32_t *fn,ADMImage *image)
239 {
240         if(!previousFilter->getNextFrame(fn,_uncompressed)) return false;
241 
242         image->copyInfo(_uncompressed);
243         image->copyPlane(_uncompressed,image,PLANAR_Y);
244 
245 		if(!_param.u)
246                 image->copyPlane(_uncompressed,image,PLANAR_U);
247 		else
248 				shiftPlane(PLANAR_U,_uncompressed,image,_param.u);
249 
250 		if(!_param.v)
251                 image->copyPlane(_uncompressed,image,PLANAR_V);
252         else
253 				shiftPlane(PLANAR_V,_uncompressed,image,_param.v);
254 
255 		if(_param.u)
256 			fixup(image,_param.u*2);
257 		if(_param.v)
258 			fixup(image,_param.v*2);
259 
260 
261       return 1;
262 }
263 // EOF
264 
265