/* * Motif Tools Library, Version 3.1 * $Id: Lookup.c,v 1.2 2002/08/22 15:06:11 andre Exp $ * * Written by David Flanagan. * Copyright (c) 1992-2001 by David Flanagan. * All Rights Reserved. See the file COPYRIGHT for details. * This is open source software. See the file LICENSE for details. * There is no warranty for this software. See NO_WARRANTY for details. * * $Log: Lookup.c,v $ * Revision 1.2 2002/08/22 15:06:11 andre * AA-2002-08-22-0 I18N: bunch of fixes for l10n * Bugtraq: #4733802, #4733201, #4733089, #4733043, * #4731976, #4731990, #4731967, #4731958, * #4731944, #4731935, #4731273, #4729700 * * Revision 1.1.1.1 2001/07/18 11:06:02 root * Initial checkin. * * Revision 1.2 2001/06/12 16:25:28 andre * *** empty log message *** * * */ #include #include #include #ifndef X_NOT_STDC_ENV #include #else extern char *getenv(); #endif /* a dummy predicate for getting language string components */ #if NeedFunctionPrototypes static Boolean always_true(String s) #else static Boolean always_true(s) String s; #endif { return True; } /* * This utility is used internally to look up things under special * "branches" of the database. The Pixmap and Bitmap converters use * it to look under _Pixmaps_ and _Bitmaps_, the string localization * code uses it to look under _Messages_, the font list converter uses * it to look under _FontLists_, and the ColorTable converter uses it * to look under _ColorTables_ * * The "path" argument specifies how the db query should be specified-- * each character in this string specifies one quark in the query, as * follows: * * P _Pixmaps_ * B _Bitmaps_ * M _Messages_ * F _FontLists_ * T _ColorTables_ * l the 'language' part of the language string. * t the 'territory' part of the language string. * c the 'codeset' part of the language string. * f the 'fontFamily' app-resource. * p the 'palette' app-resource. * C the customization string. * V the visual type. One of "color", "gray", "monochrome". * D the screen depth. An integer. * Z the screen resolution. One of "high", "medium" and "low". * * Note that many of these chars are the same as the substitution * characters used by XmtFindFile(). */ #if NeedFunctionPrototypes String _XmtLookupResource(Screen *screen, StringConst path, StringConst object) #else String _XmtLookupResource(screen, path, object) Screen *screen; StringConst path; StringConst object; #endif { Display *dpy = DisplayOfScreen(screen); Visual *visual = DefaultVisualOfScreen(screen); int depth = DefaultDepthOfScreen(screen); XrmDatabase database = XtScreenDatabase(screen); static Boolean inited; static XrmQuark qP, qB, qM, qF, qT, qf, qp, ql, qt, qc, qC; static Boolean debug; String visual_sub, size_sub; char depth_sub[4]; int screen_width; XrmQuark names[20], classes[20]; int n; XrmQuark type; XrmValue value; if (!inited) { String language, territory, codeset, customization; String appname, appclass; char resname[200], resclass[200]; String type; XrmValue resvalue; qP = XrmPermStringToQuark("_Pixmaps_"); qB = XrmPermStringToQuark("_Bitmaps_"); qM = XrmPermStringToQuark("_Messages_"); qF = XrmPermStringToQuark("_FontLists_"); qT = XrmPermStringToQuark("_ColorTables_"); XtGetApplicationNameAndClass(dpy, &appname, &appclass); sprintf(resname, "%s.fontFamily", appname); sprintf(resclass, "%s.FontFamily", appclass); if (XrmGetResource(database, resname, resclass, &type, &resvalue)) qf = XrmStringToQuark((String)resvalue.addr); sprintf(resname, "%s.palette", appname); sprintf(resclass, "%s.Palette", appclass); if (XrmGetResource(database, resname, resclass, &type, &resvalue)) qp = XrmStringToQuark((String)resvalue.addr); /* figure out the components of the language string */ language = XtResolvePathname(dpy, NULL, NULL, NULL, "%l", NULL, 0, always_true); /* printf("++++++++++++ language: '%s'\n", language); */ territory = XtResolvePathname(dpy, NULL, NULL, NULL, "%t", NULL, 0, always_true); /* printf("++++++++++++ territory: '%s'\n", territory); */ codeset = XtResolvePathname(dpy, NULL, NULL, NULL, "%c", NULL, 0, always_true); /* printf("++++++++++++ codeset: '%s'\n", codeset); */ customization = XtResolvePathname(dpy, NULL, NULL, NULL, "%C", NULL, 0, always_true); /* printf("++++++++++++ customization: '%s'\n", customization); */ if (language && *language) { /* ** FIXME ** XtResolvePathname workaround for Solaris */ if (strchr(language, '/')) { int i; static char trimmed_language[1024]; for (i=0; language[i+1] && i<1024; i++) { if (language[i+1] == '/') break; trimmed_language[i] = language[i+1]; } trimmed_language[++i] = '\0'; ql = XrmStringToQuark(trimmed_language); } else { ql = XrmStringToQuark(language); } } if (territory && *territory) { if (strchr(territory, '/')) { int i; static char trimmed_territory[1024]; for (i=0; territory[i] && i<1024; i++) { trimmed_territory[i] = territory[i]; } trimmed_territory[++i] = '\0'; qt = XrmStringToQuark(trimmed_territory); } else qt = XrmStringToQuark(territory); } if (codeset && *codeset) { /* ** FIXME ** XtResolvePathname workaround for Solaris */ if (strchr(codeset, '/')) { int i; static char trimmed_codeset[1024]; for (i=0; codeset[i] && i<1024; i++) { trimmed_codeset[i] = codeset[i]; } trimmed_codeset[++i] = '\0'; qc = XrmStringToQuark(trimmed_codeset); } else qc = XrmStringToQuark(codeset); } if (customization && *customization) qC = XrmStringToQuark(customization); XtFree(language); XtFree(territory); XtFree(codeset); XtFree(customization); #ifndef NDEBUG debug = (getenv("XMTDEBUGLOOKUP") != NULL); #endif inited = True; } n = 0; while (*path) { XrmQuark q; switch(*path) { case 'P': q = qP; break; case 'B': q = qB; break; case 'M': q = qM; break; case 'F': q = qF; break; case 'T': q = qT; break; case 'l': q = ql; break; case 't': q = qt; break; case 'c': q = qc; break; case 'f': q = qf; break; case 'p': q = qp; break; case 'C': q = qC; break; case 'V': /* these aren't precomputed, because they depend on Screen */ if (visual->map_entries == 2) visual_sub = "monochrome"; else if ((visual->class == StaticGray) || (visual->class == GrayScale)) visual_sub = "gray"; else visual_sub = "color"; q = XrmPermStringToQuark(visual_sub); break; case 'D': sprintf(depth_sub, "%d", depth); q = XrmStringToQuark(depth_sub); break; case 'Z': screen_width = DisplayWidth(dpy, XScreenNumberOfScreen(screen)); if (screen_width < 750) size_sub = "small"; else if (screen_width > 1150) size_sub = "large"; else size_sub = "medium"; q = XrmPermStringToQuark(size_sub); break; default: q = NULLQUARK; break; } /* the language and customization quarks may not be defined, so check*/ if (q) { names[n] = classes[n] = q; n++; } path++; } /* once the fixed quarks are set up, add quarks from the object name */ XrmStringToQuarkList(object, &names[n]); for(;names[n] != NULLQUARK; n++) classes[n] = names[n]; classes[n] = NULLQUARK; #ifndef NDEBUG /* if we are debugging, print a message */ if (debug) { int i; printf("Looking for: "); for(i=0; names[i] != NULLQUARK; i++) printf("%s%s", (i==0)?"":".", XrmQuarkToString(names[i])); printf("\n"); } #endif /* and go look up the resource */ if (XrmQGetResource(database, names, classes, &type, &value)) return ((String) value.addr); else return NULL; }