summaryrefslogtreecommitdiff
path: root/core/string
diff options
context:
space:
mode:
Diffstat (limited to 'core/string')
-rw-r--r--core/string/locales.h2
-rw-r--r--core/string/ustring.cpp112
-rw-r--r--core/string/ustring.h13
3 files changed, 72 insertions, 55 deletions
diff --git a/core/string/locales.h b/core/string/locales.h
index 32d6608ec2..0ccb17a436 100644
--- a/core/string/locales.h
+++ b/core/string/locales.h
@@ -1072,6 +1072,7 @@ static const char *script_list[][2] = {
{ "Jurchen", "Jurc" },
{ "Kayah Li", "Kali" },
{ "Katakana", "Kana" },
+ { "Kawi", "Kawi" },
{ "Kharoshthi", "Khar" },
{ "Khmer", "Khmr" },
{ "Khojki", "Khoj" },
@@ -1110,6 +1111,7 @@ static const char *script_list[][2] = {
{ "Meitei Mayek", "Mtei" },
{ "Multani", "Mult" },
{ "Myanmar (Burmese)", "Mymr" },
+ { "​Nag Mundari", "Nagm" },
{ "Nandinagari", "Nand" },
{ "Old North Arabian", "Narb" },
{ "Nabataean", "Nbat" },
diff --git a/core/string/ustring.cpp b/core/string/ustring.cpp
index aeddf79781..6218c21cde 100644
--- a/core/string/ustring.cpp
+++ b/core/string/ustring.cpp
@@ -970,62 +970,71 @@ const char32_t *String::get_data() const {
return size() ? &operator[](0) : &zero;
}
-String String::capitalize() const {
- String aux = this->camelcase_to_underscore(true).replace("_", " ").strip_edges();
- String cap;
- for (int i = 0; i < aux.get_slice_count(" "); i++) {
- String slice = aux.get_slicec(' ', i);
- if (slice.length() > 0) {
- slice[0] = _find_upper(slice[0]);
- if (i > 0) {
- cap += " ";
- }
- cap += slice;
- }
- }
-
- return cap;
-}
-
-String String::camelcase_to_underscore(bool lowercase) const {
+String String::_camelcase_to_underscore() const {
const char32_t *cstr = get_data();
String new_string;
int start_index = 0;
for (int i = 1; i < this->size(); i++) {
- bool is_upper = is_ascii_upper_case(cstr[i]);
- bool is_number = is_digit(cstr[i]);
+ bool is_prev_upper = is_ascii_upper_case(cstr[i - 1]);
+ bool is_prev_lower = is_ascii_lower_case(cstr[i - 1]);
+ bool is_prev_digit = is_digit(cstr[i - 1]);
- bool are_next_2_lower = false;
- bool is_next_lower = false;
- bool is_next_number = false;
- bool was_precedent_upper = is_ascii_upper_case(cstr[i - 1]);
- bool was_precedent_number = is_digit(cstr[i - 1]);
-
- if (i + 2 < this->size()) {
- are_next_2_lower = is_ascii_lower_case(cstr[i + 1]) && is_ascii_lower_case(cstr[i + 2]);
- }
+ bool is_curr_upper = is_ascii_upper_case(cstr[i]);
+ bool is_curr_lower = is_ascii_lower_case(cstr[i]);
+ bool is_curr_digit = is_digit(cstr[i]);
+ bool is_next_lower = false;
if (i + 1 < this->size()) {
is_next_lower = is_ascii_lower_case(cstr[i + 1]);
- is_next_number = is_digit(cstr[i + 1]);
}
- const bool cond_a = is_upper && !was_precedent_upper && !was_precedent_number;
- const bool cond_b = was_precedent_upper && is_upper && are_next_2_lower;
- const bool cond_c = is_number && !was_precedent_number;
- const bool can_break_number_letter = is_number && !was_precedent_number && is_next_lower;
- const bool can_break_letter_number = !is_number && was_precedent_number && (is_next_lower || is_next_number);
+ const bool cond_a = is_prev_lower && is_curr_upper; // aA
+ const bool cond_b = (is_prev_upper || is_prev_digit) && is_curr_upper && is_next_lower; // AAa, 2Aa
+ const bool cond_c = is_prev_digit && is_curr_lower && is_next_lower; // 2aa
+ const bool cond_d = (is_prev_upper || is_prev_lower) && is_curr_digit; // A2, a2
- bool should_split = cond_a || cond_b || cond_c || can_break_number_letter || can_break_letter_number;
- if (should_split) {
+ if (cond_a || cond_b || cond_c || cond_d) {
new_string += this->substr(start_index, i - start_index) + "_";
start_index = i;
}
}
new_string += this->substr(start_index, this->size() - start_index);
- return lowercase ? new_string.to_lower() : new_string;
+ return new_string.to_lower();
+}
+
+String String::capitalize() const {
+ String aux = this->_camelcase_to_underscore().replace("_", " ").strip_edges();
+ String cap;
+ for (int i = 0; i < aux.get_slice_count(" "); i++) {
+ String slice = aux.get_slicec(' ', i);
+ if (slice.length() > 0) {
+ slice[0] = _find_upper(slice[0]);
+ if (i > 0) {
+ cap += " ";
+ }
+ cap += slice;
+ }
+ }
+
+ return cap;
+}
+
+String String::to_camel_case() const {
+ String s = this->to_pascal_case();
+ if (!s.is_empty()) {
+ s[0] = _find_lower(s[0]);
+ }
+ return s;
+}
+
+String String::to_pascal_case() const {
+ return this->capitalize().replace(" ", "");
+}
+
+String String::to_snake_case() const {
+ return this->_camelcase_to_underscore().replace(" ", "_").strip_edges();
}
String String::get_with_code_lines() const {
@@ -2615,10 +2624,11 @@ double String::to_float() const {
uint32_t String::hash(const char *p_cstr) {
uint32_t hashv = 5381;
- uint32_t c;
+ uint32_t c = *p_cstr++;
- while ((c = *p_cstr++)) {
+ while (c) {
hashv = ((hashv << 5) + hashv) + c; /* hash * 33 + c */
+ c = *p_cstr++;
}
return hashv;
@@ -2644,10 +2654,11 @@ uint32_t String::hash(const wchar_t *p_cstr, int p_len) {
uint32_t String::hash(const wchar_t *p_cstr) {
uint32_t hashv = 5381;
- uint32_t c;
+ uint32_t c = *p_cstr++;
- while ((c = *p_cstr++)) {
+ while (c) {
hashv = ((hashv << 5) + hashv) + c; /* hash * 33 + c */
+ c = *p_cstr++;
}
return hashv;
@@ -2664,10 +2675,11 @@ uint32_t String::hash(const char32_t *p_cstr, int p_len) {
uint32_t String::hash(const char32_t *p_cstr) {
uint32_t hashv = 5381;
- uint32_t c;
+ uint32_t c = *p_cstr++;
- while ((c = *p_cstr++)) {
+ while (c) {
hashv = ((hashv << 5) + hashv) + c; /* hash * 33 + c */
+ c = *p_cstr++;
}
return hashv;
@@ -2678,10 +2690,11 @@ uint32_t String::hash() const {
const char32_t *chr = get_data();
uint32_t hashv = 5381;
- uint32_t c;
+ uint32_t c = *chr++;
- while ((c = *chr++)) {
+ while (c) {
hashv = ((hashv << 5) + hashv) + c; /* hash * 33 + c */
+ c = *chr++;
}
return hashv;
@@ -2692,10 +2705,11 @@ uint64_t String::hash64() const {
const char32_t *chr = get_data();
uint64_t hashv = 5381;
- uint64_t c;
+ uint64_t c = *chr++;
- while ((c = *chr++)) {
+ while (c) {
hashv = ((hashv << 5) + hashv) + c; /* hash * 33 + c */
+ c = *chr++;
}
return hashv;
@@ -4451,7 +4465,7 @@ String String::get_extension() const {
return substr(pos + 1, length());
}
-String String::plus_file(const String &p_file) const {
+String String::path_join(const String &p_file) const {
if (is_empty()) {
return p_file;
}
diff --git a/core/string/ustring.h b/core/string/ustring.h
index 6c3169f136..4b6568a502 100644
--- a/core/string/ustring.h
+++ b/core/string/ustring.h
@@ -28,11 +28,11 @@
/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */
/*************************************************************************/
-// Note: _GODOT suffix added to avoid conflict with ICU header with the same guard.
-
#ifndef USTRING_GODOT_H
#define USTRING_GODOT_H
+// Note: _GODOT suffix added to header guard to avoid conflict with ICU header.
+
#include "core/string/char_utils.h"
#include "core/templates/cowdata.h"
#include "core/templates/vector.h"
@@ -196,6 +196,7 @@ class String {
bool _base_is_subsequence_of(const String &p_string, bool case_insensitive) const;
int _count(const String &p_string, int p_from, int p_to, bool p_case_insensitive) const;
+ String _camelcase_to_underscore() const;
public:
enum {
@@ -335,7 +336,9 @@ public:
static double to_float(const char32_t *p_str, const char32_t **r_end = nullptr);
String capitalize() const;
- String camelcase_to_underscore(bool lowercase = true) const;
+ String to_camel_case() const;
+ String to_pascal_case() const;
+ String to_snake_case() const;
String get_with_code_lines() const;
int get_slice_count(String p_splitter) const;
@@ -370,11 +373,9 @@ public:
String rstrip(const String &p_chars) const;
String get_extension() const;
String get_basename() const;
- String plus_file(const String &p_file) const;
+ String path_join(const String &p_file) const;
char32_t unicode_at(int p_idx) const;
- void erase(int p_pos, int p_chars);
-
CharString ascii(bool p_allow_extended = false) const;
CharString utf8() const;
Error parse_utf8(const char *p_utf8, int p_len = -1, bool p_skip_cr = false);