// Destination and source images have their dimensions inverted. static mblk_t *copy_frame_to_true_yuv_portrait(jbyte* initial_frame, int rotation, int w, int h) { // ms_message("copy_frame_to_true_yuv_inverted : Orientation %i; width %i; height %i", orientation, w, h); MSPicture pict; mblk_t *yuv_block = ms_yuv_buf_alloc(&pict, w, h); bool clockwise = rotation == 90 ? true : false; // Copying Y uint8_t* dsty = pict.planes[0]; uint8_t* srcy = (uint8_t*) initial_frame; rotate_plane(w,h,srcy,dsty,1, clockwise); int uv_w = w/2; int uv_h = h/2; // int uorvsize = uv_w * uv_h; // Copying U uint8_t* srcu = (uint8_t*) initial_frame + (w * h); uint8_t* dstu = pict.planes[2]; rotate_plane(uv_w,uv_h,srcu,dstu, 2, clockwise); // memset(dstu, 128, uorvsize); // Copying V uint8_t* srcv = srcu + 1; uint8_t* dstv = pict.planes[1]; rotate_plane(uv_w,uv_h,srcv,dstv, 2, clockwise); // memset(dstv, 128, uorvsize); return yuv_block; }
//Main function void main(void) { char mode = 0; io_init(); //IO initialization mode = choose_mode(); //Getting choosen mode while(1) { switch(mode) //Detect mode decided and perform conrresponding effect { case 1: moving_point_in_sequence(); break; case 2: plane_left_to_right(); plane_forward_to_back(); plane_bottom_to_top(); break; case 3: flying_character_of_a_word("CYTRON"); break; case 4: contraction_expansion_square_ring(); break; case 5: expansion_box(); break; case 6: dice(); break; case 7: rotate_plane(); break; default: break; } } }
/* Destination and source images may have their dimensions inverted.*/ mblk_t *copy_ycbcrbiplanar_to_true_yuv_with_rotation_and_down_scale_by_2(uint8_t* y, uint8_t * cbcr, int rotation, int w, int h, int y_byte_per_row,int cbcr_byte_per_row, bool_t uFirstvSecond, bool_t down_scale) { MSPicture pict; int uv_w; int uv_h; uint8_t* ysrc; uint8_t* ydst; uint8_t* uvsrc; uint8_t* srcu; uint8_t* dstu; uint8_t* srcv; uint8_t* dstv; mblk_t *yuv_block = ms_yuv_buf_alloc(&pict, w, h); #ifdef ANDROID if (hasNeon == -1) { hasNeon = (android_getCpuFamily() == ANDROID_CPU_FAMILY_ARM && (android_getCpuFeatures() & ANDROID_CPU_ARM_FEATURE_NEON) != 0); } #endif #ifdef __arm__ if (down_scale && !hasNeon) { ms_error("down scaling by two requires NEON, returning empty block"); return yuv_block; } #endif if (!uFirstvSecond) { unsigned char* tmp = pict.planes[1]; pict.planes[1] = pict.planes[2]; pict.planes[2] = tmp; } uv_w = w/2; uv_h = h/2; if (rotation % 180 == 0) { int i,j; uint8_t* u_dest=pict.planes[1], *v_dest=pict.planes[2]; if (rotation == 0) { #ifdef __arm__ if (hasNeon) { deinterlace_down_scale_neon(y, cbcr, pict.planes[0], u_dest, v_dest, w, h, y_byte_per_row, cbcr_byte_per_row,down_scale); } else #endif { // plain copy for(i=0; i<h; i++) { memcpy(&pict.planes[0][i*w], &y[i*y_byte_per_row], w); } // de-interlace u/v for (i=0; i<uv_h; i++) { for(j=0; j<uv_w; j++) { *u_dest++ = cbcr[cbcr_byte_per_row*i + 2*j]; *v_dest++ = cbcr[cbcr_byte_per_row*i + 2*j + 1]; } } } } else { #ifdef __arm__ if (hasNeon) { deinterlace_down_scale_and_rotate_180_neon(y, cbcr, pict.planes[0], u_dest, v_dest, w, h, y_byte_per_row, cbcr_byte_per_row,down_scale); } else #endif { // 180° y rotation ysrc=y; ydst=&pict.planes[0][h*w-1]; for(i=0; i<h*w; i++) { *ydst-- = *ysrc++; } // 180° rotation + de-interlace u/v uvsrc=&cbcr[uv_h*uv_w*2-2]; for (i=0; i<uv_h*uv_w*2; i++) { *u_dest++ = *uvsrc--; *v_dest++ = *uvsrc--; } } } } else { bool_t clockwise = rotation == 90 ? TRUE : FALSE; // Rotate Y #ifdef __arm__ if (hasNeon) { if (clockwise) { rotate_down_scale_plane_neon_clockwise(w,h,y_byte_per_row,(uint8_t*)y,pict.planes[0],down_scale); } else { rotate_down_scale_plane_neon_anticlockwise(w,h,y_byte_per_row,(uint8_t*)y,pict.planes[0], down_scale); } } else #endif { uint8_t* dsty = pict.planes[0]; uint8_t* srcy = (uint8_t*) y; rotate_plane(w,h,y_byte_per_row,srcy,dsty,1, clockwise); } #ifdef __arm__ if (hasNeon) { rotate_down_scale_cbcr_to_cr_cb(uv_w,uv_h, cbcr_byte_per_row/2, (uint8_t*)cbcr, pict.planes[2], pict.planes[1],clockwise,down_scale); } else #endif { // Copying U srcu = cbcr; dstu = pict.planes[1]; rotate_plane(uv_w,uv_h,cbcr_byte_per_row/2,srcu,dstu, 2, clockwise); // Copying V srcv = srcu + 1; dstv = pict.planes[2]; rotate_plane(uv_w,uv_h,cbcr_byte_per_row/2,srcv,dstv, 2, clockwise); } } return yuv_block; }