1#include <cgv/base/base.h>
2#include "sliced_volume.h"
3#include "sliced_volume_io.h"
6#include <cgv/utils/file.h>
9#include <cgv/utils/tokenizer.h>
10#include <cgv/media/image/image_reader.h>
11#include <cgv/media/image/image_writer.h>
18 ooc_sliced_volume::ooc_sliced_volume()
42 std::string ooc_sliced_volume::get_slice_file_name(
int i)
const
44 static std::string long_placeholder =
"00000000$";
45 std::string file_name = file_name_pattern;
47 std::string placeholder = long_placeholder.substr(long_placeholder.size() - number.size());
55 if (!read_sliced_header(file_name, info)) {
56 std::cerr <<
"could not read header " << file_name << std::endl;
62 nr_slices = info.dimensions(2);
67 file_name_pattern = info.file_name_pattern;
68 std::string path = cgv::utils::file::get_path(file_name);
70 file_name_pattern = path +
"/" + file_name_pattern;
81 file_name_pattern = _file_name_pattern;
84 std::string pattern = _file_name_pattern;
85 std::string path = cgv::utils::file::get_path(file_name);
86 if (path.size() > 0) {
87 if (pattern.substr(0, path.size()) == path)
88 pattern = pattern.substr(path.size() + 1);
90 pattern = cgv::utils::file::clean_path(pattern);
93 if (!write_sliced_header(file_name, *
this)) {
94 std::cerr <<
"could not write header " << file_name << std::endl;
101 bool ooc_sliced_volume::is_open()
const
103 return !file_name_pattern.empty();
106 unsigned ooc_sliced_volume::get_nr_slices()
const
111 bool ooc_sliced_volume::read_slice(
int i,
const std::string& slice_file_name)
113 if (i < 0 || i >= (
int)get_nr_slices()) {
114 std::cerr <<
"slice index " << i <<
" out of range [0, " << get_nr_slices() <<
"[" << std::endl;
117 std::string file_name = slice_file_name.empty() ? get_slice_file_name(i) : slice_file_name;
120 if (cgv::utils::file::get_extension(file_name).
empty()) {
121 size_t file_size = cgv::utils::file::size(file_name);
123 if (data_size > file_size) {
124 std::cerr <<
"slice file " << file_name <<
" too small: only contains " << file_size <<
" bytes, but " <<
df.
get_nr_bytes() <<
" bytes needed." << std::endl;
127 char* content = cgv::utils::file::read(file_name);
129 std::cerr <<
"could not read slice file " << file_name <<
"." << std::endl;
132 size_t offset = file_size - data_size;
135 std::copy(content + offset, content + file_size,
dv.
get_ptr<
char>());
141 if (!ir.open(file_name)) {
142 std::cerr <<
"could not open slice file " << file_name << std::endl;
145 if (!ir.read_image(
dv)) {
146 std::cerr <<
"could not read slice file " << file_name << std::endl;
156 if (i < 0 || i >= (
int)get_nr_slices()) {
157 std::cerr <<
"slice index " << i <<
" out of range [0, " << get_nr_slices() <<
"[" << std::endl;
160 std::string file_name = get_slice_file_name(i);
163 std::cerr <<
"could not write slice file " << file_name << std::endl;
171 void ooc_sliced_volume::close()
174 file_name_pattern.clear();
178 sliced_volume_info::sliced_volume_info()
183 std::string truncate_spaces(
const std::string& s)
191 return s.substr(p, q - p);
194 bool unknown_line_callback(
const std::string& line,
const std::vector<cgv::utils::token>& toks, volume_info& info)
197 sliced_volume_info& sinfo = (sliced_volume_info&)info;
198 sinfo.file_name_pattern = truncate_spaces(line.substr(8));
202 sliced_volume_info& sinfo = (sliced_volume_info&)info;
204 std::cerr <<
"ERROR in OFFSET line: <" << truncate_spaces(line.substr(7)) <<
"> not defining an integer offset" << std::endl;
212 bool read_sliced_header(
const std::string& file_name, sliced_volume_info& info)
214 return read_vox_header(file_name, info, &unknown_line_callback);
217 bool write_sliced_header(
const std::string& file_name,
const ooc_sliced_volume& V)
219 if (!write_vox_header(file_name, V))
221 std::ofstream os(file_name, std::ofstream::app);
222 os <<
"Pattern: " << V.file_name_pattern << std::endl;
bool empty() const
return whether the data pointer is a null pointer
cgv::type::func::transfer_const< P, S * >::type get_ptr() const
return a data pointer to type S
the data view gives access to a data array of one, two, three or four dimensions.
Helper functions to convert numeric types into strings using std streams.
unsigned int replace(std::string &s, char c1, char c2)
replace char c1 with c2 in the given string _s and return number of replacements
std::string to_string(const std::string &v, unsigned int w, unsigned int p, bool)
specialization of conversion from string to strings
bool is_integer(const char *begin, const char *end, int &value)
check if the text range (begin,end( defines an integer value. If yes, store the value in the passed r...
char to_upper(char c)
convert char to upper case
bool is_space(char c)
check if char is a whitespace
Helper functions to process strings.