2 ///////////////////////////////////////////////////////////////////////////
3 // This program is free software: you can redistribute it and/or modify //
4 // it under the terms of the version 3 of the GNU General Public License //
5 // as published by the Free Software Foundation. //
7 // This program is distributed in the hope that it will be useful, but //
8 // WITHOUT ANY WARRANTY; without even the implied warranty of //
9 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU //
10 // General Public License for more details. //
12 // You should have received a copy of the GNU General Public License //
13 // along with this program. If not, see <http://www.gnu.org/licenses/>. //
15 // Written by Francois Fleuret //
16 // (C) Idiap Research Institute //
18 // Contact <francois.fleuret@idiap.ch> for comments & bug reports //
19 ///////////////////////////////////////////////////////////////////////////
27 #include "param_parser.h"
28 #include "labelled_image.h"
30 void parse_warning(const char *message, char *file, int line) {
31 cerr << message << " " << file << ":" << line << "." << endl;
35 void parse_error(const char *message, char *file, int line) {
36 cerr << message << " " << file << ":" << line << "." << endl;
41 //////////////////////////////////////////////////////////////////////
43 void list_to_pool(char *main_path, char *list_name, char *pool_name) {
44 ifstream list_stream(list_name);
46 if(list_stream.fail()) {
47 cerr << "Can not open " << list_name << " for reading." << endl;
51 ofstream pool_stream(pool_name);
53 if(pool_stream.fail()) {
54 cerr << "Can not open " << pool_name << " for writing." << endl;
62 LabelledImage *current_image = 0;
63 bool open_current_cat = false;
64 bool head_defined = false;
65 bool bounding_box_defined = false;
66 bool belly_defined = false;
69 while(!list_stream.eof() && (global.nb_images < 0 || nb_scenes < global.nb_images)) {
70 char line[large_buffer_size], token[buffer_size], full_image_name[buffer_size];
71 list_stream.getline(line, large_buffer_size);
74 s = next_word(token, s, buffer_size);
76 //////////////////////////////////////////////////////////////////////
78 if(strcmp(token, "SCENE") == 0) {
81 parse_error("Non-closed scene ", list_name, line_number);
85 s = next_word(token, s, buffer_size);
86 sprintf(full_image_name, "%s/%s", main_path, token);
88 parse_error("Image name is missing ", list_name, line_number);
91 cout << "Processing scene " << full_image_name << "." << endl;
93 int nb_cats_in_current_image = -1;
96 s = next_word(token, s, buffer_size);
97 nb_cats_in_current_image = atoi(token);
99 parse_error("Number of cats is missing ", list_name, line_number);
102 if(nb_cats_in_current_image < 0 || nb_cats_in_current_image > 100) {
103 parse_error("Weird number of cats ", list_name, line_number);
107 tmp.read_jpg(full_image_name);
109 current_image = new LabelledImage(tmp.width(),
111 nb_cats_in_current_image);
113 for(int y = 0; y < tmp.height(); y++) {
114 for(int x = 0; x < tmp.width(); x++) {
115 current_image->set_value(x, y,
116 int(scalar_t(tmp.pixel(x, y, 0)) * 0.2989 +
117 scalar_t(tmp.pixel(x, y, 1)) * 0.5870 +
118 scalar_t(tmp.pixel(x, y, 2)) * 0.1140));
125 else if(strcmp(token, "END_SCENE") == 0) {
126 if(current_image == 0)
127 parse_error("Non-open scene ", list_name, line_number);
129 if(nb_cats < current_image->nb_targets()) {
130 parse_warning("Less cats than advertised (some were ignored?), scene ignored",
131 list_name, line_number);
133 current_image->write(&pool_stream);
137 delete current_image;
141 //////////////////////////////////////////////////////////////////////
143 else if(strcmp(token, "CAT") == 0) {
145 parse_error("Non-closed cat ", list_name, line_number);
146 if(current_image == 0)
147 parse_error("Cat without scene ", list_name, line_number);
148 if(nb_cats >= current_image->nb_targets())
149 parse_error("More cats than advertised", list_name, line_number);
150 open_current_cat = true;
151 head_defined = false;
152 bounding_box_defined = false;
153 belly_defined = false;
157 else if(strcmp(token, "END_CAT") == 0) {
158 if(!open_current_cat)
159 parse_error("Undefined cat ", list_name, line_number);
161 if(!bounding_box_defined) {
162 parse_error("Undefined bounding box ", list_name, line_number);
165 if(head_defined && belly_defined) {
166 if(current_image->get_target_pose(nb_cats)->_head_radius > global.min_head_radius &&
167 current_image->get_target_pose(nb_cats)->_head_radius < global.max_head_radius) {
170 cerr << "Cat ignored since the head radius ("
171 << current_image->get_target_pose(nb_cats)->_head_radius << ") is not in the tolerance ("
172 << global.min_head_radius << ", " << global.max_head_radius
174 << list_name << ":" << line_number
179 parse_warning("Cat ignored since either the head and/or the belly are undefined",
180 list_name, line_number);
183 open_current_cat = false;
186 //////////////////////////////////////////////////////////////////////
188 else if(strcmp(token, "BOUNDINGBOX") == 0) {
189 if(!open_current_cat) parse_error("Undefined cat ", list_name, line_number);
190 if(bounding_box_defined) parse_error("Two bounding box", list_name, line_number);
191 int xmin = -1, ymin = -1, xmax = -1, ymax = -1;
192 if(s) { s = next_word(token, s, buffer_size); xmin = atoi(token); }
193 else parse_error("BOUNDINGBOX parameter xmin missing ", list_name, line_number);
194 if(s) { s = next_word(token, s, buffer_size); ymin = atoi(token); }
195 else parse_error("BOUNDINGBOX parameter ymin missing ", list_name, line_number);
196 if(s) { s = next_word(token, s, buffer_size); xmax = atoi(token); }
197 else parse_error("BOUNDINGBOX parameter xmax missing ", list_name, line_number);
198 if(s) { s = next_word(token, s, buffer_size); ymax = atoi(token); }
199 else parse_error("BOUNDINGBOX parameter ymax missing ", list_name, line_number);
200 current_image->get_target_pose(nb_cats)->_bounding_box_xmin = xmin;
201 current_image->get_target_pose(nb_cats)->_bounding_box_ymin = ymin;
202 current_image->get_target_pose(nb_cats)->_bounding_box_xmax = xmax;
203 current_image->get_target_pose(nb_cats)->_bounding_box_ymax = ymax;
204 bounding_box_defined = true;
207 //////////////////////////////////////////////////////////////////////
209 else if(strcmp(token, "HEADELLIPSE") == 0) {
210 if(!open_current_cat) parse_error("Undefined cat ", list_name, line_number);
211 if(head_defined) parse_error("Two head definitions", list_name, line_number);
212 int xmin = -1, ymin = -1, xmax = -1, ymax = -1;
213 if(s) { s = next_word(token, s, buffer_size); xmin = atoi(token); }
214 else parse_error("HEADELLIPSE parameter xmin missing ", list_name, line_number);
215 if(s) { s = next_word(token, s, buffer_size); ymin = atoi(token); }
216 else parse_error("HEADELLIPSE parameter ymin missing ", list_name, line_number);
217 if(s) { s = next_word(token, s, buffer_size); xmax = atoi(token); }
218 else parse_error("HEADELLIPSE parameter xmax missing ", list_name, line_number);
219 if(s) { s = next_word(token, s, buffer_size); ymax = atoi(token); }
220 else parse_error("HEADELLIPSE parameter ymax missing ", list_name, line_number);
221 current_image->get_target_pose(nb_cats)->_head_xc = (xmin + xmax)/2;
222 current_image->get_target_pose(nb_cats)->_head_yc = (ymin + ymax)/2;
223 current_image->get_target_pose(nb_cats)->_head_radius = int(sqrt(scalar_t(xmax - xmin) * scalar_t(ymax - ymin))/2);
227 else if(strcmp(token, "BELLYLOCATION") == 0) {
228 if(!open_current_cat) parse_error("Undefined cat ", list_name, line_number);
229 int x1 = -1, y1 = -1;
231 if(s) { s = next_word(token, s, buffer_size); x1 = atoi(token); }
232 else parse_error("BELLYLOCATION parameter x1 missing ", list_name, line_number);
233 if(s) { s = next_word(token, s, buffer_size); y1 = atoi(token); }
234 else parse_error("BELLYLOCATION parameter y1 missing ", list_name, line_number);
237 parse_error("More than one belly location. ", list_name, line_number);
240 Pose *pose = current_image->get_target_pose(nb_cats);
242 pose->_belly_xc = x1;
243 pose->_belly_yc = y1;
245 belly_defined = true;
251 //////////////////////////////////////////////////////////////////////
253 int main(int argc, char **argv) {
254 char *new_argv[argc];
259 global.init_parser(&parser);
260 parser.parse_options(argc, argv, false, &new_argc, new_argv);
261 global.read_parser(&parser);
262 cout << "-- PARAMETERS --------------------------------------------------------" << endl;
263 parser.print_all(&cout);
267 cerr << new_argv[0] << " <list file> <image path> <pool name>" << endl;
271 cout << "From list " << new_argv[1]
272 << " and image dir " << new_argv[2]
273 << ", generating pool " << new_argv[3]
276 cout << "-- GENERATING IMAGES -------------------------------------------------" << endl;
278 list_to_pool(new_argv[2], new_argv[1], new_argv[3]);
280 cout << "-- FINISHED ----------------------------------------------------------" << endl;