status_t VirtualScreen::SetConfiguration(Desktop& desktop, ScreenConfigurations& configurations, uint32* _changedScreens) { // Remember previous screen modes typedef std::map<Screen*, display_mode> ScreenModeMap; ScreenModeMap previousModes; bool previousModesFailed = false; if (_changedScreens != NULL) { *_changedScreens = 0; try { for (int32 i = 0; i < fScreenList.CountItems(); i++) { Screen* screen = fScreenList.ItemAt(i)->screen; display_mode mode; screen->GetMode(mode); previousModes.insert(std::make_pair(screen, mode)); } } catch (...) { previousModesFailed = true; *_changedScreens = ~0L; } } _Reset(); ScreenList list; status_t status = gScreenManager->AcquireScreens(&desktop, NULL, 0, desktop.TargetScreen(), false, list); if (status != B_OK) { // TODO: we would try again here with force == true return status; } for (int32 i = 0; i < list.CountItems(); i++) { Screen* screen = list.ItemAt(i); AddScreen(screen, configurations); if (!previousModesFailed && _changedScreens != NULL) { // Figure out which screens have changed their mode display_mode mode; screen->GetMode(mode); ScreenModeMap::const_iterator found = previousModes.find(screen); if (found != previousModes.end() && memcmp(&mode, &found->second, sizeof(display_mode))) *_changedScreens |= 1 << i; } } UpdateFrame(); return B_OK; }
void ScreenManager::ReleaseScreens(ScreenList& list) { BAutolock locker(this); for (int32 i = 0; i < fScreenList.CountItems(); i++) { screen_item* item = fScreenList.ItemAt(i); for (int32 j = 0; j < list.CountItems(); j++) { Screen* screen = list.ItemAt(j); if (item->screen == screen) item->owner = NULL; } } }