summaryrefslogtreecommitdiff
path: root/src/g80_sor.c
diff options
context:
space:
mode:
authorAaron Plattner <aplattner@nvidia.com>2007-07-13 13:17:52 -0700
committerAaron Plattner <aaron@weasel.nvidia.com>2007-07-13 13:19:15 -0700
commitf0ebb42ee94eac4b294d12d02f4406a444b347ff (patch)
treebb2dadeb8583dc2630767e743a1c777c129b716a /src/g80_sor.c
parentec78618d685759a39d386e9929661037b167fe68 (diff)
G80: Add an LVDS flat panel scaling property.
This property controls how non-native resolutions are scaled to the native resolution. Valid values are: * center: 1:1 pixel ratio with black borders to center the image. * fill: Scale image to the native resolution. * aspect: Scale image to fit the screen, adding black bars to preserve square pixels. Defaults to "aspect". Change with "xrandr --output LVDS --set scale <foo>".
Diffstat (limited to 'src/g80_sor.c')
-rw-r--r--src/g80_sor.c63
1 files changed, 62 insertions, 1 deletions
diff --git a/src/g80_sor.c b/src/g80_sor.c
index c4c640c..8ba3425 100644
--- a/src/g80_sor.c
+++ b/src/g80_sor.c
@@ -211,6 +211,7 @@ struct property {
static struct {
struct property dither;
+ struct property scale;
} properties;
static void
@@ -219,7 +220,9 @@ G80SorCreateResources(xf86OutputPtr output)
ScrnInfoPtr pScrn = output->scrn;
G80Ptr pNv = G80PTR(pScrn);
int data, err;
+ const char *s;
+ /******** dithering ********/
properties.dither.atom = MAKE_ATOM("dither");
properties.dither.range[0] = 0;
properties.dither.range[1] = 1;
@@ -240,6 +243,26 @@ G80SorCreateResources(xf86OutputPtr output)
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"Failed to set dithering property for %s: error %d\n",
output->name, err);
+
+ /******** scaling ********/
+ properties.scale.atom = MAKE_ATOM("scale");
+ err = RRConfigureOutputProperty(output->randr_output,
+ properties.scale.atom, FALSE, FALSE,
+ FALSE, 0, NULL);
+ if(err)
+ xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
+ "Failed to configure scaling property for %s: error %d\n",
+ output->name, err);
+
+ // Set the default value
+ s = "aspect";
+ err = RRChangeOutputProperty(output->randr_output, properties.scale.atom,
+ XA_STRING, 8, PropModeReplace, strlen(s),
+ (pointer)s, FALSE, FALSE);
+ if(err)
+ xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
+ "Failed to set scaling property for %s: error %d\n",
+ output->name, err);
}
static Bool
@@ -256,9 +279,47 @@ G80SorSetProperty(xf86OutputPtr output, Atom prop, RRPropertyValuePtr val)
return FALSE;
G80CrtcSetDither(output->crtc, i, TRUE);
+ return TRUE;
+ } else if(prop == properties.scale.atom) {
+ const char *s;
+ enum G80ScaleMode scale;
+ DisplayModePtr mode;
+ int i;
+ const struct {
+ const char *name;
+ enum G80ScaleMode scale;
+ } modes[] = {
+ { "aspect", G80_SCALE_ASPECT },
+ { "fill", G80_SCALE_FILL },
+ { "center", G80_SCALE_CENTER },
+ { NULL, 0 },
+ };
+
+ if(val->type != XA_STRING || val->format != 8)
+ return FALSE;
+ s = (char*)val->data;
+
+ for(i = 0; modes[i].name; i++) {
+ const char *name = modes[i].name;
+ const int len = strlen(name);
+
+ if(val->size == len && !strncmp(name, s, len)) {
+ scale = modes[i].scale;
+ break;
+ }
+ }
+ if(!modes[i].name)
+ return FALSE;
+
+ /* Need to construct an adjusted mode */
+ mode = xf86DuplicateMode(&output->crtc->mode);
+ output->funcs->mode_fixup(output, &output->crtc->mode, mode);
+ G80CrtcSetScale(output->crtc, mode, scale, TRUE);
+ xfree(mode);
+ return TRUE;
}
- return TRUE;
+ return FALSE;
}
#endif // RANDR_12_INTERFACE