Refactor how Composite adds visuals to the screen.

Besides being slightly simpler to read, it's now trivial to add a depth-16
visual to a depth-24 screen just by adding a line for it in the alternate
visual list.  Visuals for indexed depths are slightly tricky still.
This commit is contained in:
Adam Jackson 2007-07-14 15:21:46 -04:00
parent 21bbd7d64b
commit aed6569309

View File

@ -199,106 +199,83 @@ Bool CompositeRegisterAlternateVisuals (ScreenPtr pScreen, VisualID *vids,
return compRegisterAlternateVisuals(cs, vids, nVisuals); return compRegisterAlternateVisuals(cs, vids, nVisuals);
} }
#if COMP_INCLUDE_RGB24_VISUAL
#define NUM_COMP_ALTERNATE_VISUALS 2
#else
#define NUM_COMP_ALTERNATE_VISUALS 1
#endif
typedef struct _alternateVisual { typedef struct _alternateVisual {
int depth; int depth;
CARD32 format; CARD32 format;
} CompAlternateVisual; } CompAlternateVisual;
static CompAlternateVisual altVisuals[NUM_COMP_ALTERNATE_VISUALS] = { static CompAlternateVisual altVisuals[] = {
#if COMP_INCLUDE_RGB24_VISUAL #if COMP_INCLUDE_RGB24_VISUAL
{ 24, PICT_r8g8b8 }, { 24, PICT_r8g8b8 },
#endif #endif
{ 32, PICT_a8r8g8b8 }, { 32, PICT_a8r8g8b8 },
}; };
static const int NUM_COMP_ALTERNATE_VISUALS = sizeof(altVisuals) /
sizeof(CompAlternateVisual);
static Bool static Bool
compAddAlternateVisuals (ScreenPtr pScreen, CompScreenPtr cs) compAddAlternateVisual(ScreenPtr pScreen, CompScreenPtr cs,
CompAlternateVisual *alt)
{ {
VisualPtr visuals; VisualPtr visual, visuals;
DepthPtr depths[NUM_COMP_ALTERNATE_VISUALS];
PictFormatPtr pPictFormats[NUM_COMP_ALTERNATE_VISUALS];
int i; int i;
int numVisuals; int numVisuals;
VisualID *vids[NUM_COMP_ALTERNATE_VISUALS];
XID *installedCmaps; XID *installedCmaps;
ColormapPtr installedCmap; ColormapPtr installedCmap;
int numInstalledCmaps; int numInstalledCmaps;
int numAlternate = 0; DepthPtr depth;
int alt; PictFormatPtr pPictFormat;
VisualID *vid;
for (alt = 0; alt < NUM_COMP_ALTERNATE_VISUALS; alt++) unsigned long alphaMask;
{
DepthPtr depth;
PictFormatPtr pPictFormat;
depth = compFindVisuallessDepth (pScreen, altVisuals[alt].depth);
if (!depth)
continue;
/*
* Find the right picture format
*/
pPictFormat = PictureMatchFormat (pScreen, altVisuals[alt].depth,
altVisuals[alt].format);
if (!pPictFormat)
continue;
/*
* Allocate vid list for this depth
*/
vids[numAlternate] = xalloc (sizeof (VisualID));
if (!vids[numAlternate])
continue;
depths[numAlternate] = depth;
pPictFormats[numAlternate] = pPictFormat;
numAlternate++;
}
if (!numAlternate)
return TRUE;
/* /*
* Find the installed colormaps * The ARGB32 visual is always available. Other alternate depth visuals
* are only provided if their depth is less than the root window depth.
* There's no deep reason for this.
*/ */
if (alt->depth >= pScreen->rootDepth && alt->depth != 32)
return FALSE;
depth = compFindVisuallessDepth (pScreen, alt->depth);
if (!depth)
return FALSE;
pPictFormat = PictureMatchFormat (pScreen, alt->depth, alt->format);
if (!pPictFormat)
return FALSE;
vid = xalloc(sizeof(VisualID));
if (!vid)
return FALSE;
/* Find the installed colormaps */
installedCmaps = xalloc (pScreen->maxInstalledCmaps * sizeof (XID)); installedCmaps = xalloc (pScreen->maxInstalledCmaps * sizeof (XID));
if (!installedCmaps) if (!installedCmaps) {
{ xfree(vid);
for (alt = 0; alt < numAlternate; alt++)
xfree (vids[alt]);
return FALSE; return FALSE;
} }
numInstalledCmaps = (*pScreen->ListInstalledColormaps) (pScreen, numInstalledCmaps = pScreen->ListInstalledColormaps(pScreen,
installedCmaps); installedCmaps);
/* /* realloc the visual array to fit the new one in place */
* realloc the visual array to fit the new one in place
*/
numVisuals = pScreen->numVisuals; numVisuals = pScreen->numVisuals;
visuals = xrealloc (pScreen->visuals, visuals = xrealloc(pScreen->visuals, (numVisuals + 1) * sizeof(VisualRec));
(numVisuals + numAlternate) * sizeof (VisualRec)); if (!visuals) {
if (!visuals) xfree(vid);
{ xfree(installedCmaps);
for (alt = 0; alt < numAlternate; alt++)
xfree (vids[alt]);
xfree (installedCmaps);
return FALSE; return FALSE;
} }
/* /*
* Fix up any existing installed colormaps -- we'll assume that * Fix up any existing installed colormaps -- we'll assume that
* the only ones created so far have been installed. If this * the only ones created so far have been installed. If this
* isn't true, we'll have to walk the resource database looking * isn't true, we'll have to walk the resource database looking
* for all colormaps. * for all colormaps.
*/ */
for (i = 0; i < numInstalledCmaps; i++) for (i = 0; i < numInstalledCmaps; i++) {
{
int j; int j;
installedCmap = LookupIDByType (installedCmaps[i], RT_COLORMAP); installedCmap = LookupIDByType (installedCmaps[i], RT_COLORMAP);
if (!installedCmap) if (!installedCmap)
continue; continue;
@ -306,66 +283,64 @@ compAddAlternateVisuals (ScreenPtr pScreen, CompScreenPtr cs)
installedCmap->pVisual = &visuals[j]; installedCmap->pVisual = &visuals[j];
} }
xfree (installedCmaps); xfree(installedCmaps);
pScreen->visuals = visuals; pScreen->visuals = visuals;
pScreen->numVisuals = numVisuals + numAlternate; visual = visuals + pScreen->numVisuals; /* the new one */
pScreen->numVisuals++;
for (alt = 0; alt < numAlternate; alt++) /* Initialize the visual */
{ visual->vid = FakeClientID (0);
DepthPtr depth = depths[alt]; visual->bitsPerRGBValue = 8;
PictFormatPtr pPictFormat = pPictFormats[alt]; if (PICT_FORMAT_TYPE(alt->format) == PICT_TYPE_COLOR) {
VisualPtr visual = &visuals[numVisuals + alt]; visual->class = PseudoColor;
unsigned long alphaMask; visual->nplanes = PICT_FORMAT_BPP(alt->format);
visual->ColormapEntries = 1 << visual->nplanes;
/* } else {
* Initialize the visual DirectFormatRec *direct = &pPictFormat->direct;
*/
visual->class = TrueColor; visual->class = TrueColor;
visual->bitsPerRGBValue = 8; visual->redMask = ((unsigned long)direct->redMask) << direct->red;
visual->greenMask = ((unsigned long)direct->greenMask) << direct->green;
visual->vid = FakeClientID (0); visual->blueMask = ((unsigned long)direct->blueMask) << direct->blue;
visual->redMask = (((unsigned long) pPictFormat->direct.redMask) << alphaMask = ((unsigned long)direct->alphaMask) << direct->alpha;
pPictFormat->direct.red); visual->offsetRed = direct->red;
visual->greenMask = (((unsigned long) pPictFormat->direct.greenMask) << visual->offsetGreen = direct->green;
pPictFormat->direct.green); visual->offsetBlue = direct->blue;
visual->blueMask = (((unsigned long) pPictFormat->direct.blueMask) <<
pPictFormat->direct.blue);
alphaMask = (((unsigned long) pPictFormat->direct.alphaMask) <<
pPictFormat->direct.alpha);
visual->offsetRed = pPictFormat->direct.red;
visual->offsetGreen = pPictFormat->direct.green;
visual->offsetBlue = pPictFormat->direct.blue;
/* /*
* Include A bits in this (unlike GLX which includes only RGB) * Include A bits in this (unlike GLX which includes only RGB)
* This lets DIX compute suitable masks for colormap allocations * This lets DIX compute suitable masks for colormap allocations
*/ */
visual->nplanes = Ones (visual->redMask | visual->nplanes = Ones (visual->redMask |
visual->greenMask | visual->greenMask |
visual->blueMask | visual->blueMask |
alphaMask); alphaMask);
/* /* find widest component */
* find widest component
*/
visual->ColormapEntries = (1 << max (Ones (visual->redMask), visual->ColormapEntries = (1 << max (Ones (visual->redMask),
max (Ones (visual->greenMask), max (Ones (visual->greenMask),
Ones (visual->blueMask)))); Ones (visual->blueMask))));
/*
* remember the visual ID to detect auto-update windows
*/
compRegisterAlternateVisuals(cs, &visual->vid, 1);
/*
* Fix up the depth
*/
vids[alt][0] = visual->vid;
depth->numVids = 1;
depth->vids = vids[alt];
} }
/* remember the visual ID to detect auto-update windows */
compRegisterAlternateVisuals(cs, &visual->vid, 1);
/* Fix up the depth */
*vid = visual->vid;
depth->numVids = 1;
depth->vids = vid;
return TRUE; return TRUE;
} }
static Bool
compAddAlternateVisuals (ScreenPtr pScreen, CompScreenPtr cs)
{
int alt, ret = 0;
for (alt = 0; alt < NUM_COMP_ALTERNATE_VISUALS; alt++)
ret |= compAddAlternateVisual(pScreen, cs, altVisuals + alt);
return !!ret;
}
Bool Bool
compScreenInit (ScreenPtr pScreen) compScreenInit (ScreenPtr pScreen)
{ {