--- parser3/src/classes/image.C 2009/10/03 02:15:02 1.131 +++ parser3/src/classes/image.C 2010/07/05 05:54:46 1.134 @@ -5,7 +5,7 @@ Author: Alexandr Petrosian (http://paf.design.ru) */ -static const char * const IDENT_IMAGE_C="$Date: 2009/10/03 02:15:02 $"; +static const char * const IDENT_IMAGE_C="$Date: 2010/07/05 05:54:46 $"; /* jpegsize: gets the width and height (in pixels) of a jpeg file @@ -806,14 +806,18 @@ struct Attrib_info { }; #endif static void append_attrib_pair( - HashStringValue::key_type key, - HashStringValue::value_type value, - Attrib_info* info) { - // skip user-specified and internal(starting with "line-") attributes - if(info->skip && info->skip->get(key) || key.pos("line-")==0) + HashStringValue::key_type key, + HashStringValue::value_type value, + Attrib_info* info) { + // skip user-specified, internal(starting with "line-") attributes and border attribute with empty value + if( + (info->skip && info->skip->get(key)) + || key.pos("line-")==0 + || (key=="border" && !value->is_defined()) + ) return; - // src="a.gif" width=123 ismap[=-1] + // src="a.gif" width="123" ismap[=-1] *info->tag << " " << key; if(value->is_string() || value->as_int()>=0) *info->tag << "=\"" << value->as_string() << "\""; @@ -828,8 +832,7 @@ static void _html(Request& r, MethodPara if(params.count()) { // for backward compatibility: someday was ^html{} - Value& vattribs=r.process_to_value(params[0], - false/*don't intercept string*/); + Value& vattribs=r.process_to_value(params[0], false/*don't intercept string*/); if(!vattribs.is_string()) // allow empty if((attribs=vattribs.get_hash())) { Attrib_info info={&tag, 0}; @@ -1033,13 +1036,23 @@ static void _polybar(Request& r, MethodP // Font class -Font::Font(//, +Font::Font( + Charset& asource_charset, const String& aalphabet, gdImage* aifont, int aheight, int amonospace, int aspacebarspace, int aletterspacing): - height(aheight), monospace(amonospace), spacebarspace(aspacebarspace), + fsource_charset(asource_charset), + height(aheight), + monospace(amonospace), + spacebarspace(aspacebarspace), letterspacing(aletterspacing), ifont(aifont), alphabet(aalphabet) { + + if(fsource_charset.isUTF8()){ + size_t index=0; + for(UTF8_string_iterator i(alphabet); i.has_next(); ) + fletter2index.put_dont_replace(i.next(), index++); + } } /* ******************************** char ********************************** */ @@ -1049,6 +1062,11 @@ size_t Font::index_of(char ch) { return alphabet.pos(ch); } +size_t Font::index_of(XMLCh ch) { + if(ch==' ') return STRING_NOT_FOUND; + return fletter2index.get(ch); +} + int Font::index_width(size_t index) { if(index==STRING_NOT_FOUND) return spacebarspace; @@ -1076,17 +1094,33 @@ int Font::step_width(int index) { int Font::string_width(const String& s){ const char* cstr=s.cstr(); int result=0; - for(const char* current=cstr; *current; current++) - result+=step_width(index_of(*current)); + + if(fsource_charset.isUTF8()){ + for(UTF8_string_iterator i(s); i.has_next(); ) + result+=step_width(index_of(i.next())); + } else { + for(const char* current=cstr; *current; current++) + result+=step_width(index_of(*current)); + } + return result; } void Font::string_display(gdImage& image, int x, int y, const String& s){ const char* cstr=s.cstr(); - for(const char* current=cstr; *current; current++) { - size_t index=index_of(*current); - index_display(image, x, y, index); - x+=step_width(index); + + if(fsource_charset.isUTF8()){ + for(UTF8_string_iterator i(s); i.has_next(); ){ + size_t index=index_of(i.next()); + index_display(image, x, y, index); + x+=step_width(index); + } + } else { + for(const char* current=cstr; *current; current++) { + size_t index=index_of(*current); + index_display(image, x, y, index); + x+=step_width(index); + } } } @@ -1129,9 +1163,7 @@ static void _font(Request& r, MethodPara letter_spacing=r.process_to_value(*vletter_spacing).as_int(); } if(valid_options!=options->count()) - throw Exception(PARSER_RUNTIME, - 0, - "called with invalid option"); + throw Exception(PARSER_RUNTIME, 0, CALLED_WITH_INVALID_OPTION); } else { // backward spacebar_width=params.as_int(2, "spacebar_width must be int", r); @@ -1150,6 +1182,7 @@ static void _font(Request& r, MethodPara image->SY(), alphabet_length, remainder); GET_SELF(r, VImage).set_font(new Font( + r.charsets.source(), alphabet, image, image->SY() / alphabet_length, monospace_width, spacebar_width, letter_spacing));