📄 frarray.c
字号:
10x 2-3
110x 4-5
1110xx 6-9
11110xxx 10-17
111110xxxx 18-33
111111xxxxxxxxxxxx 34-4129
*/
switch ( pbi->bits_so_far ){
case 1:
if ( pbi->bit_pattern == 0 ){
ret_val = 1;
*run_value = 1;
}
break;
case 3:
/* Bit 1 clear */
if ( !(pbi->bit_pattern & 0x0002) ){
ret_val = 1;
*run_value = (pbi->bit_pattern & 0x0001) + 2;
}
break;
case 4:
/* Bit 1 clear */
if ( !(pbi->bit_pattern & 0x0002) ){
ret_val = 1;
*run_value = (pbi->bit_pattern & 0x0001) + 4;
}
break;
case 6:
/* Bit 2 clear */
if ( !(pbi->bit_pattern & 0x0004) ){
ret_val = 1;
*run_value = (pbi->bit_pattern & 0x0003) + 6;
}
break;
case 8:
/* Bit 3 clear */
if ( !(pbi->bit_pattern & 0x0008) ){
ret_val = 1;
*run_value = (pbi->bit_pattern & 0x0007) + 10;
}
break;
case 10:
/* Bit 4 clear */
if ( !(pbi->bit_pattern & 0x0010) ){
ret_val = 1;
*run_value = (pbi->bit_pattern & 0x000F) + 18;
}
break;
case 18:
ret_val = 1;
*run_value = (pbi->bit_pattern & 0x0FFF) + 34;
break;
default:
ret_val = 0;
break;
}
/* todo: handle additional bits for values over 4129 */
return ret_val;
}
static void GetNextBInit(PB_INSTANCE *pbi){
long ret;
theora_read(pbi->opb,1,&ret);
pbi->NextBit = (unsigned char)ret;
/* Read run length */
FrArrayDeCodeInit(pbi);
do theora_read(pbi->opb,1,&ret);
while (FrArrayDeCodeBlockRun(pbi,ret,&pbi->BitsLeft)==0);
}
static unsigned char GetNextBBit (PB_INSTANCE *pbi){
long ret;
if ( !pbi->BitsLeft ){
/* Toggle the value. */
pbi->NextBit = ( pbi->NextBit == 1 ) ? 0 : 1;
/* Read next run */
FrArrayDeCodeInit(pbi);
do theora_read(pbi->opb,1,&ret);
while (FrArrayDeCodeBlockRun(pbi,ret,&pbi->BitsLeft)==0);
}
/* Have read a bit */
pbi->BitsLeft--;
/* Return next bit value */
return pbi->NextBit;
}
static void GetNextSbInit(PB_INSTANCE *pbi){
long ret;
theora_read(pbi->opb,1,&ret);
pbi->NextBit = (unsigned char)ret;
/* Read run length */
FrArrayDeCodeInit(pbi);
do theora_read(pbi->opb,1,&ret);
while (FrArrayDeCodeSBRun(pbi,ret,&pbi->BitsLeft)==0);
}
static unsigned char GetNextSbBit (PB_INSTANCE *pbi){
long ret;
if ( !pbi->BitsLeft ){
/* Toggle the value. */
pbi->NextBit = ( pbi->NextBit == 1 ) ? 0 : 1;
/* Read next run */
FrArrayDeCodeInit(pbi);
do theora_read(pbi->opb,1,&ret);
while (FrArrayDeCodeSBRun(pbi,ret,&pbi->BitsLeft)==0);
}
/* Have read a bit */
pbi->BitsLeft--;
/* Return next bit value */
return pbi->NextBit;
}
void QuadDecodeDisplayFragments ( PB_INSTANCE *pbi ){
ogg_uint32_t SB, MB, B;
int DataToDecode;
ogg_int32_t dfIndex;
ogg_uint32_t MBIndex = 0;
/* Reset various data structures common to key frames and inter frames. */
pbi->CodedBlockIndex = 0;
memset ( pbi->display_fragments, 0, pbi->UnitFragments );
/* For "Key frames" mark all blocks as coded and return. */
/* Else initialise the ArrayPtr array to 0 (all blocks uncoded by default) */
if ( GetFrameType(pbi) == KEY_FRAME ) {
memset( pbi->SBFullyFlags, 1, pbi->SuperBlocks );
memset( pbi->SBCodedFlags, 1, pbi->SuperBlocks );
memset( pbi->MBCodedFlags, 0, pbi->MacroBlocks );
}else{
memset( pbi->SBFullyFlags, 0, pbi->SuperBlocks );
memset( pbi->MBCodedFlags, 0, pbi->MacroBlocks );
/* Un-pack the list of partially coded Super-Blocks */
GetNextSbInit(pbi);
for( SB = 0; SB < pbi->SuperBlocks; SB++){
pbi->SBCodedFlags[SB] = GetNextSbBit (pbi);
}
/* Scan through the list of super blocks. Unless all are marked
as partially coded we have more to do. */
DataToDecode = 0;
for ( SB=0; SB<pbi->SuperBlocks; SB++ ) {
if ( !pbi->SBCodedFlags[SB] ) {
DataToDecode = 1;
break;
}
}
/* Are there further block map bits to decode ? */
if ( DataToDecode ) {
/* Un-pack the Super-Block fully coded flags. */
GetNextSbInit(pbi);
for( SB = 0; SB < pbi->SuperBlocks; SB++) {
/* Skip blocks already marked as partially coded */
while( (SB < pbi->SuperBlocks) && pbi->SBCodedFlags[SB] )
SB++;
if ( SB < pbi->SuperBlocks ) {
pbi->SBFullyFlags[SB] = GetNextSbBit (pbi);
if ( pbi->SBFullyFlags[SB] ) /* If SB is fully coded. */
pbi->SBCodedFlags[SB] = 1; /* Mark the SB as coded */
}
}
}
/* Scan through the list of coded super blocks. If at least one
is marked as partially coded then we have a block list to
decode. */
for ( SB=0; SB<pbi->SuperBlocks; SB++ ) {
if ( pbi->SBCodedFlags[SB] && !pbi->SBFullyFlags[SB] ) {
/* Initialise the block list decoder. */
GetNextBInit(pbi);
break;
}
}
}
/* Decode the block data from the bit stream. */
for ( SB=0; SB<pbi->SuperBlocks; SB++ ){
for ( MB=0; MB<4; MB++ ){
/* If MB is in the frame */
if ( QuadMapToMBTopLeft(pbi->BlockMap, SB,MB) >= 0 ){
/* Only read block level data if SB was fully or partially coded */
if ( pbi->SBCodedFlags[SB] ) {
for ( B=0; B<4; B++ ){
/* If block is valid (in frame)... */
dfIndex = QuadMapToIndex1( pbi->BlockMap, SB, MB, B );
if ( dfIndex >= 0 ){
if ( pbi->SBFullyFlags[SB] )
pbi->display_fragments[dfIndex] = 1;
else
pbi->display_fragments[dfIndex] = GetNextBBit(pbi);
/* Create linear list of coded block indices */
if ( pbi->display_fragments[dfIndex] ) {
pbi->MBCodedFlags[MBIndex] = 1;
pbi->CodedBlockList[pbi->CodedBlockIndex] = dfIndex;
pbi->CodedBlockIndex++;
}
}
}
}
MBIndex++;
}
}
}
}
CODING_MODE FrArrayUnpackMode(PB_INSTANCE *pbi){
long ret;
/* Coding scheme:
Token Codeword Bits
Entry 0 (most frequent) 0 1
Entry 1 10 2
Entry 2 110 3
Entry 3 1110 4
Entry 4 11110 5
Entry 5 111110 6
Entry 6 1111110 7
Entry 7 1111111 7
*/
/* Initialise the decoding. */
pbi->bits_so_far = 0;
theora_read(pbi->opb,1,&ret);
pbi->bit_pattern = ret;
/* Do we have a match */
if ( pbi->bit_pattern == 0 )
return (CODING_MODE)0;
/* Get the next bit */
theora_read(pbi->opb,1,&ret);
pbi->bit_pattern = (pbi->bit_pattern << 1) | ret;
/* Do we have a match */
if ( pbi->bit_pattern == 0x0002 )
return (CODING_MODE)1;
theora_read(pbi->opb,1,&ret);
pbi->bit_pattern = (pbi->bit_pattern << 1) | ret;
/* Do we have a match */
if ( pbi->bit_pattern == 0x0006 )
return (CODING_MODE)2;
theora_read(pbi->opb,1,&ret);
pbi->bit_pattern = (pbi->bit_pattern << 1) | ret;
/* Do we have a match */
if ( pbi->bit_pattern == 0x000E )
return (CODING_MODE)3;
theora_read(pbi->opb,1,&ret);
pbi->bit_pattern = (pbi->bit_pattern << 1) | ret;
/* Do we have a match */
if ( pbi->bit_pattern == 0x001E )
return (CODING_MODE)4;
theora_read(pbi->opb,1,&ret);
pbi->bit_pattern = (pbi->bit_pattern << 1) | ret;
/* Do we have a match */
if ( pbi->bit_pattern == 0x003E )
return (CODING_MODE)5;
theora_read(pbi->opb,1,&ret);
pbi->bit_pattern = (pbi->bit_pattern << 1) | ret;
/* Do we have a match */
if ( pbi->bit_pattern == 0x007E )
return (CODING_MODE)6;
else
return (CODING_MODE)7;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -