#pragma once inline size_t str_len(const char *s) { return strlen(s); } inline size_t str_len(const wchar_t *s) { return wcslen(s); } template struct TextUnion { enum { ShortTextCapacity = 0x10 / sizeof(CharT) }; union { const CharT *text; // 0x0 CharT chars[ShortTextCapacity]; }; size_t size, // 0x10 capacity; bool isValid() const { if (size <= 0 || size > capacity) return false; const CharT *t = getText(); return Engine::isAddressWritable(t, size) && str_len(t) == size; } const CharT *getText() const { return capacity < ShortTextCapacity ? chars : text; } void setText(const CharT *_text, size_t _size) { if (_size < ShortTextCapacity) ::memcpy(chars, _text, (_size + 1) * sizeof(CharT)); else text = _text; capacity = size = _size; } void setLongText(const CharT *_text, size_t _size) { text = _text; size = _size; capacity = max(ShortTextCapacity, _size); } void setText(const std::basic_string &text) { setText((const CharT *)text.c_str(), text.size()); } void setLongText(const std::basic_string &text) { setLongText((const CharT *)text.c_str(), text.size()); } }; using TextUnionA = TextUnion; using TextUnionW = TextUnion; // EOF