Commit Diff


commit - db27122d3942ebec4471c260403d87cdd6541add
commit + 48da9bd71ddae0c51f8aff4c0d6806a8e32c4e23
blob - a097ca4d06153adbebdcc349d1a046b2df65c72a
blob + 455e81260e7250d98d3a6ed12a225eba90c8d1d0
--- src/cmd/fontsrv/x11.c
+++ src/cmd/fontsrv/x11.c
@@ -66,19 +66,16 @@ load(XFont *f)
 		return;
 
 	e = FT_New_Face(lib, f->fontfile, f->index, &face);
-
 	if(e){
 		fprint(2, "load failed for %s (%s) index:%d\n", f->name, f->fontfile, f->index);
 		return;
 	}
-
 	if(!FT_IS_SCALABLE(face)) {
 		fprint(2, "%s is a non scalable font, skipping\n", f->name);
 		FT_Done_Face(face);
-	    f->loaded = 1;
+		f->loaded = 1;
 		return;
 	}
-
 	f->unit = face->units_per_EM;
 	f->height = (int)((face->ascender - face->descender) * 1.2);
 	f->originy = face->descender; // bbox.yMin (or descender)  is negative, becase the baseline is y-coord 0
@@ -96,7 +93,11 @@ load(XFont *f)
 			f->nrange++;
 		}
 	}
-
+	// libdraw expects U+0000 to be present
+	if(!f->range[0]) {
+		f->range[0] = 1;
+		f->nrange++;
+	}
 	FT_Done_Face(face);
 	f->loaded = 1;
 }
@@ -108,14 +109,13 @@ mksubfont(XFont *xf, char *name, int lo, int hi, int s
 	FT_Error e;
 	Memimage *m, *mc, *m1;
 	double pixel_size;
-	int x, y, y0;
+	int w, x, y, y0;
 	int i;
 	Fontchar *fc, *fc0;
 	Memsubfont *sf;
 	//Point rect_points[4];
 
 	e = FT_New_Face(lib, xf->fontfile, xf->index, &face);
-
 	if(e){
 		fprint(2, "load failed for %s (%s) index:%d\n", xf->name, xf->fontfile, xf->index);
 		return nil;
@@ -129,16 +129,16 @@ mksubfont(XFont *xf, char *name, int lo, int hi, int s
 	}
 
 	pixel_size = (dpi*size)/72.0;
-	x = (int)((face->max_advance_width) * pixel_size/xf->unit + 0.99999999);
+	w = x = (int)((face->max_advance_width) * pixel_size/xf->unit + 0.99999999);
 	y = (int)((face->ascender - face->descender) * pixel_size/xf->unit + 0.99999999);
 	y0 = (int)(-face->descender * pixel_size/xf->unit + 0.99999999);
 
-	m = allocmemimage(Rect(0, 0, x*(hi+1-lo), y), antialias ? GREY8 : GREY1);
+	m = allocmemimage(Rect(0, 0, x*(hi+1-lo)+1, y+1), antialias ? GREY8 : GREY1);
 	if(m == nil) {
 		FT_Done_Face(face);
 		return nil;
 	}
-	mc = allocmemimage(Rect(0, 0, x, y), antialias ? GREY8 : GREY1);
+	mc = allocmemimage(Rect(0, 0, x+1, y+1), antialias ? GREY8 : GREY1);
 	if(mc == nil) {
 		freememimage(m);
 		FT_Done_Face(face);
@@ -165,41 +165,42 @@ mksubfont(XFont *xf, char *name, int lo, int hi, int s
 
 	x = 0;
 	for(i=lo; i<=hi; i++, fc++) {
-		int r;
+		int k, r;
 		int advance;
 
 		memfillcolor(mc, DBlack);
 
-		e = FT_Load_Char(face, i, FT_LOAD_RENDER|FT_LOAD_NO_HINTING|(antialias ? 0:FT_LOAD_TARGET_MONO));
-		if(e){
-			fprint(2, "FT_Load_Char failed for %d\n", i);
-			//mempoly(mc, rect_points, 4, Endsquare, Endsquare, 0, memopaque, ZP, S);
-			memimageline(mc, m->r.min, Pt(m->r.max.x, m->r.min.y), Endsquare, Endsquare, 0, memopaque, ZP, S);
-			memimageline(mc, m->r.min, Pt(m->r.min.x, m->r.max.y), Endsquare, Endsquare, 0, memopaque, ZP, S);
-			memimageline(mc, Pt(m->r.max.x, m->r.min.y), m->r.max, Endsquare, Endsquare, 0, memopaque, ZP, S);
-			memimageline(mc, Pt(m->r.min.x, m->r.max.y), m->r.max, Endsquare, Endsquare, 0, memopaque, ZP, S);
-			memimageline(mc, m->r.min, m->r.max, Endsquare, Endsquare, 0, memopaque, ZP, S);
-			advance = Dx(m->r);
+		fc->x = x;
+		fc->top = 0;
+		fc->bottom = Dy(m->r);
+		e = 1;
+		k = FT_Get_Char_Index(face, i);
+		if(k != 0) {
+			e = FT_Load_Glyph(face, k, FT_LOAD_RENDER|FT_LOAD_NO_HINTING|(antialias ? 0:FT_LOAD_TARGET_MONO));
+		}
+		if(e || face->glyph->advance.x <= 0) {
+			fc->width = 0;
+			fc->left = 0;
+			if(i == 0) {
+				drawpjw(m, fc, x, w, y, y - y0);
+				x += fc->width;
+			}
+			continue;
+		}
 
-			memimagedraw(m, Rect(x, 0, x + advance, y), mc, ZP, memopaque, ZP, S);
-		} else {
-			FT_Bitmap *bitmap = &face->glyph->bitmap;
-			uchar *base = byteaddr(mc, mc->r.min);
-			advance = (face->glyph->advance.x+32) >> 6;
+		FT_Bitmap *bitmap = &face->glyph->bitmap;
+		uchar *base = byteaddr(mc, mc->r.min);
+		advance = (face->glyph->advance.x+32) >> 6;
 
-			for(r=0; r < bitmap->rows; r++)
-				memmove(base + r*mc->width*sizeof(u32int), bitmap->buffer + r*bitmap->pitch, bitmap->pitch);
+		for(r=0; r < bitmap->rows; r++)
+			memmove(base + r*mc->width*sizeof(u32int), bitmap->buffer + r*bitmap->pitch, bitmap->pitch);
 
-			memimagedraw(m, Rect(x, 0, x + advance, y), mc,
-				Pt(-face->glyph->bitmap_left, -(y - y0 - face->glyph->bitmap_top)),
-				memopaque, ZP, S);
-		}
+		memimagedraw(m, Rect(x, 0, x + advance, y), mc,
+			Pt(-face->glyph->bitmap_left, -(y - y0 - face->glyph->bitmap_top)),
+			memopaque, ZP, S);
 
-		fc->x = x;
-		fc->top = 0;
-		fc->bottom = y;
-		fc->left = 0;
 		fc->width = advance;
+		fc->left = 0;
 		x += advance;
 
 #ifdef DEBUG_FT_BITMAP
@@ -229,6 +230,10 @@ mksubfont(XFont *xf, char *name, int lo, int hi, int s
 	// round up to 32-bit boundary
 	// so that in-memory data is same
 	// layout as in-file data.
+	if(x == 0)
+		x = 1;
+	if(y == 0)
+		y = 1;
 	if(antialias)
 		x += -x & 3;
 	else