unique_ptr<gui_theme::draw_style_data> gui_theme::process_draw_style_data(const gui_theme::DRAW_STYLE style, const xml::xml_node* node) { // const auto str_to_float4 = [](const string& float4_str) -> float4 { const vector<string> float4_tokens { core::tokenize(float4_str, ',') }; if(float4_tokens.size() != 4) { oclr_error("invalid float4 token count: %u!", float4_tokens.size()); return float4(0.0f, 1.0f, 0.0f, 1.0f); // green -> invalid color/float4 } return float4(string2float(float4_tokens[0]), string2float(float4_tokens[1]), string2float(float4_tokens[2]), string2float(float4_tokens[3])); }; const auto str_to_ui_color = [&str_to_float4](const string& color_str) -> ui_color { const auto comma_pos(color_str.find(",")); // no comma -> must be a scheme reference if(comma_pos == string::npos) { return ui_color { color_str }; // validity must be checked later } // comma -> must be a raw color return ui_color { str_to_float4(color_str) }; }; // gradient helpers: const auto str_to_gradient = [](const string& gradient_str) -> gfx2d::GRADIENT_TYPE { static const unordered_map<string, gfx2d::GRADIENT_TYPE> types { { "horizontal", gfx2d::GRADIENT_TYPE::HORIZONTAL }, { "vertical", gfx2d::GRADIENT_TYPE::VERTICAL }, { "diagonal_lr", gfx2d::GRADIENT_TYPE::DIAGONAL_LR }, { "diagonal_rl", gfx2d::GRADIENT_TYPE::DIAGONAL_RL }, }; const auto iter = types.find(gradient_str); if(iter == types.cend()) { oclr_error("invalid gradient type: %s!", gradient_str); return gfx2d::GRADIENT_TYPE::HORIZONTAL; } return iter->second; }; const auto str_to_gradient_stops = [](const string& stops_str) -> float4 { const auto tokens = core::tokenize(stops_str, ','); float4 ret(0.0f); for(size_t i = 0; i < std::min(tokens.size(), (size_t)4); i++) { ret[i] = string2float(tokens[i]); } return ret; }; const auto str_to_gradient_colors = [&str_to_ui_color](const string& gradient_colors) -> vector<ui_color> { const auto color_tokens = core::tokenize(gradient_colors, ';'); vector<ui_color> colors; for(size_t i = 0; i < std::min(color_tokens.size(), (size_t)4); i++) { colors.emplace_back(str_to_ui_color(color_tokens[i])); } return colors; }; // texture helpers: const auto str_to_coords = [](const string& coords_str) -> pair<float2, float2> { if(coords_str == "INVALID") return make_pair(float2(0.0f), float2(1.0f)); // default const auto coords_tokens = core::tokenize(coords_str, ';'); if(coords_tokens.size() != 2) { oclr_error("invalid coord token count (%u) for coords: %s!", coords_tokens.size(), coords_str); return make_pair(float2(0.0f), float2(1.0f)); } const auto bottom_left_tokens = core::tokenize(coords_tokens[0], ','); const auto top_right_tokens = core::tokenize(coords_tokens[1], ','); return make_pair(bottom_left_tokens.size() >= 2 ? float2(string2float(bottom_left_tokens[0]), string2float(bottom_left_tokens[1])) : float2(string2float(bottom_left_tokens[0])), top_right_tokens.size() >= 2 ? float2(string2float(top_right_tokens[0]), string2float(top_right_tokens[1])) : float2(string2float(top_right_tokens[0]))); }; // switch(style) { case DRAW_STYLE::FILL: return make_unique<ds_fill>(str_to_ui_color((*node)["color"])); case DRAW_STYLE::BORDER_FILL: return make_unique<ds_border_fill>(str_to_ui_float(str_to_ui_float_pair((*node)["thickness"])), str_to_ui_color((*node)["color"])); case DRAW_STYLE::GRADIENT: return make_unique<ds_gradient>(str_to_gradient((*node)["gradient"]), str_to_gradient_stops((*node)["stops"]), str_to_gradient_colors((*node)["colors"])); case DRAW_STYLE::BORDER_GRADIENT: return make_unique<ds_border_gradient>(str_to_ui_float(str_to_ui_float_pair((*node)["thickness"])), str_to_gradient((*node)["gradient"]), str_to_gradient_stops((*node)["stops"]), str_to_gradient_colors((*node)["colors"])); case DRAW_STYLE::BORDER_TEXTURE: case DRAW_STYLE::TEXTURE: { string tex_name = (*node)["name"]; image* texture = nullptr; if(tex_name.find(".png") != string::npos) { // TODO: stores textures; add/allow internal engine image names? texture = texture_manager::add_texture(oclraster::data_path(tex_name)); tex_name = ""; } auto coords = str_to_coords((*node)["coords"]); float depth = ((*node)["depth"] == "INVALID" ? 0.0f : string2float((*node)["depth"])); bool passthrough = ((*node)["passthrough"] == "INVALID" ? false : string2bool((*node)["passthrough"])); bool is_gradient = ((*node)["gradient"] != "INVALID"); const bool is_mul_color = ((*node)["mul"] != "INVALID"); const bool is_add_color = ((*node)["add"] != "INVALID"); const bool is_grad_mul_interp = ((*node)["mul_interpolator"] != "INVALID"); const bool is_grad_add_interp = ((*node)["add_interpolator"] != "INVALID"); if(style == DRAW_STYLE::TEXTURE) { return make_unique<ds_texture>(std::move(texture), std::move(tex_name), std::move(coords.first), std::move(coords.second), std::move(depth), std::move(passthrough), is_mul_color ? str_to_ui_color((*node)["mul"]) : ui_color(float4(1.0f)), is_add_color ? str_to_ui_color((*node)["add"]) : ui_color(float4(0.0f)), std::move(is_gradient), is_grad_mul_interp ? str_to_float4((*node)["mul_interpolator"]) : float4(0.5f), is_grad_add_interp ? str_to_float4((*node)["add_interpolator"]) : float4(0.0f), is_gradient ? ds_gradient(str_to_gradient((*node)["gradient"]), str_to_gradient_stops((*node)["stops"]), str_to_gradient_colors((*node)["colors"])) : ds_gradient()); } return make_unique<ds_border_texture>(str_to_ui_float(str_to_ui_float_pair((*node)["thickness"])), std::move(texture), std::move(tex_name), std::move(coords.first), std::move(coords.second), std::move(depth), std::move(passthrough), is_mul_color ? str_to_ui_color((*node)["mul"]) : ui_color(float4(1.0f)), is_add_color ? str_to_ui_color((*node)["add"]) : ui_color(float4(0.0f)), std::move(is_gradient), is_grad_mul_interp ? str_to_float4((*node)["mul_interpolator"]) : float4(0.5f), is_grad_add_interp ? str_to_float4((*node)["add_interpolator"]) : float4(0.0f), is_gradient ? ds_gradient(str_to_gradient((*node)["gradient"]), str_to_gradient_stops((*node)["stops"]), str_to_gradient_colors((*node)["colors"])) : ds_gradient()); } case DRAW_STYLE::TEXT: return make_unique<ds_text>(str_to_ui_color((*node)["color"])); } oclr_unreachable(); }
void iLedlif::xmlParseDevice(XMLNode deviceNode) { std::string name; std::string deviceClass; std::string deviceName; std::string deviceType; std::string devicePortName; std::string deviceBaudRate; std::string elementName; std::string deviceFilePath; std::string val; std::string deviceFilename; std::string helpedDevice; std::string deviceCommType; std::vector<lifLED*> leds; std::vector<lifTSDIOPin*> pins; //Variables for pin std::string pinName; std::string dirBase; std::string dirOffset; std::string valBase; std::string valOffset; std::string bitNum; std::string enLow; //Variables for LED std::string ledName; std::string ledWL; std::string LEDPower; //Start reading in device information deviceClass = deviceNode.getChildNode("Class").getText(); deviceName = deviceNode.getChildNode("Name").getText(); deviceType = deviceNode.getChildNode("Type").getText(); deviceFilePath = deviceNode.getChildNode("Path_Name").getText(); helpedDevice = deviceNode.getChildNode("Helped_Device").getText(); //Check if there is a communication port entry for device if (deviceNode.nChildNode("Com_Port") > 0) { deviceCommType = deviceNode.getChildNode("Com_Port").getChildNode("Type").getText(); if (deviceCommType == "Serial") { devicePortName = deviceNode.getChildNode("Com_Port").getChildNode("Port").getText(); std::cout << deviceName << " " << devicePortName << std::endl; deviceBaudRate = deviceNode.getChildNode("Com_Port").getChildNode("Baud").getText(); } } //Load any defined pins for (int i = 0; i < deviceNode.nChildNode("Pin"); i++) { pinName = deviceNode.getChildNode("Pin", i).getChildNode("Name").getText(); dirBase = deviceNode.getChildNode("Pin", i).getChildNode("DirectionAddressBase").getText(); dirOffset = deviceNode.getChildNode("Pin", i).getChildNode("DirectionAddressOffset").getText(); valBase = deviceNode.getChildNode("Pin", i).getChildNode("ValueAddressBase").getText(); valOffset = deviceNode.getChildNode("Pin", i).getChildNode("ValueAddressOffset").getText(); bitNum = deviceNode.getChildNode("Pin", i).getChildNode("BitNumber").getText(); enLow = deviceNode.getChildNode("Pin", i).getChildNode("EnabledLow").getText(); pins.push_back(new lifTSDIOPin(pinName, string2int(bitNum), hexstring2int(dirBase), hexstring2int(dirOffset), hexstring2int(valBase), hexstring2int(valOffset), string2bool(enLow))); } //Load any LEDs for (int i = 0; i < deviceNode.nChildNode("LED"); i++) { ledName = deviceNode.getChildNode("LED", i).getChildNode("Name").getText(); ledWL = deviceNode.getChildNode("LED", i).getChildNode("Wavelength").getText(); LEDPower = deviceNode.getChildNode("LED", i).getChildNode("PowerSource").getText(); leds.push_back(new lifLED(ledName, string2int(ledWL), LEDPower)); } //declare device if (deviceClass == "Spectrometer") { std::cout << "iLedlif: Starting to load Spectrometer " << deviceName << std::endl; lifDevices.push_back((lifDevice*) (new lifSpectrometer(deviceName, deviceType, &mainMsgQueue, &mainMsgMutex, &mainMsgQueuePushed, deviceFilePath, devicePortName, string2int(deviceBaudRate), *pins.front()))); std::cout << "iLedlif: Loaded Spectrometer " << deviceName << std::endl; } else if (deviceClass == "Main Com") { lifDevices.push_back((lifDevice*) (new lifMainComm(deviceName, deviceType, &mainMsgQueue, &mainMsgMutex, &mainMsgQueuePushed, devicePortName, string2int(deviceBaudRate)))); std::cout << "iLedlif: Loaded Main Comm " << deviceName << std::endl; } else if (deviceClass == "LED Array") { lifDevices.push_back((lifDevice*) (new lifLEDArray(deviceName, deviceType, &mainMsgQueue, &mainMsgMutex, &mainMsgQueuePushed, leds))); std::cout << "iLedlif: Loaded LED Array " << deviceName << std::endl; } else if (deviceClass == "Spec Helper") { lifDevices.push_back((lifDevice*) (new lifSpecHelper(deviceName, deviceType, &mainMsgQueue, &mainMsgMutex, &mainMsgQueuePushed, helpedDevice))); std::cout << "iLedlif: Loaded Spec Helper " << deviceName << std::endl; } else if (deviceClass == "DIO Device") { lifDevices.push_back((lifDevice*) (new lifDIODevice(deviceName, deviceType, &mainMsgQueue, &mainMsgMutex, &mainMsgQueuePushed, pins))); std::cout << "iLedlif: Loaded DIO Device " << deviceName << std::endl; } else if (deviceClass == "SSP Controller") { lifDevices.push_back((lifDevice*) (new lifSSPController(deviceName, deviceType, &mainMsgQueue, &mainMsgMutex, &mainMsgQueuePushed))); std::cout << "iLedlif: Loaded SSP Controller " << deviceName << std::endl; } else if (deviceClass == "Generic Device") { lifDevices.push_back(new lifDevice(deviceName, deviceType, &mainMsgQueue, &mainMsgMutex, &mainMsgQueuePushed)); std::cout << "Generic Device added" << std::endl; } else if (deviceClass == "Program Runner") { lifDevices.push_back((lifDevice*) (new lifProgramRunner( deviceName, deviceType, &mainMsgQueue, &mainMsgMutex, &mainMsgQueuePushed, deviceFilename))); std::cout << "iLedlif: Loaded ProgramRunner " << deviceName << std::endl; } }