diff --git a/src/forms/dlg_huepicker.cpp b/src/forms/dlg_huepicker.cpp index 762cf44..1573f9a 100644 --- a/src/forms/dlg_huepicker.cpp +++ b/src/forms/dlg_huepicker.cpp @@ -11,17 +11,18 @@ #include #include #include - - -const int colorsPerHue = 32; // how much colors does a hue entry contain +#include Dlg_HuePicker::Dlg_HuePicker(QWidget *parent) : QDialog(parent), ui(new Ui::dlg_huepicker) { - m_selectedHueIndex = 0; + setWindowFlags(windowFlags() & ~Qt::WindowContextHelpButtonHint); // disable the '?' (what's this) in the title bar + + m_selectedHueIndex = -1; m_brightnessPercent = 0; + m_shadeIndex = 25; m_previewIsItem = true; m_previewDisplayId = 0x1F13; // worldgem bit large (lg) @@ -30,6 +31,8 @@ Dlg_HuePicker::Dlg_HuePicker(QWidget *parent) : ui->radioButton_item->setChecked(true); drawHueBar(); + ui->horizontalSlider_shade->setValue(m_shadeIndex); + // Set up the hue table - we use a QLabel for each hue in the table, and set its color by creating a QPixmap static const int hueTableBlocksH = 50; @@ -52,7 +55,7 @@ Dlg_HuePicker::Dlg_HuePicker(QWidget *parent) : { // build each grid element EnhancedLabel* labelHueGridElem = new EnhancedLabel(this); - labelHueGridElem->setMinimumSize(10,6); + labelHueGridElem->setMinimumSize(9,5); labelHueGridElem->setScaledContents(true); m_hueTableBlocks.push_back(labelHueGridElem); @@ -82,12 +85,15 @@ Dlg_HuePicker::Dlg_HuePicker(QWidget *parent) : Dlg_HuePicker::~Dlg_HuePicker() { delete ui; + + delete m_hueTableMapClick; + delete m_hueTableMapDoubleClick; } void Dlg_HuePicker::onManual_hueTableClicked_mapped(int index) { - m_selectedHueIndex = index + 1; - QString hueText = QString("0") + QString::number(index, 16) + " (dec: " + QString::number(index, 10) + ")"; + m_selectedHueIndex = index; + QString hueText = QString("0") + QString::number(index+1, 16) + " (dec: " + QString::number(index+1, 10) + ")"; ui->label_hueIdx->setText(hueText); QString hueName(g_UOHues->getHueEntry(index).getName().c_str()); ui->label_hueName->setText(hueName); @@ -103,16 +109,20 @@ void Dlg_HuePicker::onManual_hueTableDoubleClicked_mapped(int index) void Dlg_HuePicker::drawHueBar() { + if (!g_UOHues) + return; + static const int colorBlockWidth = 14; static const int colorBlockHeight = 22; - QImage qimgHueDetail(colorsPerHue * colorBlockWidth, colorBlockHeight, QImage::Format_RGB32); + QImage qimgHueDetail(UOHueEntry::kColorTableSize * colorBlockWidth, colorBlockHeight, QImage::Format_RGB32); if (!g_UOHues || !m_selectedHueIndex) qimgHueDetail.fill(0); else { - UOHueEntry hueSelected = g_UOHues->getHueEntry(m_selectedHueIndex); - for (int i = 0; i < colorsPerHue; ++i) // color blocks = 32 + int hueIdx = (m_selectedHueIndex == -1) ? 0 : m_selectedHueIndex; + UOHueEntry hueSelected = g_UOHues->getHueEntry(hueIdx); + for (int i = 0; i < UOHueEntry::kColorTableSize; ++i) // color blocks = 32 { ARGB32 color32 = ARGB32(hueSelected.getColor(i)); color32.adjustBrightness(m_brightnessPercent); @@ -134,13 +144,16 @@ void Dlg_HuePicker::drawHueTable() return; setUpdatesEnabled(false); - int hueIdx = 1; - for (QLabel* curLabel : m_hueTableBlocks) + int hueIdx = 0; + for (EnhancedLabel* curLabel : m_hueTableBlocks) { UOHueEntry curHue = g_UOHues->getHueEntry(hueIdx); + + // Get the "mean" color + /* unsigned int meanR, meanG, meanB; meanR = meanG = meanB = 0; - for (int i = 0; i < colorsPerHue; ++i) // color blocks = 32 + for (int i = 0; i < UOHueEntry::kColorTableSize; ++i) // color blocks = 32 { ARGB32 color32 = ARGB32(curHue.getColor(i)); color32.adjustBrightness(m_brightnessPercent); @@ -151,9 +164,14 @@ void Dlg_HuePicker::drawHueTable() meanR /= 32; meanG /= 32; meanB /= 32; - QImage qimg(1,1,QImage::Format_RGB32); qimg.fill(qRgb(meanR,meanG,meanB)); + */ + + ARGB32 color32 = ARGB32(curHue.getColor(m_shadeIndex)); + color32.adjustBrightness(m_brightnessPercent); + QImage qimg(1,1,QImage::Format_RGB32); + qimg.fill(color32.getVal()); QPixmap qpix = QPixmap::fromImage(qimg); curLabel->setPixmap(qpix); @@ -164,6 +182,9 @@ void Dlg_HuePicker::drawHueTable() void Dlg_HuePicker::drawPreview() { + if (!g_UOArt || !g_UOAnim || !g_UOHues) + return; + if (m_previewDisplayId == 0) { if (ui->graphicsView->scene() != nullptr) @@ -172,10 +193,11 @@ void Dlg_HuePicker::drawPreview() } QImage* frameimg = nullptr; + int hueIdx = (m_selectedHueIndex == -1) ? 0 : m_selectedHueIndex; if (m_previewIsItem) - frameimg = g_UOArt->drawArt(UOArt::kItemsOffset + m_previewDisplayId, m_selectedHueIndex, false); + frameimg = g_UOArt->drawArt(UOArt::kItemsOffset + m_previewDisplayId, hueIdx+1, false); else - frameimg = g_UOAnim->drawAnimFrame(m_previewDisplayId, 0, 1, 0, m_selectedHueIndex); + frameimg = g_UOAnim->drawAnimFrame(m_previewDisplayId, 0, 1, 0, hueIdx+1); if (frameimg == nullptr) return; @@ -192,22 +214,44 @@ void Dlg_HuePicker::drawPreview() void Dlg_HuePicker::on_horizontalSlider_brightness_valueChanged(int value) { - if ((value != m_brightnessPercent)) + if (value != m_brightnessPercent) { m_brightnessPercent = value * 5; drawHueTable(); } } +void Dlg_HuePicker::on_horizontalSlider_shade_valueChanged(int value) +{ + if (value != m_shadeIndex) + { + m_shadeIndex = value; + drawHueTable(); + } +} + void Dlg_HuePicker::on_pushButton_set_clicked() { - ks::KeystrokeSender::sendStringFastAsync(std::string(".xcolor ") + std::to_string(m_selectedHueIndex), true, true); + std::string strToSend = ".xcolor " + std::to_string(m_selectedHueIndex + 1); + auto ksResult = ks::KeystrokeSender::sendStringFastAsync(strToSend, true, g_sendKeystrokeAndFocusClient); + if (ksResult != ks::KSERR_OK) + { + QMessageBox errorDlg(QMessageBox::Warning, "Warning", ks::getErrorStringStatic(ksResult), QMessageBox::NoButton, this); + errorDlg.exec(); + } } void Dlg_HuePicker::on_pushButton_setClose_clicked() { - ks::KeystrokeSender::sendStringFastAsync(std::string(".xcolor ") + std::to_string(m_selectedHueIndex), true, true); - this->close(); + std::string strToSend = ".xcolor " + std::to_string(m_selectedHueIndex); + auto ksResult = ks::KeystrokeSender::sendStringFastAsync(strToSend, true, g_sendKeystrokeAndFocusClient); + if (ksResult != ks::KSERR_OK) + { + QMessageBox errorDlg(QMessageBox::Warning, "Warning", ks::getErrorStringStatic(ksResult), QMessageBox::NoButton, this); + errorDlg.exec(); + } + else + this->close(); } void Dlg_HuePicker::on_radioButton_item_toggled(bool checked) @@ -281,4 +325,3 @@ void EnhancedLabel::paintEvent(QPaintEvent *e) } */ - diff --git a/src/forms/dlg_huepicker.h b/src/forms/dlg_huepicker.h index 934a562..83686f3 100644 --- a/src/forms/dlg_huepicker.h +++ b/src/forms/dlg_huepicker.h @@ -45,19 +45,21 @@ class Dlg_HuePicker : public QDialog private slots: void on_horizontalSlider_brightness_valueChanged(int value); + void on_horizontalSlider_shade_valueChanged(int value); void on_pushButton_set_clicked(); void on_pushButton_setClose_clicked(); void on_radioButton_item_toggled(bool checked); void on_radioButton_npc_toggled(bool checked); void on_lineEdit_preview_returnPressed(); void onManual_hueTableClicked_mapped(int); - void onManual_hueTableDoubleClicked_mapped(int); + void onManual_hueTableDoubleClicked_mapped(int); private: Ui::dlg_huepicker *ui; int m_selectedHueIndex; int m_brightnessPercent; + int m_shadeIndex; bool m_previewIsItem; int m_previewDisplayId; std::vector m_hueTableBlocks; diff --git a/src/forms/dlg_huepicker.ui b/src/forms/dlg_huepicker.ui index ba04cde..187152d 100644 --- a/src/forms/dlg_huepicker.ui +++ b/src/forms/dlg_huepicker.ui @@ -6,8 +6,8 @@ 0 0 - 742 - 408 + 714 + 445 @@ -17,14 +17,10 @@ - - - - - Adjust Brightness: - - - + + + 2 + @@ -41,20 +37,7 @@ - - - - - 0 - 0 - - - - Hue Name: - - - - + Qt::Vertical @@ -70,6 +53,26 @@ + + + + Adjust Brightness: + + + + + + + + 0 + 0 + + + + Hue Name: + + + @@ -86,6 +89,47 @@ + + + + + 0 + 0 + + + + -5 + + + 5 + + + 5 + + + 5 + + + true + + + Qt::Horizontal + + + QSlider::NoTicks + + + 5 + + + + + + + 0 + + + @@ -127,46 +171,28 @@ - - - - - 0 - 0 - - + + - -5 + 0 - 5 - - - 5 + 31 - - 5 - - - true + + 0 Qt::Horizontal - - QSlider::NoTicks - - - 5 - - - - - 0 + + + + Select Shade: - + diff --git a/src/forms/maintab_chars.cpp b/src/forms/maintab_chars.cpp index 190f567..4f340c7 100644 --- a/src/forms/maintab_chars.cpp +++ b/src/forms/maintab_chars.cpp @@ -220,10 +220,9 @@ void MainTab_Chars::on_treeView_objList_doubleClicked(const QModelIndex &index) std::string strToSend = ".add " + IDIndex.data().toString().toStdString(); auto ksResult = ks::KeystrokeSender::sendStringFastAsync(strToSend, true, g_sendKeystrokeAndFocusClient); - if (ksResult != ks::KSError::KSERR_OK) + if (ksResult != ks::KSERR_OK) { - QMessageBox errorDlg(this); - errorDlg.setText(ks::KeystrokeSender::getErrorStringStatic(ksResult).c_str()); + QMessageBox errorDlg(QMessageBox::Warning, "Warning", ks::getErrorStringStatic(ksResult), QMessageBox::NoButton, this); errorDlg.exec(); } } @@ -280,10 +279,9 @@ void MainTab_Chars::on_pushButton_summon_clicked() std::string strToSend = ".add " + selection->selectedRows(1)[0].data().toString().toStdString(); auto ksResult = ks::KeystrokeSender::sendStringFastAsync(strToSend, true, g_sendKeystrokeAndFocusClient); - if (ksResult != ks::KSError::KSERR_OK) + if (ksResult != ks::KSERR_OK) { - QMessageBox errorDlg(this); - errorDlg.setText(ks::KeystrokeSender::getErrorStringStatic(ksResult).c_str()); + QMessageBox errorDlg(QMessageBox::Warning, "Warning", ks::getErrorStringStatic(ksResult), QMessageBox::NoButton, this); errorDlg.exec(); } } @@ -292,10 +290,9 @@ void MainTab_Chars::on_pushButton_remove_clicked() { std::string strToSend = ".remove"; auto ksResult = ks::KeystrokeSender::sendStringFastAsync(strToSend, true, g_sendKeystrokeAndFocusClient); - if (ksResult != ks::KSError::KSERR_OK) + if (ksResult != ks::KSERR_OK) { - QMessageBox errorDlg(this); - errorDlg.setText(ks::KeystrokeSender::getErrorStringStatic(ksResult).c_str()); + QMessageBox errorDlg(QMessageBox::Warning, "Warning", ks::getErrorStringStatic(ksResult), QMessageBox::NoButton, this); errorDlg.exec(); } } diff --git a/src/forms/maintab_chars.ui b/src/forms/maintab_chars.ui index 4e10060..8d8f351 100644 --- a/src/forms/maintab_chars.ui +++ b/src/forms/maintab_chars.ui @@ -80,14 +80,7 @@ - - - Spawner - - - - - + 0 @@ -95,12 +88,19 @@ - Remove + Summon - + + + Spawner + + + + + 0 @@ -108,7 +108,7 @@ - Summon + Remove diff --git a/src/forms/maintab_items.cpp b/src/forms/maintab_items.cpp index b8edc2d..e4b6fef 100644 --- a/src/forms/maintab_items.cpp +++ b/src/forms/maintab_items.cpp @@ -24,6 +24,7 @@ MainTab_Items::MainTab_Items(QWidget *parent) : installEventFilter(this); // catch the keystrokes m_scriptSearch = nullptr; + m_lockDown = false; // Create the model for the organizer tree view m_organizer_model = new QStandardItemModel(0,0); @@ -257,12 +258,12 @@ void MainTab_Items::on_treeView_objList_doubleClicked(const QModelIndex &index) QModelIndex IDIndex(m_objList_model->index(index.row(), 1, index.parent())); - std::string strToSend = ".add " + IDIndex.data().toString().toStdString(); + std::string addCmd(m_lockDown ? ".static " : ".add "); + std::string strToSend = addCmd + IDIndex.data().toString().toStdString(); auto ksResult = ks::KeystrokeSender::sendStringFastAsync(strToSend, true, g_sendKeystrokeAndFocusClient); if (ksResult != ks::KSERR_OK) { - QMessageBox errorDlg(this); - errorDlg.setText(ks::KeystrokeSender::getErrorStringStatic(ksResult).c_str()); + QMessageBox errorDlg(QMessageBox::Warning, "Warning", ks::getErrorStringStatic(ksResult), QMessageBox::NoButton, this); errorDlg.exec(); } } @@ -318,12 +319,12 @@ void MainTab_Items::on_pushButton_add_clicked() if (!selection->hasSelection()) return; - std::string strToSend = ".add " + selection->selectedRows(1)[0].data().toString().toStdString(); + std::string addCmd(m_lockDown ? ".static " : ".add "); + std::string strToSend = addCmd + selection->selectedRows(1)[0].data().toString().toStdString(); auto ksResult = ks::KeystrokeSender::sendStringFastAsync(strToSend, true, g_sendKeystrokeAndFocusClient); if (ksResult != ks::KSERR_OK) { - QMessageBox errorDlg(this); - errorDlg.setText(ks::KeystrokeSender::getErrorStringStatic(ksResult).c_str()); + QMessageBox errorDlg(QMessageBox::Warning, "Warning", ks::getErrorStringStatic(ksResult), QMessageBox::NoButton, this); errorDlg.exec(); } } @@ -334,8 +335,7 @@ void MainTab_Items::on_pushButton_remove_clicked() auto ksResult = ks::KeystrokeSender::sendStringFastAsync(strToSend, true, g_sendKeystrokeAndFocusClient); if (ksResult != ks::KSERR_OK) { - QMessageBox errorDlg(this); - errorDlg.setText(ks::KeystrokeSender::getErrorStringStatic(ksResult).c_str()); + QMessageBox errorDlg(QMessageBox::Warning, "Warning", ks::getErrorStringStatic(ksResult), QMessageBox::NoButton, this); errorDlg.exec(); } } @@ -453,3 +453,8 @@ void MainTab_Items::on_pushButton_spawner_clicked() ScriptObj *script = m_objMapQItemToScript[qitem]; emit selectedScriptObjChanged(script); } + +void MainTab_Items::on_checkBox_lockDown_stateChanged(int arg1) +{ + m_lockDown = (arg1 != Qt::Unchecked); +} diff --git a/src/forms/maintab_items.h b/src/forms/maintab_items.h index b92eb25..295fcb0 100644 --- a/src/forms/maintab_items.h +++ b/src/forms/maintab_items.h @@ -44,8 +44,8 @@ private slots: void on_pushButton_search_clicked(); void on_pushButton_search_back_clicked(); void on_pushButton_search_next_clicked(); - void on_pushButton_spawner_clicked(); + void on_checkBox_lockDown_stateChanged(int arg1); private: Ui::MainTab_Items *ui; @@ -61,6 +61,8 @@ private slots: std::unique_ptr m_scriptSearch; ScriptSearch::SearchData_t m_lastSearchData; + bool m_lockDown; + void doSearch (bool backwards); }; diff --git a/src/forms/maintab_items.ui b/src/forms/maintab_items.ui index 6120c9c..1a77e54 100644 --- a/src/forms/maintab_items.ui +++ b/src/forms/maintab_items.ui @@ -152,14 +152,14 @@ - + - Spawner + LockDown - + 0 @@ -167,12 +167,19 @@ - Remove + Add - + + + Spawner + + + + + 0 @@ -180,7 +187,7 @@ - Add + Remove diff --git a/src/forms/subdlg_spawn.cpp b/src/forms/subdlg_spawn.cpp index 5786f07..dd367a9 100644 --- a/src/forms/subdlg_spawn.cpp +++ b/src/forms/subdlg_spawn.cpp @@ -3,6 +3,7 @@ #include "../spherescript/scriptobjects.h" #include "../keystrokesender/keystrokesender.h" #include "../globals.h" +#include SubDlg_Spawn::SubDlg_Spawn(QWidget *parent) : @@ -25,7 +26,12 @@ void SubDlg_Spawn::on_pushButton_place_clicked() if (!m_selectedScriptObj) return; - ks::KeystrokeSender::sendStringFastAsync(".add 01ea7", true, g_sendKeystrokeAndFocusClient); + auto ksResult = ks::KeystrokeSender::sendStringFastAsync(".add 01ea7", true, g_sendKeystrokeAndFocusClient); + if (ksResult != ks::KSERR_OK) + { + QMessageBox errorDlg(QMessageBox::Warning, "Warning", ks::getErrorStringStatic(ksResult), QMessageBox::NoButton, this); + errorDlg.exec(); + } } void SubDlg_Spawn::on_pushButton_init_clicked() @@ -46,11 +52,16 @@ void SubDlg_Spawn::on_pushButton_init_clicked() if (ui->lineEdit_amount->text().toInt()) { std::string amount_cmd = ".act.amount "+ ui->lineEdit_amount->text().toStdString(); - stringsToSend.push_back(amount_cmd.c_str()); + stringsToSend.push_back(amount_cmd); } stringsToSend.emplace_back(".act.timer 1"); - ks::KeystrokeSender::sendStringsFastAsync(stringsToSend, true, g_sendKeystrokeAndFocusClient); + auto ksResult = ks::KeystrokeSender::sendStringsFastAsync(stringsToSend, true, g_sendKeystrokeAndFocusClient); + if (ksResult != ks::KSERR_OK) + { + QMessageBox errorDlg(QMessageBox::Warning, "Warning", ks::getErrorStringStatic(ksResult), QMessageBox::NoButton, this); + errorDlg.exec(); + } } void SubDlg_Spawn::on_pushButton_customCmd_clicked() @@ -65,7 +76,12 @@ void SubDlg_Spawn::on_pushButton_customCmd_clicked() QString maxTime = ui->lineEdit_maxTime->text(); QString command = QString::fromStdString(g_settings.m_customSpawnCmd).arg(objDefname, amount, maxDist, minTime, maxTime); - ks::KeystrokeSender::sendStringFastAsync(command.toStdString(), true, g_sendKeystrokeAndFocusClient); + auto ksResult = ks::KeystrokeSender::sendStringFastAsync(command.toStdString(), true, g_sendKeystrokeAndFocusClient); + if (ksResult != ks::KSERR_OK) + { + QMessageBox errorDlg(QMessageBox::Warning, "Warning", ks::getErrorStringStatic(ksResult), QMessageBox::NoButton, this); + errorDlg.exec(); + } } void SubDlg_Spawn::on_checkBox_top_toggled(bool checked) diff --git a/src/keystrokesender/keystrokesender.cpp b/src/keystrokesender/keystrokesender.cpp index 4123751..891f687 100644 --- a/src/keystrokesender/keystrokesender.cpp +++ b/src/keystrokesender/keystrokesender.cpp @@ -4,6 +4,10 @@ namespace ks { +char const * getErrorStringStatic(KSError err) { + return KSErrorString[err]; +} + void KeystrokeSender::setSetFocusToWindow(bool value) { m_setFocusToWindow = value; } @@ -19,8 +23,5 @@ UOClientType KeystrokeSender::getClientType() const { return m_clientType; } -std::string KeystrokeSender::getErrorStringStatic(KSError err) { - return KSErrorString[err]; -} } diff --git a/src/keystrokesender/keystrokesender.h b/src/keystrokesender/keystrokesender.h index 647f235..3fdcb6b 100644 --- a/src/keystrokesender/keystrokesender.h +++ b/src/keystrokesender/keystrokesender.h @@ -9,6 +9,8 @@ namespace ks { +const char * getErrorStringStatic(KSError err); + #ifdef _WIN32 class KeystrokeSender : public KeystrokeSender_Windows @@ -29,8 +31,6 @@ class KeystrokeSender : public KeystrokeSender_Linux std::string getErrorString() const; UOClientType getClientType() const; - static std::string getErrorStringStatic(KSError err); - // Public methods inherited from KeystrokeSender_Windows and KeystrokeSender_Linux: // sendCharFast(); // sendEnterFast(); diff --git a/src/keystrokesender/keystrokesender_common.cpp b/src/keystrokesender/keystrokesender_common.cpp index 5208a4b..7bc022c 100644 --- a/src/keystrokesender/keystrokesender_common.cpp +++ b/src/keystrokesender/keystrokesender_common.cpp @@ -4,13 +4,13 @@ namespace ks { -const char *UOClientWindowTitles[] +const char * const UOClientWindowTitles[] { // The string order must match the UOClientType enum order. "Ultima Online", // for Classic Client "UOSA -" // for Enhanced Client }; -const char *KSErrorString[] +const char * const KSErrorString[] { // The string order must match the UOClientComError enum order. "No error.", "UO Client window was not found.", diff --git a/src/keystrokesender/keystrokesender_common.h b/src/keystrokesender/keystrokesender_common.h index a333893..b4f79af 100644 --- a/src/keystrokesender/keystrokesender_common.h +++ b/src/keystrokesender/keystrokesender_common.h @@ -22,8 +22,8 @@ enum KSError KSERR_STRINGSHORT, }; -extern const char *UOClientWindowTitles[]; -extern const char *KSErrorString[]; +extern const char * const UOClientWindowTitles[]; +extern const char * const KSErrorString[]; } diff --git a/src/spherescript/scriptparser.cpp b/src/spherescript/scriptparser.cpp index a3fbe56..4d118b9 100644 --- a/src/spherescript/scriptparser.cpp +++ b/src/spherescript/scriptparser.cpp @@ -137,7 +137,9 @@ void ScriptParser::run() // Iterate one time for the items and one for the chars auto curChildObjects = displayID_childObjects[tree_i]; - for (size_t child_i = 0, child_s = curChildObjects->size(); child_i < child_s; ++child_i) + size_t child_s = curChildObjects->size(); + //#pragma omp parallel for schedule(static) private(curChildObjects, child_s) + for (size_t child_i = 0; child_i < child_s; ++child_i) { // Iterate through each object of the tree. // Now look inside each object of each subsection of each category to find the parent object. diff --git a/src/uofiles/uoanimmul.cpp b/src/uofiles/uoanimmul.cpp index e26c461..744df43 100644 --- a/src/uofiles/uoanimmul.cpp +++ b/src/uofiles/uoanimmul.cpp @@ -361,9 +361,9 @@ QImage* UOAnimMul::drawAnimFrame(int bodyID, int action, int direction, int fram uint8_t palette_index = 0; fs_anim.read(reinterpret_cast(&palette_index), 1); ARGB16 color_argb16 = palette[palette_index]; // ^ 0x8000; - if (hueIndex != 0) + if (hueIndex > 0) // client starts to count from 1 (0 means do not change the color) { - UOHueEntry hue = g_UOHues->getHueEntry(hueIndex); + UOHueEntry hue = g_UOHues->getHueEntry(hueIndex-1); color_argb16 = hue.applyToColor(color_argb16, applyToGrayOnly); } ARGB32 color_argb32 = argb16_to_argb32(color_argb16); diff --git a/src/uofiles/uoanimuop.cpp b/src/uofiles/uoanimuop.cpp index 2d94b60..58b1ec2 100644 --- a/src/uofiles/uoanimuop.cpp +++ b/src/uofiles/uoanimuop.cpp @@ -12,7 +12,7 @@ UOAnimUOP::UOAnimUOP(std::string clientPath, std::function reportProgress) : - m_clientPath(clientPath), m_isLoading(false) + m_clientPath(clientPath), m_isInitializing(false) { buildAnimTable(reportProgress); } @@ -23,7 +23,7 @@ UOAnimUOP::UOAnimUOP(std::string clientPath, std::function reportProg void UOAnimUOP::buildAnimTable(std::function reportProgress) { - m_isLoading = true; + m_isInitializing = true; memset((void*)m_animationsMatrix, 0, sizeof(m_animationsMatrix[0][0]) * kAnimIdMax * kGroupIdMax); // We need to know which animations are in the uop files @@ -44,12 +44,12 @@ void UOAnimUOP::buildAnimTable(std::function reportProgress) } // Read the data in order to access later to each file by its hash - uoppackage::UOPPackage& package = m_animUOPs[uopFile_i - 1]; + uopp::UOPPackage& package = m_animUOPs[uopFile_i - 1]; package.load(path); - if (uoppackage::errorHandler.errorOccurred()) // check if there was an error when extracting the uop file + if (uopp::errorHandler.errorOccurred()) // check if there was an error when extracting the uop file { appendToLog("UOPPackage error!"); - auto errors = uoppackage::errorHandler.getErrorQueue(); + auto errors = uopp::errorHandler.getErrorQueue(); for (std::string str : errors) appendToLog(str); return; @@ -59,11 +59,11 @@ void UOAnimUOP::buildAnimTable(std::function reportProgress) for (size_t block_i = 0, block_max = blocks.size(); block_i < block_max; ++block_i) { - uoppackage::UOPBlock* curBlock = blocks[block_i]; + uopp::UOPBlock* curBlock = blocks[block_i]; auto files = curBlock->getFiles(); for (size_t file_i = 0, file_max = files.size(); file_i < file_max; ++file_i) { - uoppackage::UOPFile* curFile = files[file_i]; + uopp::UOPFile* curFile = files[file_i]; UOPAnimationData data; data.animFileIdx = uopFile_i; @@ -91,7 +91,7 @@ void UOAnimUOP::buildAnimTable(std::function reportProgress) progressVal = 0; // It would be more logical to have animId as outer loop and groupId as inner loop, but the kGroupIdMax is < than kAnimIdMax, - // so this way we create the threads much less often. + // so this way we assign work to the OpenMP threads (in its thread pool) less often (dunno if it actually causes overhead, but who knows...) for (int groupId = 0; groupId < kGroupIdMax; ++groupId) { #pragma omp parallel for schedule(static) // split the workload between some threads with OpenMP! @@ -99,7 +99,7 @@ void UOAnimUOP::buildAnimTable(std::function reportProgress) { char hashString[100]; sprintf(hashString, "build/animationlegacyframe/%06i/%02i.bin", animId, groupId); - unsigned long long hash = uoppackage::UOPPackage::getHash(hashString); + unsigned long long hash = uopp::UOPPackage::getHash(hashString); int found = -1; for (int i = 0, max = (int)m_animationsData.size(); i < max; ++i) { @@ -117,15 +117,18 @@ void UOAnimUOP::buildAnimTable(std::function reportProgress) if ( reportProgress && (progressValNow > progressVal) ) { progressVal = progressValNow; - reportProgress(progressVal); // it's a bit of a mess to pass the progress to the main Qt thread... + reportProgress(progressVal); } } - m_isLoading = false; + m_isInitializing = false; } bool UOAnimUOP::animExists(int animID) { + if (isInitializing()) + return false; + for (int i = 0; i < kGroupIdMax; ++i) { if (m_animationsMatrix[animID][i] != nullptr) // do we have almost an action (group) for this animId? @@ -136,10 +139,13 @@ bool UOAnimUOP::animExists(int animID) UOAnimUOP::UOPFrameData UOAnimUOP::loadFrameData(int animID, int groupID, int direction, int frame, char* &decData, size_t &decDataSize) { + if (isInitializing()) + return UOPFrameData{}; + UOPAnimationData* animData = m_animationsMatrix[animID][groupID]; - uoppackage::UOPPackage& animPkg = m_animUOPs[animData->animFileIdx - 1]; - uoppackage::UOPFile* animFile = animPkg.getFileByIndex((int)animData->blockIdx, (int)animData->fileIdx); + uopp::UOPPackage& animPkg = m_animUOPs[animData->animFileIdx - 1]; + uopp::UOPFile* animFile = animPkg.getFileByIndex((int)animData->blockIdx, (int)animData->fileIdx); std::string path = m_clientPath + "AnimationFrame" + std::to_string(animData->animFileIdx) + ".uop"; std::ifstream fin; @@ -148,10 +154,10 @@ UOAnimUOP::UOPFrameData UOAnimUOP::loadFrameData(int animID, int groupID, int di animFile->unpack(fin, decData, decDataSize); fin.close(); - if (uoppackage::errorHandler.errorOccurred()) // check if there was an error when extracting the uop file + if (uopp::errorHandler.errorOccurred()) // check if there was an error when extracting the uop file { appendToLog("UOPPackage error!"); - auto errors = uoppackage::errorHandler.getErrorQueue(); + auto errors = uopp::errorHandler.getErrorQueue(); for (std::string str : errors) appendToLog(str); return UOPFrameData{}; @@ -246,6 +252,9 @@ UOAnimUOP::UOPFrameData UOAnimUOP::loadFrameData(int animID, int groupID, int di QImage* UOAnimUOP::drawAnimFrame(int bodyID, int action, int direction, int frame, int hueIndex) { + if (isInitializing()) + return nullptr; + // select the group (action) we have chosen or, if invalid, the first valid one int groupID = -1; if (m_animationsMatrix[bodyID][action] != nullptr) @@ -331,9 +340,9 @@ QImage* UOAnimUOP::drawAnimFrame(int bodyID, int action, int direction, int fram decDataOff += 1; ARGB16 color_argb16 = palette[palette_index]; // ^ 0x8000; - if (hueIndex != 0) + if (hueIndex > 0) // client starts to count from 1 (0 means do not change the color) { - UOHueEntry hue = g_UOHues->getHueEntry(hueIndex); + UOHueEntry hue = g_UOHues->getHueEntry(hueIndex-1); color_argb16 = hue.applyToColor(color_argb16, applyToGrayOnly); } ARGB32 color_argb32 = argb16_to_argb32(color_argb16); diff --git a/src/uofiles/uoanimuop.h b/src/uofiles/uoanimuop.h index 7f3f8d6..1012f0e 100644 --- a/src/uofiles/uoanimuop.h +++ b/src/uofiles/uoanimuop.h @@ -15,8 +15,8 @@ class UOAnimUOP UOAnimUOP(std::string clientPath, std::function reportProgress); //~UOAnimUOP(); - bool isLoading() const { - return m_isLoading; + bool isInitializing() const { + return m_isInitializing; } bool animExists(int animID); QImage* drawAnimFrame(int bodyID, int action, int direction, int frame, int hueIndex); @@ -33,20 +33,20 @@ class UOAnimUOP struct UOPFrameData { size_t dataStart = 0; - //uint_fast16_t frameId; + //uint16_t frameId; unsigned int pixelDataOffset = 0; }; std::string m_clientPath; - uoppackage::UOPPackage m_animUOPs[4]; + uopp::UOPPackage m_animUOPs[4]; std::vector m_animationsData; // sort animationsData by [animID][groupID]: static const int kAnimIdMax = 2048; // animation ID static const int kGroupIdMax = 100; // action ID - UOPAnimationData* m_animationsMatrix[kAnimIdMax][kGroupIdMax]; - bool m_isLoading; + UOPAnimationData* m_animationsMatrix[kAnimIdMax][kGroupIdMax]; // the matrix is thread-safe if we aren't writing in the same position in different threads + bool m_isInitializing; void buildAnimTable(std::function reportProgress); UOPFrameData loadFrameData(int animID, int groupID, int direction, int frame, char *&decData, size_t& decDataSize); // decData: buffer for decompressed anim data diff --git a/src/uofiles/uoart.cpp b/src/uofiles/uoart.cpp index 0e2ae62..402aa58 100644 --- a/src/uofiles/uoart.cpp +++ b/src/uofiles/uoart.cpp @@ -96,9 +96,9 @@ QImage* UOArt::drawArt(unsigned int id, unsigned int hueIndex, bool partialHue) ARGB16 color_argb16 = ARGB16(rawcolor_argb16); //if ( (color &0x7FF) == 0 || (color & 0x7FF)==0x7FF ) // continue; - if (hueIndex != 0) + if (hueIndex > 0) // client starts to count from 1 (0 means do not change the color) { - UOHueEntry hue = g_UOHues->getHueEntry(hueIndex); + UOHueEntry hue = g_UOHues->getHueEntry(hueIndex-1); color_argb16 = hue.applyToColor(color_argb16, partialHue); } ARGB32 color_argb32 = argb16_to_argb32(color_argb16); @@ -119,9 +119,9 @@ QImage* UOArt::drawArt(unsigned int id, unsigned int hueIndex, bool partialHue) ARGB16 color_argb16 = ARGB16(rawcolor_argb16); //if ( (color &0x7FF) == 0 || (color & 0x7FF)==0x7FF ) // continue; - if (hueIndex != 0) + if (hueIndex > 0) // client starts to count from 1 (0 means do not change the color) { - UOHueEntry hue = g_UOHues->getHueEntry(hueIndex); + UOHueEntry hue = g_UOHues->getHueEntry(hueIndex-1); color_argb16 = hue.applyToColor(color_argb16, partialHue); } ARGB32 color_argb32 = argb16_to_argb32(color_argb16); @@ -196,9 +196,9 @@ QImage* UOArt::drawArt(unsigned int id, unsigned int hueIndex, bool partialHue) uint16_t rawcolor_argb16 = 0; fs_art.read(reinterpret_cast(&rawcolor_argb16), 2); ARGB16 color_argb16 = ARGB16(rawcolor_argb16); - if (hueIndex != 0) + if (hueIndex > 0) // client starts to count from 1 (0 means do not change the color) { - UOHueEntry hue = g_UOHues->getHueEntry(hueIndex); + UOHueEntry hue = g_UOHues->getHueEntry(hueIndex-1); color_argb16 = hue.applyToColor(color_argb16, partialHue); } ARGB32 color_argb32 = argb16_to_argb32(color_argb16); diff --git a/src/uofiles/uohues.cpp b/src/uofiles/uohues.cpp index 487af02..ecfb670 100644 --- a/src/uofiles/uohues.cpp +++ b/src/uofiles/uohues.cpp @@ -2,6 +2,7 @@ #include "globals.h" #include + ARGB32 argb16_to_argb32(ARGB16 argb16, bool maxOpacity) { // In ARGB16 each color is 5 bits, so a value between 0-31 @@ -43,6 +44,24 @@ ARGB32 argb16_to_argb32(ARGB16 argb16, bool maxOpacity) return ARGB32(a, r, g, b); } +void ARGB32::adjustBrightness(int percent) +{ + int tempR = m_color_r + ((m_color_r * percent) / 100); + if (tempR > 255) tempR = 255; + else if (tempR < 0) tempR = 0; + m_color_r = tempR; + + int tempG = m_color_g + ((m_color_g * percent) / 100); + if (tempG > 255) tempG = 255; + else if (tempG < 0) tempG = 0; + m_color_g = tempG; + + int tempB = m_color_b + ((m_color_r * percent) / 100); + if (tempB > 255) tempB = 255; + else if (tempB < 0) tempB = 0; + m_color_b = tempB; +} + UOHues::UOHues(std::string path_hues) { appendToLog("Loading hues.mul"); @@ -107,13 +126,24 @@ UOHueEntry UOHues::getHueEntry(int index) const // for the client: 0 is no hue // for hues.mul: 0 is the first entry // so the client starts to count from 1 - index -= 1; if (index >= 0 && index < 3000) return hues[index]; else return hues[0]; } +ARGB16 UOHueEntry::getColor(unsigned int index) const +{ + if (index >= kColorTableSize) + return ARGB16(0); + return ARGB16(color_table[index]); +} + +std::string UOHueEntry::getName() const +{ + return std::string(name); +} + ARGB16 UOHueEntry::applyToColor(ARGB16 color16, bool applyToGrayOnly) { /* @@ -145,15 +175,3 @@ ARGB16 UOHueEntry::applyToColor(ARGB16 color16, bool applyToGrayOnly) return ARGB16(color_table[color16.getR()]); // ret will always be < 32 } -ARGB16 UOHueEntry::getColor(unsigned int index) const -{ - if (index > 32) - return ARGB16(0); - return ARGB16(color_table[index]); -} - -std::string UOHueEntry::getName() const -{ - return std::string(name); -} - diff --git a/src/uofiles/uohues.h b/src/uofiles/uohues.h index bdcca30..07a836d 100644 --- a/src/uofiles/uohues.h +++ b/src/uofiles/uohues.h @@ -147,41 +147,28 @@ class ARGB32 // Colors used by Leviathan's interface are RGB32 return this->getVal(); } - void adjustBrightness(int percent) { - int tempR = m_color_r + ((m_color_r * percent) / 100); - if (tempR > 255) tempR = 255; - else if (tempR < 0) tempR = 0; - m_color_r = tempR; - - int tempG = m_color_g + ((m_color_g * percent) / 100); - if (tempG > 255) tempG = 255; - else if (tempG < 0) tempG = 0; - m_color_g = tempG; - - int tempB = m_color_b + ((m_color_r * percent) / 100); - if (tempB > 255) tempB = 255; - else if (tempB < 0) tempB = 0; - m_color_b = tempB; - } + void adjustBrightness(int percent); }; //--------hues.mul class UOHues; -class UOHueEntry +struct UOHueEntry { friend class UOHues; + static const int kColorTableSize = 32; private: //uint32_t index; char name[20]; - uint16_t color_table[32]; + uint16_t color_table[kColorTableSize]; public: - ARGB16 applyToColor(ARGB16 color16, bool applyToGrayOnly = false); // apply hue to the RGB16 color ARGB16 getColor(unsigned int index) const; std::string getName() const; + + ARGB16 applyToColor(ARGB16 color16, bool applyToGrayOnly = false); // apply hue to the RGB16 color }; diff --git a/src/uofiles/uoppackage/UOPBlock.cpp b/src/uofiles/uoppackage/UOPBlock.cpp index a172249..68da2aa 100644 --- a/src/uofiles/uoppackage/UOPBlock.cpp +++ b/src/uofiles/uoppackage/UOPBlock.cpp @@ -2,7 +2,7 @@ #include "UOPFile.h" -namespace uoppackage +namespace uopp { diff --git a/src/uofiles/uoppackage/UOPBlock.h b/src/uofiles/uoppackage/UOPBlock.h index ad1623d..2abb0f8 100644 --- a/src/uofiles/uoppackage/UOPBlock.h +++ b/src/uofiles/uoppackage/UOPBlock.h @@ -7,7 +7,7 @@ #include -namespace uoppackage +namespace uopp { class UOPFile; diff --git a/src/uofiles/uoppackage/UOPCompression.h b/src/uofiles/uoppackage/UOPCompression.h index 1d178bd..02a906b 100644 --- a/src/uofiles/uoppackage/UOPCompression.h +++ b/src/uofiles/uoppackage/UOPCompression.h @@ -1,7 +1,7 @@ #ifndef UOPCOMPRESSION_H #define UOPCOMPRESSION_H -namespace uoppackage +namespace uopp { diff --git a/src/uofiles/uoppackage/UOPError.cpp b/src/uofiles/uoppackage/UOPError.cpp index a127c98..4eca923 100644 --- a/src/uofiles/uoppackage/UOPError.cpp +++ b/src/uofiles/uoppackage/UOPError.cpp @@ -2,7 +2,7 @@ #include "zlib.h" -namespace uoppackage +namespace uopp { UOPError errorHandler; diff --git a/src/uofiles/uoppackage/UOPError.h b/src/uofiles/uoppackage/UOPError.h index 0068b92..7b1aefd 100644 --- a/src/uofiles/uoppackage/UOPError.h +++ b/src/uofiles/uoppackage/UOPError.h @@ -5,7 +5,7 @@ #include -namespace uoppackage +namespace uopp { diff --git a/src/uofiles/uoppackage/UOPFile.cpp b/src/uofiles/uoppackage/UOPFile.cpp index 5f2157a..e3e7305 100644 --- a/src/uofiles/uoppackage/UOPFile.cpp +++ b/src/uofiles/uoppackage/UOPFile.cpp @@ -7,7 +7,7 @@ #define ADDERROR(_x_) errorHandler.m_errorQueue.push_front(_x_) -namespace uoppackage +namespace uopp { diff --git a/src/uofiles/uoppackage/UOPFile.h b/src/uofiles/uoppackage/UOPFile.h index 24127c8..56bbb3b 100644 --- a/src/uofiles/uoppackage/UOPFile.h +++ b/src/uofiles/uoppackage/UOPFile.h @@ -5,7 +5,7 @@ #include -namespace uoppackage +namespace uopp { diff --git a/src/uofiles/uoppackage/UOPHeader.cpp b/src/uofiles/uoppackage/UOPHeader.cpp index dbd3a6e..675732e 100644 --- a/src/uofiles/uoppackage/UOPHeader.cpp +++ b/src/uofiles/uoppackage/UOPHeader.cpp @@ -4,7 +4,7 @@ #define ADDERROR(_x_) errorHandler.m_errorQueue.push_front(_x_) -namespace uoppackage +namespace uopp { diff --git a/src/uofiles/uoppackage/UOPHeader.h b/src/uofiles/uoppackage/UOPHeader.h index fecf6c7..3ebc6fc 100644 --- a/src/uofiles/uoppackage/UOPHeader.h +++ b/src/uofiles/uoppackage/UOPHeader.h @@ -4,7 +4,7 @@ #include -namespace uoppackage +namespace uopp { diff --git a/src/uofiles/uoppackage/UOPPackage.cpp b/src/uofiles/uoppackage/UOPPackage.cpp index 78f0eb3..303b832 100644 --- a/src/uofiles/uoppackage/UOPPackage.cpp +++ b/src/uofiles/uoppackage/UOPPackage.cpp @@ -9,7 +9,7 @@ #define ADDERROR errorHandler.m_errorQueue.push_front -namespace uoppackage +namespace uopp { diff --git a/src/uofiles/uoppackage/UOPPackage.h b/src/uofiles/uoppackage/UOPPackage.h index ec9d427..84d81b1 100644 --- a/src/uofiles/uoppackage/UOPPackage.h +++ b/src/uofiles/uoppackage/UOPPackage.h @@ -14,7 +14,7 @@ #include -namespace uoppackage +namespace uopp { class UOPFile; diff --git a/src/version.h b/src/version.h index a8e0335..88db125 100644 --- a/src/version.h +++ b/src/version.h @@ -1,7 +1,7 @@ #ifndef VERSION_H #define VERSION_H -#define LEVIATHAN_VERSION 0.2 +#define LEVIATHAN_VERSION 0.2.1 #define BUILD_NOT_AUTOMATIC #endif // VERSION_H