Mercurial > libavcodec.hg
comparison motion_est_template.c @ 4255:f775fd9f3b05 libavcodec
hexagon search
dia_size=512 + hexagon size (513 is the normal one used in h264)
large to small diamond search
dia_size=256 + diamond size
author | michael |
---|---|
date | Sat, 02 Dec 2006 10:45:51 +0000 |
parents | b2c06cdd6154 |
children | b3e17d30dde2 |
comparison
equal
deleted
inserted
replaced
4254:bd7f921813b1 | 4255:f775fd9f3b05 |
---|---|
656 #endif | 656 #endif |
657 } | 657 } |
658 return dmin; | 658 return dmin; |
659 } | 659 } |
660 | 660 |
661 static int umh_search(MpegEncContext * s, int *best, int dmin, | 661 static int hex_search(MpegEncContext * s, int *best, int dmin, |
662 int src_index, int ref_index, int const penalty_factor, | 662 int src_index, int ref_index, int const penalty_factor, |
663 int size, int h, int flags) | 663 int size, int h, int flags, int dia_size) |
664 { | 664 { |
665 MotionEstContext * const c= &s->me; | 665 MotionEstContext * const c= &s->me; |
666 me_cmp_func cmpf, chroma_cmpf; | 666 me_cmp_func cmpf, chroma_cmpf; |
667 LOAD_COMMON | 667 LOAD_COMMON |
668 LOAD_COMMON2 | 668 LOAD_COMMON2 |
669 int map_generation= c->map_generation; | 669 int map_generation= c->map_generation; |
670 int x,y,x2,y2, i, j, d; | 670 int x,y,i,d; |
671 static const int hex[16][2]={{-4,-2}, {-4,-1}, {-4, 0}, {-4, 1}, {-4, 2}, | 671 static const int hex[6][2]={{-2, 0}, { 2,0}, {-1,-2}, {1,-2}, {-1,2},{1,2}}; |
672 { 4,-2}, { 4,-1}, { 4, 0}, { 4, 1}, { 4, 2}, | |
673 {-2, 3}, { 0, 4}, { 2, 3}, | |
674 {-2,-3}, { 0,-4}, { 2,-3},}; | |
675 static const int hex2[6][2]={{-2, 0}, { 2,0}, {-1,-2}, {1,-2}, {-1,2},{1,2}}; | |
676 | 672 |
677 cmpf= s->dsp.me_cmp[size]; | 673 cmpf= s->dsp.me_cmp[size]; |
678 chroma_cmpf= s->dsp.me_cmp[size+1]; | 674 chroma_cmpf= s->dsp.me_cmp[size+1]; |
679 | 675 |
680 x= best[0]; | 676 for(;dia_size; dia_size--){ |
681 y= best[1]; | 677 do{ |
682 for(x2=FFMAX(x-15, xmin); x2<=FFMIN(x+15,xmax); x2+=2){ | 678 x= best[0]; |
683 CHECK_MV(x2, y); | 679 y= best[1]; |
684 } | 680 for(i=0; i<6; i++){ |
685 for(y2=FFMAX(y- 7, ymin); y2<=FFMIN(y+ 7,ymax); y2+=2){ | 681 CHECK_CLIPED_MV(x+hex[i][0]*dia_size, y+hex[i][1]*dia_size); |
686 CHECK_MV(x, y2); | 682 } |
687 } | 683 }while(best[0] != x || best[1] != y); |
688 | 684 } |
689 x= best[0]; | |
690 y= best[1]; | |
691 for(y2=FFMAX(y-2, ymin); y2<=FFMIN(y+2,ymax); y2++){ | |
692 for(x2=FFMAX(x-2, xmin); x2<=FFMIN(x+2,xmax); x2++){ | |
693 CHECK_MV(x2, y2); | |
694 } | |
695 } | |
696 | |
697 //FIXME prevent the CLIP stuff | |
698 | |
699 for(j=1; j<=4; j++){ | |
700 for(i=0; i<16; i++){ | |
701 CHECK_CLIPED_MV(x+hex[i][0]*j, y+hex[i][1]*j); | |
702 } | |
703 } | |
704 | |
705 do{ | |
706 x= best[0]; | |
707 y= best[1]; | |
708 for(i=0; i<6; i++){ | |
709 CHECK_CLIPED_MV(x+hex2[i][0], y+hex2[i][1]); | |
710 } | |
711 }while(best[0] != x || best[1] != y); | |
712 | 685 |
713 do{ | 686 do{ |
714 x= best[0]; | 687 x= best[0]; |
715 y= best[1]; | 688 y= best[1]; |
716 CHECK_CLIPED_MV(x+1, y); | 689 CHECK_CLIPED_MV(x+1, y); |
718 CHECK_CLIPED_MV(x-1, y); | 691 CHECK_CLIPED_MV(x-1, y); |
719 CHECK_CLIPED_MV(x, y-1); | 692 CHECK_CLIPED_MV(x, y-1); |
720 }while(best[0] != x || best[1] != y); | 693 }while(best[0] != x || best[1] != y); |
721 | 694 |
722 return dmin; | 695 return dmin; |
696 } | |
697 | |
698 static int l2s_dia_search(MpegEncContext * s, int *best, int dmin, | |
699 int src_index, int ref_index, int const penalty_factor, | |
700 int size, int h, int flags) | |
701 { | |
702 MotionEstContext * const c= &s->me; | |
703 me_cmp_func cmpf, chroma_cmpf; | |
704 LOAD_COMMON | |
705 LOAD_COMMON2 | |
706 int map_generation= c->map_generation; | |
707 int x,y,i,d, dia_size; | |
708 static const int hex[8][2]={{-2, 0}, {-1,-1}, { 0,-2}, { 1,-1}, | |
709 { 2, 0}, { 1, 1}, { 0, 2}, {-1, 1}}; | |
710 | |
711 cmpf= s->dsp.me_cmp[size]; | |
712 chroma_cmpf= s->dsp.me_cmp[size+1]; | |
713 | |
714 for(dia_size= c->dia_size&0xFF; dia_size; dia_size--){ | |
715 do{ | |
716 x= best[0]; | |
717 y= best[1]; | |
718 for(i=0; i<8; i++){ | |
719 CHECK_CLIPED_MV(x+hex[i][0]*dia_size, y+hex[i][1]*dia_size); | |
720 } | |
721 }while(best[0] != x || best[1] != y); | |
722 } | |
723 | |
724 x= best[0]; | |
725 y= best[1]; | |
726 CHECK_CLIPED_MV(x+1, y); | |
727 CHECK_CLIPED_MV(x, y+1); | |
728 CHECK_CLIPED_MV(x-1, y); | |
729 CHECK_CLIPED_MV(x, y-1); | |
730 | |
731 return dmin; | |
732 } | |
733 | |
734 static int umh_search(MpegEncContext * s, int *best, int dmin, | |
735 int src_index, int ref_index, int const penalty_factor, | |
736 int size, int h, int flags) | |
737 { | |
738 MotionEstContext * const c= &s->me; | |
739 me_cmp_func cmpf, chroma_cmpf; | |
740 LOAD_COMMON | |
741 LOAD_COMMON2 | |
742 int map_generation= c->map_generation; | |
743 int x,y,x2,y2, i, j, d; | |
744 static const int hex[16][2]={{-4,-2}, {-4,-1}, {-4, 0}, {-4, 1}, {-4, 2}, | |
745 { 4,-2}, { 4,-1}, { 4, 0}, { 4, 1}, { 4, 2}, | |
746 {-2, 3}, { 0, 4}, { 2, 3}, | |
747 {-2,-3}, { 0,-4}, { 2,-3},}; | |
748 | |
749 cmpf= s->dsp.me_cmp[size]; | |
750 chroma_cmpf= s->dsp.me_cmp[size+1]; | |
751 | |
752 x= best[0]; | |
753 y= best[1]; | |
754 for(x2=FFMAX(x-15, xmin); x2<=FFMIN(x+15,xmax); x2+=2){ | |
755 CHECK_MV(x2, y); | |
756 } | |
757 for(y2=FFMAX(y- 7, ymin); y2<=FFMIN(y+ 7,ymax); y2+=2){ | |
758 CHECK_MV(x, y2); | |
759 } | |
760 | |
761 x= best[0]; | |
762 y= best[1]; | |
763 for(y2=FFMAX(y-2, ymin); y2<=FFMIN(y+2,ymax); y2++){ | |
764 for(x2=FFMAX(x-2, xmin); x2<=FFMIN(x+2,xmax); x2++){ | |
765 CHECK_MV(x2, y2); | |
766 } | |
767 } | |
768 | |
769 //FIXME prevent the CLIP stuff | |
770 | |
771 for(j=1; j<=4; j++){ | |
772 for(i=0; i<16; i++){ | |
773 CHECK_CLIPED_MV(x+hex[i][0]*j, y+hex[i][1]*j); | |
774 } | |
775 } | |
776 | |
777 return hex_search(s, best, dmin, src_index, ref_index, penalty_factor, size, h, flags, 1); | |
723 } | 778 } |
724 | 779 |
725 #define SAB_CHECK_MV(ax,ay)\ | 780 #define SAB_CHECK_MV(ax,ay)\ |
726 {\ | 781 {\ |
727 const int key= ((ay)<<ME_MAP_MV_BITS) + (ax) + map_generation;\ | 782 const int key= ((ay)<<ME_MAP_MV_BITS) + (ax) + map_generation;\ |
917 return umh_search(s, best, dmin, src_index, ref_index, penalty_factor, size, h, flags); | 972 return umh_search(s, best, dmin, src_index, ref_index, penalty_factor, size, h, flags); |
918 else if(c->dia_size<-1) | 973 else if(c->dia_size<-1) |
919 return sab_diamond_search(s, best, dmin, src_index, ref_index, penalty_factor, size, h, flags); | 974 return sab_diamond_search(s, best, dmin, src_index, ref_index, penalty_factor, size, h, flags); |
920 else if(c->dia_size<2) | 975 else if(c->dia_size<2) |
921 return small_diamond_search(s, best, dmin, src_index, ref_index, penalty_factor, size, h, flags); | 976 return small_diamond_search(s, best, dmin, src_index, ref_index, penalty_factor, size, h, flags); |
977 else if(c->dia_size>512) | |
978 return hex_search(s, best, dmin, src_index, ref_index, penalty_factor, size, h, flags, c->dia_size&0xFF); | |
979 else if(c->dia_size>256) | |
980 return l2s_dia_search(s, best, dmin, src_index, ref_index, penalty_factor, size, h, flags); | |
922 else | 981 else |
923 return var_diamond_search(s, best, dmin, src_index, ref_index, penalty_factor, size, h, flags); | 982 return var_diamond_search(s, best, dmin, src_index, ref_index, penalty_factor, size, h, flags); |
924 } | 983 } |
925 | 984 |
926 static always_inline int epzs_motion_search_internal(MpegEncContext * s, int *mx_ptr, int *my_ptr, | 985 static always_inline int epzs_motion_search_internal(MpegEncContext * s, int *mx_ptr, int *my_ptr, |