作者 QQ: 35327864,msn: fgwf1@hotmail.com,mail: agooou@gmail.com
directfb
AMP
amp_test
main()
global_init(): init osd layer and video layer.
DirectFBInit (argc, argv);
DirectFBCreate (&gdfb);
gdfb->SetCooperativeLevel (gdfb, DFSCL_NORMAL);
gdfb->GetScreen (gdfb, 0, &screen);
gdfb->CreateInputEventBuffer (gdfb, DICAPS_KEYS, DFB_TRUE, &keybuffer);
keybuffer->CreateFileDescriptor (keybuffer, &keyfd);
init_osd_layer (false);
gdfb->GetDisplayLayer (gdfb, DLID_PRIMARY, &layer);
layer->SetCooperativeLevel (layer, DLSCL_ADMINISTRATIVE);
layer->SetBackgroundMode (layer, DLBM_DONTCARE);
layer->EnableCursor (layer, 0);
DFBDisplayLayerConfig dlcfg;
dlcfg.flags = (DFBDisplayLayerConfigFlags) (DLCONF_BUFFERMODE|DLCONF_PIXELFORMAT);
dlcfg.buffermode = osd2Buf ? DLBM_BACKVIDEO:DLBM_FRONTONLY;
dlcfg.pixelformat = bpp == 8 ?DSPF_LUT8 : (bpp == 16 ? DSPF_ARGB4444 : DSPF_ARGB);
layer->SetConfiguration (layer, &dlcfg);
gdfb->GetDisplayLayer (gdfb, 2, &layer_mv);
layer_mv->SetCooperativeLevel (layer_mv, DLSCL_EXCLUSIVE);
layer->GetConfiguration (layer, &dlcfg); // find out size of the primay surface
xres = dlcfg.width;
yres = dlcfg.height;
get_signal_resolution(signal);
DFBFontDescription desc;
desc.flags = DFDESC_HEIGHT;
desc.height = yres/40;
gdfb->CreateFont (gdfb, font_filename, &desc, &font);
font->GetHeight (font, &fontheight);
font->GetAscender (font, &fontascender);
font->GetDescender (font, &fontdescender);
global_init_osd_resources (osdBPP);
init_osd_layer (bpp);
layer->GetSurface (layer, &primary);
primary->SetDrawingFlags (primary, DSDRAW_NOFX);
layer->SetBackgroundColor (layer, 0xFF, 0xFF, 0xFF, 0x00);
layer->SetBackgroundMode (layer, DLBM_COLOR);
--enable_gui ()
init_gui ()
layer->CreateWindow (layer, &wdsc, &sts_window);
layer->CreateWindow (layer, &wdsc, &msg_window);
layer->CreateWindow (layer, &wdsc, &info_window);
layer->CreateWindow (layer, &wdsc, &adj_window);
info_window->LowerToBottom (info_window);
msg_window->RaiseToTop (msg_window);
init_hotplug ();
check_mnt_point(INT_STOR);
read_dev_properties(INT_STOR,&prop_i_stor);
check_mnt_point(EXT_STOR);
read_dev_properties(EXT_STOR,&prop_e_stor);
open_fifo ()
mkfifo ("/tmp/bdp.fifo", S_IRUSR|S_IWUSR); //why "/tmp/bdp.fifo", it is used by /sbin/usb-storage , which is in cs_rootfs_1.2.6/package/hotplug2/files/usb-storage:BDP_FIFO=/tmp/bdp.fifo
hotplug_fd = open ("/tmp/bdp.fifo");
gdfb->CreateImageProvider (gdfb, tinyGifName, &preLoadImg);
gdfb->GetInterface (gdfb, "IAdvancedMediaProvider", NULL, (void*)(MAX_AMP_INSTANCES-1), (void*)&cfgamp);
cfgamp->SetApplicationCallbacks (cfgamp, (void*)&processConfigPreview, (void*)&processConfigConfirm, CMD_INVALID_CALLBACK, CMD_INVALID_CALLBACK);
cfgamp->GetDescription (cfgamp, &desc); //avoid of this call.
if(pCrtVideoCfg) cfgamp->SetConfiguration (cfgamp, pCrtVideoCfg, NULL); //if not default video setting.
print_video_settings (pCrtVideoCfg);
if (pCrtAudioCfg) cfgamp->SetConfiguration (cfgamp, NULL, pCrtAudioCfg);
print_audio_setting ();
if (pCrtDRMCfg) cfgamp->SetConfiguration (cfgamp, NULL, NULL);
print_drm_settings ();
DFBScreenMixerConfig mixcfg;
mixcfg.flags = (DFBScreenMixerConfigFlags) (DSMCONF_BACKGROUND|DSMCONF_LAYERS);
mixcfg.background.a = 0;
mixcfg.background.r = 0;
mixcfg.background.g = 0;
mixcfg.background.b = 0;
DFB_DISPLAYLAYER_IDS_EMPTY (mixcfg.layers);
DFB_DISPLAYLAYER_IDS_ADD (mixcfg.layers, EM86LAYER_OSD);
if (useBackground) DFB_DISPLAYLAYER_IDS_ADD (mixcfg.layers, EM86LAYER_BKGND);
screen->SetMixerConfiguration (screen, 0, &mixcfg);
for (i=0; i < amps; i++)
InitAMP (i);
StartMediaPresentation(gdfb, i, &_table[i].ampfd, &_table[i].layerID, &_table[i].amp, &_table[i].img_size);
dfb->GetInstance (dfb, "IAdvancedMediaPrivider", "EM8630", (void*)media->ampID, &dummy); //at this time, will power on hdmi.
err = media->amp->GetEventBuffer(media->amp, &media->ampEvent);
err = media->amp->OpenMedia (media->amp, media->url, &media->format, media->openParam);
IAdvancedMediaProvider_EM8630_OpenMedia()
CreateLpbNavigator()
ThreadLauncher()
media->ampEvent->WaitForEvent (media->ampEvent);
DFBEvent event;
media->ampEvent->GetEvent (media->ampEvent, &event);
assert (media->ampEvent->HasEvent(media->ampEvent) != DFB_OK);
ProcessMediaEvents (ampIndex);
media->amp->UploadStatusChanges(media->amp, &media->status.generic, (DFBBollean)false);
err = media->amp->StartPresentation(media->amp, (DFBBoolean)!media->noAutoPlay);
media->ampEvent->WaitForEvent (media->ampEvent);
DFBEvent event;
media->ampEvent->GetEvent (media->ampEvent, &event);
ProcessMediaEvents (ampIndex);
media->amp->UploadStatusChanges(media->amp, &media->status.generic, (DFBBollean)false);
err = media->ampEvent->CreateFileDescriptor (media->ampEvent, pEventFD); //this time we can create fd!!!
// there is a special set for second video, do not use interlace.
gdfb->GetDisplayLayer (gdfb, amp_table[i].layerID, &_table[i].layer);
amp_table[i].layer->SetCooperativeLevel (amp_table[i].layer, DLSCL_EXCLUSIVE);
amp_table[i].layer->SetScreenRectangle (amp_table[i].layer, amp_table[i].dst_area.x, amp_table[i].dst_area.y, amp_table[i].dst_area.w, amp_table[i].dst_area.h);
screen->GetMixerConfiguration (screen, 0, &mixcfg);
mixcfg.flags = DSMCONF_LAYERS;
DFB_DISPLAYLAYER_IDS_ADD(mixcfg.layers, amp_table[i].layerID);
if (layer_bg) DFB_DISPLAYLAYER_IDS_ADD(mixcfg.layers, EM86LAYER_BKGND);
screen->SetMixerConfiguration (screen, 0, &mixcfg);
set_active_amp (0, true, true);
amp_table[ampIndex].layer->SetScreenRectangle (amp_table[ampIndex].layer, dst_rect.x, dst_rect.y, dst_rect.w, dst_rect.h);
amp_table[ampIndex].layer->SetSourceRectangle (amp_table[ampIndex].layer, src_rect.x, src_rect.y, src_rect.w, src_rect.h);
for (i=0; i<amps; i++)
amp_table[i].layer->GetConfiguration(amp_table[i].layer, &lcfg);
if (allow_screen_rect_change) amp_table[ampIndex].layer->SetScreenRectangle (amp_table[ampIndex].layer, dst_rect.x, dst_rect.y, dst_rect.w, dst_rect.h);
if (allow_src_rect_change) amp_table[ampIndex].layer->SetSourceRectangle (amp_table[ampIndex].layer, src_rect.x, src_rect.y, src_rect.w, src_rect.h);
if (amp_table[i].layerID == EM86LAYER_SECVIDEO) amp_table[i].layer->SetLevel (amp_table[i].layer, -2);
//while (1) {
FD_ZERO (&set);
FD_SET (keyfd, &set);
if (hotplug_fd != -1) FD_SET (hotplug_fd, &set);
if (amp) FD_SET (ampfd, &set);
select (FD_SETSIZE, &set, NULL, NULL, &timeout);
if (FD_ISSET(keyfd,&set)) {
} else if (FD_ISSET(ampfd, &set)) {
} else if (FD_ISSET(hotplug_fd, &set)) {
}
//}
if (cfgamp) cfgamp->Release (cfgamp);
uninit_hotplug ();
close_fifo ();
close (hotplug_fd);
unlink ("/tmp/bdp.fifo");
global_uninit ();
//for (i=0; i<amps; i++) {
TerminateAMP (i, true);
EndMediaPresentation (ampIndex, releaseAMP);
disable_secosd_gui();
disable_sv_layer ();
screen->GetMixerConfiguration(screen, 0, &mixcfg);
mixcfg.flags=(DFBScreenMixerConfigFlags)(DSMCONF_LAYERS);
screen->SetMixerConfiguration(screen, 0, &mixcfg); //disable the layer output
amp_table[ampIndex].layer->Release (amp_table[ampIndex].layer);
//if EM86LAYER_SECVIDEO {
screen->GetEncoderConfiguration (screen, 0, &enc_cfg);
enc_cfg.flags=(DFBScreenEncoderConfigFlags) (DSECONF_DEINTERLACING_MODE|DSECONF_DELAYED_CONFIG);
screen->SetEncoderConfiguration (screen, 0, &enc_cfg);
//}
FreePlaylist (i);
//}
disable_background_layer ();
disable_sv_layer ();
layer_mv->Release(layer_mv);
global_uninit_osd_resources ();
uninit_gui ();
if(layer_sec)layer_sec->Release (layer_sec);
if (font) font->Release (font);
if (fontSmall) fontSmall->Release (fontSmall);
if (screen) screen->Release (screen);
if (keybuffer) keybuffer->Release (keybuffer);
if (gdfb) gdfb->Release ();
注:
StartMediaPresentation详细过程:
dfb->GetInstance (dfb, "IAdvancedMediaPrivider", "EM8630", (void*)media->ampID, &dummy); //at this time, will power on hdmi.
err = media->amp->GetEventBuffer(media->amp, &media->ampEvent);
err = media->amp->OpenMedia (media->amp, media->url, &media->format, media->openParam);
IAdvancedMediaProvider_EM8630_OpenMedia()
CreateLpbNavigator()
ThreadLauncher()
media->ampEvent->WaitForEvent (media->ampEvent);
DFBEvent event;
media->ampEvent->GetEvent (media->ampEvent, &event);
assert (media->ampEvent->HasEvent(media->ampEvent) != DFB_OK);
ProcessMediaEvents (ampIndex);
err = media->amp->StartPresentation(media->amp, (DFBBoolean)!media->noAutoPlay);
media->ampEvent->WaitForEvent (media->ampEvent);
DFBEvent event;
media->ampEvent->GetEvent (media->ampEvent, &event);
ProcessMediaEvents (ampIndex);
err = media->ampEvent->CreateFileDescriptor (media->ampEvent, pEventFD); //this time we can create fd!!!
关于DirectFB
DirectFB是dcchd的主要组成部分。SMP865X通过DirectFB抽象了底层的输入,OSD输出,Video输出等。
1,输入部分(Input Device)
遥控器RC是被映射成一个输入设备,通过IDirectFBInputDevice接口使用。驱动将RC的keycode映射成DirectFB中的DIKS code(在directfb_keyboard.h中),并缓存到IDirectFBEventBuffer中,并可以通过一个file descriptor调用。之后,这个fd可以在线程中被select和read。
IDirectFBEventBuffer* keybuffer = NULL;
int keyfd;
DFBCHECK( gdfb->CreateInputEventBuffer (gdfb, DICAPS_KEYS, DFB_TRUE, &keybuffer));
DFBCHECK(keybuffer->CreateFileDescriptor (keybuffer, &keyfd))
2,显卡(Graphic Card)
在通常情况下,smp863x有1个graphic层,2个video层,1个background层。顺序是固定的,从上到下分别为:graphic, video, background,但2个video层可以改变顺序。大部分画图操作已经被加速了,包含颜色转换,blit等。
FillRectangle(),Blit() ,TileBlit() ,StretchBlit() 已经被加速。
A)Screen的配置(Screen Config)
a)通过IDirectFBScreen接口进行设置。用Get/Test/SetXXXConfiguration的方法
b)通过命令行或配置文件
命令行下可用:--dfb:smp-gfx-only,配置文件有/etc/directfbrc,~/.directfbrc,/etc/directfbrc.execname或~/.directfbrc.execname,其中execname要替换成程序名。
B)Layers配置
a)Main Graphics layer ("OSD")
b)Secondary Graphics layer ("SecOSD")
c)Background layer ("BGND")
d)Main Video layer ("MainVideo")
e)Secondary Video layer ("2ndVideo")
C)“GFX-only”模式
之用directfb来进行加速,--dfb:smp-gfx-only,可以参考例子dfb_play_picture
D)Image Provider接口
E)Video Provider接口
使用IDirectFBAdvancedMediaProvider
F)Font Provide接口
DrawString() 和DrawGlyph()加速了,用来进行写字。
3,AMP (Advanced Media Provider 接口)
查看:AMP reference document.
SMP865X广告机之dcchd
最新推荐文章于 2014-01-06 15:38:00 发布