summaryrefslogtreecommitdiff
path: root/core
diff options
context:
space:
mode:
Diffstat (limited to 'core')
-rw-r--r--core/global_constants.cpp37
-rw-r--r--core/math/a_star.cpp2
-rw-r--r--core/math/math_2d.cpp63
-rw-r--r--core/math/math_2d.h88
-rw-r--r--core/math/matrix3.cpp9
-rw-r--r--core/math/matrix3.h3
-rw-r--r--core/os/file_access.cpp31
-rw-r--r--core/os/file_access.h1
-rw-r--r--core/os/input_event.cpp18
-rw-r--r--core/os/input_event.h4
-rw-r--r--core/os/threaded_array_processor.cpp2
-rw-r--r--core/os/threaded_array_processor.h80
-rw-r--r--core/string_buffer.cpp2
-rw-r--r--core/string_db.h17
-rw-r--r--core/ustring.cpp95
-rw-r--r--core/ustring.h26
16 files changed, 325 insertions, 153 deletions
diff --git a/core/global_constants.cpp b/core/global_constants.cpp
index a8f6e4da6c..b390590cf2 100644
--- a/core/global_constants.cpp
+++ b/core/global_constants.cpp
@@ -98,6 +98,11 @@ void register_global_constants() {
BIND_GLOBAL_ENUM_CONSTANT(MARGIN_RIGHT);
BIND_GLOBAL_ENUM_CONSTANT(MARGIN_BOTTOM);
+ BIND_GLOBAL_ENUM_CONSTANT(CORNER_TOP_LEFT);
+ BIND_GLOBAL_ENUM_CONSTANT(CORNER_TOP_RIGHT);
+ BIND_GLOBAL_ENUM_CONSTANT(CORNER_BOTTOM_RIGHT);
+ BIND_GLOBAL_ENUM_CONSTANT(CORNER_BOTTOM_LEFT);
+
BIND_GLOBAL_ENUM_CONSTANT(VERTICAL);
BIND_GLOBAL_ENUM_CONSTANT(HORIZONTAL);
@@ -573,6 +578,38 @@ void register_global_constants() {
BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("TYPE_VECTOR3_ARRAY", Variant::POOL_VECTOR3_ARRAY);
BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("TYPE_COLOR_ARRAY", Variant::POOL_COLOR_ARRAY);
BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("TYPE_MAX", Variant::VARIANT_MAX);
+
+ //comparation
+ BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("OP_EQUAL", Variant::OP_EQUAL);
+ BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("OP_NOT_EQUAL", Variant::OP_NOT_EQUAL);
+ BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("OP_LESS", Variant::OP_LESS);
+ BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("OP_LESS_EQUAL", Variant::OP_LESS_EQUAL);
+ BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("OP_GREATER", Variant::OP_GREATER);
+ BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("OP_GREATER_EQUAL", Variant::OP_GREATER_EQUAL);
+ //mathematic
+ BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("OP_ADD", Variant::OP_ADD);
+ BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("OP_SUBTRACT", Variant::OP_SUBTRACT);
+ BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("OP_MULTIPLY", Variant::OP_MULTIPLY);
+ BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("OP_DIVIDE", Variant::OP_DIVIDE);
+ BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("OP_NEGATE", Variant::OP_NEGATE);
+ BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("OP_POSITIVE", Variant::OP_POSITIVE);
+ BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("OP_MODULE", Variant::OP_MODULE);
+ BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("OP_STRING_CONCAT", Variant::OP_STRING_CONCAT);
+ //bitwise
+ BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("OP_SHIFT_LEFT", Variant::OP_SHIFT_LEFT);
+ BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("OP_SHIFT_RIGHT", Variant::OP_SHIFT_RIGHT);
+ BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("OP_BIT_AND", Variant::OP_BIT_AND);
+ BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("OP_BIT_OR", Variant::OP_BIT_OR);
+ BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("OP_BIT_XOR", Variant::OP_BIT_XOR);
+ BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("OP_BIT_NEGATE", Variant::OP_BIT_NEGATE);
+ //logic
+ BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("OP_AND", Variant::OP_AND);
+ BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("OP_OR", Variant::OP_OR);
+ BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("OP_XOR", Variant::OP_XOR);
+ BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("OP_NOT", Variant::OP_NOT);
+ //containment
+ BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("OP_IN", Variant::OP_IN);
+ BIND_GLOBAL_ENUM_CONSTANT_CUSTOM("OP_MAX", Variant::OP_MAX);
}
void unregister_global_constants() {
diff --git a/core/math/a_star.cpp b/core/math/a_star.cpp
index 4498efeb41..7c5dbc895a 100644
--- a/core/math/a_star.cpp
+++ b/core/math/a_star.cpp
@@ -459,7 +459,7 @@ void AStar::_bind_methods() {
ClassDB::bind_method(D_METHOD("has_point", "id"), &AStar::has_point);
ClassDB::bind_method(D_METHOD("get_points"), &AStar::get_points);
- ClassDB::bind_method(D_METHOD("get_point_connections"), &AStar::get_point_connections);
+ ClassDB::bind_method(D_METHOD("get_point_connections", "id"), &AStar::get_point_connections);
ClassDB::bind_method(D_METHOD("connect_points", "id", "to_id", "bidirectional"), &AStar::connect_points, DEFVAL(true));
ClassDB::bind_method(D_METHOD("disconnect_points", "id", "to_id"), &AStar::disconnect_points);
diff --git a/core/math/math_2d.cpp b/core/math/math_2d.cpp
index 11003c1cd5..8ad164d4dc 100644
--- a/core/math/math_2d.cpp
+++ b/core/math/math_2d.cpp
@@ -102,69 +102,6 @@ Vector2 Vector2::cross(real_t p_other) const {
return Vector2(p_other * y, -p_other * x);
}
-Vector2 Vector2::operator+(const Vector2 &p_v) const {
-
- return Vector2(x + p_v.x, y + p_v.y);
-}
-void Vector2::operator+=(const Vector2 &p_v) {
-
- x += p_v.x;
- y += p_v.y;
-}
-Vector2 Vector2::operator-(const Vector2 &p_v) const {
-
- return Vector2(x - p_v.x, y - p_v.y);
-}
-void Vector2::operator-=(const Vector2 &p_v) {
-
- x -= p_v.x;
- y -= p_v.y;
-}
-
-Vector2 Vector2::operator*(const Vector2 &p_v1) const {
-
- return Vector2(x * p_v1.x, y * p_v1.y);
-};
-
-Vector2 Vector2::operator*(const real_t &rvalue) const {
-
- return Vector2(x * rvalue, y * rvalue);
-};
-void Vector2::operator*=(const real_t &rvalue) {
-
- x *= rvalue;
- y *= rvalue;
-};
-
-Vector2 Vector2::operator/(const Vector2 &p_v1) const {
-
- return Vector2(x / p_v1.x, y / p_v1.y);
-};
-
-Vector2 Vector2::operator/(const real_t &rvalue) const {
-
- return Vector2(x / rvalue, y / rvalue);
-};
-
-void Vector2::operator/=(const real_t &rvalue) {
-
- x /= rvalue;
- y /= rvalue;
-};
-
-Vector2 Vector2::operator-() const {
-
- return Vector2(-x, -y);
-}
-
-bool Vector2::operator==(const Vector2 &p_vec2) const {
-
- return x == p_vec2.x && y == p_vec2.y;
-}
-bool Vector2::operator!=(const Vector2 &p_vec2) const {
-
- return x != p_vec2.x || y != p_vec2.y;
-}
Vector2 Vector2::floor() const {
return Vector2(Math::floor(x), Math::floor(y));
diff --git a/core/math/math_2d.h b/core/math/math_2d.h
index 60351445c0..4939e7ae99 100644
--- a/core/math/math_2d.h
+++ b/core/math/math_2d.h
@@ -187,6 +187,70 @@ _FORCE_INLINE_ Vector2 operator*(real_t p_scalar, const Vector2 &p_vec) {
return p_vec * p_scalar;
}
+_FORCE_INLINE_ Vector2 Vector2::operator+(const Vector2 &p_v) const {
+
+ return Vector2(x + p_v.x, y + p_v.y);
+}
+_FORCE_INLINE_ void Vector2::operator+=(const Vector2 &p_v) {
+
+ x += p_v.x;
+ y += p_v.y;
+}
+_FORCE_INLINE_ Vector2 Vector2::operator-(const Vector2 &p_v) const {
+
+ return Vector2(x - p_v.x, y - p_v.y);
+}
+_FORCE_INLINE_ void Vector2::operator-=(const Vector2 &p_v) {
+
+ x -= p_v.x;
+ y -= p_v.y;
+}
+
+_FORCE_INLINE_ Vector2 Vector2::operator*(const Vector2 &p_v1) const {
+
+ return Vector2(x * p_v1.x, y * p_v1.y);
+};
+
+_FORCE_INLINE_ Vector2 Vector2::operator*(const real_t &rvalue) const {
+
+ return Vector2(x * rvalue, y * rvalue);
+};
+_FORCE_INLINE_ void Vector2::operator*=(const real_t &rvalue) {
+
+ x *= rvalue;
+ y *= rvalue;
+};
+
+_FORCE_INLINE_ Vector2 Vector2::operator/(const Vector2 &p_v1) const {
+
+ return Vector2(x / p_v1.x, y / p_v1.y);
+};
+
+_FORCE_INLINE_ Vector2 Vector2::operator/(const real_t &rvalue) const {
+
+ return Vector2(x / rvalue, y / rvalue);
+};
+
+_FORCE_INLINE_ void Vector2::operator/=(const real_t &rvalue) {
+
+ x /= rvalue;
+ y /= rvalue;
+};
+
+_FORCE_INLINE_ Vector2 Vector2::operator-() const {
+
+ return Vector2(-x, -y);
+}
+
+_FORCE_INLINE_ bool Vector2::operator==(const Vector2 &p_vec2) const {
+
+ return x == p_vec2.x && y == p_vec2.y;
+}
+_FORCE_INLINE_ bool Vector2::operator!=(const Vector2 &p_vec2) const {
+
+ return x != p_vec2.x || y != p_vec2.y;
+}
+
Vector2 Vector2::linear_interpolate(const Vector2 &p_b, real_t p_t) const {
Vector2 res = *this;
@@ -239,22 +303,31 @@ struct Rect2 {
inline real_t distance_to(const Vector2 &p_point) const {
- real_t dist = 1e20;
+ real_t dist;
+ bool inside = true;
if (p_point.x < position.x) {
- dist = MIN(dist, position.x - p_point.x);
+ real_t d = position.x - p_point.x;
+ dist = inside ? d : MIN(dist, d);
+ inside = false;
}
if (p_point.y < position.y) {
- dist = MIN(dist, position.y - p_point.y);
+ real_t d = position.y - p_point.y;
+ dist = inside ? d : MIN(dist, d);
+ inside = false;
}
if (p_point.x >= (position.x + size.x)) {
- dist = MIN(p_point.x - (position.x + size.x), dist);
+ real_t d = p_point.x - (position.x + size.x);
+ dist = inside ? d : MIN(dist, d);
+ inside = false;
}
if (p_point.y >= (position.y + size.y)) {
- dist = MIN(p_point.y - (position.y + size.y), dist);
+ real_t d = p_point.y - (position.y + size.y);
+ dist = inside ? d : MIN(dist, d);
+ inside = false;
}
- if (dist == 1e20)
+ if (inside)
return 0;
else
return dist;
@@ -336,9 +409,10 @@ struct Rect2 {
g.size.height += p_by * 2;
return g;
}
+
inline Rect2 grow_margin(Margin p_margin, real_t p_amount) const {
Rect2 g = *this;
- g.grow_individual((MARGIN_LEFT == p_margin) ? p_amount : 0,
+ g = g.grow_individual((MARGIN_LEFT == p_margin) ? p_amount : 0,
(MARGIN_TOP == p_margin) ? p_amount : 0,
(MARGIN_RIGHT == p_margin) ? p_amount : 0,
(MARGIN_BOTTOM == p_margin) ? p_amount : 0);
diff --git a/core/math/matrix3.cpp b/core/math/matrix3.cpp
index ab3bca79ae..5346141470 100644
--- a/core/math/matrix3.cpp
+++ b/core/math/matrix3.cpp
@@ -311,6 +311,15 @@ void Basis::rotate(const Vector3 &p_axis, real_t p_phi) {
*this = rotated(p_axis, p_phi);
}
+void Basis::rotate_local(const Vector3 &p_axis, real_t p_phi) {
+
+ *this = rotated_local(p_axis, p_phi);
+}
+Basis Basis::rotated_local(const Vector3 &p_axis, real_t p_phi) const {
+
+ return (*this) * Basis(p_axis, p_phi);
+}
+
Basis Basis::rotated(const Vector3 &p_euler) const {
return Basis(p_euler) * (*this);
}
diff --git a/core/math/matrix3.h b/core/math/matrix3.h
index 9a33b8203d..9a75308f08 100644
--- a/core/math/matrix3.h
+++ b/core/math/matrix3.h
@@ -75,6 +75,9 @@ public:
void rotate(const Vector3 &p_axis, real_t p_phi);
Basis rotated(const Vector3 &p_axis, real_t p_phi) const;
+ void rotate_local(const Vector3 &p_axis, real_t p_phi);
+ Basis rotated_local(const Vector3 &p_axis, real_t p_phi) const;
+
void rotate(const Vector3 &p_euler);
Basis rotated(const Vector3 &p_euler) const;
diff --git a/core/os/file_access.cpp b/core/os/file_access.cpp
index 20c1221f2b..133c70b671 100644
--- a/core/os/file_access.cpp
+++ b/core/os/file_access.cpp
@@ -569,6 +569,37 @@ String FileAccess::get_md5(const String &p_file) {
return ret;
}
+String FileAccess::get_multiple_md5(const Vector<String> &p_file) {
+
+ MD5_CTX md5;
+ MD5Init(&md5);
+
+ for (int i = 0; i < p_file.size(); i++) {
+ FileAccess *f = FileAccess::open(p_file[i], READ);
+ ERR_CONTINUE(!f);
+
+ unsigned char step[32768];
+
+ while (true) {
+
+ int br = f->get_buffer(step, 32768);
+ if (br > 0) {
+
+ MD5Update(&md5, step, br);
+ }
+ if (br < 4096)
+ break;
+ }
+ memdelete(f);
+ }
+
+ MD5Final(&md5);
+
+ String ret = String::md5(md5.digest);
+
+ return ret;
+}
+
String FileAccess::get_sha256(const String &p_file) {
FileAccess *f = FileAccess::open(p_file, READ);
diff --git a/core/os/file_access.h b/core/os/file_access.h
index 6fda3d9668..548d7b71f1 100644
--- a/core/os/file_access.h
+++ b/core/os/file_access.h
@@ -155,6 +155,7 @@ public:
static String get_md5(const String &p_file);
static String get_sha256(const String &p_file);
+ static String get_multiple_md5(const Vector<String> &p_file);
static Vector<uint8_t> get_file_as_array(const String &p_path);
diff --git a/core/os/input_event.cpp b/core/os/input_event.cpp
index 9b2bd30868..0cab8c10ef 100644
--- a/core/os/input_event.cpp
+++ b/core/os/input_event.cpp
@@ -32,14 +32,6 @@
#include "input_map.h"
#include "os/keyboard.h"
-void InputEvent::set_id(uint32_t p_id) {
- id = p_id;
-}
-
-uint32_t InputEvent::get_id() const {
- return id;
-}
-
void InputEvent::set_device(int p_device) {
device = p_device;
}
@@ -99,9 +91,6 @@ bool InputEvent::is_action_type() const {
void InputEvent::_bind_methods() {
- ClassDB::bind_method(D_METHOD("set_id", "id"), &InputEvent::set_id);
- ClassDB::bind_method(D_METHOD("get_id"), &InputEvent::get_id);
-
ClassDB::bind_method(D_METHOD("set_device", "device"), &InputEvent::set_device);
ClassDB::bind_method(D_METHOD("get_device"), &InputEvent::get_device);
@@ -125,7 +114,6 @@ void InputEvent::_bind_methods() {
InputEvent::InputEvent() {
- id = 0;
device = 0;
}
@@ -441,7 +429,6 @@ Ref<InputEvent> InputEventMouseButton::xformed_by(const Transform2D &p_xform, co
Ref<InputEventMouseButton> mb;
mb.instance();
- mb->set_id(get_id());
mb->set_device(get_device());
mb->set_modifiers_from_event(this);
@@ -557,7 +544,6 @@ Ref<InputEvent> InputEventMouseMotion::xformed_by(const Transform2D &p_xform, co
Ref<InputEventMouseMotion> mm;
mm.instance();
- mm->set_id(get_id());
mm->set_device(get_device());
mm->set_modifiers_from_event(this);
@@ -764,7 +750,6 @@ Ref<InputEvent> InputEventScreenTouch::xformed_by(const Transform2D &p_xform, co
Ref<InputEventScreenTouch> st;
st.instance();
- st->set_id(get_id());
st->set_device(get_device());
st->set_index(index);
st->set_position(p_xform.xform(pos + p_local_ofs));
@@ -845,7 +830,6 @@ Ref<InputEvent> InputEventScreenDrag::xformed_by(const Transform2D &p_xform, con
sd.instance();
- sd->set_id(get_id());
sd->set_device(get_device());
sd->set_index(index);
@@ -968,7 +952,6 @@ Ref<InputEvent> InputEventMagnifyGesture::xformed_by(const Transform2D &p_xform,
Ref<InputEventMagnifyGesture> ev;
ev.instance();
- ev->set_id(get_id());
ev->set_device(get_device());
ev->set_modifiers_from_event(this);
@@ -1006,7 +989,6 @@ Ref<InputEvent> InputEventPanGesture::xformed_by(const Transform2D &p_xform, con
Ref<InputEventPanGesture> ev;
ev.instance();
- ev->set_id(get_id());
ev->set_device(get_device());
ev->set_modifiers_from_event(this);
diff --git a/core/os/input_event.h b/core/os/input_event.h
index 614a3289ba..9b1a2736b1 100644
--- a/core/os/input_event.h
+++ b/core/os/input_event.h
@@ -144,16 +144,12 @@ enum JoystickList {
class InputEvent : public Resource {
GDCLASS(InputEvent, Resource)
- uint32_t id;
int device;
protected:
static void _bind_methods();
public:
- void set_id(uint32_t p_id);
- uint32_t get_id() const;
-
void set_device(int p_device);
int get_device() const;
diff --git a/core/os/threaded_array_processor.cpp b/core/os/threaded_array_processor.cpp
new file mode 100644
index 0000000000..8e92508ea5
--- /dev/null
+++ b/core/os/threaded_array_processor.cpp
@@ -0,0 +1,2 @@
+#include "threaded_array_processor.h"
+
diff --git a/core/os/threaded_array_processor.h b/core/os/threaded_array_processor.h
new file mode 100644
index 0000000000..e584fbb193
--- /dev/null
+++ b/core/os/threaded_array_processor.h
@@ -0,0 +1,80 @@
+#ifndef THREADED_ARRAY_PROCESSOR_H
+#define THREADED_ARRAY_PROCESSOR_H
+
+#include "os/mutex.h"
+#include "os/os.h"
+#include "os/thread.h"
+#include "safe_refcount.h"
+#include "thread_safe.h"
+
+template <class C, class U>
+struct ThreadArrayProcessData {
+ uint32_t elements;
+ uint32_t index;
+ C *instance;
+ U userdata;
+ void (C::*method)(uint32_t, U);
+
+ void process(uint32_t p_index) {
+ (instance->*method)(p_index, userdata);
+ }
+};
+
+#ifndef NO_THREADS
+
+template <class T>
+void process_array_thread(void *ud) {
+
+ T &data = *(T *)ud;
+ while (true) {
+ uint32_t index = atomic_increment(&data.index);
+ if (index >= data.elements)
+ break;
+ data.process(index);
+ }
+}
+
+template <class C, class M, class U>
+void thread_process_array(uint32_t p_elements, C *p_instance, M p_method, U p_userdata) {
+
+ ThreadArrayProcessData<C, U> data;
+ data.method = p_method;
+ data.instance = p_instance;
+ data.userdata = p_userdata;
+ data.index = 0;
+ data.elements = p_elements;
+ data.process(data.index); //process first, let threads increment for next
+
+ Vector<Thread *> threads;
+
+ threads.resize(OS::get_singleton()->get_processor_count());
+
+ for (int i = 0; i < threads.size(); i++) {
+ threads[i] = Thread::create(process_array_thread<ThreadArrayProcessData<C, U> >, &data);
+ }
+
+ for (int i = 0; i < threads.size(); i++) {
+ Thread::wait_to_finish(threads[i]);
+ memdelete(threads[i]);
+ }
+}
+
+#else
+
+template <class C, class M, class U>
+void thread_process_array(uint32_t p_elements, C *p_instance, M p_method, U p_userdata) {
+
+ ThreadArrayProcessData<C, U> data;
+ data.method = p_method;
+ data.instance = p_instance;
+ data.userdata = p_userdata;
+ data.index = 0;
+ data.elements = p_elements;
+ for (uint32_t i = 0; i < p_elements; i++) {
+ data.process(i);
+ }
+}
+
+#endif
+
+#endif // THREADED_ARRAY_PROCESSOR_H
diff --git a/core/string_buffer.cpp b/core/string_buffer.cpp
index 8489df2599..3b47685fc9 100644
--- a/core/string_buffer.cpp
+++ b/core/string_buffer.cpp
@@ -46,7 +46,7 @@ StringBuffer &StringBuffer::append(const char *p_str) {
reserve(string_length + len + 1);
CharType *buf = current_buffer_ptr();
- for (const char *c_ptr = p_str; c_ptr; ++c_ptr) {
+ for (const char *c_ptr = p_str; *c_ptr; ++c_ptr) {
buf[string_length++] = *c_ptr;
}
return *this;
diff --git a/core/string_db.h b/core/string_db.h
index de91e2abd8..9665198ecd 100644
--- a/core/string_db.h
+++ b/core/string_db.h
@@ -138,7 +138,22 @@ public:
_FORCE_INLINE_ bool operator()(const StringName &l, const StringName &r) const {
- return l.operator String() < r.operator String();
+ const char *l_cname = l._data ? l._data->cname : "";
+ const char *r_cname = r._data ? r._data->cname : "";
+
+ if (l_cname) {
+
+ if (r_cname)
+ return is_str_less(l_cname, r_cname);
+ else
+ return is_str_less(l_cname, r._data->name.ptr());
+ } else {
+
+ if (r_cname)
+ return is_str_less(l._data->name.ptr(), r_cname);
+ else
+ return is_str_less(l._data->name.ptr(), r._data->name.ptr());
+ }
}
};
diff --git a/core/ustring.cpp b/core/ustring.cpp
index ceafe209ea..fc6312355a 100644
--- a/core/ustring.cpp
+++ b/core/ustring.cpp
@@ -56,34 +56,49 @@
#define IS_DIGIT(m_d) ((m_d) >= '0' && (m_d) <= '9')
#define IS_HEX_DIGIT(m_d) (((m_d) >= '0' && (m_d) <= '9') || ((m_d) >= 'a' && (m_d) <= 'f') || ((m_d) >= 'A' && (m_d) <= 'F'))
-/** STRING **/
+bool is_symbol(CharType c) {
+ return c != '_' && ((c >= '!' && c <= '/') || (c >= ':' && c <= '@') || (c >= '[' && c <= '`') || (c >= '{' && c <= '~') || c == '\t' || c == ' ');
+}
-bool CharString::operator<(const CharString &p_right) const {
+bool select_word(const String &p_s, int p_col, int &r_beg, int &r_end) {
- if (length() == 0) {
- return p_right.length() != 0;
+ const String &s = p_s;
+ int beg = CLAMP(p_col, 0, s.length());
+ int end = beg;
+
+ if (s[beg] > 32 || beg == s.length()) {
+
+ bool symbol = beg < s.length() && is_symbol(s[beg]);
+
+ while (beg > 0 && s[beg - 1] > 32 && (symbol == is_symbol(s[beg - 1]))) {
+ beg--;
+ }
+ while (end < s.length() && s[end + 1] > 32 && (symbol == is_symbol(s[end + 1]))) {
+ end++;
+ }
+
+ if (end < s.length())
+ end += 1;
+
+ r_beg = beg;
+ r_end = end;
+
+ return true;
+ } else {
+
+ return false;
}
+}
- const char *this_str = get_data();
- const char *that_str = p_right.get_data();
- while (true) {
+/** STRING **/
- if (*that_str == 0 && *this_str == 0)
- return false; //this can't be equal, sadly
- else if (*this_str == 0)
- return true; //if this is empty, and the other one is not, then we're less.. I think?
- else if (*that_str == 0)
- return false; //otherwise the other one is smaller..
- else if (*this_str < *that_str) //more than
- return true;
- else if (*this_str > *that_str) //less than
- return false;
+bool CharString::operator<(const CharString &p_right) const {
- this_str++;
- that_str++;
+ if (length() == 0) {
+ return p_right.length() != 0;
}
- return false; //should never reach here anyway
+ return is_str_less(get_data(), p_right.get_data());
}
const char *CharString::get_data() const {
@@ -372,25 +387,7 @@ bool String::operator<(const CharType *p_str) const {
if (empty())
return true;
- const CharType *this_str = c_str();
- while (true) {
-
- if (*p_str == 0 && *this_str == 0)
- return false; //this can't be equal, sadly
- else if (*this_str == 0)
- return true; //if this is empty, and the other one is not, then we're less.. I think?
- else if (*p_str == 0)
- return false; //otherwise the other one is smaller..
- else if (*this_str < *p_str) //more than
- return true;
- else if (*this_str > *p_str) //less than
- return false;
-
- this_str++;
- p_str++;
- }
-
- return false; //should never reach here anyway
+ return is_str_less(c_str(), p_str);
}
bool String::operator<=(const String &p_str) const {
@@ -405,25 +402,7 @@ bool String::operator<(const char *p_str) const {
if (empty())
return true;
- const CharType *this_str = c_str();
- while (true) {
-
- if (*p_str == 0 && *this_str == 0)
- return false; //this can't be equal, sadly
- else if (*this_str == 0)
- return true; //if this is empty, and the other one is not, then we're less.. I think?
- else if (*p_str == 0)
- return false; //otherwise the other one is smaller..
- else if (*this_str < *p_str) //more than
- return true;
- else if (*this_str > *p_str) //less than
- return false;
-
- this_str++;
- p_str++;
- }
-
- return false; //should never reach here anyway
+ return is_str_less(c_str(), p_str);
}
bool String::operator<(const String &p_str) const {
diff --git a/core/ustring.h b/core/ustring.h
index 73537bfd13..3be3161a4a 100644
--- a/core/ustring.h
+++ b/core/ustring.h
@@ -279,6 +279,29 @@ struct NaturalNoCaseComparator {
}
};
+template <typename L, typename R>
+_FORCE_INLINE_ bool is_str_less(const L *l_ptr, const R *r_ptr) {
+
+ while (true) {
+
+ if (*l_ptr == 0 && *r_ptr == 0)
+ return false;
+ else if (*l_ptr == 0)
+ return true;
+ else if (*r_ptr == 0)
+ return false;
+ else if (*l_ptr < *r_ptr)
+ return true;
+ else if (*l_ptr > *r_ptr)
+ return false;
+
+ l_ptr++;
+ r_ptr++;
+ }
+
+ CRASH_COND(true); // unreachable
+}
+
/* end of namespace */
//tool translate
@@ -295,4 +318,7 @@ String TTR(const String &);
//tool or regular translate
String RTR(const String &);
+bool is_symbol(CharType c);
+bool select_word(const String &p_s, int p_col, int &r_beg, int &r_end);
+
#endif