motion.c
上传用户:sun1608
上传日期:2007-02-02
资源大小:6116k
文件大小:6k
源码类别:

流媒体/Mpeg4/MP4

开发平台:

Visual C++

  1. #include "mpeg3video.h"
  2. #include "vlc.h"
  3. #include <stdio.h>
  4. /* calculate motion vector component */
  5. void mpeg3video_calc_mv(int *pred, int r_size, int motion_code, int motion_r, int full_pel_vector)
  6. {
  7. int lim = 16 << r_size;
  8. int vec = full_pel_vector ? (*pred >> 1) : (*pred);
  9. if(motion_code > 0)
  10. {
  11.      vec += ((motion_code - 1) << r_size) + motion_r + 1;
  12.      if(vec >= lim) vec -= lim + lim;
  13. }
  14. else 
  15. if(motion_code < 0)
  16. {
  17.      vec -= ((-motion_code - 1) << r_size) + motion_r + 1;
  18.      if(vec < -lim) vec += lim + lim;
  19. }
  20. *pred = full_pel_vector ? (vec << 1) : vec;
  21. }
  22. /*
  23. int *dmvector, * differential motion vector *
  24. int mvx, int mvy  * decoded mv components (always in field format) *
  25. */
  26. void mpeg3video_calc_dmv(mpeg3video_t *video, 
  27. int DMV[][2], 
  28. int *dmvector, 
  29. int mvx, 
  30. int mvy)
  31. {
  32. if(video->pict_struct == FRAME_PICTURE)
  33. {
  34.      if(video->topfirst)
  35. {
  36. /* vector for prediction of top field from bottom field */
  37.      DMV[0][0] = ((mvx  + (mvx>0)) >> 1) + dmvector[0];
  38.      DMV[0][1] = ((mvy  + (mvy>0)) >> 1) + dmvector[1] - 1;
  39. /* vector for prediction of bottom field from top field */
  40.      DMV[1][0] = ((3 * mvx + (mvx > 0)) >> 1) + dmvector[0];
  41.      DMV[1][1] = ((3 * mvy + (mvy > 0)) >> 1) + dmvector[1] + 1;
  42.      }
  43.      else 
  44. {
  45. /* vector for prediction of top field from bottom field */
  46.      DMV[0][0] = ((3 * mvx + (mvx>0)) >> 1) + dmvector[0];
  47.      DMV[0][1] = ((3 * mvy + (mvy>0)) >> 1) + dmvector[1] - 1;
  48. /* vector for prediction of bottom field from top field */
  49.      DMV[1][0] = ((mvx + (mvx>0)) >> 1) + dmvector[0];
  50.      DMV[1][1] = ((mvy + (mvy>0)) >> 1) + dmvector[1] + 1;
  51.      }
  52. }
  53. else 
  54. {
  55. /* vector for prediction from field of opposite 'parity' */
  56.      DMV[0][0] = ((mvx + (mvx > 0)) >> 1) + dmvector[0];
  57.      DMV[0][1] = ((mvy + (mvy > 0)) >> 1) + dmvector[1];
  58. /* correct for vertical field shift */
  59.      if(video->pict_struct == TOP_FIELD)
  60. DMV[0][1]--;
  61.      else 
  62. DMV[0][1]++;
  63. }
  64. }
  65. int mpeg3video_get_mv(mpeg3_slice_t *slice)
  66. {
  67.    int code;
  68. mpeg3_slice_buffer_t *slice_buffer = slice->slice_buffer;
  69.    if(mpeg3slice_getbit(slice_buffer))
  70. {
  71.      return 0;
  72.    }
  73.    if((code = mpeg3slice_showbits9(slice_buffer)) >= 64)
  74. {
  75.      code >>= 6;
  76.      mpeg3slice_flushbits(slice_buffer, mpeg3_MVtab0[code].len);
  77.      return mpeg3slice_getbit(slice_buffer) ? -mpeg3_MVtab0[code].val : mpeg3_MVtab0[code].val;
  78.    }
  79.    if(code >= 24)
  80. {
  81.      code >>= 3;
  82.      mpeg3slice_flushbits(slice_buffer, mpeg3_MVtab1[code].len);
  83.     return mpeg3slice_getbit(slice_buffer) ? -mpeg3_MVtab1[code].val : mpeg3_MVtab1[code].val;
  84.    }
  85.    if((code -= 12) < 0)
  86. {
  87. /*     fprintf(stdout,"mpeg3video_get_mv: invalid motion_vector coden"); */
  88.      slice->fault = 1;
  89.      return 1;
  90.    }
  91.    mpeg3slice_flushbits(slice_buffer, mpeg3_MVtab2[code].len);
  92.   return mpeg3slice_getbit(slice_buffer) ? -mpeg3_MVtab2[code].val : mpeg3_MVtab2[code].val;
  93. }
  94. /* get differential motion vector (for dual prime prediction) */
  95. int mpeg3video_get_dmv(mpeg3_slice_t *slice)
  96. {
  97. mpeg3_slice_buffer_t *slice_buffer = slice->slice_buffer;
  98.    if(mpeg3slice_getbit(slice_buffer))
  99. {
  100.      return mpeg3slice_getbit(slice_buffer) ? -1 : 1;
  101.    }
  102.    else 
  103. {
  104.      return 0;
  105.    }
  106. }
  107. /* get and decode motion vector and differential motion vector */
  108. void mpeg3video_motion_vector(mpeg3_slice_t *slice,
  109. mpeg3video_t *video, 
  110. int *PMV, 
  111. int *dmvector, 
  112. int h_r_size, 
  113. int v_r_size,
  114. int dmv, 
  115. int mvscale, 
  116. int full_pel_vector)
  117. {
  118. int motion_r;
  119. int motion_code = mpeg3video_get_mv(slice);
  120. mpeg3_slice_buffer_t *slice_buffer = slice->slice_buffer;
  121. if(slice->fault) return;
  122. motion_r = (h_r_size != 0 && motion_code != 0) ? mpeg3slice_getbits(slice_buffer, h_r_size) : 0;
  123.    mpeg3video_calc_mv(&PMV[0], h_r_size, motion_code, motion_r, full_pel_vector);
  124.    if(dmv) dmvector[0] = mpeg3video_get_dmv(slice);
  125.    motion_code = mpeg3video_get_mv(slice);
  126.    if(slice->fault)  return;
  127.    motion_r = (v_r_size != 0 && motion_code != 0) ? mpeg3slice_getbits(slice_buffer, v_r_size) : 0;
  128. /* DIV 2 */
  129.    if(mvscale) PMV[1] >>= 1; 
  130.    mpeg3video_calc_mv(&PMV[1], v_r_size, motion_code, motion_r, full_pel_vector);
  131. if(mvscale) PMV[1] <<= 1;
  132. if(dmv) dmvector[1] = mpeg3video_get_dmv(slice);
  133. }
  134. int mpeg3video_motion_vectors(mpeg3_slice_t *slice,
  135. mpeg3video_t *video, 
  136. int PMV[2][2][2], 
  137. int dmvector[2], 
  138. int mv_field_sel[2][2],
  139. int s, 
  140. int mv_count, 
  141. int mv_format, 
  142. int h_r_size, 
  143. int v_r_size, 
  144. int dmv, 
  145. int mvscale)
  146. {
  147. int result = 0;
  148. mpeg3_slice_buffer_t *slice_buffer = slice->slice_buffer;
  149. if(mv_count == 1)
  150. {
  151. if(mv_format == MV_FIELD && !dmv)
  152. {
  153. mv_field_sel[1][s] = mv_field_sel[0][s] = mpeg3slice_getbit(slice_buffer);
  154. }
  155.      mpeg3video_motion_vector(slice, 
  156. video, 
  157. PMV[0][s], 
  158. dmvector, 
  159. h_r_size, 
  160. v_r_size, 
  161. dmv, 
  162. mvscale, 
  163. 0);
  164.      if(slice->fault) return 1;
  165. /* update other motion vector predictors */
  166.      PMV[1][s][0] = PMV[0][s][0];
  167.      PMV[1][s][1] = PMV[0][s][1];
  168.    }
  169.    else 
  170. {
  171.      mv_field_sel[0][s] = mpeg3slice_getbit(slice_buffer);
  172.      mpeg3video_motion_vector(slice, 
  173. video, 
  174. PMV[0][s], 
  175. dmvector, 
  176. h_r_size, 
  177. v_r_size, 
  178. dmv, 
  179. mvscale, 
  180. 0);
  181.      if(slice->fault) return 1;
  182.      mv_field_sel[1][s] = mpeg3slice_getbit(slice_buffer);
  183.      mpeg3video_motion_vector(slice, 
  184. video, 
  185. PMV[1][s], 
  186. dmvector, 
  187. h_r_size, 
  188. v_r_size, 
  189. dmv, 
  190. mvscale, 
  191. 0);
  192.      if(slice->fault) return 1;
  193.    }
  194. return 0;
  195. }