Ejemplo n.º 1
0
static DFBEnumerationResult
screen_callback( DFBScreenID           id,
                 DFBScreenDescription  desc,
                 void                 *arg )
{
     int              i;
     DFBResult        ret;
     IDirectFBScreen *screen;

     ret = dfb->GetScreen( dfb, id, &screen );
     if (ret)
          DirectFBErrorFatal( "IDirectFB::GetScreen", ret );

     /* Name */
     printf( "Screen (%02x) %-30s", id, desc.name );

     switch (id) {
          case DSCID_PRIMARY:
               printf( "  (primary screen)" );
               break;
          default:
               break;
     }

     printf( "\n" );

     /* Caps */
     printf( "   Caps: " );

     for (i=0; screen_caps[i].capability; i++) {
          if (desc.caps & screen_caps[i].capability)
               printf( "%s ", screen_caps[i].name );
     }

     printf( "\n\n" );


     /* Mixers */
     if (desc.mixers)
          dump_mixers( screen, desc.mixers );

     /* Encoders */
     if (desc.encoders)
          dump_encoders( screen, desc.encoders );

     /* Outputs */
     if (desc.outputs)
          dump_outputs( screen, desc.outputs );

     /* Display layers */
     enum_display_layers( screen );

     screen->Release( screen );

     return DFB_OK;
}
void
DirectFB_InitModes(_THIS)
{
    SDL_DFB_DEVICEDATA(_this);
    IDirectFBDisplayLayer *layer = NULL;
    SDL_VideoDisplay display;
    DFB_DisplayData *dispdata = NULL;
    SDL_DisplayMode mode;
    DFBGraphicsDeviceDescription caps;
    DFBDisplayLayerConfig dlc;
    struct screen_callback_t *screencbdata;

    int tcw[DFB_MAX_SCREENS];
    int tch[DFB_MAX_SCREENS];
    int i;
    DFBResult ret;

    SDL_DFB_ALLOC_CLEAR(screencbdata, sizeof(*screencbdata));

    screencbdata->numscreens = 0;

    for (i = 0; i < DFB_MAX_SCREENS; i++) {
        screencbdata->gralayer[i] = -1;
        screencbdata->vidlayer[i] = -1;
    }

    SDL_DFB_CHECKERR(devdata->dfb->EnumScreens(devdata->dfb, &EnumScreensCallback,
                                               screencbdata));

    for (i = 0; i < screencbdata->numscreens; i++) {
        IDirectFBScreen *screen;

        SDL_DFB_CHECKERR(devdata->dfb->GetScreen(devdata->dfb,
                                                 screencbdata->screenid
                                                 [i], &screen));

        screencbdata->aux = i;
        SDL_DFB_CHECKERR(screen->EnumDisplayLayers(screen, &EnumLayersCallback,
                                                   screencbdata));
        screen->GetSize(screen, &tcw[i], &tch[i]);

        screen->Release(screen);
    }

    /* Query card capabilities */

    devdata->dfb->GetDeviceDescription(devdata->dfb, &caps);

    for (i = 0; i < screencbdata->numscreens; i++) {
        SDL_DFB_CHECKERR(devdata->dfb->GetDisplayLayer(devdata->dfb,
                                                       screencbdata->gralayer
                                                       [i], &layer));

        SDL_DFB_CHECKERR(layer->SetCooperativeLevel(layer,
                                                    DLSCL_ADMINISTRATIVE));
        layer->EnableCursor(layer, 1);
        SDL_DFB_CHECKERR(layer->SetCursorOpacity(layer, 0xC0));

        if (devdata->use_yuv_underlays) {
            dlc.flags = DLCONF_PIXELFORMAT | DLCONF_OPTIONS;
            dlc.pixelformat = DSPF_ARGB;
            dlc.options = DLOP_ALPHACHANNEL;

            ret = layer->SetConfiguration(layer, &dlc);
            if (ret != DFB_OK) {
                /* try AiRGB if the previous failed */
                dlc.pixelformat = DSPF_AiRGB;
                SDL_DFB_CHECKERR(layer->SetConfiguration(layer, &dlc));
            }
        }

        /* Query layer configuration to determine the current mode and pixelformat */
        dlc.flags = DLCONF_ALL;
        SDL_DFB_CHECKERR(layer->GetConfiguration(layer, &dlc));

        mode.format = DirectFB_DFBToSDLPixelFormat(dlc.pixelformat);
        
        if (mode.format == SDL_PIXELFORMAT_UNKNOWN) {
            SDL_DFB_ERR("Unknown dfb pixelformat %x !\n", dlc.pixelformat);
            goto error;
        }

        mode.w = dlc.width;
        mode.h = dlc.height;
        mode.refresh_rate = 0;
        mode.driverdata = NULL;

        SDL_DFB_ALLOC_CLEAR(dispdata, sizeof(*dispdata));

        dispdata->layer = layer;
        dispdata->pixelformat = dlc.pixelformat;
        dispdata->cw = tcw[i];
        dispdata->ch = tch[i];

        /* YUV - Video layer */

        dispdata->vidID = screencbdata->vidlayer[i];
        dispdata->vidIDinuse = 0;

        SDL_zero(display);

        display.desktop_mode = mode;
        display.current_mode = mode;
        display.driverdata = dispdata;

#if (DFB_VERSION_ATLEAST(1,2,0))
        dlc.flags =
            DLCONF_WIDTH | DLCONF_HEIGHT | DLCONF_PIXELFORMAT |
            DLCONF_OPTIONS;
        ret = layer->SetConfiguration(layer, &dlc);
#endif

        SDL_DFB_CHECKERR(layer->SetCooperativeLevel(layer, DLSCL_SHARED));

        SDL_AddVideoDisplay(&display);
    }
    SDL_DFB_FREE(screencbdata);
    return;
  error:
    /* FIXME: Cleanup not complete, Free existing displays */
    SDL_DFB_FREE(dispdata);
    SDL_DFB_RELEASE(layer);
    return;
}