Commit 62ba4e56 authored by nanahira's avatar nanahira

Merge branch 'develop' of git.mycard.moe:mycard/ygopro into develop

parents 76404842 1a8a48fa
......@@ -7,4 +7,5 @@ git clone --depth=1 https://code.mycard.moe/mycard/ygopro-database
cp -rf ./ygopro-database/locales/$TARGET_LOCALE/* .
# ygopro-images
mkdir pics
# skip it in develop branch
# wget -O - https://cdn01.moecube.com/images/ygopro-images-${TARGET_LOCALE}.zip | bsdtar -C pics -xf -
......@@ -18,6 +18,8 @@
/ygopro
/ygopro.exe
/ygopro.app
/ikpMP3.dll
/irrKlang.dll
/bin
/build
......
......@@ -79,9 +79,9 @@ video::IImage* SGUITTGlyph::createGlyphImage(const FT_Bitmap& bits, video::IVide
const u32 image_pitch = image->getPitch() / sizeof(u16);
u16* image_data = (u16*)image->lock();
u8* glyph_data = bits.buffer;
for (s32 y = 0; y < bits.rows; ++y) {
for (s32 y = 0; y < (s32)bits.rows; ++y) {
u16* row = image_data;
for (s32 x = 0; x < bits.width; ++x) {
for (s32 x = 0; x < (s32)bits.width; ++x) {
// Monochrome bitmaps store 8 pixels per byte. The left-most pixel is the bit 0x80.
// So, we go through the data each bit at a time.
if ((glyph_data[y * bits.pitch + (x / 8)] & (0x80 >> (x % 8))) != 0)
......@@ -105,9 +105,9 @@ video::IImage* SGUITTGlyph::createGlyphImage(const FT_Bitmap& bits, video::IVide
const u32 image_pitch = image->getPitch() / sizeof(u32);
u32* image_data = (u32*)image->lock();
u8* glyph_data = bits.buffer;
for (s32 y = 0; y < bits.rows; ++y) {
for (s32 y = 0; y < (s32)bits.rows; ++y) {
u8* row = glyph_data;
for (s32 x = 0; x < bits.width; ++x) {
for (s32 x = 0; x < (s32)bits.width; ++x) {
image_data[y * image_pitch + x] |= static_cast<u32>(255.0f * (static_cast<float>(*row++) / gray_count)) << 24;
//data[y * image_pitch + x] |= ((u32)(*bitsdata++) << 24);
}
......@@ -154,8 +154,8 @@ void SGUITTGlyph::preload(u32 char_index, FT_Face face, video::IVideoDriver* dri
glyph_page = parent->getLastGlyphPageIndex();
u32 texture_side_length = page->texture_size.Width - font_size;
u32 margin = font_size * 0.5;
u32 sprite_size = font_size * 1.5;
u32 margin = (u32)(font_size * 0.5);
u32 sprite_size = (u32)(font_size * 1.5);
core::vector2di page_position(
(s32)(page->used_slots % (s32)(texture_side_length / sprite_size)) * sprite_size + margin,
(s32)(page->used_slots / (s32)(texture_side_length / sprite_size)) * sprite_size + margin
......@@ -527,29 +527,28 @@ void CGUITTFont::draw(const core::stringw& text, const core::rect<s32>& position
core::ustring::const_iterator iter(utext);
while (!iter.atEnd()) {
uchar32_t currentChar = *iter;
n = getGlyphIndexByChar(currentChar);
bool visible = (Invisible.findFirst(currentChar) == -1);
if (n > 0 && visible) {
bool lineBreak = false;
if (currentChar == L'\r') { // Mac or Windows breaks
lineBreak = true;
if (*(iter + 1) == (uchar32_t)'\n') // Windows line breaks.
if (*(iter + 1) == L'\n') // Windows line breaks.
currentChar = *(++iter);
} else if (currentChar == (uchar32_t)'\n') { // Unix breaks
} else if (currentChar == L'\n') { // Unix breaks
lineBreak = true;
}
if (lineBreak) {
previousChar = 0;
offset.Y += supposed_line_height; //font_metrics.ascender / 64;
offset.X = position.UpperLeftCorner.X;
if (hcenter)
offset.X += (position.getWidth() - textDimension.Width) >> 1;
++iter;
continue;
}
n = getGlyphIndexByChar(currentChar);
bool visible = (Invisible.findFirst(currentChar) == -1);
if (n > 0 && visible) {
// Calculate the glyph offset.
s32 offx = Glyphs[n - 1].offset.X;
s32 offy = (font_metrics.ascender / 64) - Glyphs[n - 1].offset.Y;
......
#ifndef BUFFERIO_H
#define BUFFERIO_H
#ifdef _MSC_VER
#pragma warning(disable: 4244)
#endif
#include <cstdint>
#include "../ocgcore/buffer.h"
class BufferIO {
public:
inline static int ReadInt32(unsigned char*& p) {
int ret = *(int*)p;
p += 4;
return ret;
return buffer_read<int32_t>(p);
}
inline static short ReadInt16(unsigned char*& p) {
short ret = *(short*)p;
p += 2;
return ret;
return buffer_read<int16_t>(p);
}
inline static char ReadInt8(unsigned char*& p) {
char ret = *(char*)p;
p++;
return ret;
return buffer_read<char>(p);
}
inline static unsigned char ReadUInt8(unsigned char*& p) {
unsigned char ret = *(unsigned char*)p;
p++;
return ret;
return buffer_read<unsigned char>(p);
}
inline static void WriteInt32(unsigned char*& p, int val) {
(*(int*)p) = val;
p += 4;
buffer_write<int32_t>(p, val);
}
inline static void WriteInt16(unsigned char*& p, short val) {
(*(short*)p) = val;
p += 2;
buffer_write<int16_t>(p, val);
}
inline static void WriteInt8(unsigned char*& p, char val) {
*p = val;
p++;
buffer_write<char>(p, val);
}
template<typename T1, typename T2>
inline static int CopyWStr(T1* src, T2* pstr, int bufsize) {
int l = 0;
while(src[l] && l < bufsize - 1) {
pstr[l] = src[l];
pstr[l] = (T2)src[l];
l++;
}
pstr[l] = 0;
......@@ -53,7 +41,7 @@ public:
inline static int CopyWStrRef(T1* src, T2*& pstr, int bufsize) {
int l = 0;
while(src[l] && l < bufsize - 1) {
pstr[l] = src[l];
pstr[l] = (T2)src[l];
l++;
}
pstr += l;
......@@ -65,7 +53,7 @@ public:
char* pstr = str;
while(*wsrc != 0) {
if(*wsrc < 0x80) {
*str = *wsrc;
*str = (char)*wsrc;
++str;
} else if(*wsrc < 0x800) {
str[0] = ((*wsrc >> 6) & 0x1f) | 0xc0;
......@@ -131,12 +119,14 @@ public:
return wp - wstr;
}
static int GetVal(const wchar_t* pstr) {
int ret = 0;
unsigned int ret = 0;
while(*pstr >= L'0' && *pstr <= L'9') {
ret = ret * 10 + (*pstr - L'0');
pstr++;
}
return ret;
if (*pstr == 0)
return (int)ret;
return 0;
}
};
......
......@@ -7,9 +7,13 @@ namespace ygo {
ClientCard::~ClientCard() {
ClearTarget();
if (equipTarget)
if (equipTarget) {
equipTarget->is_showequip = false;
equipTarget->equipped.erase(this);
for (auto card : equipped) {
equipTarget = nullptr;
}
for (auto& card : equipped) {
card->is_showequip = false;
card->equipTarget = nullptr;
}
equipped.clear();
......@@ -21,8 +25,9 @@ ClientCard::~ClientCard() {
else
++it;
}
overlayTarget = nullptr;
}
for (auto card : overlayed) {
for (auto& card : overlayed) {
card->overlayTarget = nullptr;
}
overlayed.clear();
......@@ -108,10 +113,10 @@ void ClientCard::UpdateInfo(unsigned char* buf) {
if(flag & QUERY_REASON_CARD)
buf += 4;
if(flag & QUERY_EQUIP_CARD) {
int c = BufferIO::ReadInt8(buf);
int l = BufferIO::ReadInt8(buf);
int s = BufferIO::ReadInt8(buf);
BufferIO::ReadInt8(buf);
int c = BufferIO::ReadUInt8(buf);
unsigned int l = BufferIO::ReadUInt8(buf);
int s = BufferIO::ReadUInt8(buf);
BufferIO::ReadUInt8(buf);
ClientCard* ecard = mainGame->dField.GetCard(mainGame->LocalPlayer(c), l, s);
if (ecard) {
equipTarget = ecard;
......@@ -121,10 +126,10 @@ void ClientCard::UpdateInfo(unsigned char* buf) {
if(flag & QUERY_TARGET_CARD) {
int count = BufferIO::ReadInt32(buf);
for(int i = 0; i < count; ++i) {
int c = BufferIO::ReadInt8(buf);
int l = BufferIO::ReadInt8(buf);
int s = BufferIO::ReadInt8(buf);
BufferIO::ReadInt8(buf);
int c = BufferIO::ReadUInt8(buf);
unsigned int l = BufferIO::ReadUInt8(buf);
int s = BufferIO::ReadUInt8(buf);
BufferIO::ReadUInt8(buf);
ClientCard* tcard = mainGame->dField.GetCard(mainGame->LocalPlayer(c), l, s);
if (tcard) {
cardTarget.insert(tcard);
......@@ -206,10 +211,6 @@ void ClientCard::ClearData() {
rscstring[0] = 0;
lscstring[0] = 0;
counters.clear();
for (auto card : equipped) {
card->equipTarget = nullptr;
}
equipped.clear();
}
bool ClientCard::client_card_sort(ClientCard* c1, ClientCard* c2) {
if(c1->is_selected != c2->is_selected)
......@@ -220,23 +221,26 @@ bool ClientCard::client_card_sort(ClientCard* c1, ClientCard* c2) {
return cp1 < cp2;
if(c1->location != c2->location)
return c1->location < c2->location;
if(c1->location & LOCATION_OVERLAY)
if(c1->overlayTarget != c2->overlayTarget)
if (c1->location & LOCATION_OVERLAY) {
if (c1->overlayTarget != c2->overlayTarget)
return c1->overlayTarget->sequence < c2->overlayTarget->sequence;
else return c1->sequence < c2->sequence;
else
return c1->sequence < c2->sequence;
}
else {
if(c1->location & (LOCATION_DECK | LOCATION_GRAVE | LOCATION_REMOVED | LOCATION_EXTRA)) {
auto it1 = std::find_if(mainGame->dField.chains.rbegin(), mainGame->dField.chains.rend(), [c1](const auto& ch) {
auto it1 = std::find_if(mainGame->dField.chains.rbegin(), mainGame->dField.chains.rend(), [c1](const ChainInfo& ch) {
return c1 == ch.chain_card || ch.target.find(c1) != ch.target.end();
});
auto it2 = std::find_if(mainGame->dField.chains.rbegin(), mainGame->dField.chains.rend(), [c2](const auto& ch) {
auto it2 = std::find_if(mainGame->dField.chains.rbegin(), mainGame->dField.chains.rend(), [c2](const ChainInfo& ch) {
return c2 == ch.chain_card || ch.target.find(c2) != ch.target.end();
});
if(it1 != mainGame->dField.chains.rend() || it2 != mainGame->dField.chains.rend()) {
return it1 < it2;
}
return c1->sequence > c2->sequence;
} else
}
else
return c1->sequence < c2->sequence;
}
}
......
......@@ -11,21 +11,9 @@
namespace ygo {
using CardData = card_data;
struct CardDataC {
unsigned int code;
unsigned int alias;
unsigned long long setcode;
unsigned int type;
unsigned int level;
unsigned int attribute;
unsigned int race;
int attack;
int defense;
unsigned int lscale;
unsigned int rscale;
unsigned int link_marker;
unsigned int ot;
unsigned int category;
struct CardDataC : card_data {
unsigned int ot{};
unsigned int category{};
};
struct CardString {
std::wstring name;
......@@ -33,6 +21,7 @@ struct CardString {
std::wstring desc[16];
};
typedef std::unordered_map<unsigned int, CardDataC>::const_iterator code_pointer;
typedef std::unordered_map<unsigned int, CardString>::const_iterator string_pointer;
class ClientCard {
public:
......
......@@ -19,39 +19,39 @@ ClientField::ClientField() {
}
ClientField::~ClientField() {
for (int i = 0; i < 2; ++i) {
for (auto card : deck[i]) {
for (auto& card : deck[i]) {
delete card;
}
deck[i].clear();
for (auto card : hand[i]) {
for (auto& card : hand[i]) {
delete card;
}
hand[i].clear();
for (auto card : mzone[i]) {
for (auto& card : mzone[i]) {
if (card)
delete card;
card = nullptr;
}
for (auto card : szone[i]) {
for (auto& card : szone[i]) {
if (card)
delete card;
card = nullptr;
}
for (auto card : grave[i]) {
for (auto& card : grave[i]) {
delete card;
}
grave[i].clear();
for (auto card : remove[i]) {
for (auto& card : remove[i]) {
delete card;
}
remove[i].clear();
for (auto card : extra[i]) {
for (auto& card : extra[i]) {
delete card;
}
extra[i].clear();
}
for (auto card : overlay_cards) {
for (auto& card : overlay_cards) {
delete card;
}
overlay_cards.clear();
......@@ -192,7 +192,7 @@ void ClientField::AddCard(ClientCard* pcard, int controler, int location, int se
case LOCATION_DECK: {
if (sequence != 0 || deck[controler].size() == 0) {
deck[controler].push_back(pcard);
pcard->sequence = deck[controler].size() - 1;
pcard->sequence = (unsigned char)(deck[controler].size() - 1);
} else {
deck[controler].push_back(0);
for(int i = deck[controler].size() - 1; i > 0; --i) {
......@@ -207,7 +207,7 @@ void ClientField::AddCard(ClientCard* pcard, int controler, int location, int se
}
case LOCATION_HAND: {
hand[controler].push_back(pcard);
pcard->sequence = hand[controler].size() - 1;
pcard->sequence = (unsigned char)(hand[controler].size() - 1);
break;
}
case LOCATION_MZONE: {
......@@ -220,18 +220,18 @@ void ClientField::AddCard(ClientCard* pcard, int controler, int location, int se
}
case LOCATION_GRAVE: {
grave[controler].push_back(pcard);
pcard->sequence = grave[controler].size() - 1;
pcard->sequence = (unsigned char)(grave[controler].size() - 1);
break;
}
case LOCATION_REMOVED: {
remove[controler].push_back(pcard);
pcard->sequence = remove[controler].size() - 1;
pcard->sequence = (unsigned char)(remove[controler].size() - 1);
break;
}
case LOCATION_EXTRA: {
if(extra_p_count[controler] == 0 || (pcard->position & POS_FACEUP)) {
extra[controler].push_back(pcard);
pcard->sequence = extra[controler].size() - 1;
pcard->sequence = (unsigned char)(extra[controler].size() - 1);
} else {
extra[controler].push_back(0);
int p = extra[controler].size() - extra_p_count[controler] - 1;
......@@ -1489,15 +1489,7 @@ static bool is_declarable(T const& cd, const std::vector<int>& opcode) {
if (stack.size() >= 1) {
int set_code = stack.top();
stack.pop();
unsigned long long sc = cd.setcode;
bool res = false;
int settype = set_code & 0xfff;
int setsubtype = set_code & 0xf000;
while (sc) {
if ((sc & 0xfff) == settype && (sc & 0xf000 & setsubtype) == setsubtype)
res = true;
sc = sc >> 16;
}
bool res = cd.is_setcode(set_code);
stack.push(res);
}
break;
......@@ -1555,9 +1547,11 @@ void ClientField::UpdateDeclarableList() {
}
mainGame->lstANCard->clear();
ancard.clear();
for(auto cit = dataManager._strings.begin(); cit != dataManager._strings.end(); ++cit) {
for(auto cit = dataManager.strings_begin; cit != dataManager.strings_end; ++cit) {
if(cit->second.name.find(pname) != std::wstring::npos) {
auto cp = dataManager.GetCodePointer(cit->first); //verified by _strings
auto cp = dataManager.GetCodePointer(cit->first);
if (cp == dataManager.datas_end)
continue;
//datas.alias can be double card names or alias
if(is_declarable(cp->second, declare_opcodes)) {
if(pname == cit->second.name || trycode == cit->first) { //exact match or last used
......
......@@ -86,10 +86,8 @@ using namespace video;
using namespace io;
using namespace gui;
typedef int BOOL;
extern const unsigned short PRO_VERSION;
extern int enable_log;
extern unsigned int enable_log;
extern bool exit_on_return;
extern bool open_file;
extern wchar_t open_file_name[256];
......
......@@ -9,6 +9,13 @@ byte DataManager::scriptBuffer[0x20000];
IFileSystem* DataManager::FileSystem;
DataManager dataManager;
DataManager::DataManager() : _datas(16384), _strings(16384) {
datas_begin = _datas.begin();
datas_end = _datas.end();
strings_begin = _strings.begin();
strings_end = _strings.end();
extra_setcode = { {8512558u, {0x8f, 0x54, 0x59, 0x82, 0x13a}}, };
}
bool DataManager::LoadDB(const wchar_t* wfile) {
char file[256];
BufferIO::EncodeUTF8(wfile, file);
......@@ -34,11 +41,11 @@ bool DataManager::LoadDB(const wchar_t* wfile) {
const char* sql = "select * from datas,texts where datas.id=texts.id";
if(sqlite3_prepare_v2(pDB, sql, -1, &pStmt, 0) != SQLITE_OK)
return Error(&db);
CardDataC cd;
CardString cs;
wchar_t strBuffer[4096];
int step = 0;
do {
CardDataC cd;
CardString cs;
step = sqlite3_step(pStmt);
if(step == SQLITE_BUSY || step == SQLITE_ERROR || step == SQLITE_MISUSE)
return Error(&db, pStmt);
......@@ -46,7 +53,19 @@ bool DataManager::LoadDB(const wchar_t* wfile) {
cd.code = sqlite3_column_int(pStmt, 0);
cd.ot = sqlite3_column_int(pStmt, 1);
cd.alias = sqlite3_column_int(pStmt, 2);
cd.setcode = sqlite3_column_int64(pStmt, 3);
auto setcode = sqlite3_column_int64(pStmt, 3);
if (setcode) {
auto it = extra_setcode.find(cd.code);
if (it != extra_setcode.end()) {
int len = it->second.size();
if (len > SIZE_SETCODE)
len = SIZE_SETCODE;
if (len)
memcpy(cd.setcode, it->second.data(), len * sizeof(uint16_t));
}
else
cd.set_setcode(setcode);
}
cd.type = sqlite3_column_int(pStmt, 4);
cd.attack = sqlite3_column_int(pStmt, 5);
cd.defense = sqlite3_column_int(pStmt, 6);
......@@ -83,6 +102,10 @@ bool DataManager::LoadDB(const wchar_t* wfile) {
sqlite3_finalize(pStmt);
spmemvfs_close_db(&db);
spmemvfs_env_fini();
datas_begin = _datas.begin();
datas_end = _datas.end();
strings_begin = _strings.begin();
strings_end = _strings.end();
return true;
}
bool DataManager::LoadStrings(const char* file) {
......@@ -116,24 +139,30 @@ bool DataManager::LoadStrings(IReadFile* reader) {
void DataManager::ReadStringConfLine(const char* linebuf) {
if(linebuf[0] != '!')
return;
char strbuf[256];
int value;
wchar_t strBuffer[4096];
sscanf(linebuf, "!%s", strbuf);
char strbuf[256]{};
int value{};
wchar_t strBuffer[4096]{};
if (sscanf(linebuf, "!%63s", strbuf) != 1)
return;
if(!strcmp(strbuf, "system")) {
sscanf(&linebuf[7], "%d %240[^\n]", &value, strbuf);
if (sscanf(&linebuf[7], "%d %240[^\n]", &value, strbuf) != 2)
return;
BufferIO::DecodeUTF8(strbuf, strBuffer);
_sysStrings[value] = strBuffer;
} else if(!strcmp(strbuf, "victory")) {
sscanf(&linebuf[8], "%x %240[^\n]", &value, strbuf);
if (sscanf(&linebuf[8], "%x %240[^\n]", &value, strbuf) != 2)
return;
BufferIO::DecodeUTF8(strbuf, strBuffer);
_victoryStrings[value] = strBuffer;
} else if(!strcmp(strbuf, "counter")) {
sscanf(&linebuf[8], "%x %240[^\n]", &value, strbuf);
if (sscanf(&linebuf[8], "%x %240[^\n]", &value, strbuf) != 2)
return;
BufferIO::DecodeUTF8(strbuf, strBuffer);
_counterStrings[value] = strBuffer;
} else if(!strcmp(strbuf, "setname")) {
sscanf(&linebuf[8], "%x %240[^\t\n]", &value, strbuf);//using tab for comment
//using tab for comment
if (sscanf(&linebuf[8], "%x %240[^\t\n]", &value, strbuf) != 2)
return;
BufferIO::DecodeUTF8(strbuf, strBuffer);
_setnameStrings[value] = strBuffer;
}
......@@ -148,14 +177,14 @@ bool DataManager::Error(spmemvfs_db_t* pDB, sqlite3_stmt* pStmt) {
return false;
}
bool DataManager::GetData(unsigned int code, CardData* pData) {
auto cdit = _datas.find(code);
code_pointer cdit = _datas.find(code);
if(cdit == _datas.end())
return false;
auto data = cdit->second;
auto& data = cdit->second;
if (pData) {
pData->code = data.code;
pData->alias = data.alias;
pData->setcode = data.setcode;
memcpy(pData->setcode, data.setcode, SIZE_SETCODE);
pData->type = data.type;
pData->level = data.level;
pData->attribute = data.attribute;
......@@ -168,10 +197,13 @@ bool DataManager::GetData(unsigned int code, CardData* pData) {
}
return true;
}
code_pointer DataManager::GetCodePointer(int code) {
code_pointer DataManager::GetCodePointer(unsigned int code) const {
return _datas.find(code);
}
bool DataManager::GetString(int code, CardString* pStr) {
string_pointer DataManager::GetStringPointer(unsigned int code) const {
return _strings.find(code);
}
bool DataManager::GetString(unsigned int code, CardString* pStr) {
auto csit = _strings.find(code);
if(csit == _strings.end()) {
pStr->name = unknown_string;
......@@ -181,7 +213,7 @@ bool DataManager::GetString(int code, CardString* pStr) {
*pStr = csit->second;
return true;
}
const wchar_t* DataManager::GetName(int code) {
const wchar_t* DataManager::GetName(unsigned int code) {
auto csit = _strings.find(code);
if(csit == _strings.end())
return unknown_string;
......@@ -189,7 +221,7 @@ const wchar_t* DataManager::GetName(int code) {
return csit->second.name.c_str();
return unknown_string;
}
const wchar_t* DataManager::GetText(int code) {
const wchar_t* DataManager::GetText(unsigned int code) {
auto csit = _strings.find(code);
if(csit == _strings.end())
return unknown_string;
......@@ -198,7 +230,7 @@ const wchar_t* DataManager::GetText(int code) {
return unknown_string;
}
const wchar_t* DataManager::GetDesc(unsigned int strCode) {
if(strCode < 10000u)
if (strCode < (MIN_CARD_ID << 4))
return GetSysString(strCode);
unsigned int code = (strCode >> 4) & 0x0fffffff;
unsigned int offset = strCode & 0xf;
......@@ -210,7 +242,7 @@ const wchar_t* DataManager::GetDesc(unsigned int strCode) {
return unknown_string;
}
const wchar_t* DataManager::GetSysString(int code) {
if(code < 0 || code >= 2048)
if (code < 0 || code > MAX_STRING_ID)
return unknown_string;
auto csit = _sysStrings.find(code);
if(csit == _sysStrings.end())
......@@ -322,10 +354,12 @@ const wchar_t* DataManager::FormatType(int type) {
return unknown_string;
return tpBuffer;
}
const wchar_t* DataManager::FormatSetName(unsigned long long setcode) {
const wchar_t* DataManager::FormatSetName(const uint16_t setcode[]) {
wchar_t* p = scBuffer;
for(int i = 0; i < 4; ++i) {
const wchar_t* setname = GetSetName((setcode >> i * 16) & 0xffff);
for(int i = 0; i < 10; ++i) {
if (!setcode[i])
break;
const wchar_t* setname = GetSetName(setcode[i]);
if(setname) {
BufferIO::CopyWStrRef(setname, p, 32);
*p = L'|';
......
......@@ -8,20 +8,23 @@
#include <unordered_map>
namespace ygo {
constexpr int MAX_STRING_ID = 0x7ff;
constexpr unsigned int MIN_CARD_ID = (unsigned int)(MAX_STRING_ID + 1) >> 4;
class DataManager {
public:
DataManager(): _datas(16384), _strings(16384) {}
DataManager();
bool LoadDB(const wchar_t* wfile);
bool LoadStrings(const char* file);
bool LoadStrings(IReadFile* reader);
void ReadStringConfLine(const char* linebuf);
bool Error(spmemvfs_db_t* pDB, sqlite3_stmt* pStmt = 0);
bool GetData(unsigned int code, CardData* pData);
code_pointer GetCodePointer(int code);
bool GetString(int code, CardString* pStr);
const wchar_t* GetName(int code);
const wchar_t* GetText(int code);
code_pointer GetCodePointer(unsigned int code) const;
string_pointer GetStringPointer(unsigned int code) const;
bool GetString(unsigned int code, CardString* pStr);
const wchar_t* GetName(unsigned int code);
const wchar_t* GetText(unsigned int code);
const wchar_t* GetDesc(unsigned int strCode);
const wchar_t* GetSysString(int code);
const wchar_t* GetVictoryString(int code);
......@@ -33,23 +36,25 @@ public:
const wchar_t* FormatAttribute(int attribute);
const wchar_t* FormatRace(int race);
const wchar_t* FormatType(int type);
const wchar_t* FormatSetName(unsigned long long setcode);
const wchar_t* FormatSetName(const uint16_t setcode[]);
const wchar_t* FormatLinkMarker(int link_marker);
std::unordered_map<unsigned int, CardDataC> _datas;
std::unordered_map<unsigned int, CardString> _strings;
std::unordered_map<unsigned int, std::wstring> _counterStrings;
std::unordered_map<unsigned int, std::wstring> _victoryStrings;
std::unordered_map<unsigned int, std::wstring> _setnameStrings;
std::unordered_map<unsigned int, std::wstring> _sysStrings;
code_pointer datas_begin;
code_pointer datas_end;
string_pointer strings_begin;
string_pointer strings_end;
wchar_t numStrings[301][4];
wchar_t numBuffer[6];
wchar_t attBuffer[128];
wchar_t racBuffer[128];
wchar_t tpBuffer[128];
wchar_t scBuffer[128];
wchar_t lmBuffer[32];
wchar_t numStrings[301][4]{};
wchar_t numBuffer[6]{};
wchar_t attBuffer[128]{};
wchar_t racBuffer[128]{};
wchar_t tpBuffer[128]{};
wchar_t scBuffer[128]{};
wchar_t lmBuffer[32]{};
static byte scriptBuffer[0x20000];
static const wchar_t* unknown_string;
......@@ -57,6 +62,11 @@ public:
static byte* ScriptReaderEx(const char* script_name, int* slen);
static byte* ScriptReader(const char* script_name, int* slen);
static IFileSystem* FileSystem;
private:
std::unordered_map<unsigned int, CardDataC> _datas;
std::unordered_map<unsigned int, CardString> _strings;
std::unordered_map<unsigned int, std::vector<uint16_t>> extra_setcode;
};
extern DataManager dataManager;
......
......@@ -40,23 +40,6 @@ static int parse_filter(const wchar_t* pstr, unsigned int* type) {
return 0;
}
static bool check_set_code(const CardDataC& data, int set_code) {
unsigned long long sc = data.setcode;
if (data.alias) {
auto aptr = dataManager._datas.find(data.alias);
if (aptr != dataManager._datas.end())
sc = aptr->second.setcode;
}
bool res = false;
int settype = set_code & 0xfff;
int setsubtype = set_code & 0xf000;
while (sc) {
if ((sc & 0xfff) == settype && (sc & 0xf000 & setsubtype) == setsubtype)
res = true;
sc = sc >> 16;
}
return res;
}
static inline bool havePopupWindow() {
return mainGame->wQuery->isVisible() || mainGame->wCategories->isVisible() || mainGame->wLinkMarks->isVisible() || mainGame->wDeckManage->isVisible() || mainGame->wDMQuery->isVisible();
......@@ -111,6 +94,7 @@ void DeckBuilder::Terminate() {
mainGame->btnBigCardZoomIn->setVisible(false);
mainGame->btnBigCardZoomOut->setVisible(false);
mainGame->btnBigCardClose->setVisible(false);
mainGame->ResizeChatInputWindow();
mainGame->PopupElement(mainGame->wMainMenu);
mainGame->device->setEventReceiver(&mainGame->menuHandler);
mainGame->wACMessage->setVisible(false);
......@@ -1030,7 +1014,7 @@ bool DeckBuilder::OnEvent(const irr::SEvent& event) {
dragx = event.MouseInput.X;
dragy = event.MouseInput.Y;
draging_pointer = dataManager.GetCodePointer(hovered_code);
if(draging_pointer == dataManager._datas.end())
if(draging_pointer == dataManager.datas_end)
break;
if(hovered_pos == 4) {
if(!check_limit(draging_pointer))
......@@ -1084,7 +1068,7 @@ bool DeckBuilder::OnEvent(const irr::SEvent& event) {
if(hovered_pos == 0 || hovered_seq == -1)
break;
auto pointer = dataManager.GetCodePointer(hovered_code);
if(pointer == dataManager._datas.end())
if(pointer == dataManager.datas_end)
break;
soundManager.PlaySoundEffect(SOUND_CARD_DROP);
if(hovered_pos == 1) {
......@@ -1119,7 +1103,7 @@ bool DeckBuilder::OnEvent(const irr::SEvent& event) {
pop_side(hovered_seq);
} else {
auto pointer = dataManager.GetCodePointer(hovered_code);
if(pointer == dataManager._datas.end())
if(pointer == dataManager.datas_end)
break;
if(!check_limit(pointer))
break;
......@@ -1154,6 +1138,8 @@ bool DeckBuilder::OnEvent(const irr::SEvent& event) {
if (is_draging)
break;
auto pointer = dataManager.GetCodePointer(hovered_code);
if (pointer == dataManager.datas_end)
break;
if(!check_limit(pointer))
break;
soundManager.PlaySoundEffect(SOUND_CARD_PICK);
......@@ -1351,7 +1337,7 @@ void DeckBuilder::FilterCards() {
results.clear();
struct element_t {
std::wstring keyword;
int setcode;
unsigned int setcode;
enum class type_t {
all,
name,
......@@ -1421,9 +1407,11 @@ void DeckBuilder::FilterCards() {
query_elements.push_back(element);
}
}
auto strpointer = dataManager._strings.begin();
for(code_pointer ptr = dataManager._datas.begin(); ptr != dataManager._datas.end(); ++ptr, ++strpointer) {
for(code_pointer ptr = dataManager.datas_begin; ptr != dataManager.datas_end; ++ptr) {
const CardDataC& data = ptr->second;
auto strpointer = dataManager.GetStringPointer(ptr->first);
if (strpointer == dataManager.strings_end)
continue;
const CardString& text = strpointer->second;
if(data.type & TYPE_TOKEN)
continue;
......@@ -1502,14 +1490,14 @@ void DeckBuilder::FilterCards() {
if (elements_iterator->type == element_t::type_t::name) {
match = CardNameContains(text.name.c_str(), elements_iterator->keyword.c_str());
} else if (elements_iterator->type == element_t::type_t::setcode) {
match = elements_iterator->setcode && check_set_code(data, elements_iterator->setcode);
match = elements_iterator->setcode && data.is_setcode(elements_iterator->setcode);
} else {
int trycode = BufferIO::GetVal(elements_iterator->keyword.c_str());
bool tryresult = dataManager.GetData(trycode, 0);
if(!tryresult) {
match = CardNameContains(text.name.c_str(), elements_iterator->keyword.c_str())
|| text.text.find(elements_iterator->keyword) != std::wstring::npos
|| (elements_iterator->setcode && check_set_code(data, elements_iterator->setcode));
|| (elements_iterator->setcode && data.is_setcode(elements_iterator->setcode));
} else {
match = data.code == trycode || data.alias == trycode;
}
......
......@@ -41,49 +41,49 @@ public:
void pop_side(int seq);
bool check_limit(code_pointer pointer);
long long filter_effect;
unsigned int filter_type;
unsigned int filter_type2;
unsigned int filter_attrib;
unsigned int filter_race;
unsigned int filter_atktype;
int filter_atk;
unsigned int filter_deftype;
int filter_def;
unsigned int filter_lvtype;
unsigned int filter_lv;
unsigned int filter_scltype;
unsigned int filter_scl;
unsigned int filter_marks;
int filter_lm;
long long filter_effect{};
unsigned int filter_type{};
unsigned int filter_type2{};
unsigned int filter_attrib{};
unsigned int filter_race{};
unsigned int filter_atktype{};
int filter_atk{};
unsigned int filter_deftype{};
int filter_def{};
unsigned int filter_lvtype{};
unsigned int filter_lv{};
unsigned int filter_scltype{};
unsigned int filter_scl{};
unsigned int filter_marks{};
int filter_lm{};
position2di mouse_pos;
int hovered_code;
int hovered_pos;
int hovered_seq;
int is_lastcard;
int click_pos;
bool is_draging;
bool is_starting_dragging;
int dragx;
int dragy;
int bigcard_code;
float bigcard_zoom;
size_t pre_mainc;
size_t pre_extrac;
size_t pre_sidec;
int hovered_code{};
int hovered_pos{};
int hovered_seq{ -1 };
int is_lastcard{};
int click_pos{};
bool is_draging{};
bool is_starting_dragging{};
int dragx{};
int dragy{};
int bigcard_code{};
float bigcard_zoom{};
size_t pre_mainc{};
size_t pre_extrac{};
size_t pre_sidec{};
code_pointer draging_pointer;
int prev_category;
int prev_deck;
s32 prev_operation;
int prev_sel;
bool is_modified;
bool readonly;
bool showing_pack;
int prev_category{};
int prev_deck{};
s32 prev_operation{};
int prev_sel{ -1 };
bool is_modified{};
bool readonly{};
bool showing_pack{};
mt19937 rnd;
const std::unordered_map<int, int>* filterList;
std::vector<code_pointer> results;
wchar_t result_string[8];
wchar_t result_string[8]{};
std::vector<std::wstring> expansionPacks;
};
......
......@@ -5,21 +5,22 @@
namespace ygo {
char DeckManager::deckBuffer[0x10000];
char DeckManager::deckBuffer[0x10000]{};
DeckManager deckManager;
void DeckManager::LoadLFListSingle(const char* path) {
LFList* cur = nullptr;
FILE* fp = fopen(path, "r");
char linebuf[256];
wchar_t strBuffer[256];
char linebuf[256]{};
wchar_t strBuffer[256]{};
if(fp) {
while(fgets(linebuf, 256, fp)) {
if(linebuf[0] == '#')
continue;
if(linebuf[0] == '!') {
int sa = BufferIO::DecodeUTF8(&linebuf[1], strBuffer);
while(strBuffer[sa - 1] == L'\r' || strBuffer[sa - 1] == L'\n' ) sa--;
while(strBuffer[sa - 1] == L'\r' || strBuffer[sa - 1] == L'\n' )
sa--;
strBuffer[sa] = 0;
LFList newlist;
_lfList.push_back(newlist);
......@@ -28,20 +29,18 @@ void DeckManager::LoadLFListSingle(const char* path) {
cur->hash = 0x7dfcee6a;
continue;
}
int p = 0;
while(linebuf[p] != ' ' && linebuf[p] != '\t' && linebuf[p] != 0) p++;
if(linebuf[p] == 0)
if(linebuf[0] == 0)
continue;
linebuf[p++] = 0;
int sa = p;
int code = atoi(linebuf);
if(code == 0)
int code = 0;
int count = -1;
if (sscanf(linebuf, "%d %d", &code, &count) != 2)
continue;
if (code <= 0 || code > 99999999)
continue;
if (count < 0 || count > 2)
continue;
if (!cur)
continue;
while(linebuf[p] == ' ' || linebuf[p] == '\t') p++;
while(linebuf[p] != ' ' && linebuf[p] != '\t' && linebuf[p] != 0) p++;
linebuf[p] = 0;
int count = atoi(&linebuf[sa]);
if(!cur) continue;
cur->content[code] = count;
cur->hash = cur->hash ^ ((code << 18) | (code >> 14)) ^ ((code << (27 + count)) | (code >> (5 - count)));
}
......@@ -161,7 +160,7 @@ int DeckManager::LoadDeck(Deck& deck, int* dbuf, int mainc, int sidec, bool is_p
else if(cd.type & (TYPE_FUSION | TYPE_SYNCHRO | TYPE_XYZ | TYPE_LINK)) {
if(deck.extra.size() >= 15)
continue;
deck.extra.push_back(dataManager.GetCodePointer(code)); //verified by GetData()
deck.extra.push_back(dataManager.GetCodePointer(code));
} else if(deck.main.size() < 60) {
deck.main.push_back(dataManager.GetCodePointer(code));
}
......@@ -175,7 +174,7 @@ int DeckManager::LoadDeck(Deck& deck, int* dbuf, int mainc, int sidec, bool is_p
if(cd.type & TYPE_TOKEN)
continue;
if(deck.side.size() < 15)
deck.side.push_back(dataManager.GetCodePointer(code)); //verified by GetData()
deck.side.push_back(dataManager.GetCodePointer(code));
}
return errorcode;
}
......
......@@ -10,7 +10,7 @@
namespace ygo {
struct LFList {
unsigned int hash;
unsigned int hash{};
std::wstring listName;
std::unordered_map<int, int> content;
};
......
......@@ -989,26 +989,40 @@ void Game::DrawSpec() {
showChat = false;
hideChatTimer--;
}
int chatRectY = 0;
for(int i = 0; i < 8; ++i) {
static unsigned int chatColor[] = {0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xff8080ff, 0xffff4040, 0xffff4040,
0xffff4040, 0xff40ff40, 0xff4040ff, 0xff40ffff, 0xffff40ff, 0xffffff40, 0xffffffff, 0xff808080, 0xff404040};
if(chatTiming[i]) {
chatTiming[i]--;
if(mainGame->dInfo.isStarted && i >= 5)
if(!is_building) {
if(dInfo.isStarted && i >= 5)
continue;
if(!showChat && i > 2)
continue;
int w = guiFont->getDimension(chatMsg[i].c_str()).Width;
}
int x = wChat->getRelativePosition().UpperLeftCorner.X;
int y = window_size.Height - 25;
int maxwidth = 705 * xScale;
if(is_building) {
x = 810 * xScale;
maxwidth = 205 * xScale;
}
std::wstring msg = SetStaticText(nullptr, maxwidth, guiFont, chatMsg[i].c_str());
int w = guiFont->getDimension(msg).Width;
int h = guiFont->getDimension(msg).Height + 2;
recti rectloc(mainGame->wChat->getRelativePosition().UpperLeftCorner.X, mainGame->window_size.Height - 45, mainGame->wChat->getRelativePosition().UpperLeftCorner.X + 2 + w, mainGame->window_size.Height - 25);
rectloc -= position2di(0, i * 20);
recti msgloc(mainGame->wChat->getRelativePosition().UpperLeftCorner.X, mainGame->window_size.Height - 45, mainGame->wChat->getRelativePosition().UpperLeftCorner.X - 4, mainGame->window_size.Height - 25);
msgloc -= position2di(0, i * 20);
recti rectloc(x, y - chatRectY - h, x + 2 + w, y - chatRectY);
recti msgloc(x, y - chatRectY - h, x - 4, y - chatRectY);
recti shadowloc = msgloc + position2di(1, 1);
driver->draw2DRectangle(rectloc, 0xa0000000, 0xa0000000, 0xa0000000, 0xa0000000);
guiFont->draw(chatMsg[i].c_str(), msgloc, 0xff000000, false, false);
guiFont->draw(chatMsg[i].c_str(), shadowloc, chatColor[chatType[i]], false, false);
guiFont->draw(msg.c_str(), msgloc, 0xff000000, false, false);
guiFont->draw(msg.c_str(), shadowloc, chatColor[chatType[i]], false, false);
chatRectY += h;
}
}
}
......@@ -1197,10 +1211,10 @@ void Game::DrawDeckBd() {
dx = 436.0f / (lx - 1);
}
int padding = scrPackCards->getPos() * lx;
for(size_t i = 0; i < mainsize - padding && i < 7 * lx; ++i) {
size_t j = i + padding;
for(int i = 0; i < mainsize - padding && i < 7 * lx; ++i) {
int j = i + padding;
DrawThumb(deckManager.current_deck.main[j], position2di(314 + (i % lx) * dx, 164 + (i / lx) * dy), deckBuilder.filterList);
if(deckBuilder.hovered_pos == 1 && deckBuilder.hovered_seq == (int)j)
if(deckBuilder.hovered_pos == 1 && deckBuilder.hovered_seq == j)
driver->draw2DRectangleOutline(Resize(313 + (i % lx) * dx, 163 + (i / lx) * dy, 359 + (i % lx) * dx, 228 + (i / lx) * dy));
}
if(!deckBuilder.showing_pack) {
......@@ -1235,6 +1249,11 @@ void Game::DrawDeckBd() {
driver->draw2DRectangleOutline(Resize(313 + i * dx, 563, 359 + i * dx, 629));
}
}
if(is_siding) {
// side chat background
driver->draw2DRectangle(Resize(805, 10, 1020, 630), 0x400000ff, 0x400000ff, 0x40000000, 0x40000000);
driver->draw2DRectangleOutline(Resize(804, 9, 1020, 630));
} else {
//search result
driver->draw2DRectangle(Resize(805, 137, 926, 157), 0x400000ff, 0x400000ff, 0x40000000, 0x40000000);
driver->draw2DRectangleOutline(Resize(804, 136, 926, 157));
......@@ -1242,6 +1261,7 @@ void Game::DrawDeckBd() {
DrawShadowText(numFont, deckBuilder.result_string, Resize(875, 137, 935, 157), Resize(1, 1, 1, 1), 0xffffffff, 0xff000000, false, true);
driver->draw2DRectangle(Resize(805, 160, 1020, 630), 0x400000ff, 0x400000ff, 0x40000000, 0x40000000);
driver->draw2DRectangleOutline(Resize(804, 159, 1020, 630));
}
for(size_t i = 0; i < 9 && i + scrFilter->getPos() < deckBuilder.results.size(); ++i) {
code_pointer ptr = deckBuilder.results[i + scrFilter->getPos()];
if(i >= 7)
......
This diff is collapsed.
......@@ -20,15 +20,14 @@ namespace ygo {
class DuelClient {
private:
static unsigned int connect_state;
static unsigned char response_buf[64];
static unsigned char response_len;
static unsigned char response_buf[SIZE_RETURN_VALUE];
static unsigned int response_len;
static unsigned int watching;
static unsigned char selftype;
static bool is_host;
static event_base* client_base;
static bufferevent* client_bev;
static unsigned char duel_client_read[0x2000];
static unsigned char duel_client_write[0x2000];
static unsigned char duel_client_read[SIZE_NETWORK_BUFFER];
static unsigned char duel_client_write[SIZE_NETWORK_BUFFER];
static bool is_closing;
static bool is_swapping;
static int select_hint;
......@@ -39,6 +38,7 @@ private:
static wchar_t event_string[256];
static mt19937 rnd;
public:
static unsigned char selftype;
static bool StartClient(unsigned int ip, unsigned short port, bool create_game = true);
static void ConnectTimeout(evutil_socket_t fd, short events, void* arg);
static void StopClient(bool is_exiting = false);
......@@ -49,7 +49,7 @@ public:
static int ClientAnalyze(unsigned char* msg, unsigned int len);
static void SwapField();
static void SetResponseI(int respI);
static void SetResponseB(void* respB, unsigned char len);
static void SetResponseB(void* respB, unsigned int len);
static void SendResponse();
static void SendPacketToServer(unsigned char proto) {
auto p = duel_client_write;
......@@ -60,17 +60,25 @@ public:
template<typename ST>
static void SendPacketToServer(unsigned char proto, ST& st) {
auto p = duel_client_write;
BufferIO::WriteInt16(p, 1 + sizeof(ST));
int blen = sizeof(ST);
if (blen > MAX_DATA_SIZE)
blen = MAX_DATA_SIZE;
BufferIO::WriteInt16(p, (short)(1 + blen));
BufferIO::WriteInt8(p, proto);
memcpy(p, &st, sizeof(ST));
bufferevent_write(client_bev, duel_client_write, sizeof(ST) + 3);
memcpy(p, &st, blen);
bufferevent_write(client_bev, duel_client_write, blen + 3);
}
static void SendBufferToServer(unsigned char proto, void* buffer, size_t len) {
auto p = duel_client_write;
BufferIO::WriteInt16(p, 1 + len);
int blen = len;
if (blen < 0)
return;
if (blen > MAX_DATA_SIZE)
blen = MAX_DATA_SIZE;
BufferIO::WriteInt16(p, (short)(1 + blen));
BufferIO::WriteInt8(p, proto);
memcpy(p, buffer, len);
bufferevent_write(client_bev, duel_client_write, len + 3);
memcpy(p, buffer, blen);
bufferevent_write(client_bev, duel_client_write, blen + 3);
}
protected:
......
......@@ -127,6 +127,7 @@ bool ClientField::OnEvent(const irr::SEvent& event) {
if(mainGame->dInfo.player_type == 7) {
DuelClient::StopClient();
mainGame->dInfo.isStarted = false;
mainGame->dInfo.isInDuel = false;
mainGame->dInfo.isFinished = false;
mainGame->device->setEventReceiver(&mainGame->menuHandler);
mainGame->CloseDuelWindow();
......@@ -771,7 +772,7 @@ bool ClientField::OnEvent(const irr::SEvent& event) {
myswprintf(formatBuffer, L"%d", select_min);
mainGame->stCardPos[id - BUTTON_CARD_0]->setText(formatBuffer);
if(select_min == select_max) {
unsigned char respbuf[64];
unsigned char respbuf[SIZE_RETURN_VALUE];
for(int i = 0; i < select_max; ++i)
respbuf[i] = sort_list[i] - 1;
DuelClient::SetResponseB(respbuf, select_max);
......@@ -1903,7 +1904,7 @@ bool ClientField::OnCommonEvent(const irr::SEvent& event) {
break;
}
case CHECKBOX_DISABLE_CHAT: {
bool show = mainGame->is_building ? false : !mainGame->chkIgnore1->isChecked();
bool show = (mainGame->is_building && !mainGame->is_siding) ? false : !mainGame->chkIgnore1->isChecked();
mainGame->wChat->setVisible(show);
if(!show)
mainGame->ClearChatMsg();
......@@ -2176,6 +2177,7 @@ void ClientField::GetHoverField(int x, int y) {
hovered_location = LOCATION_REMOVED;
}
} else if(rule == 1 && boardx >= matManager.vFieldSzone[1][7][rule][1].Pos.X && boardx <= matManager.vFieldSzone[1][7][rule][2].Pos.X) {
// deprecated szone[7]
if(boardy >= matManager.vFieldSzone[1][7][rule][2].Pos.Y && boardy <= matManager.vFieldSzone[1][7][rule][0].Pos.Y) {
hovered_controler = 1;
hovered_location = LOCATION_SZONE;
......@@ -2207,7 +2209,8 @@ void ClientField::GetHoverField(int x, int y) {
hovered_controler = 1;
hovered_location = LOCATION_EXTRA;
}
} else if(rule == 0 && boardx >= matManager.vFieldSzone[0][7][rule][0].Pos.X && boardx <= matManager.vFieldSzone[0][7][rule][1].Pos.X) {
} else if(rule == 1 && boardx >= matManager.vFieldSzone[0][7][rule][0].Pos.X && boardx <= matManager.vFieldSzone[0][7][rule][1].Pos.X) {
// deprecated szone[7]
if(boardy >= matManager.vFieldSzone[0][7][rule][0].Pos.Y && boardy <= matManager.vFieldSzone[0][7][rule][2].Pos.Y) {
hovered_controler = 0;
hovered_location = LOCATION_SZONE;
......@@ -2475,7 +2478,7 @@ void ClientField::ShowCardInfoInList(ClientCard* pcard, irr::gui::IGUIElement* e
}
}
void ClientField::SetResponseSelectedCards() const {
unsigned char respbuf[64];
unsigned char respbuf[SIZE_RETURN_VALUE];
respbuf[0] = selected_cards.size();
for (size_t i = 0; i < selected_cards.size(); ++i)
respbuf[i + 1] = selected_cards[i]->select_seq;
......
This diff is collapsed.
......@@ -9,65 +9,68 @@
#include <vector>
#include <list>
#define DEFAULT_DUEL_RULE 5
namespace ygo {
struct Config {
bool use_d3d;
bool use_image_scale;
unsigned short antialias;
unsigned short serverport;
unsigned char textfontsize;
wchar_t lasthost[100];
wchar_t lastport[10];
wchar_t nickname[20];
wchar_t gamename[20];
wchar_t lastcategory[64];
wchar_t lastdeck[64];
wchar_t textfont[256];
wchar_t numfont[256];
wchar_t roompass[20];
wchar_t bot_deck_path[64];
bool use_d3d{ false };
bool use_image_scale{ true };
unsigned short antialias{ 0 };
unsigned short serverport{ 7911 };
unsigned char textfontsize{ 14 };
wchar_t lasthost[100]{};
wchar_t lastport[10]{};
wchar_t nickname[20]{};
wchar_t gamename[20]{};
wchar_t lastcategory[64]{};
wchar_t lastdeck[64]{};
wchar_t textfont[256]{};
wchar_t numfont[256]{};
wchar_t roompass[20]{};
wchar_t bot_deck_path[64]{};
//settings
int chkMAutoPos;
int chkSTAutoPos;
int chkRandomPos;
int chkAutoChain;
int chkWaitChain;
int chkDefaultShowChain;
int chkIgnore1;
int chkIgnore2;
int use_lflist;
int default_lflist;
int default_rule;
int hide_setname;
int hide_hint_button;
int control_mode;
int draw_field_spell;
int separate_clear_button;
int auto_search_limit;
int search_multiple_keywords;
int chkIgnoreDeckChanges;
int defaultOT;
int enable_bot_mode;
int quick_animation;
int auto_save_replay;
int draw_single_chain;
int hide_player_name;
int prefer_expansion_script;
bool enable_sound;
bool enable_music;
double sound_volume;
double music_volume;
int music_mode;
bool window_maximized;
int window_width;
int window_height;
bool resize_popup_menu;
int chkMAutoPos{ 0 };
int chkSTAutoPos{ 1 };
int chkRandomPos{ 0 };
int chkAutoChain{ 0 };
int chkWaitChain{ 0 };
int chkDefaultShowChain{ 0 };
int chkIgnore1{ 0 };
int chkIgnore2{ 0 };
int use_lflist{ 1 };
int default_lflist{ 0 };
int default_rule{ DEFAULT_DUEL_RULE };
int hide_setname{ 0 };
int hide_hint_button{ 0 };
int control_mode{ 0 };
int draw_field_spell{ 1 };
int separate_clear_button{ 1 };
int auto_search_limit{ -1 };
int search_multiple_keywords{ 1 };
int chkIgnoreDeckChanges{ 0 };
int defaultOT{ 1 };
int enable_bot_mode{ 0 };
int quick_animation{ 0 };
int auto_save_replay{ 0 };
int draw_single_chain{ 0 };
int hide_player_name{ 0 };
int prefer_expansion_script{ 0 };
bool enable_sound{ true };
bool enable_music{ true };
double sound_volume{ 0.5 };
double music_volume{ 0.5 };
int music_mode{ 1 };
bool window_maximized{ false };
int window_width{ 1024 };
int window_height{ 640 };
bool resize_popup_menu{ false };
};
struct DuelInfo {
bool isStarted{ false };
bool isFinished{ false };
bool isInDuel{ false };
bool isFinished{false};
bool isReplay{ false };
bool isReplaySkiping{ false };
bool isFirst{ false };
......@@ -96,13 +99,13 @@ struct DuelInfo {
};
struct BotInfo {
wchar_t name[256];
wchar_t command[256];
wchar_t desc[256];
bool support_master_rule_3;
bool support_new_master_rule;
bool support_master_rule_2020;
bool select_deckfile;
wchar_t name[256]{};
wchar_t command[256]{};
wchar_t desc[256]{};
bool support_master_rule_3{ false };
bool support_new_master_rule{ false };
bool support_master_rule_2020{ false };
bool select_deckfile{ false };
};
struct FadingUnit {
......@@ -156,7 +159,7 @@ public:
void ShowCardInfo(int code, bool resize = false);
void ClearCardInfo(int player = 0);
void AddLog(const wchar_t* msg, int param = 0);
void AddChatMsg(const wchar_t* msg, int player);
void AddChatMsg(const wchar_t* msg, int player, bool play_sound = false);
void ClearChatMsg();
void AddDebugMsg(const char* msgbuf);
void ErrorLog(const char* msgbuf);
......@@ -165,7 +168,9 @@ public:
void CloseGameWindow();
void CloseDuelWindow();
int LocalPlayer(int player);
int LocalPlayer(int player) const;
int OppositePlayer(int player);
int ChatLocalPlayer(int player);
const wchar_t* LocalName(int local_player);
bool HasFocus(EGUI_ELEMENT_TYPE type) const {
......@@ -180,6 +185,7 @@ public:
}
void OnResize();
void ResizeChatInputWindow();
recti Resize(s32 x, s32 y, s32 x2, s32 y2);
recti Resize(s32 x, s32 y, s32 x2, s32 y2, s32 dx, s32 dy, s32 dx2, s32 dy2);
position2di Resize(s32 x, s32 y);
......@@ -215,8 +221,8 @@ public:
int hideChatTimer;
bool hideChat;
int chatTiming[8];
int chatType[8];
int chatTiming[8]{};
int chatType[8]{};
unsigned short linePatternD3D;
unsigned short linePatternGL;
int waitFrame;
......@@ -824,8 +830,5 @@ extern Game* mainGame;
#define AVAIL_SC 0x8
#define AVAIL_OCGTCG (AVAIL_OCG|AVAIL_TCG)
#define DEFAULT_DUEL_RULE 5
#define CARD_ARTWORK_VERSIONS_OFFSET 10
#define MAX_LAYER_COUNT 6
#endif // GAME_H
......@@ -7,7 +7,7 @@
#import <CoreFoundation/CoreFoundation.h>
#endif
int enable_log = 0;
unsigned int enable_log = 0x3;
bool exit_on_return = false;
bool open_file = false;
wchar_t open_file_name[256] = L"";
......
......@@ -21,11 +21,11 @@ public:
S3DVertex vFieldSpell2[4];
//S3DVertex vBackLine[76];
S3DVertex vFieldDeck[2][4];
S3DVertex vFieldGrave[2][2][4];
S3DVertex vFieldGrave[2][2][4]; //[player][rule], rule = 0: dule_rule <= 3, 1: dule_rule >= 4
S3DVertex vFieldExtra[2][4];
S3DVertex vFieldRemove[2][2][4];
S3DVertex vFieldMzone[2][7][4];
S3DVertex vFieldSzone[2][8][2][4];
S3DVertex vFieldRemove[2][2][4]; //[player][rule]
S3DVertex vFieldMzone[2][7][4]; //[player][sequence]
S3DVertex vFieldSzone[2][8][2][4]; //[player][sequence][rule]
irr::core::vector3df vFieldContiAct[4];
S3DVertex vArrow[40];
SColor c2d[4];
......
......@@ -314,11 +314,17 @@ bool MenuHandler::OnEvent(const irr::SEvent& event) {
for(int i = 0; i < max; ++i) {
int main = replay.ReadInt32();
Deck tmp_deck;
for(int j = 0; j < main; ++j)
tmp_deck.main.push_back(dataManager.GetCodePointer(replay.ReadInt32()));
for (int j = 0; j < main; ++j) {
auto card = dataManager.GetCodePointer(replay.ReadInt32());
if (card != dataManager.datas_end)
tmp_deck.main.push_back(card);
}
int extra = replay.ReadInt32();
for(int j = 0; j < extra; ++j)
tmp_deck.extra.push_back(dataManager.GetCodePointer(replay.ReadInt32()));
for (int j = 0; j < extra; ++j) {
auto card = dataManager.GetCodePointer(replay.ReadInt32());
if (card != dataManager.datas_end)
tmp_deck.extra.push_back(card);
}
FileSystem::SafeFileName(namebuf[i]);
myswprintf(filename, L"deck/%ls-%d %ls.ydk", ex_filename, i + 1, namebuf[i]);
deckManager.SaveDeck(tmp_deck, filename);
......
......@@ -9,8 +9,8 @@ event_base* NetServer::net_evbase = 0;
event* NetServer::broadcast_ev = 0;
evconnlistener* NetServer::listener = 0;
DuelMode* NetServer::duel_mode = 0;
unsigned char NetServer::net_server_read[0x2000];
unsigned char NetServer::net_server_write[0x2000];
unsigned char NetServer::net_server_read[SIZE_NETWORK_BUFFER];
unsigned char NetServer::net_server_write[SIZE_NETWORK_BUFFER];
unsigned short NetServer::last_sent = 0;
bool NetServer::StartServer(unsigned short port) {
......@@ -40,9 +40,9 @@ bool NetServer::StartBroadcast() {
if(!net_evbase)
return false;
SOCKET udp = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
BOOL opt = TRUE;
setsockopt(udp, SOL_SOCKET, SO_BROADCAST, (const char*)&opt, sizeof(BOOL));
setsockopt(udp, SOL_SOCKET, SO_REUSEADDR, (const char*)&opt, sizeof(BOOL));
int opt = TRUE;
setsockopt(udp, SOL_SOCKET, SO_BROADCAST, (const char*)&opt, sizeof opt);
setsockopt(udp, SOL_SOCKET, SO_REUSEADDR, (const char*)&opt, sizeof opt);
sockaddr_in addr;
memset(&addr, 0, sizeof(addr));
addr.sin_family = AF_INET;
......@@ -180,7 +180,7 @@ void NetServer::HandleCTOSPacket(DuelPlayer* dp, unsigned char* data, unsigned i
case CTOS_RESPONSE: {
if(!dp->game || !duel_mode->pduel)
return;
duel_mode->GetResponse(dp, pdata, len > 64 ? 64 : len - 1);
duel_mode->GetResponse(dp, pdata, len - 1);
break;
}
case CTOS_TIME_CONFIRM: {
......
......@@ -18,8 +18,8 @@ private:
static event* broadcast_ev;
static evconnlistener* listener;
static DuelMode* duel_mode;
static unsigned char net_server_read[0x2000];
static unsigned char net_server_write[0x2000];
static unsigned char net_server_read[SIZE_NETWORK_BUFFER];
static unsigned char net_server_write[SIZE_NETWORK_BUFFER];
static unsigned short last_sent;
public:
......@@ -43,26 +43,34 @@ public:
last_sent = 3;
if(!dp)
return;
bufferevent_write(dp->bev, net_server_write, last_sent);
bufferevent_write(dp->bev, net_server_write, 3);
}
template<typename ST>
static void SendPacketToPlayer(DuelPlayer* dp, unsigned char proto, ST& st) {
auto p = net_server_write;
BufferIO::WriteInt16(p, 1 + sizeof(ST));
int blen = sizeof(ST);
if (blen > MAX_DATA_SIZE)
blen = MAX_DATA_SIZE;
BufferIO::WriteInt16(p, (short)(1 + blen));
BufferIO::WriteInt8(p, proto);
memcpy(p, &st, sizeof(ST));
last_sent = sizeof(ST) + 3;
if(dp)
bufferevent_write(dp->bev, net_server_write, last_sent);
memcpy(p, &st, blen);
last_sent = blen + 3;
if (dp)
bufferevent_write(dp->bev, net_server_write, blen + 3);
}
static void SendBufferToPlayer(DuelPlayer* dp, unsigned char proto, void* buffer, size_t len) {
auto p = net_server_write;
BufferIO::WriteInt16(p, 1 + len);
int blen = len;
if (blen < 0)
return;
if (blen > MAX_DATA_SIZE)
blen = MAX_DATA_SIZE;
BufferIO::WriteInt16(p, (short)(1 + blen));
BufferIO::WriteInt8(p, proto);
memcpy(p, buffer, len);
last_sent = len + 3;
if(dp)
bufferevent_write(dp->bev, net_server_write, last_sent);
memcpy(p, buffer, blen);
last_sent = blen + 3;
if (dp)
bufferevent_write(dp->bev, net_server_write, blen + 3);
}
static void ReSendToPlayer(DuelPlayer* dp) {
if(dp)
......
......@@ -10,18 +10,20 @@
#include <event2/thread.h>
namespace ygo {
constexpr int SIZE_NETWORK_BUFFER = 0x2000;
constexpr int MAX_DATA_SIZE = SIZE_NETWORK_BUFFER - 3;
struct HostInfo {
unsigned int lflist;
unsigned char rule;
unsigned char mode;
unsigned char duel_rule;
bool no_check_deck;
bool no_shuffle_deck;
unsigned int start_lp;
unsigned char start_hand;
unsigned char draw_count;
unsigned short time_limit;
unsigned int lflist{ 0 };
unsigned char rule{ 0 };
unsigned char mode{ 0 };
unsigned char duel_rule{ 0 };
bool no_check_deck{ false };
bool no_shuffle_deck{ false };
unsigned int start_lp{ 0 };
unsigned char start_hand{ 0 };
unsigned char draw_count{ 0 };
unsigned short time_limit{ 0 };
};
struct HostPacket {
unsigned short identifier;
......@@ -99,22 +101,16 @@ struct STOC_HS_WatchChange {
class DuelMode;
struct DuelPlayer {
unsigned short name[20];
DuelMode* game;
unsigned char type;
unsigned char state;
bufferevent* bev;
DuelPlayer() {
game = 0;
type = 0;
state = 0;
bev = 0;
}
unsigned short name[20]{};
DuelMode* game{ nullptr };
unsigned char type{ 0 };
unsigned char state{ 0 };
bufferevent* bev{ 0 };
};
class DuelMode {
public:
DuelMode(): host_player(0), pduel(0), duel_stage(0) {}
DuelMode(): host_player(nullptr), pduel(0), duel_stage(0) {}
virtual ~DuelMode() {}
virtual void Chat(DuelPlayer* dp, void* pdata, int len) {}
virtual void JoinGame(DuelPlayer* dp, void* pdata, bool is_creater) {}
......
#include "replay.h"
#include "../ocgcore/ocgapi.h"
#include "../ocgcore/common.h"
#include "lzma/LzmaLib.h"
namespace ygo {
......@@ -54,7 +52,7 @@ void Replay::WriteData(const void* data, int length, bool flush) {
return;
if (length < 0 || (pdata - replay_data) + length > MAX_REPLAY_SIZE)
return;
memcpy(pdata, data, length);
std::memcpy(pdata, data, length);
pdata += length;
#ifdef _WIN32
DWORD size;
......@@ -70,8 +68,7 @@ void Replay::WriteInt32(int data, bool flush) {
return;
if ((pdata - replay_data) + 4 > MAX_REPLAY_SIZE)
return;
*((int*)(pdata)) = data;
pdata += 4;
BufferIO::WriteInt32(pdata, data);
#ifdef _WIN32
DWORD size;
WriteFile(recording_fp, &data, sizeof(int), &size, NULL);
......@@ -86,8 +83,7 @@ void Replay::WriteInt16(short data, bool flush) {
return;
if ((pdata - replay_data) + 2 > MAX_REPLAY_SIZE)
return;
*((short*)(pdata)) = data;
pdata += 2;
BufferIO::WriteInt16(pdata, data);
#ifdef _WIN32
DWORD size;
WriteFile(recording_fp, &data, sizeof(short), &size, NULL);
......@@ -102,8 +98,7 @@ void Replay::WriteInt8(char data, bool flush) {
return;
if ((pdata - replay_data) + 1 > MAX_REPLAY_SIZE)
return;
*pdata = data;
pdata++;
BufferIO::WriteInt8(pdata, data);
#ifdef _WIN32
DWORD size;
WriteFile(recording_fp, &data, sizeof(char), &size, NULL);
......@@ -260,13 +255,13 @@ bool Replay::RenameReplay(const wchar_t* oldname, const wchar_t* newname) {
return result == 0;
#endif
}
bool Replay::ReadNextResponse(unsigned char resp[64]) {
bool Replay::ReadNextResponse(unsigned char resp[]) {
if(pdata - replay_data >= (int)replay_size)
return false;
int len = *pdata++;
if(len > 64)
if(len > SIZE_RETURN_VALUE)
return false;
memcpy(resp, pdata, len);
std::memcpy(resp, pdata, len);
pdata += len;
return true;
}
......@@ -280,27 +275,26 @@ void Replay::ReadName(wchar_t* data) {
void Replay::ReadData(void* data, int length) {
if(!is_replaying)
return;
memcpy(data, pdata, length);
std::memcpy(data, pdata, length);
pdata += length;
}
int Replay::ReadInt32() {
if(!is_replaying)
return -1;
int ret = *((int*)pdata);
pdata += 4;
int ret = BufferIO::ReadInt32(pdata);
return ret;
}
short Replay::ReadInt16() {
if(!is_replaying)
return -1;
short ret = *((short*)pdata);
pdata += 2;
short ret = BufferIO::ReadInt16(pdata);
return ret;
}
char Replay::ReadInt8() {
if(!is_replaying)
return -1;
return *pdata++;
char ret= BufferIO::ReadInt8(pdata);
return ret;
}
void Replay::Rewind() {
pdata = replay_data;
......
......@@ -50,7 +50,7 @@ public:
static bool CheckReplay(const wchar_t* name);
static bool DeleteReplay(const wchar_t* name);
static bool RenameReplay(const wchar_t* oldname, const wchar_t* newname);
bool ReadNextResponse(unsigned char resp[64]);
bool ReadNextResponse(unsigned char resp[]);
void ReadName(wchar_t* data);
//void ReadHeader(ReplayHeader& header);
void ReadData(void* data, int length);
......
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
......@@ -197,7 +197,7 @@ workspace "YGOPro"
filter { "configurations:Release", "action:vs*" }
flags { "LinkTimeOptimization" }
staticruntime "On"
disablewarnings { "4244", "4267", "4838", "4577", "4819", "4018", "4996", "4477", "4091", "4828", "4800", "6011", "6031", "6054", "6262" }
disablewarnings { "4244", "4267", "4838", "4577", "4018", "4996", "4477", "4091", "4800", "6011", "6031", "6054", "6262" }
filter { "configurations:Release", "not action:vs*" }
symbols "On"
......@@ -207,7 +207,7 @@ workspace "YGOPro"
end
filter { "configurations:Debug", "action:vs*" }
disablewarnings { "4819", "4828", "6011", "6031", "6054", "6262" }
disablewarnings { "6011", "6031", "6054", "6262" }
filter "action:vs*"
vectorextensions "SSE2"
......
......@@ -318,8 +318,8 @@
!system 1260 大师规则
!system 1261 大师规则2
!system 1262 大师规则3
!system 1263 新大师规则
!system 1264 大师规则2020
!system 1263 新大师规则2017
!system 1264 大师规则2020
!system 1270 卡片信息
!system 1271 消息记录
!system 1272 清除记录
......@@ -657,6 +657,8 @@
!counter 0x68 指示物(图腾柱)
!counter 0x69 指示物(吠陀-优婆尼沙昙)
!counter 0x6a 响鸣指示物
!counter 0x6b 狂乱指示物
!counter 0x6c 访问指示物
#setnames, using tab for comment
!setname 0x1 正义盟军 AOJ
!setname 0x2 次世代 ジェネクス
......@@ -1183,7 +1185,7 @@
!setname 0x18f 防火 ファイアウォール
!setname 0x190 末那愚子族 マナドゥム
!setname 0x191 妮穆蕾莉娅 ネムレリア
!setname 0x192 金傲大奖赛 GP(ゴールド・プライド)
!setname 0x192 黄金荣耀 GP(ゴールド・プライド)
!setname 0x193 迷宫壁 ラビリンス・ウォール
!setname 0x194 至爱 フェイバリット
!setname 0x195 征服斗魂 VS(ヴァンキッシュ・ソウル)
......@@ -1207,3 +1209,14 @@
!setname 0x1a6 肃声 粛声
!setname 0x1a7 白斗气 ホワイト・オーラ
!setname 0x1a8 玩具 トイ
!setname 0x1a9 灿幻 燦幻
!setname 0x1aa 天杯龙 天盃龍
!setname 0x1ab 蕾祸 蕾禍
!setname 0x1ac 飞龙炎 Salamandra
!setname 0x1ad 灰尽 Ashened
!setname 0x1ae 千年 千年/ミレニアム
!setname 0x1af 艾格佐德 エグゾード
!setname 0x1b0 刻魔 デモンスミス
!setname 0x1b1 白森林 白き森
!setname 0x1b2 欢聚友伴 マルチャミー
!setname 0x1b3 徽记 エンブレーマ
......@@ -41,6 +41,7 @@ bot_deck_path = ./botdeck
quick_animation = 0
auto_save_replay = 0
draw_single_chain = 0
hide_player_name = 0
prefer_expansion_script = 0
window_maximized = 0
window_width = 1280
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment