Diff for /parser3/src/classes/image.C between versions 1.148 and 1.154

version 1.148, 2015/10/09 11:42:38 version 1.154, 2016/10/04 22:05:28
Line 1 Line 1
 /** @file  /** @file
         Parser: @b image parser class.          Parser: @b image parser class.
   
         Copyright (c) 2001-2012 Art. Lebedev Studio (http://www.artlebedev.com)          Copyright (c) 2001-2015 Art. Lebedev Studio (http://www.artlebedev.com)
         Author: Alexandr Petrosian <paf@design.ru> (http://paf.design.ru)          Author: Alexandr Petrosian <paf@design.ru> (http://paf.design.ru)
 */  */
   
Line 45  public: Line 45  public:
   
 // globals  // globals
   
 DECLARE_CLASS_VAR(image, new MImage, 0);  DECLARE_CLASS_VAR(image, new MImage);
   
 // helpers  // helpers
   
Line 179  public: Line 179  public:
                 EXIF_TAG(0xa40b,        DeviceSettingDescription);                  EXIF_TAG(0xa40b,        DeviceSettingDescription);
                 EXIF_TAG(0xa40c,        SubjectDistanceRange);                  EXIF_TAG(0xa40c,        SubjectDistanceRange);
                 EXIF_TAG(0xa420,        ImageUniqueID);                  EXIF_TAG(0xa420,        ImageUniqueID);
   
                   // other tags
                   EXIF_TAG(0xa430,        CameraOwnerName);
                   EXIF_TAG(0xa431,        BodySerialNumber);
                   EXIF_TAG(0xa432,        LensSpecification);
                   EXIF_TAG(0xa433,        LensManufactor);
                   EXIF_TAG(0xa434,        LensModel);
                   EXIF_TAG(0xa435,        LensSerialNumber);
         }          }
 } exif_tag_value2name;  } exif_tag_value2name;
   
