Files
player/Project/Src/MJPEG/avi.c

370 lines
11 KiB
C
Raw Normal View History

2025-06-27 00:32:57 +08:00
#include "touch_043.h"
#include "usart.h"
#include "timer.h"
#include "avi.h"
#include "mjpeg.h"
#include "lcd_rgb.h"
#include "mymem.h"
#include "ff.h"
#include "dac.h"
//////////////////////////////////////////////////////////////////////////////////
2025-07-05 19:47:28 +08:00
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ֻ<EFBFBD><D6BB>ѧϰʹ<CFB0>ã<EFBFBD>δ<EFBFBD><CEB4><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ɣ<EFBFBD><C9A3><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>κ<EFBFBD><CEBA><EFBFBD>;
//ALIENTEK STM32F407<30><37><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
//AVI<56><49>Ƶ<EFBFBD><C6B5>ʽ<EFBFBD><CABD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD>
//<2F><><EFBFBD><EFBFBD>ԭ<EFBFBD><D4AD>@ALIENTEK
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>̳:www.openedv.com
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>:2014/7/20
//<2F><EFBFBD><E6B1BE>V1.0
//<2F><>Ȩ<EFBFBD><C8A8><EFBFBD>У<EFBFBD><D0A3><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ؾ<EFBFBD><D8BE><EFBFBD>
//Copyright(C) <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ӿƼ<D3BF><C6BC><EFBFBD><EFBFBD>޹<EFBFBD>˾ 2009-2019
2025-06-27 00:32:57 +08:00
//All rights reserved
//*******************************************************************************
2025-07-05 19:47:28 +08:00
//<2F>޸<EFBFBD><DEB8><EFBFBD>Ϣ
//<2F><>
2025-06-27 00:32:57 +08:00
//////////////////////////////////////////////////////////////////////////////////
2025-07-05 19:47:28 +08:00
AVI_INFO avix; //avi<76>ļ<EFBFBD><C4BC><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ϣ
u8*const AVI_VIDS_FLAG_TBL[2]={"00dc","01dc"};//<2F><>Ƶ<EFBFBD><C6B5><EFBFBD><EFBFBD><EFBFBD><EFBFBD>־<EFBFBD>ַ<EFBFBD><D6B7><EFBFBD>,00dc/01dc
u8*const AVI_AUDS_FLAG_TBL[2]={"00wb","01wb"};//<2F><>Ƶ<EFBFBD><C6B5><EFBFBD><EFBFBD><EFBFBD><EFBFBD>־<EFBFBD>ַ<EFBFBD><D6B7><EFBFBD>,00wb/01wb
2025-06-27 00:32:57 +08:00
2025-07-05 19:47:28 +08:00
static vu8 g_i2splaybuf; //<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ŵ<EFBFBD><C5B5><EFBFBD>Ƶ֡<C6B5><D6A1><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
static u8* g_i2sbuf[4]; //<2F><>Ƶ<EFBFBD><C6B5><EFBFBD><EFBFBD>֡,<2C><>4֡,4*5K=20K
2025-06-27 00:32:57 +08:00
2025-07-05 19:47:28 +08:00
//<2F><>Ƶ<EFBFBD><C6B5><EFBFBD><EFBFBD>I2S DMA<4D><41><EFBFBD><EFBFBD><EFBFBD>ص<EFBFBD><D8B5><EFBFBD><EFBFBD><EFBFBD>
2025-06-27 00:32:57 +08:00
void audio_i2s_dma_callback(DAC_UserStruct *dac)
{
g_i2splaybuf++;
if(g_i2splaybuf>3)g_i2splaybuf=0;
if(dac->buff_useing==1)
{
DMA_MemoryTargetConfig(DMA1_Stream5,(u32)g_i2sbuf[g_i2splaybuf], DMA_Memory_0);
}
else
{
DMA_MemoryTargetConfig(DMA1_Stream5,(u32)g_i2sbuf[g_i2splaybuf], DMA_Memory_1);
}
}
2025-07-05 19:47:28 +08:00
//avi<76><69><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ʼ<EFBFBD><CABC>
//buf:<3A><><EFBFBD><EFBFBD><EBBBBA><EFBFBD><EFBFBD>
//size:<3A><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>С
//<2F><><EFBFBD><EFBFBD>ֵ:AVI_OK,avi<76>ļ<EFBFBD><C4BC><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ɹ<EFBFBD>
// <20><><EFBFBD><EFBFBD>,<2C><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
2025-06-27 00:32:57 +08:00
AVISTATUS avi_init(u8 *buf,int size)
{
u16 offset;
u8 *tbuf;
AVISTATUS res=AVI_OK;
AVI_HEADER *aviheader;
LIST_HEADER *listheader;
AVIH_HEADER *avihheader;
STRH_HEADER *strhheader;
STRF_BMPHEADER *bmpheader;
STRF_WAVHEADER *wavheader;
tbuf=buf;
aviheader=(AVI_HEADER*)buf;
2025-07-05 19:47:28 +08:00
if(aviheader->RiffID!=AVI_RIFF_ID)return AVI_RIFF_ERR; //RIFF ID<49><44><EFBFBD><EFBFBD>
if(aviheader->AviID!=AVI_AVI_ID)return AVI_AVI_ERR; //AVI ID<49><44><EFBFBD><EFBFBD>
buf+=sizeof(AVI_HEADER); //ƫ<><C6AB>
2025-06-27 00:32:57 +08:00
listheader=(LIST_HEADER*)(buf);
2025-07-05 19:47:28 +08:00
if(listheader->ListID!=AVI_LIST_ID)return AVI_LIST_ERR; //LIST ID<49><44><EFBFBD><EFBFBD>
if(listheader->ListType!=AVI_HDRL_ID)return AVI_HDRL_ERR; //HDRL ID<49><44><EFBFBD><EFBFBD>
buf+=sizeof(LIST_HEADER); //ƫ<><C6AB>
2025-06-27 00:32:57 +08:00
avihheader=(AVIH_HEADER*)(buf);
2025-07-05 19:47:28 +08:00
if(avihheader->BlockID!=AVI_AVIH_ID)return AVI_AVIH_ERR; //AVIH ID<49><44><EFBFBD><EFBFBD>
avix.SecPerFrame=avihheader->SecPerFrame; //<2F>õ<EFBFBD>֡<EFBFBD><D6A1><EFBFBD><EFBFBD>ʱ<EFBFBD><CAB1>
avix.TotalFrame=avihheader->TotalFrame; //<2F>õ<EFBFBD><C3B5><EFBFBD>֡<EFBFBD><D6A1>
buf+=avihheader->BlockSize+8; //ƫ<><C6AB>
2025-06-27 00:32:57 +08:00
listheader=(LIST_HEADER*)(buf);
2025-07-05 19:47:28 +08:00
if(listheader->ListID!=AVI_LIST_ID)return AVI_LIST_ERR; //LIST ID<49><44><EFBFBD><EFBFBD>
if(listheader->ListType!=AVI_STRL_ID)return AVI_STRL_ERR; //STRL ID<49><44><EFBFBD><EFBFBD>
2025-06-27 00:32:57 +08:00
strhheader=(STRH_HEADER*)(buf+12);
2025-07-05 19:47:28 +08:00
if(strhheader->BlockID!=AVI_STRH_ID)return AVI_STRH_ERR; //STRH ID<49><44><EFBFBD><EFBFBD>
if(strhheader->StreamType==AVI_VIDS_STREAM) //<2F><>Ƶ֡<C6B5><D6A1>ǰ
2025-06-27 00:32:57 +08:00
{
2025-07-05 19:47:28 +08:00
if(strhheader->Handler!=AVI_FORMAT_MJPG)return AVI_FORMAT_ERR; //<2F><>MJPG<50><47>Ƶ<EFBFBD><C6B5>,<2C><>֧<EFBFBD><D6A7>
avix.VideoFLAG=(u8*)AVI_VIDS_FLAG_TBL[0]; //<2F><>Ƶ<EFBFBD><C6B5><EFBFBD><EFBFBD><EFBFBD><EFBFBD> "00dc"
avix.AudioFLAG=(u8*)AVI_AUDS_FLAG_TBL[1]; //<2F><>Ƶ<EFBFBD><C6B5><EFBFBD><EFBFBD><EFBFBD><EFBFBD> "01wb"
2025-06-27 00:32:57 +08:00
bmpheader=(STRF_BMPHEADER*)(buf+12+strhheader->BlockSize+8);//strf
2025-07-05 19:47:28 +08:00
if(bmpheader->BlockID!=AVI_STRF_ID)return AVI_STRF_ERR; //STRF ID<49><44><EFBFBD><EFBFBD>
2025-06-27 00:32:57 +08:00
avix.Width=bmpheader->bmiHeader.Width;
avix.Height=bmpheader->bmiHeader.Height;
2025-07-05 19:47:28 +08:00
buf+=listheader->BlockSize+8; //ƫ<><C6AB>
2025-06-27 00:32:57 +08:00
listheader=(LIST_HEADER*)(buf);
2025-07-05 19:47:28 +08:00
if(listheader->ListID!=AVI_LIST_ID)//<2F>Dz<EFBFBD><C7B2><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ƶ֡<C6B5><D6A1><EFBFBD><EFBFBD>Ƶ<EFBFBD>ļ<EFBFBD>
2025-06-27 00:32:57 +08:00
{
2025-07-05 19:47:28 +08:00
avix.SampleRate=0; //<2F><>Ƶ<EFBFBD><C6B5><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
avix.Channels=0; //<2F><>Ƶͨ<C6B5><CDA8><EFBFBD><EFBFBD>
avix.AudioType=0; //<2F><>Ƶ<EFBFBD><C6B5>ʽ
2025-06-27 00:32:57 +08:00
}else
{
2025-07-05 19:47:28 +08:00
if(listheader->ListType!=AVI_STRL_ID)return AVI_STRL_ERR; //STRL ID<49><44><EFBFBD><EFBFBD>
2025-06-27 00:32:57 +08:00
strhheader=(STRH_HEADER*)(buf+12);
2025-07-05 19:47:28 +08:00
if(strhheader->BlockID!=AVI_STRH_ID)return AVI_STRH_ERR; //STRH ID<49><44><EFBFBD><EFBFBD>
if(strhheader->StreamType!=AVI_AUDS_STREAM)return AVI_FORMAT_ERR;//<2F><>ʽ<EFBFBD><CABD><EFBFBD><EFBFBD>
2025-06-27 00:32:57 +08:00
wavheader=(STRF_WAVHEADER*)(buf+12+strhheader->BlockSize+8);//strf
2025-07-05 19:47:28 +08:00
if(wavheader->BlockID!=AVI_STRF_ID)return AVI_STRF_ERR; //STRF ID<49><44><EFBFBD><EFBFBD>
avix.SampleRate=wavheader->SampleRate; //<2F><>Ƶ<EFBFBD><C6B5><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
avix.Channels=wavheader->Channels; //<2F><>Ƶͨ<C6B5><CDA8><EFBFBD><EFBFBD>
avix.AudioType=wavheader->FormatTag; //<2F><>Ƶ<EFBFBD><C6B5>ʽ
2025-06-27 00:32:57 +08:00
}
2025-07-05 19:47:28 +08:00
}else if(strhheader->StreamType==AVI_AUDS_STREAM) //<2F><>Ƶ֡<C6B5><D6A1>ǰ
2025-06-27 00:32:57 +08:00
{
2025-07-05 19:47:28 +08:00
avix.VideoFLAG=(u8*)AVI_VIDS_FLAG_TBL[1]; //<2F><>Ƶ<EFBFBD><C6B5><EFBFBD><EFBFBD><EFBFBD><EFBFBD> "01dc"
avix.AudioFLAG=(u8*)AVI_AUDS_FLAG_TBL[0]; //<2F><>Ƶ<EFBFBD><C6B5><EFBFBD><EFBFBD><EFBFBD><EFBFBD> "00wb"
2025-06-27 00:32:57 +08:00
wavheader=(STRF_WAVHEADER*)(buf+12+strhheader->BlockSize+8);//strf
2025-07-05 19:47:28 +08:00
if(wavheader->BlockID!=AVI_STRF_ID)return AVI_STRF_ERR; //STRF ID<49><44><EFBFBD><EFBFBD>
avix.SampleRate=wavheader->SampleRate; //<2F><>Ƶ<EFBFBD><C6B5><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
avix.Channels=wavheader->Channels; //<2F><>Ƶͨ<C6B5><CDA8><EFBFBD><EFBFBD>
avix.AudioType=wavheader->FormatTag; //<2F><>Ƶ<EFBFBD><C6B5>ʽ
buf+=listheader->BlockSize+8; //ƫ<><C6AB>
2025-06-27 00:32:57 +08:00
listheader=(LIST_HEADER*)(buf);
2025-07-05 19:47:28 +08:00
if(listheader->ListID!=AVI_LIST_ID)return AVI_LIST_ERR; //LIST ID<49><44><EFBFBD><EFBFBD>
if(listheader->ListType!=AVI_STRL_ID)return AVI_STRL_ERR; //STRL ID<49><44><EFBFBD><EFBFBD>
2025-06-27 00:32:57 +08:00
strhheader=(STRH_HEADER*)(buf+12);
2025-07-05 19:47:28 +08:00
if(strhheader->BlockID!=AVI_STRH_ID)return AVI_STRH_ERR; //STRH ID<49><44><EFBFBD><EFBFBD>
if(strhheader->StreamType!=AVI_VIDS_STREAM)return AVI_FORMAT_ERR;//<2F><>ʽ<EFBFBD><CABD><EFBFBD><EFBFBD>
2025-06-27 00:32:57 +08:00
bmpheader=(STRF_BMPHEADER*)(buf+12+strhheader->BlockSize+8);//strf
2025-07-05 19:47:28 +08:00
if(bmpheader->BlockID!=AVI_STRF_ID)return AVI_STRF_ERR; //STRF ID<49><44><EFBFBD><EFBFBD>
if(bmpheader->bmiHeader.Compression!=AVI_FORMAT_MJPG)return AVI_FORMAT_ERR;//<2F><>ʽ<EFBFBD><CABD><EFBFBD><EFBFBD>
2025-06-27 00:32:57 +08:00
avix.Width=bmpheader->bmiHeader.Width;
avix.Height=bmpheader->bmiHeader.Height;
}
2025-07-05 19:47:28 +08:00
offset=avi_srarch_id(tbuf,size,"movi"); //<2F><><EFBFBD><EFBFBD>movi ID
if(offset==0)return AVI_MOVI_ERR; //MOVI ID<49><44><EFBFBD><EFBFBD>
if(avix.SampleRate)//<2F><><EFBFBD><EFBFBD>Ƶ<EFBFBD><C6B5>,<2C>Ų<EFBFBD><C5B2><EFBFBD>
2025-06-27 00:32:57 +08:00
{
tbuf+=offset;
2025-07-05 19:47:28 +08:00
offset=avi_srarch_id(tbuf,size,avix.AudioFLAG); //<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ƶ<EFBFBD><C6B5><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
if(offset==0)return AVI_STREAM_ERR; //<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
2025-06-27 00:32:57 +08:00
tbuf+=offset+4;
2025-07-05 19:47:28 +08:00
avix.AudioBufSize=*((u16*)tbuf); //<2F>õ<EFBFBD><C3B5><EFBFBD>Ƶ<EFBFBD><C6B5>buf<75><66>С.
2025-06-27 00:32:57 +08:00
}
// printf("avi init ok\r\n");
// printf("avix.SecPerFrame:%d\r\n",avix.SecPerFrame);
// printf("avix.TotalFrame:%d\r\n",avix.TotalFrame);
// printf("avix.Width:%d\r\n",avix.Width);
// printf("avix.Height:%d\r\n",avix.Height);
// printf("avix.AudioType:%d\r\n",avix.AudioType);
// printf("avix.SampleRate:%d\r\n",avix.SampleRate);
// printf("avix.Channels:%d\r\n",avix.Channels);
// printf("avix.AudioBufSize:%d\r\n",avix.AudioBufSize);
// printf("avix.VideoFLAG:%s\r\n",avix.VideoFLAG);
// printf("avix.AudioFLAG:%s\r\n",avix.AudioFLAG);
return res;
}
2025-07-05 19:47:28 +08:00
//<2F><><EFBFBD><EFBFBD> ID
//buf:<3A><><EFBFBD><EFBFBD><E9BBBA><EFBFBD><EFBFBD>
//size:<3A><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>С
//id:Ҫ<><D2AA><EFBFBD>ҵ<EFBFBD>id,<2C><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>4<EFBFBD>ֽڳ<D6BD><DAB3><EFBFBD>
//<2F><><EFBFBD><EFBFBD>ֵ:0,<2C><><EFBFBD><EFBFBD>ʧ<EFBFBD><CAA7>,<2C><><EFBFBD><EFBFBD>:movi IDƫ<44><C6AB><EFBFBD><EFBFBD>
2025-06-27 00:32:57 +08:00
u16 avi_srarch_id(u8* buf,int size,u8 *id)
{
u16 i;
size-=4;
for(i=0;i<size;i++)
{
if(buf[i]==id[0])
if(buf[i+1]==id[1])
if(buf[i+2]==id[2])
2025-07-05 19:47:28 +08:00
if(buf[i+3]==id[3])return i;//<2F>ҵ<EFBFBD>"id"<22><><EFBFBD>ڵ<EFBFBD>λ<EFBFBD><CEBB>
2025-06-27 00:32:57 +08:00
}
return 0;
}
2025-07-05 19:47:28 +08:00
//<2F>õ<EFBFBD>stream<61><6D><EFBFBD><EFBFBD>Ϣ
//buf:<3A><><EFBFBD><EFBFBD>ʼ<EFBFBD><CABC>ַ(<28><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>01wb/00wb/01dc/00dc<64><63>ͷ)
2025-06-27 00:32:57 +08:00
AVISTATUS avi_get_streaminfo(u8* buf)
{
int offset=0;
2025-07-05 19:47:28 +08:00
avix.StreamID=MAKEWORD(buf+2); //<2F>õ<EFBFBD><C3B5><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
avix.StreamSize=MAKEDWORD(buf+4); //<2F>õ<EFBFBD><C3B5><EFBFBD><EFBFBD><EFBFBD>С
if(avix.StreamSize%2)avix.StreamSize++; //<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>1(avix.StreamSize,<2C><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ż<EFBFBD><C5BC>)
2025-06-27 00:32:57 +08:00
if(avix.StreamID==AVI_VIDS_FLAG||avix.StreamID==AVI_AUDS_FLAG)return AVI_OK;
return AVI_STREAM_ERR;
}
static vu8 g_frame_en=0;
void avi_timer_irq (void)
{
g_frame_en=1;
}
2025-07-05 19:47:28 +08:00
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>avix.SecPerFrame
2025-06-27 00:32:57 +08:00
void avi_timer_init (u32 t)
{
TIMER_InitStruct timer_init={0};
timer_init.Cycle=t/1;
timer_init.Tim=TIM3;
timer_init.UpdataCall=avi_timer_irq;
TIMER_InitNormal(&timer_init);
}
void avi_tiemr_delete (void)
{
TIMER_DeInit (TIM3);
}
2025-07-05 19:47:28 +08:00
#define AVI_AUDIO_BUF_SIZE 1024*5 //<2F><><EFBFBD><EFBFBD>avi<76><69><EFBFBD><EFBFBD>ʱ,<2C><>Ƶbuf<75><66>С.
#define AVI_VIDEO_BUF_SIZE 1024*200 //<2F><><EFBFBD><EFBFBD>avi<76><69><EFBFBD><EFBFBD>ʱ,<2C><>Ƶbuf<75><66>С.
2025-06-27 00:32:57 +08:00
2025-07-05 19:47:28 +08:00
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ƶ
2025-06-27 00:32:57 +08:00
int video_play (char *pname,int loop)
{
2025-07-05 19:47:28 +08:00
u8 listhead[8]={0};//<2F><><EFBFBD><EFBFBD>ͷ
2025-06-27 00:32:57 +08:00
u32 fresh=0;
2025-07-05 19:47:28 +08:00
u8* framebuf; //<2F><>Ƶ<EFBFBD><C6B5><EFBFBD><EFBFBD>buf
u8* pbuf; //bufָ<66><D6B8>
2025-06-27 00:32:57 +08:00
FIL *favi;
u8 res=0;
u16 offset=0;
2025-06-28 22:15:49 +08:00
UINT nr;
2025-06-27 00:32:57 +08:00
u8 key;
u8 i2ssavebuf;
DAC_UserStruct dac={0};
u8 *audio_buff=mymalloc (AVI_AUDIO_BUF_SIZE);
2025-07-05 19:47:28 +08:00
framebuf=mymalloc(AVI_VIDEO_BUF_SIZE); //<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ƶbuf
favi=(FIL*)mymalloc(sizeof(FIL)); //<2F><><EFBFBD><EFBFBD>favi<76>ڴ<EFBFBD>
g_i2sbuf[0]=mymalloc(AVI_AUDIO_BUF_SIZE); //<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ƶ<EFBFBD>ڴ<EFBFBD>
g_i2sbuf[1]=mymalloc(AVI_AUDIO_BUF_SIZE); //<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ƶ<EFBFBD>ڴ<EFBFBD>
g_i2sbuf[2]=mymalloc(AVI_AUDIO_BUF_SIZE); //<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ƶ<EFBFBD>ڴ<EFBFBD>
g_i2sbuf[3]=mymalloc(AVI_AUDIO_BUF_SIZE); //<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ƶ<EFBFBD>ڴ<EFBFBD>
2025-06-27 00:32:57 +08:00
mymemset(g_i2sbuf[0],0,AVI_AUDIO_BUF_SIZE);
mymemset(g_i2sbuf[1],0,AVI_AUDIO_BUF_SIZE);
mymemset(g_i2sbuf[2],0,AVI_AUDIO_BUF_SIZE);
mymemset(g_i2sbuf[3],0,AVI_AUDIO_BUF_SIZE);
while(res==0)
{
res=f_open(favi,(char *)pname,FA_READ);
if(res==0)
{
pbuf=framebuf;
2025-07-05 19:47:28 +08:00
res=f_read(favi,pbuf,AVI_VIDEO_BUF_SIZE,&nr);//<2F><>ʼ<EFBFBD><CABC>ȡ
2025-06-27 00:32:57 +08:00
if(res)
{
break;
}
2025-07-05 19:47:28 +08:00
//<2F><>ʼavi<76><69><EFBFBD><EFBFBD>
res=avi_init(pbuf,AVI_VIDEO_BUF_SIZE); //avi<76><69><EFBFBD><EFBFBD>
2025-06-27 00:32:57 +08:00
if(res)
{
break;
}
//avi_timer_init (avix.SecPerFrame);
2025-07-05 19:47:28 +08:00
offset=avi_srarch_id(pbuf,AVI_VIDEO_BUF_SIZE,(u8*)"movi");//Ѱ<><D1B0>movi ID
avi_get_streaminfo(pbuf+offset+4); //<2F><>ȡ<EFBFBD><C8A1><EFBFBD><EFBFBD>Ϣ
f_lseek(favi,offset+12-8); //<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>־ID,<2C><><EFBFBD><EFBFBD>ַƫ<D6B7>Ƶ<EFBFBD><C6B5><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ݿ<EFBFBD>ʼ<EFBFBD><CABC>
2025-06-27 00:32:57 +08:00
extern void jdmerge_setvideo_xsize (int xsize,int lcd_xsize);
2025-07-05 19:47:28 +08:00
jdmerge_setvideo_xsize (avix.Width,LCD_GetLcdSizeX());//<2F><><EFBFBD>õ<EFBFBD>ַ<EFBFBD>Զ<EFBFBD><D4B6><EFBFBD><EFBFBD><EFBFBD>
res=mjpegdec_init((LCD_GetLcdSizeX()-avix.Width)/2,(LCD_GetLcdSizeY()-avix.Height)/2);//JPG<50><47><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ʼ<EFBFBD><CABC>
if(avix.SampleRate) //<2F><><EFBFBD><EFBFBD>Ƶ<EFBFBD><C6B5>Ϣ,<2C>ų<EFBFBD>ʼ<EFBFBD><CABC>
2025-06-27 00:32:57 +08:00
{
2025-07-05 19:47:28 +08:00
//<2F><>ʼ<EFBFBD><CABC>DAC
2025-06-27 00:32:57 +08:00
dac.buff1=(u32 *)g_i2sbuf[1];
dac.buff2=(u32 *)g_i2sbuf[2];
dac.buff_size=avix.AudioBufSize;
dac.rate=DAC_GetRate(avix.SampleRate);
dac.call_back=audio_i2s_dma_callback;
DAC_NormalInit (&dac);
}
2025-07-05 19:47:28 +08:00
while(1)//<2F><><EFBFBD><EFBFBD>ѭ<EFBFBD><D1AD>
2025-06-27 00:32:57 +08:00
{
f_read(favi,listhead,8,&nr);
2025-07-05 19:47:28 +08:00
if(avi_get_streaminfo(listhead))//<2F><>ȡ<EFBFBD><C8A1>һ֡ <20><><EFBFBD><EFBFBD>־
2025-06-27 00:32:57 +08:00
{
break;
}
2025-07-05 19:47:28 +08:00
if (Touch_GetState()->x[1]!=0) break; //<2F><>Ļ<EFBFBD><C4BB><EFBFBD><EFBFBD><E3B4A5><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
if (USART3_GetKeyPressed()&(0x08)) break;//<2F><><EFBFBD>·<EFBFBD><C2B7>ؼ<EFBFBD><D8BC><EFBFBD><EFBFBD><EFBFBD>
if(avix.StreamID==AVI_VIDS_FLAG) //<2F><>Ƶ<EFBFBD><C6B5>
2025-06-27 00:32:57 +08:00
{
pbuf=framebuf;
//mymemset (pbuf,0,AVI_VIDEO_BUF_SIZE);
2025-07-05 19:47:28 +08:00
f_read(favi,pbuf,avix.StreamSize+8-8,&nr); //<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>֡+<2B><>һ<EFBFBD><D2BB><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ID<49><44>Ϣ
//<2F>ȴ<EFBFBD>֡ʱ<D6A1><CAB1>
2025-06-27 00:32:57 +08:00
//while (g_frame_en==0){} g_frame_en=0;
while (LCD_GetLayerUpdataStat ()==0);
LCD_SwitchLayerBuff();
res=mjpegdec_decode(pbuf,avix.StreamSize);
if (res==0)
{
LCD_ExitLayerBuff();
}
if(res)
{
//break;
}
2025-07-05 19:47:28 +08:00
}else //<2F><>Ƶ<EFBFBD><C6B5>
2025-06-27 00:32:57 +08:00
{
2025-07-05 19:47:28 +08:00
// f_read(favi,audio_buff,avix.StreamSize+8-8,&nr);//<2F><><EFBFBD><EFBFBD>i2sbuf
2025-06-27 00:32:57 +08:00
// pbuf=audio_buff;
i2ssavebuf++;
if(i2ssavebuf>3)i2ssavebuf=0;
do
{
nr=g_i2splaybuf;
if(nr)nr--;
else nr=3;
2025-07-05 19:47:28 +08:00
}while(i2ssavebuf==nr);//<2F><>ײ<EFBFBD>ȴ<EFBFBD>.
f_read(favi,g_i2sbuf[i2ssavebuf],avix.StreamSize,&nr);//<2F><><EFBFBD><EFBFBD>i2sbuf
2025-06-27 00:32:57 +08:00
u16 *p=(u16 *)g_i2sbuf[i2ssavebuf];
for (int i=0;i<avix.StreamSize/2;i++)
p[i]=(p[i]+0x8000)>>4;
pbuf=g_i2sbuf[i2ssavebuf];
}
}
//avi_tiemr_delete();
2025-07-05 19:47:28 +08:00
mjpegdec_free(); //<2F>ͷ<EFBFBD><CDB7>ڴ<EFBFBD>
2025-06-27 00:32:57 +08:00
f_close(favi);
}
if (loop==0)
break;
}
myfree(framebuf);
myfree(favi);
myfree(audio_buff);
myfree(g_i2sbuf[0]);
myfree(g_i2sbuf[1]);
myfree(g_i2sbuf[2]);
myfree(g_i2sbuf[3]);
DAC_NormalDeInit (&dac);
return (int)res;
}