Go to the documentation of this file.00001
00002 #include "vidl_color.h"
00003
00004
00005
00006
00007
00008 #include <vcl_iostream.h>
00009
00010
00011 const unsigned int num_types = 5;
00012
00013 namespace {
00014
00015
00016 template <class T1, class T2>
00017 struct func_ptr
00018 {
00019 typedef void (*type)(const T1* in, T2* out);
00020 };
00021
00022
00023
00024 template <class T>
00025 struct type_index;
00026 #define vidl_type_index_mac(T,NUM)\
00027 VCL_DEFINE_SPECIALIZATION \
00028 struct type_index<T> \
00029 {\
00030 enum { index = NUM };\
00031 }
00032
00033 vidl_type_index_mac(vxl_byte, 0);
00034 vidl_type_index_mac(bool, 1);
00035 vidl_type_index_mac(vxl_uint_16, 2);
00036 vidl_type_index_mac(vxl_ieee_32, 3);
00037 vidl_type_index_mac(vxl_ieee_64, 4);
00038
00039 #undef vidl_type_index_mac
00040
00041
00042
00043
00044 template <vidl_pixel_color in_color, vidl_pixel_color out_color, class fptr_T>
00045 struct table_entry_init
00046 {
00047 static inline void set_entry(vidl_color_conv_fptr& table_entry)
00048 {
00049 if (!table_entry) {
00050 fptr_T fp = &vidl_color_converter<in_color,out_color>::convert;
00051 table_entry = reinterpret_cast<vidl_color_conv_fptr>(fp);
00052 }
00053 }
00054 };
00055
00056
00057 template <int Fmt_Code>
00058 struct table_init
00059 {
00060 static inline void populate(vidl_color_conv_fptr table[VIDL_PIXEL_COLOR_ENUM_END][VIDL_PIXEL_COLOR_ENUM_END]
00061 [num_types][num_types])
00062 {
00063 const vidl_pixel_format in_fmt = vidl_pixel_format(Fmt_Code/VIDL_PIXEL_FORMAT_ENUM_END);
00064 const vidl_pixel_format out_fmt = vidl_pixel_format(Fmt_Code%VIDL_PIXEL_FORMAT_ENUM_END);
00065 vidl_pixel_color in_color = static_cast<vidl_pixel_color>(vidl_pixel_traits_of<in_fmt>::color_idx);
00066 vidl_pixel_color out_color = static_cast<vidl_pixel_color>(vidl_pixel_traits_of<out_fmt>::color_idx);
00067 typedef typename vidl_pixel_traits_of<in_fmt>::type in_type;
00068 typedef typename vidl_pixel_traits_of<out_fmt>::type out_type;
00069 unsigned in_type_num = type_index<in_type>::index;
00070 unsigned out_type_num = type_index<out_type>::index;
00071 typedef typename func_ptr<in_type,out_type>::type fptr;
00072 table_entry_init<static_cast<vidl_pixel_color>(vidl_pixel_traits_of<in_fmt>::color_idx),
00073 static_cast<vidl_pixel_color>(vidl_pixel_traits_of<out_fmt>::color_idx),
00074 fptr>::set_entry(table[in_color][out_color][in_type_num][out_type_num]);
00075 table_init<Fmt_Code-1>::populate(table);
00076 }
00077 };
00078
00079
00080
00081 VCL_DEFINE_SPECIALIZATION
00082 struct table_init<0>
00083 {
00084 static inline void populate(vidl_color_conv_fptr table[VIDL_PIXEL_COLOR_ENUM_END][VIDL_PIXEL_COLOR_ENUM_END]
00085 [num_types][num_types])
00086 {
00087 const vidl_pixel_format in_fmt = vidl_pixel_format(0);
00088 const vidl_pixel_format out_fmt = vidl_pixel_format(0);
00089 vidl_pixel_color in_color = static_cast<vidl_pixel_color>(vidl_pixel_traits_of<in_fmt>::color_idx);
00090 vidl_pixel_color out_color = static_cast<vidl_pixel_color>(vidl_pixel_traits_of<out_fmt>::color_idx);
00091 typedef vidl_pixel_traits_of<in_fmt>::type in_type;
00092 typedef vidl_pixel_traits_of<out_fmt>::type out_type;
00093 unsigned in_type_num = type_index<in_type>::index;
00094 unsigned out_type_num = type_index<out_type>::index;
00095 typedef func_ptr<in_type,out_type>::type fptr;
00096 table_entry_init<static_cast<vidl_pixel_color>(vidl_pixel_traits_of<in_fmt>::color_idx),
00097 static_cast<vidl_pixel_color>(vidl_pixel_traits_of<out_fmt>::color_idx),
00098 fptr>::set_entry(table[in_color][out_color][in_type_num][out_type_num]);
00099 }
00100 };
00101
00102
00103
00104
00105 template <int Fmt>
00106 struct type_table_init
00107 {
00108 static inline void populate(const vcl_type_info* type_table[num_types])
00109 {
00110 typedef typename vidl_pixel_traits_of<static_cast<vidl_pixel_format>(Fmt)>::type dtype;
00111 type_table[type_index<dtype>::index] = &typeid(dtype);
00112 type_table_init<Fmt-1>::populate(type_table);
00113 }
00114 };
00115
00116
00117
00118 VCL_DEFINE_SPECIALIZATION
00119 struct type_table_init<0>
00120 {
00121 static inline void populate(const vcl_type_info* type_table[num_types])
00122 {
00123 typedef vidl_pixel_traits_of<static_cast<vidl_pixel_format>(0)>::type dtype;
00124 type_table[type_index<dtype>::index] = &typeid(dtype);
00125 }
00126 };
00127
00128
00129
00130 class converter
00131 {
00132 public:
00133
00134 converter()
00135 {
00136
00137 table_init<VIDL_PIXEL_FORMAT_ENUM_END*VIDL_PIXEL_FORMAT_ENUM_END-1>::populate(table);
00138 type_table_init<VIDL_PIXEL_FORMAT_ENUM_END-1>::populate(type_table);
00139 #if 0
00140 for (unsigned int i=0; i<num_types; ++i){
00141 if (type_table[i])
00142 vcl_cout << "type "<<i<<" is "<<type_table[i]->name() << vcl_endl;
00143 }
00144 #endif // 0
00145 }
00146
00147
00148 vidl_color_conv_fptr operator()(vidl_pixel_color in_C, const vcl_type_info& in_type,
00149 vidl_pixel_color out_C, const vcl_type_info& out_type) const
00150 {
00151 unsigned int in_idx = type_index(in_type);
00152 unsigned int out_idx = type_index(out_type);
00153 return table[in_C][out_C][in_idx][out_idx];
00154 }
00155
00156 unsigned int type_index(const vcl_type_info& t) const
00157 {
00158 for (unsigned int i=0; i<num_types; ++i)
00159 {
00160 if ( type_table[i] && t == *type_table[i] )
00161 return i;
00162 }
00163 vcl_cerr << "error: unregistered pixel data type - "<<t.name()<<vcl_endl;
00164 return static_cast<unsigned int>(-1);
00165 }
00166 private:
00167
00168 vidl_color_conv_fptr table[VIDL_PIXEL_COLOR_ENUM_END][VIDL_PIXEL_COLOR_ENUM_END][num_types][num_types];
00169 const vcl_type_info* type_table[num_types];
00170 };
00171
00172
00173 converter conversion_table;
00174
00175 }
00176
00177
00178
00179
00180
00181
00182
00183 vidl_color_conv_fptr
00184 vidl_color_converter_func( vidl_pixel_color in_C, const vcl_type_info& in_type,
00185 vidl_pixel_color out_C, const vcl_type_info& out_type)
00186 {
00187 return conversion_table(in_C, in_type, out_C, out_type);
00188 }