00001 #include "EF232LensDatabase.h"
00002
00003 #include <fstream>
00004 #include <iostream>
00005 #include <sstream>
00006
00007
00008 #if defined(EF232_DEBUG)
00009 #define dprintf(...) \
00010 printf("EF232[LensDatabase]: "); \
00011 printf(__VA_ARGS__);
00012 #else
00013 #define dprintf(...)
00014 #endif
00015
00016 #define eprintf(...) \
00017 fprintf(stderr,"EF232[LensDatabase]: ERROR! "); \
00018 fprintf(stderr, __VA_ARGS__);
00019
00020 namespace FCam {
00021
00022 unsigned int EF232LensInfo::minApertureAt(unsigned int focusDistance) const {
00023 if (minApertureList.size() == 0) return 0;
00024 std::map<unsigned int, unsigned int>::const_iterator iter=minApertureList.upper_bound(focusDistance);
00025 if (iter != minApertureList.begin())
00026 iter--;
00027 return iter->second;
00028 }
00029
00030 bool EF232LensInfo::operator<(const EF232LensInfo &rhs) const {
00031 if (focalLengthMin == rhs.focalLengthMin) {
00032 return focalLengthMax < rhs.focalLengthMax;
00033 } else {
00034 return focalLengthMin < rhs.focalLengthMin;
00035 }
00036 }
00037
00038 void EF232LensInfo::print(std::ostream &out) const {
00039 out << "{" << name << "}\n";
00040 out << "focalLengthMin=" << focalLengthMin << std::endl;
00041 out << "focalLengthMax=" << focalLengthMax << std::endl;
00042 out << "focusDistMin=" << focusDistMin << std::endl;
00043 out << "apertureMax=" << apertureMax << std::endl;
00044 out << "focusSpeed=" << focusSpeed << std::endl;
00045 out << "hasImageStabilization=" << hasImageStabilization << std::endl;
00046 out << "hasFullTimeManual=" << hasFullTimeManual << std::endl;
00047 for (minApertureListCIter iter = minApertureList.begin();
00048 iter != minApertureList.end(); iter++) {
00049 out << "aperture["<<iter->first<<"]="<<iter->second<<std::endl;
00050 }
00051 out << std::endl;
00052 }
00053
00054 EF232LensInfo::EF232LensInfo():
00055 name("Unknown"), focalLengthMin(0), focalLengthMax(0),
00056 focusDistMin(0), apertureMax(0), focusSpeed(0),
00057 hasImageStabilization(false),
00058 hasFullTimeManual(false)
00059 {
00060 }
00061
00062 EF232LensDatabase::EF232LensDatabase(const std::string &srcFile) {
00063 if (!db) {
00064 db = new std::set<EF232LensInfo>;
00065 load(srcFile);
00066 }
00067 }
00068
00069 const EF232LensInfo* EF232LensDatabase::find(unsigned int focalLengthMin,
00070 unsigned int focalLengthMax) {
00071 EF232LensInfo key;
00072 key.focalLengthMin = focalLengthMin;
00073 key.focalLengthMax = focalLengthMax;
00074 return find(key);
00075 }
00076
00077 const EF232LensInfo* EF232LensDatabase::find(const EF232LensInfo &key) {
00078 std::set<EF232LensInfo>::iterator iter = db->find(key);
00079 if (iter == db->end()) iter = db->insert(db->begin(), key);
00080 return &*iter;
00081 }
00082
00083 const EF232LensInfo* EF232LensDatabase::update(const EF232LensInfo &lensInfo) {
00084 std::set<EF232LensInfo>::iterator iter = db->find(lensInfo);
00085 if (iter != db->end()) db->erase(iter++);
00086 return &*(db->insert(iter, lensInfo));
00087 }
00088
00089 void EF232LensDatabase::load(const std::string &srcFile) {
00090 std::ifstream dbFile(srcFile.c_str());
00091
00092 if (!dbFile.is_open()) {
00093 dprintf("Unable to open database file %s\n", srcFile.c_str());
00094 return;
00095 }
00096
00097
00098
00099
00100
00101
00102
00103
00104
00105
00106 std::string line;
00107 std::size_t pos1,pos2;
00108 int lineNum = 0;
00109 EF232LensInfo *newLens = NULL;
00110 while(!dbFile.eof()) {
00111 std::getline(dbFile, line);
00112 lineNum++;
00113 line = line.substr(0, line.find_first_of("#"));
00114
00115 if ( (pos1 = line.find_first_of('{') != line.npos) ) {
00116 if (newLens != NULL) {
00117 db->insert(*newLens);
00118 delete newLens;
00119 }
00120
00121 pos2=line.find_first_of('}');
00122 if (pos2 == line.npos) {
00123 eprintf("Malformed database entry on line %d: %s\n", lineNum, line.c_str());
00124 return;
00125 }
00126 newLens = new EF232LensInfo;
00127 newLens->name = line.substr(pos1, pos2-pos1);
00128 dprintf("Reading in lens information for lens '%s'\n", newLens->name.c_str());
00129 }
00130
00131 if ( (pos1 = line.find_first_of('=')) != line.npos ) {
00132 std::string attribute = line.substr(0, pos1);
00133 std::stringstream value(line.substr(pos1+1));
00134 dprintf(" Attribute: %s, value: %s\n", attribute.c_str(), value.str().c_str());
00135 value >> std::ws;
00136 if (attribute.find("focalLengthMin") != attribute.npos) {
00137 value >> newLens->focalLengthMin;
00138 } else if (attribute.find("focalLengthMax") != attribute.npos) {
00139 value >> newLens->focalLengthMax;
00140 } else if (attribute.find("focusDistMin") != attribute.npos) {
00141 value >> newLens->focusDistMin;
00142 } else if (attribute.find("apertureMax") != attribute.npos) {
00143 value >> newLens->apertureMax;
00144 } else if (attribute.find("focusSpeed") != attribute.npos) {
00145 value >> newLens->focusSpeed;
00146 } else if (attribute.find("hasImageStabilization") != attribute.npos) {
00147 value >> newLens->hasImageStabilization;
00148 } else if (attribute.find("hasFullTimeManual") != attribute.npos ){
00149 value >> newLens->hasFullTimeManual;
00150 } else if (attribute.find("aperture") != attribute.npos ){
00151 pos1 = attribute.find_first_of('[');
00152 pos2 = attribute.find_first_of(']',pos1);
00153 if (pos1 == attribute.npos || pos2 == attribute.npos) {
00154 eprintf("Malformed database entry on line %d: %s\n", lineNum, line.c_str());
00155 return;
00156 }
00157 std::stringstream index(attribute.substr(pos1+1, pos2-pos1-1));
00158 index >> std::ws;
00159 EF232LensInfo::apertureChange newApertureChange;
00160 index >> newApertureChange.first;
00161 value >> newApertureChange.second;
00162 newLens->minApertureList.insert(newApertureChange);
00163 } else {
00164 eprintf("Ignoring unknown database field %s on line %d: %s\n", attribute.c_str(), lineNum, line.c_str());
00165 }
00166 }
00167 }
00168 if (newLens != NULL) {
00169 db->insert(*newLens);
00170 delete newLens;
00171 }
00172 }
00173
00174 void EF232LensDatabase::save(const std::string &dstFile) const {
00175 std::ofstream dbFile(dstFile.c_str());
00176 if (!dbFile.is_open()) {
00177 eprintf("Unable to open database file %s for writing!\n", dstFile.c_str());
00178 return;
00179 }
00180
00181 dbFile << "########################\n";
00182 dbFile << "# EF-232 Lens Database file for Canon EOS lens parameters\n";
00183 dbFile << "# Auto-generated by EF232LensDatabase.cpp\n";
00184 dbFile << "# Units in mm, f/stops, or 0=false, 1=true\n";
00185 dbFile << "\n\n";
00186
00187 for (std::set<EF232LensInfo>::iterator dbIter = db->begin();
00188 dbIter != db->end();
00189 dbIter++) {
00190 dbIter->print(dbFile);
00191 }
00192
00193 dbFile <<"\n\n";
00194 dbFile <<"# End autogenerated lens database file\n";
00195 }
00196
00197 std::set<EF232LensInfo> *EF232LensDatabase::db = NULL;
00198
00199 }