Line 230  public: Line 238  public:
 };  };
   
 class Measure_file_reader: public Measure_reader {  class Measure_file_reader: public Measure_reader {
         const String& file_name; const char* fname;          const String& file_name;
         int f;          int f;
   
 public:  public:
         Measure_file_reader(int af, const String& afile_name, const char* afname):           Measure_file_reader(int af, const String& afile_name):
                 file_name(afile_name), fname(afname), f(af) {                  file_name(afile_name), f(af) {
         }          }
   
         override size_t read(const char* &abuf, size_t limit) {          override size_t read(const char* &abuf, size_t limit) {
Line 251  public: Line 259  public:
   
         override void seek(long value, int whence) {          override void seek(long value, int whence) {
                 if(lseek(f, value, whence)<0)                  if(lseek(f, value, whence)<0)
                         throw Exception(IMAGE_FORMAT,                          throw Exception(IMAGE_FORMAT, &file_name, "seek(value=%ld, whence=%d) failed: %s (%d)", value, whence, strerror(errno), errno);
                                 &file_name,   
                                 "seek(value=%ld, whence=%d) failed: %s (%d), actual filename '%s'",   
                                         value, whence, strerror(errno), errno, fname);  
         }          }
   
         override long tell() { return lseek(f, 0, SEEK_CUR); }          override long tell() { return lseek(f, 0, SEEK_CUR); }
Line 392  inline uint endian_to_uint(bool is_big, Line 397  inline uint endian_to_uint(bool is_big,
                 x_endian_to_uint(b[0], b[1], b[2], b[3]);                  x_endian_to_uint(b[0], b[1], b[2], b[3]);
 }  }
   
 static void measure_gif(const String& origin_string,   static void measure_gif(const String& origin_string, Measure_reader& reader, ushort& width, ushort& height) {
                          Measure_reader& reader, ushort& width, ushort& height) {  
   
         const char* buf;          const char* buf;
         const size_t head_size=sizeof(GIF_Header);          const size_t head_size=sizeof(GIF_Header);
Line 630  static Value* parse_exif(Measure_reader& Line 634  static Value* parse_exif(Measure_reader&
         return vhash;          return vhash;
 }  }
   
 static void measure_jpeg(const String& origin_string,   static void measure_jpeg(const String& origin_string, Measure_reader& reader, ushort& width, ushort& height, Value** exif) {
                          Measure_reader& reader, ushort& width, ushort& height, Value** exif) {  
         // JFIF format markers          // JFIF format markers
         const uchar MARKER=0xFF;          const uchar MARKER=0xFF;
         const uchar CODE_SIZE_A=0xC0;          const uchar CODE_SIZE_A=0xC0;
Line 698  static void measure_jpeg(const String& o Line 701  static void measure_jpeg(const String& o
                 "broken JPEG file - size frame not found");                  "broken JPEG file - size frame not found");
 }  }
   
 static void measure_png(const String& origin_string,   static void measure_png(const String& origin_string, Measure_reader& reader, ushort& width, ushort& height) {
                          Measure_reader& reader, ushort& width, ushort& height) {  
   
         const char* buf;          const char* buf;
         const size_t head_size=sizeof(PNG_Header);          const size_t head_size=sizeof(PNG_Header);
         if(reader.read(buf, head_size)<head_size)          if(reader.read(buf, head_size)<head_size)
                 throw Exception(IMAGE_FORMAT,                   throw Exception(IMAGE_FORMAT, &origin_string, "not PNG file - too small");
                         &origin_string,   
                         "not PNG file - too small");  
         PNG_Header *head=(PNG_Header *)buf;          PNG_Header *head=(PNG_Header *)buf;
   
         if(strncmp(head->signature, "IHDR", 4)!=0)          if(strncmp(head->signature, "IHDR", 4)!=0)
                 throw Exception(IMAGE_FORMAT,                   throw Exception(IMAGE_FORMAT, &origin_string, "not PNG file - wrong signature");
                         &origin_string,   
                         "not PNG file - wrong signature");        
   
         width=endian_to_ushort(true, head->width);          width=endian_to_ushort(true, head->width);
         height=endian_to_ushort(true, head->height);          height=endian_to_ushort(true, head->height);
Line 720  static void measure_png(const String& or Line 718  static void measure_png(const String& or
   
 // measure center  // measure center
   
 static void measure(const String& file_name,   static void measure(const String& file_name, Measure_reader& reader, ushort& width, ushort& height, Value** exif) {
                          Measure_reader& reader, ushort& width, ushort& height, Value** exif) {  
         const char* file_name_cstr=file_name.taint_cstr(String::L_FILE_SPEC);          const char* file_name_cstr=file_name.taint_cstr(String::L_FILE_SPEC);
         if(const char* cext=strrchr(file_name_cstr, '.')) {          if(const char* cext=strrchr(file_name_cstr, '.')) {
                 cext++;                  cext++;
Line 732  static void measure(const String& file_n Line 729  static void measure(const String& file_n
                 else if(strcasecmp(cext, "PNG")==0)                  else if(strcasecmp(cext, "PNG")==0)
                         measure_png(file_name, reader, width, height);                          measure_png(file_name, reader, width, height);
                 else                  else
                         throw Exception(IMAGE_FORMAT,                           throw Exception(IMAGE_FORMAT, &file_name, "unhandled image file name extension '%s'", cext);
                                 &file_name,   
                                 "unhandled image file name extension '%s'", cext);  
         } else          } else
                 throw Exception(IMAGE_FORMAT,                   throw Exception(IMAGE_FORMAT, &file_name, "can not determine image type - no file name extension");
                         &file_name,   
                         "can not determine image type - no file name extension");  
 }  }
   
 // methods  // methods
Line 748  struct File_measure_action_info { Line 741  struct File_measure_action_info {
         ushort* width;          ushort* width;
         ushort* height;          ushort* height;
         Value** exif;          Value** exif;
         const String* file_name;  
 };  };
 #endif  #endif
 static void file_measure_action(  static void file_measure_action(struct stat& /*finfo*/, int f, const String& file_spec, void *context) {
                                                                 struct stat& /*finfo*/, int f,   
                                                                 const String& /*file_spec*/, const char* fname, bool /*as_text*/,  
                                                                 void *context) {  
         File_measure_action_info& info=*static_cast<File_measure_action_info *>(context);          File_measure_action_info& info=*static_cast<File_measure_action_info *>(context);
   
         Measure_file_reader reader(f, *info.file_name, fname);          Measure_file_reader reader(f, file_spec);
         measure(*info.file_name, reader, *info.width, *info.height, info.exif);          measure(file_spec, reader, *info.width, *info.height, info.exif);
 }  }
   
 static void _measure(Request& r, MethodParams& params) {  static void _measure(Request& r, MethodParams& params) {
Line 771  static void _measure(Request& r, MethodP Line 760  static void _measure(Request& r, MethodP
         if((file_name=data.get_string())) {          if((file_name=data.get_string())) {
                 File_measure_action_info info={                  File_measure_action_info info={
                         &width, &height,                          &width, &height,
                         &exif,                          &exif
                         file_name  
                 };                  };
                 file_read_action_under_lock(r.absolute(*file_name),                   file_read_action_under_lock(r.absolute(*file_name), "measure", file_measure_action, &info);
                         "measure", file_measure_action, &info);  
         } else {          } else {
                 VFile* vfile=data.as_vfile(String::L_AS_IS);                  VFile* vfile=data.as_vfile(String::L_AS_IS);
                 file_name=&vfile->fields().get(name_name)->as_string();                  file_name=&vfile->fields().get(name_name)->as_string();
Line 823  static void _html(Request& r, MethodPara Line 810  static void _html(Request& r, MethodPara
   
         if(params.count()) {          if(params.count()) {
                 // for backward compatibility: someday was ^html{}                  // for backward compatibility: someday was ^html{}
                 Value& vattribs=r.process_to_value(params[0], false/*don't intercept string*/);                  Value& vattribs=r.process(params[0]);
                 if(!vattribs.is_string()) { // allow empty                  if(!vattribs.is_string()) { // allow empty
                         if((attribs=vattribs.get_hash())) {                          if((attribs=vattribs.get_hash())) {
                                 Attrib_info info={&tag, 0};                                  Attrib_info info={&tag, 0};
Line 1146  static void _font(Request& r, MethodPara Line 1133  static void _font(Request& r, MethodPara
                         int valid_options=0;                          int valid_options=0;
                         if(Value* vspacebar_width=options->get(spacebar_width_name)){                          if(Value* vspacebar_width=options->get(spacebar_width_name)){
                                 valid_options++;                                  valid_options++;
                                 spacebar_width=r.process_to_value(*vspacebar_width).as_int();                                  spacebar_width=r.process(*vspacebar_width).as_int();
                         }                          }
                         if(Value* vmonospace_width=options->get(monospace_width_name)){                          if(Value* vmonospace_width=options->get(monospace_width_name)){
                                 valid_options++;                                  valid_options++;
                                 monospace_width=r.process_to_value(*vmonospace_width).as_int();                                  monospace_width=r.process(*vmonospace_width).as_int();
                                 if(!monospace_width)                                  if(!monospace_width)
                                         monospace_width=image->SX();                                          monospace_width=image->SX();
                         }                          }
                         if(Value* vletter_spacing=options->get(letter_spacing_name)){                          if(Value* vletter_spacing=options->get(letter_spacing_name)){
                                 valid_options++;                                  valid_options++;
                                 letter_spacing=r.process_to_value(*vletter_spacing).as_int();                                  letter_spacing=r.process(*vletter_spacing).as_int();
                         }                          }
                         if(valid_options!=options->count())                          if(valid_options!=options->count())
                                 throw Exception(PARSER_RUNTIME, 0, CALLED_WITH_INVALID_OPTION);                                  throw Exception(PARSER_RUNTIME, 0, CALLED_WITH_INVALID_OPTION);

Removed from v.1.148  
changed lines
  Added in v.1.154


E-mail: