Also log the loglevel
[notion/jeffpc.git] / de / fontset.c
blob8da573987501f3a111f17d742190e7e690944ef9
1 /*
2 * notion/de/fontset.c
3 *
4 * This file contains routines to attempt to add fonts to a font pattern
5 * so that XCreateFontSet will not fail because the given font(s) do not
6 * contain all the characters required by the locale.
8 * The original code was apparently written by Tomohiro Kubota; see
9 * <http://www.debian.org/doc/manuals/intro-i18n/ch-examples.en.html#s13.4.5>.
11 * However, the code that this file is based on, was taken from:
13 * Screen.cc for Blackbox - an X11 Window manager
14 * Copyright (c) 2001 - 2002 Sean 'Shaleh' Perry <shaleh@debian.org>
15 * Copyright (c) 1997 - 2000 Brad Hughes (bhughes@tcac.net)
17 * Permission is hereby granted, free of charge, to any person obtaining a
18 * copy of this software and associated documentation files (the "Software"),
19 * to deal in the Software without restriction, including without limitation
20 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
21 * and/or sell copies of the Software, and to permit persons to whom the
22 * Software is furnished to do so, subject to the following conditions:
24 * The above copyright notice and this permission notice shall be included in
25 * all copies or substantial portions of the Software.
27 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
28 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
29 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
30 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
31 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
32 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
33 * DEALINGS IN THE SOFTWARE.
36 #include <string.h>
37 #include <ctype.h>
38 #include <locale.h>
40 #include <ioncore/common.h>
41 #include <ioncore/global.h>
42 #include <ioncore/log.h>
44 #ifndef CF_FONT_ELEMENT_SIZE
45 #define CF_FONT_ELEMENT_SIZE 50
46 #endif
48 static const char *get_font_element(const char *pattern, char *buf,
49 int bufsiz, ...)
51 const char *p, *v;
52 char *p2;
53 va_list va;
55 va_start(va, bufsiz);
56 buf[bufsiz-1]=0;
57 buf[bufsiz-2]='*';
58 while((v=va_arg(va, char *))!=NULL){
59 p=libtu_strcasestr(pattern, v);
60 if(p){
61 strncpy(buf, p+1, bufsiz-2);
62 p2=strchr(buf, '-');
63 if(p2) *p2=0;
64 va_end(va);
65 return p;
68 va_end(va);
69 strncpy(buf, "*", bufsiz);
70 return NULL;
74 static const char *get_font_size(const char *pattern, int *size)
76 const char *p;
77 const char *p2=NULL;
78 int n=0;
80 for(p=pattern; 1; p++){
81 if(!*p){
82 if(p2!=NULL && n>1 && n<72){
83 *size=n; return p2+1;
84 }else{
85 *size=16; return NULL;
87 }else if(*p=='-'){
88 if(n>1 && n<72 && p2!=NULL){
89 *size=n;
90 return p2+1;
92 p2=p; n=0;
93 }else if(*p>='0' && *p<='9' && p2!=NULL){
94 n*=10;
95 n+=*p-'0';
96 }else{
97 p2=NULL; n=0;
103 XFontSet de_create_font_set(const char *fontname)
105 XFontSet fs;
106 char **missing=NULL, *def="-";
107 int nmissing, pixel_size=0;
108 char weight[CF_FONT_ELEMENT_SIZE], slant[CF_FONT_ELEMENT_SIZE];
109 const char *nfontname=fontname;
110 char *pattern2=NULL;
111 int i;
113 LOG(DEBUG, FONT, "Creating fontset for: %s", fontname);
115 fs=XCreateFontSet(ioncore_g.dpy, fontname, &missing, &nmissing, &def);
117 if(fs && nmissing==0){
118 if(missing!=NULL)
119 XFreeStringList(missing);
120 LOG(DEBUG, FONT, "Found a font without missing charsets for %s, returning it.", fontname);
121 return fs;
124 /* Not a warning, nothing serious */
125 LOG(DEBUG, FONT, "Failed to load fontset.");
127 if(!fs){
128 char *lcc=NULL;
129 const char *lc;
130 if(missing!=NULL)
131 XFreeStringList(missing);
133 lc=setlocale(LC_CTYPE, NULL);
134 if(lc!=NULL && strcmp(lc, "POSIX")!=0 && strcmp(lc, "C")!=0)
135 lcc=scopy(lc);
137 setlocale(LC_CTYPE, "C");
139 LOG(DEBUG, FONT, "Found a font with %d missing charsets for %s, trying with the C locale.", nmissing, fontname);
140 fs=XCreateFontSet(ioncore_g.dpy, fontname, &missing, &nmissing, &def);
142 if(lcc!=NULL){
143 setlocale(LC_CTYPE, lcc);
144 free(lcc);
148 #ifndef CF_NO_FONTSET_KLUDGE
150 if(fs){
151 XFontStruct **fontstructs;
152 char **fontnames;
153 XFontsOfFontSet(fs, &fontstructs, &fontnames);
154 nfontname=fontnames[0];
157 LOG(DEBUG, FONT, "Doing the no_fontset_kludge with fontname %s.", nfontname);
159 get_font_element(nfontname, weight, CF_FONT_ELEMENT_SIZE,
160 "-medium-", "-bold-", "-demibold-", "-regular-", NULL);
161 get_font_element(nfontname, slant, CF_FONT_ELEMENT_SIZE,
162 "-r-", "-i-", "-o-", "-ri-", "-ro-", NULL);
163 get_font_size(nfontname, &pixel_size);
165 if(!strcmp(weight, "*"))
166 strncpy(weight, "medium", CF_FONT_ELEMENT_SIZE);
167 if(!strcmp(slant, "*"))
168 strncpy(slant, "r", CF_FONT_ELEMENT_SIZE);
169 if(pixel_size<3)
170 pixel_size=3;
171 else if(pixel_size>97)
172 pixel_size=97;
174 if(ioncore_g.enc_utf8){
175 libtu_asprintf(&pattern2,
176 "%s,"
177 "-misc-fixed-%s-%s-*-*-%d-*-*-*-*-*-*-*,"
178 "-misc-fixed-*-*-*-*-%d-*-*-*-*-*-*-*",
179 fontname, weight, slant, pixel_size, pixel_size);
180 }else{
181 libtu_asprintf(&pattern2,
182 "%s,"
183 "-*-*-%s-%s-*-*-%d-*-*-*-*-*-*-*,"
184 "-*-*-*-*-*-*-%d-*-*-*-*-*-*-*",
185 fontname, weight, slant, pixel_size, pixel_size);
188 if(pattern2==NULL)
189 return NULL;
191 LOG(DEBUG, FONT, "no_fontset_kludge resulted in fontname %s", pattern2);
193 nfontname=pattern2;
195 if(nmissing)
196 XFreeStringList(missing);
197 if(fs){
198 XFreeFontSet(ioncore_g.dpy, fs);
199 LOG(DEBUG, FONT, "Trying '%s'.", nfontname);
203 fs=XCreateFontSet(ioncore_g.dpy, nfontname, &missing, &nmissing, &def);
205 free(pattern2);
207 #endif
209 if(missing!=NULL)
210 XFreeStringList(missing);
212 return fs;