123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291 |
- Constructor TX11Modes.Create(ADisplay : PDisplay; AScreen : cint);
- Begin
- FDisplay := ADisplay;
- FScreen := AScreen;
- End;
- Constructor TX11ModesNoModeSwitching.Create(ADisplay : PDisplay; AScreen : cint);
- Begin
- Inherited;
- FWidth := DisplayWidth(FDisplay, FScreen);
- FHeight := DisplayHeight(FDisplay, FScreen);
- End;
- Procedure TX11ModesNoModeSwitching.GetModes(Var AModes : TPTCModeDynArray; ACurrentDesktopFormat : TPTCFormat);
- Begin
- SetLength(AModes, 2);
- AModes[0] := TPTCMode.Create(FWidth,
- FHeight,
- ACurrentDesktopFormat);
- AModes[1] := TPTCMode.Create;
- End;
- Procedure TX11ModesNoModeSwitching.SetBestMode(AWidth, AHeight : Integer);
- Begin
- FWidth := DisplayWidth(FDisplay, FScreen);
- FHeight := DisplayHeight(FDisplay, FScreen);
- End;
- Procedure TX11ModesNoModeSwitching.RestorePreviousMode;
- Begin
- { do nothing }
- End;
- Function TX11ModesNoModeSwitching.GetWidth : Integer;
- Begin
- Result := FWidth;
- End;
- Function TX11ModesNoModeSwitching.GetHeight : Integer;
- Begin
- Result := FHeight;
- End;
- {$IFDEF ENABLE_X11_EXTENSION_XRANDR}
- Constructor TX11ModesXrandr.Create(ADisplay : PDisplay; AScreen : cint);
- Var
- dummy1, dummy2 : cint;
- Major, Minor : cint;
- Begin
- Inherited;
- If Not XRRQueryExtension(FDisplay, @dummy1, @dummy2) Then
- Raise TPTCError.Create('Xrandr extension not available');
- XRRQueryVersion(FDisplay, @Major, @Minor); // todo: check
- LOG('Xrandr version: ' + IntToStr(Major) + '.' + IntToStr(Minor));
- FRoot := RootWindow(FDisplay, FScreen);
- FXRRConfig := XRRGetScreenInfo(FDisplay, FRoot);
- If FXRRConfig = Nil Then
- Raise TPTCError.Create('XRRGetScreenInfo failed');
- Raise TPTCError.Create('Xrandr mode switcher is not yet implemented...');
- End;
- Destructor TX11ModesXrandr.Destroy;
- Begin
- If FXRRConfig <> Nil Then
- XRRFreeScreenConfigInfo(FXRRConfig);
- Inherited;
- End;
- Procedure TX11ModesXrandr.GetModes(Var AModes : TPTCModeDynArray; ACurrentDesktopFormat : TPTCFormat);
- Begin
- {...}
- End;
- Procedure TX11ModesXrandr.SetBestMode(AWidth, AHeight : Integer);
- Begin
- {todo...}
- End;
- Procedure TX11ModesXrandr.RestorePreviousMode;
- Begin
- {todo...}
- End;
- Function TX11ModesXrandr.GetWidth : Integer;
- Begin
- // todo...
- End;
- Function TX11ModesXrandr.GetHeight : Integer;
- Begin
- // todo...
- End;
- {$ENDIF ENABLE_X11_EXTENSION_XRANDR}
- {$IFDEF ENABLE_X11_EXTENSION_XF86VIDMODE}
- Constructor TX11ModesXF86VidMode.Create(ADisplay : PDisplay; AScreen : Integer);
- Var
- dummy1, dummy2 : cint;
- Begin
- Inherited;
- FSavedMode := Nil;
- FSavedDotClock := 0;
- FModeList := Nil;
- FModeListCount := 0;
- If Not XF86VidModeQueryExtension(FDisplay, @dummy1, @dummy2) Then
- Raise TPTCError.Create('VidMode extension not available');
- End;
- Destructor TX11ModesXF86VidMode.Destroy;
- Begin
- If FSavedMode <> Nil Then
- Begin
- RestorePreviousMode;
- If FSavedMode^.privsize <> 0 Then
- XFree(FSavedMode^.c_private);
- Dispose(FSavedMode);
- End;
- If FModeList <> Nil Then
- XFree(FModeList);
- Inherited Destroy;
- End;
- {todo: move the saving of the previous mode to a separate function...}
- Procedure TX11ModesXF86VidMode.RetrieveModeList;
- Begin
- { If we have been called before, do nothing }
- If FModeList <> Nil Then
- Exit;
- { Save previous mode }
- New(FSavedMode);
- FillChar(FSavedMode^, SizeOf(FSavedMode^), 0);
- XF86VidModeGetModeLine(FDisplay, FScreen, @FSavedDotClock, FSavedMode);
- { Get all available video modes }
- XF86VidModeGetAllModeLines(FDisplay, FScreen, @FModeListCount, @FModeList);
- End;
- Procedure TX11ModesXF86VidMode.GetModes(Var AModes : TPTCModeDynArray; ACurrentDesktopFormat : TPTCFormat);
- Var
- I : Integer;
- Begin
- RetrieveModeList;
- SetLength(AModes, FModeListCount + 1);
- AModes[FModeListCount] := TPTCMode.Create;
- For I := 0 To FModeListCount - 1 Do
- AModes[I] := TPTCMode.Create(FModeList[I]^.hdisplay, FModeList[I]^.vdisplay, ACurrentDesktopFormat);
- End;
- Function TX11ModesXF86VidMode.FindNumberOfBestMode(AWidth, AHeight : Integer) : Integer;
- Var
- min_diff : Integer;
- d_x, d_y : Integer;
- found_mode : Integer;
- I : Integer;
- Begin
- { Try an exact match }
- For I := 0 To FModeListCount - 1 Do
- If (FModeList[I]^.hdisplay = AWidth) And (FModeList[I]^.vdisplay = AHeight) Then
- Exit(I);
- { Try to find a mode that matches the width first }
- For I := 0 To FModeListCount - 1 Do
- If (FModeList[I]^.hdisplay = AWidth) And (FModeList[I]^.vdisplay >= AHeight) Then
- Exit(I);
- { Next try to match the height }
- For I := 0 To FModeListCount - 1 Do
- If (FModeList[I]^.hdisplay >= AWidth) And (FModeList[I]^.vdisplay = AHeight) Then
- Exit(I);
- { Finally, find the mode that is bigger than the requested one and makes }
- { the least difference }
- found_mode := -1;
- min_diff := High(Integer);
- For I := 0 To FModeListCount - 1 Do
- If (FModeList[I]^.hdisplay >= AWidth) And (FModeList[I]^.vdisplay >= AHeight) Then
- Begin
- d_x := Sqr(FModeList[I]^.hdisplay - AWidth);
- d_y := Sqr(FModeList[I]^.vdisplay - AHeight);
- If (d_x + d_y) < min_diff Then
- Begin
- min_diff := d_x + d_y;
- found_mode := I;
- End;
- End;
- If found_mode <> -1 Then
- Result := found_mode
- Else
- Raise TPTCError.Create('Cannot find matching video mode');
- End;
- Procedure TX11ModesXF86VidMode.SetBestMode(AWidth, AHeight : Integer);
- Var
- BestMode : Integer;
- Begin
- RetrieveModeList;
- BestMode := FindNumberOfBestMode(AWidth, AHeight);
- If Not XF86VidModeSwitchToMode(FDisplay, FScreen, FModeList[BestMode]) Then
- Raise TPTCError.Create('Error switching to the requested video mode');
- FWidth := FModeList[BestMode]^.hdisplay;
- FHeight := FModeList[BestMode]^.vdisplay;
- XWarpPointer(FDisplay, None, RootWindow(FDisplay, FScreen), 0, 0, 0, 0,
- FWidth Div 2,
- FHeight Div 2);
- If Not XF86VidModeSetViewPort(FDisplay, FScreen, 0, 0) Then
- Raise TPTCError.Create('Error moving the viewport to the upper-left corner');
- End;
- Procedure TX11ModesXF86VidMode.RestorePreviousMode;
- Var
- ModeInfo : TXF86VidModeModeInfo;
- Begin
- If FSavedMode <> Nil Then
- Begin
- {FSavedMode is a TXF86VidModeModeLine, but XF86VidModeSwitchToMode wants a
- TXF86VidModeModeInfo :}
- FillChar(ModeInfo, SizeOf(ModeInfo), 0);
- ModeInfo.dotclock := FSavedDotClock;
- ModeInfo.hdisplay := FSavedMode^.hdisplay;
- ModeInfo.hsyncstart := FSavedMode^.hsyncstart;
- ModeInfo.hsyncend := FSavedMode^.hsyncend;
- ModeInfo.htotal := FSavedMode^.htotal;
- ModeInfo.vdisplay := FSavedMode^.vdisplay;
- ModeInfo.vsyncstart := FSavedMode^.vsyncstart;
- ModeInfo.vsyncend := FSavedMode^.vsyncend;
- ModeInfo.vtotal := FSavedMode^.vtotal;
- ModeInfo.flags := FSavedMode^.flags;
- ModeInfo.privsize := FSavedMode^.privsize;
- ModeInfo.c_private := FSavedMode^.c_private;
- XF86VidModeSwitchToMode(FDisplay, FScreen, @ModeInfo);
- End;
- End;
- Function TX11ModesXF86VidMode.GetWidth : Integer;
- Begin
- Result := FWidth;
- End;
- Function TX11ModesXF86VidMode.GetHeight : Integer;
- Begin
- Result := FHeight;
- End;
- {$ENDIF ENABLE_X11_EXTENSION_XF86VIDMODE}
|