00001
00002
00003
00004
00005
00006
00007 #include "comboBoxComponent.h"
00008 #include "deleteObjects.h"
00009
00010
00011 ComboBoxComponent::ComboBoxComponent(TTF_Draw& ttf_resource)
00012 : ttf(ttf_resource),
00013 fore_color(Black), back_color(White),
00014 focused_fore_color(White), focused_back_color(Blue),
00015 menu(NULL), selected_item(NULL), selected_surface(NULL),
00016 button_label(NULL), button_surface(NULL), button_offset(VXV::Grid(0,0)),
00017 fill_normal(NULL), fill_focused(NULL), now_index(0), view_list(false),
00018 font_size(DefaultFontSize), focused(false), decided(false) {
00019 w = 0;
00020 h = 0;
00021 position = VXV::Grid(0, 0);
00022 }
00023
00024
00025 ComboBoxComponent::~ComboBoxComponent(void) {
00026 deleteObject();
00027 }
00028
00029
00030 void ComboBoxComponent::deleteObject(void) {
00031 for_each(items_normal.begin(), items_normal.end(), DeleteObjects());
00032 items_normal.clear();
00033
00034 for_each(items_focused.begin(), items_focused.end(), DeleteObjects());
00035 items_focused.clear();
00036
00037 for_each(surface_normal.begin(), surface_normal.end(), DeleteObjects());
00038 surface_normal.clear();
00039
00040 for_each(surface_focused.begin(), surface_focused.end(), DeleteObjects());
00041 surface_focused.clear();
00042
00043 delete selected_item;
00044 selected_item = NULL;
00045
00046 delete button_label;
00047 button_label = NULL;
00048
00049 delete button_surface;
00050 button_surface = NULL;
00051
00052 delete selected_surface;
00053 selected_surface = NULL;
00054
00055 delete fill_normal;
00056 fill_normal = NULL;
00057
00058 delete fill_focused;
00059 fill_focused = NULL;
00060
00061 delete menu;
00062 menu = NULL;
00063 }
00064
00065
00066 bool ComboBoxComponent::draw(unsigned long ticks, const UserInput& ui) {
00067
00068 if (items.empty()) {
00069 return true;
00070 }
00071
00072
00073 selected_item->setPosition(position);
00074 selected_item->draw(ticks, ui);
00075
00076
00077 button_label->setPosition(position + button_offset, VXV::Middle);
00078 button_label->draw(ticks, ui);
00079
00080
00081 menu->setPosition(position + VXV::Grid(0, selected_item->h));
00082 menu->draw(ticks, ui);
00083
00084
00085 if (selected_item->isPressed() ||
00086 (!view_list && focused &&
00087 ((ui.state.isPressedCode(SDLK_DOWN) ||
00088 (ui.state.ctrl_pressed && ui.state.isPressedCode(SDLK_n)))))) {
00089 view_list = !view_list;
00090 menu->hide(!view_list);
00091
00092 } else if (menu->isDecided()) {
00093
00094 decided = true;
00095 view_list = !view_list;
00096 int index = menu->getNowIndex();
00097 if (index >= 0) {
00098 setNowIndex(index);
00099 }
00100 menu->hide(!view_list);
00101 menu->activate(true);
00102
00103 } else if (ui.state.left_released) {
00104 view_list = false;
00105 menu->hide(true);
00106 }
00107 return true;
00108 }
00109
00110
00111 void ComboBoxComponent::add(const Uint16* text) {
00112 add_text.push_back(text);
00113 }
00114
00115
00116 void ComboBoxComponent::add(const char* text) {
00117 int n = static_cast<int>(strlen(text)) +1;
00118 Uint16* p = new Uint16[n];
00119 for (int i = 0; i < n; ++i) {
00120 p[i] = text[i];
00121 }
00122 add_text.push_back(p);
00123 char_text.push_back(p);
00124 }
00125
00126
00127 void ComboBoxComponent::setColor(unsigned long fore, unsigned long back,
00128 unsigned long focused_fore,
00129 unsigned long focused_back) {
00130 fore_color = fore;
00131 back_color = back;
00132 focused_fore_color = focused_fore;
00133 focused_back_color = focused_back;
00134 }
00135
00136
00137 void ComboBoxComponent::setFontSize(int size) {
00138 font_size = size;
00139 }
00140
00141
00142 void ComboBoxComponent::updateSelected(void) {
00143 if (items.empty()) {
00144 return;
00145 }
00146
00147 delete selected_surface;
00148 selected_surface = new MultiSurface(VXV::Rect(fill_normal->w,
00149 fill_normal->h));
00150 selected_surface->addSurface(fill_normal);
00151 selected_surface->addSurface(surface_normal[now_index]);
00152
00153 delete selected_item;
00154 selected_item = new ButtonComponent(selected_surface);
00155 }
00156
00157
00158 void ComboBoxComponent::activate(bool on) {
00159
00160
00161 deleteObject();
00162 for (std::vector<const Uint16*>::iterator it = add_text.begin();
00163 it != add_text.end(); ++it) {
00164 DrawSurface* normal =
00165 new DrawSurface(ttf.createText(*it, font_size, fore_color, back_color));
00166 DrawSurface* focused =
00167 new DrawSurface(ttf.createText(*it, font_size,
00168 focused_fore_color, focused_back_color));
00169 surface_normal.push_back(normal);
00170 surface_focused.push_back(focused);
00171
00172 w = (normal->w > w) ? normal->w : w;
00173 h = (normal->h > h) ? normal->h : h;
00174 }
00175 for (std::vector<Uint16*>::iterator it = char_text.begin();
00176 it != char_text.end(); ++it) {
00177 delete [] *it;
00178 }
00179 add_text.clear();
00180 char_text.clear();
00181
00182
00183 int btn_size = font_size >> 1;
00184 btn_size = (btn_size < 12) ? 12 : btn_size;
00185 if (!button_surface) {
00186 Uint16 button_text[] = { 0x25bc, 0x0000 };
00187 button_surface = new DrawSurface(ttf.createText(button_text, btn_size,
00188 fore_color, back_color));
00189 button_label = new LabelComponent(button_surface);
00190 button_offset = VXV::Grid(w + btn_size/3, h/2);
00191 }
00192 w += button_surface->w + btn_size/2;
00193
00194
00195 delete fill_normal;
00196 VXV::Rect fill_rect = VXV::Rect(w, h);
00197 fill_normal = new FillSurface(fill_rect, back_color);
00198 delete fill_focused;
00199 fill_focused = new FillSurface(fill_rect, focused_back_color);
00200
00201
00202
00203 menu = new MenuComponent();
00204 menu->defaultSelection(false);
00205 std::vector<DrawSurface*>::iterator focused = surface_focused.begin();
00206 for (std::vector<DrawSurface*>::iterator normal = surface_normal.begin();
00207 normal != surface_normal.end(); ++normal, ++focused) {
00208
00209 MultiSurface* multi = new MultiSurface(VXV::Rect(w, h));
00210 multi->addSurface(fill_normal);
00211 multi->addSurface(*normal);
00212 items_normal.push_back(multi);
00213 ButtonComponent* button = new ButtonComponent(multi);
00214
00215 multi = new MultiSurface(VXV::Rect(w, h));
00216 multi->addSurface(fill_focused);
00217 multi->addSurface(*focused);
00218 items_focused.push_back(multi);
00219 button->setFocusedSurface(multi);
00220 items.push_back(button);
00221
00222 menu->add(button);
00223 }
00224
00225
00226 menu->hide(true);
00227 menu->activate(true);
00228
00229 updateSelected();
00230 }
00231
00232
00233 void ComboBoxComponent::setNowIndex(int index) {
00234 now_index = index;
00235 if (menu) {
00236 menu->setNowIndex(index);
00237 }
00238 updateSelected();
00239 }
00240
00241
00242 bool ComboBoxComponent::isDecided(void) {
00243 return decided;
00244 }
00245
00246
00247 unsigned int ComboBoxComponent::getNowIndex(void) {
00248 decided = false;
00249 return now_index;
00250 }
00251
00252
00253 void ComboBoxComponent::beginFocus(void) {
00254 focused = true;
00255 view_list = true;
00256 menu->hide(false);
00257 }
00258
00259
00260 void ComboBoxComponent::endFocus(void) {
00261 focused = false;
00262 view_list = false;
00263 menu->hide(true);
00264 }
00265