00001
00017 #include "global.h"
00018 #include "intra16x16_pred.h"
00019 #include "mb_access.h"
00020 #include "image.h"
00021
00032 static inline int intra16x16_dc_pred(ImageParameters *img,
00033 Macroblock *currMB,
00034 ColorPlane pl)
00035 {
00036 int s0 = 0, s1 = 0, s2 = 0;
00037
00038 int i,j;
00039
00040 imgpel **imgY = (pl) ? dec_picture->imgUV[pl - 1] : dec_picture->imgY;
00041 imgpel **mb_pred = &(img->mb_pred[pl][0]);
00042
00043 PixelPos up;
00044 PixelPos left[17];
00045
00046 int up_avail, left_avail, left_up_avail;
00047
00048 s1=s2=0;
00049
00050 for (i=0;i<17;i++)
00051 {
00052 getNeighbour(currMB, -1, i-1, img->mb_size[IS_LUMA], &left[i]);
00053 }
00054 getNeighbour(currMB, 0, -1, img->mb_size[IS_LUMA], &up);
00055
00056 if (!active_pps->constrained_intra_pred_flag)
00057 {
00058 up_avail = up.available;
00059 left_avail = left[1].available;
00060 left_up_avail = left[0].available;
00061 }
00062 else
00063 {
00064 up_avail = up.available ? img->intra_block[up.mb_addr] : 0;
00065 for (i = 1, left_avail = 1; i < 17; i++)
00066 left_avail &= left[i].available ? img->intra_block[left[i].mb_addr]: 0;
00067 left_up_avail = left[0].available ? img->intra_block[left[0].mb_addr]: 0;
00068 }
00069
00070 for (i = 0; i < MB_BLOCK_SIZE; i++)
00071 {
00072 if (up_avail)
00073 s1 += imgY[up.pos_y][up.pos_x+i];
00074 if (left_avail)
00075 s2 += imgY[left[i + 1].pos_y][left[i + 1].pos_x];
00076 }
00077 if (up_avail && left_avail)
00078 s0 = (s1 + s2 + 16)>>5;
00079 else if (!up_avail && left_avail)
00080 s0 = (s2 + 8)>>4;
00081 else if (up_avail && !left_avail)
00082 s0 = (s1 + 8)>>4;
00083 else
00084 s0 = img->dc_pred_value_comp[pl];
00085
00086 for(j = 0; j < MB_BLOCK_SIZE; j++)
00087 {
00088 for(i = 0; i < MB_BLOCK_SIZE; i++)
00089 {
00090 mb_pred[j][i]=(imgpel) s0;
00091 }
00092 }
00093
00094 return DECODING_OK;
00095 }
00096
00097
00108 static inline int intra16x16_vert_pred(ImageParameters *img,
00109 Macroblock *currMB,
00110 ColorPlane pl)
00111 {
00112 int j;
00113
00114 imgpel **imgY = (pl) ? dec_picture->imgUV[pl - 1] : dec_picture->imgY;
00115
00116 PixelPos up;
00117
00118 int up_avail;
00119
00120 getNeighbour(currMB, 0, -1, img->mb_size[IS_LUMA], &up);
00121
00122 if (!active_pps->constrained_intra_pred_flag)
00123 {
00124 up_avail = up.available;
00125 }
00126 else
00127 {
00128 up_avail = up.available ? img->intra_block[up.mb_addr] : 0;
00129 }
00130
00131 if (!up_avail)
00132 error ("invalid 16x16 intra pred Mode VERT_PRED_16",500);
00133
00134 for(j=0;j<MB_BLOCK_SIZE;j++)
00135 memcpy(img->mb_pred[pl][j], &(imgY[up.pos_y][up.pos_x]), MB_BLOCK_SIZE * sizeof(imgpel));
00136
00137 return DECODING_OK;
00138 }
00139
00140
00151 static inline int intra16x16_hor_pred(ImageParameters *img,
00152 Macroblock *currMB,
00153 ColorPlane pl)
00154 {
00155 int i,j;
00156
00157 imgpel **imgY = (pl) ? dec_picture->imgUV[pl - 1] : dec_picture->imgY;
00158 imgpel **mb_pred = &(img->mb_pred[pl][0]);
00159 imgpel prediction;
00160
00161 PixelPos left[17];
00162
00163 int left_avail, left_up_avail;
00164
00165 for (i=0;i<17;i++)
00166 {
00167 getNeighbour(currMB, -1, i-1, img->mb_size[IS_LUMA], &left[i]);
00168 }
00169
00170 if (!active_pps->constrained_intra_pred_flag)
00171 {
00172 left_avail = left[1].available;
00173 left_up_avail = left[0].available;
00174 }
00175 else
00176 {
00177 for (i = 1, left_avail = 1; i < 17; i++)
00178 left_avail &= left[i].available ? img->intra_block[left[i].mb_addr]: 0;
00179 left_up_avail = left[0].available ? img->intra_block[left[0].mb_addr]: 0;
00180 }
00181
00182 if (!left_avail)
00183 error ("invalid 16x16 intra pred Mode HOR_PRED_16",500);
00184
00185 for(j = 0; j < MB_BLOCK_SIZE; j++)
00186 {
00187 prediction = imgY[left[j+1].pos_y][left[j+1].pos_x];
00188 for(i = 0; i < MB_BLOCK_SIZE; i++)
00189 mb_pred[j][i]= prediction;
00190 }
00191
00192 return DECODING_OK;
00193 }
00194
00205 static inline int intra16x16_plane_pred(ImageParameters *img,
00206 Macroblock *currMB,
00207 ColorPlane pl)
00208 {
00209 int i,j;
00210
00211 int ih = 0, iv = 0;
00212 int ib,ic,iaa;
00213
00214 imgpel **imgY = (pl) ? dec_picture->imgUV[pl - 1] : dec_picture->imgY;
00215 imgpel **mb_pred = &(img->mb_pred[pl][0]);
00216 imgpel *mpr_line;
00217 int max_imgpel_value = img->max_imgpel_value_comp[pl];
00218
00219 PixelPos up;
00220 PixelPos left[17];
00221
00222 int up_avail, left_avail, left_up_avail;
00223
00224 for (i=0;i<17;i++)
00225 {
00226 getNeighbour(currMB, -1, i-1, img->mb_size[IS_LUMA], &left[i]);
00227 }
00228 getNeighbour(currMB, 0, -1, img->mb_size[IS_LUMA], &up);
00229
00230 if (!active_pps->constrained_intra_pred_flag)
00231 {
00232 up_avail = up.available;
00233 left_avail = left[1].available;
00234 left_up_avail = left[0].available;
00235 }
00236 else
00237 {
00238 up_avail = up.available ? img->intra_block[up.mb_addr] : 0;
00239 for (i = 1, left_avail = 1; i < 17; i++)
00240 left_avail &= left[i].available ? img->intra_block[left[i].mb_addr]: 0;
00241 left_up_avail = left[0].available ? img->intra_block[left[0].mb_addr]: 0;
00242 }
00243
00244 if (!up_avail || !left_up_avail || !left_avail)
00245 error ("invalid 16x16 intra pred Mode PLANE_16",500);
00246
00247 mpr_line = &imgY[up.pos_y][up.pos_x+7];
00248 for (i = 1; i < 8; i++)
00249 {
00250 ih += i*(mpr_line[i] - mpr_line[-i]);
00251 iv += i*(imgY[left[8+i].pos_y][left[8+i].pos_x] - imgY[left[8-i].pos_y][left[8-i].pos_x]);
00252 }
00253
00254 ih += 8*(mpr_line[8] - imgY[left[0].pos_y][left[0].pos_x]);
00255 iv += 8*(imgY[left[16].pos_y][left[16].pos_x] - imgY[left[0].pos_y][left[0].pos_x]);
00256
00257 ib=(5 * ih + 32)>>6;
00258 ic=(5 * iv + 32)>>6;
00259
00260 iaa=16 * (mpr_line[8] + imgY[left[16].pos_y][left[16].pos_x]);
00261 for (j = 0;j < MB_BLOCK_SIZE; j++)
00262 {
00263 for (i = 0;i < MB_BLOCK_SIZE; i++)
00264 {
00265 mb_pred[j][i] = (imgpel) iClip1(max_imgpel_value, ((iaa + (i - 7) * ib + (j - 7) * ic + 16) >> 5));
00266 }
00267 }
00268
00269 return DECODING_OK;
00270 }
00271
00282 int intrapred16x16(ImageParameters *img,
00283 Macroblock *currMB,
00284 ColorPlane pl,
00285 int predmode)
00286 {
00287 switch (predmode)
00288 {
00289 case VERT_PRED_16:
00290 return (intra16x16_vert_pred(img, currMB, pl));
00291 break;
00292 case HOR_PRED_16:
00293 return (intra16x16_hor_pred(img, currMB, pl));
00294 break;
00295 case DC_PRED_16:
00296 return (intra16x16_dc_pred(img, currMB, pl));
00297 break;
00298 case PLANE_16:
00299 return (intra16x16_plane_pred(img, currMB, pl));
00300 break;
00301 default:
00302 {
00303 printf("illegal 16x16 intra prediction mode input: %d\n",predmode);
00304 return SEARCH_SYNC;
00305 }
00306 }
00307
00308 return DECODING_OK;
00309 }
00310