1/**************************************************************************/
2/* variant.cpp */
3/**************************************************************************/
4/* This file is part of: */
5/* GODOT ENGINE */
6/* https://godotengine.org */
7/**************************************************************************/
8/* Copyright (c) 2014-present Godot Engine contributors (see AUTHORS.md). */
9/* Copyright (c) 2007-2014 Juan Linietsky, Ariel Manzur. */
10/* */
11/* Permission is hereby granted, free of charge, to any person obtaining */
12/* a copy of this software and associated documentation files (the */
13/* "Software"), to deal in the Software without restriction, including */
14/* without limitation the rights to use, copy, modify, merge, publish, */
15/* distribute, sublicense, and/or sell copies of the Software, and to */
16/* permit persons to whom the Software is furnished to do so, subject to */
17/* the following conditions: */
18/* */
19/* The above copyright notice and this permission notice shall be */
20/* included in all copies or substantial portions of the Software. */
21/* */
22/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, */
23/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF */
24/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. */
25/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY */
26/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, */
27/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE */
28/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */
29/**************************************************************************/
30
31#include "variant.h"
32
33#include "core/core_string_names.h"
34#include "core/debugger/engine_debugger.h"
35#include "core/io/json.h"
36#include "core/io/marshalls.h"
37#include "core/io/resource.h"
38#include "core/math/math_funcs.h"
39#include "core/string/print_string.h"
40#include "core/variant/variant_parser.h"
41
42PagedAllocator<Variant::Pools::BucketSmall, true> Variant::Pools::_bucket_small;
43PagedAllocator<Variant::Pools::BucketMedium, true> Variant::Pools::_bucket_medium;
44PagedAllocator<Variant::Pools::BucketLarge, true> Variant::Pools::_bucket_large;
45
46String Variant::get_type_name(Variant::Type p_type) {
47 switch (p_type) {
48 case NIL: {
49 return "Nil";
50 }
51
52 // Atomic types.
53 case BOOL: {
54 return "bool";
55 }
56 case INT: {
57 return "int";
58 }
59 case FLOAT: {
60 return "float";
61 }
62 case STRING: {
63 return "String";
64 }
65
66 // Math types.
67 case VECTOR2: {
68 return "Vector2";
69 }
70 case VECTOR2I: {
71 return "Vector2i";
72 }
73 case RECT2: {
74 return "Rect2";
75 }
76 case RECT2I: {
77 return "Rect2i";
78 }
79 case TRANSFORM2D: {
80 return "Transform2D";
81 }
82 case VECTOR3: {
83 return "Vector3";
84 }
85 case VECTOR3I: {
86 return "Vector3i";
87 }
88 case VECTOR4: {
89 return "Vector4";
90 }
91 case VECTOR4I: {
92 return "Vector4i";
93 }
94 case PLANE: {
95 return "Plane";
96 }
97 case AABB: {
98 return "AABB";
99 }
100 case QUATERNION: {
101 return "Quaternion";
102 }
103 case BASIS: {
104 return "Basis";
105 }
106 case TRANSFORM3D: {
107 return "Transform3D";
108 }
109 case PROJECTION: {
110 return "Projection";
111 }
112
113 // Miscellaneous types.
114 case COLOR: {
115 return "Color";
116 }
117 case RID: {
118 return "RID";
119 }
120 case OBJECT: {
121 return "Object";
122 }
123 case CALLABLE: {
124 return "Callable";
125 }
126 case SIGNAL: {
127 return "Signal";
128 }
129 case STRING_NAME: {
130 return "StringName";
131 }
132 case NODE_PATH: {
133 return "NodePath";
134 }
135 case DICTIONARY: {
136 return "Dictionary";
137 }
138 case ARRAY: {
139 return "Array";
140 }
141
142 // Arrays.
143 case PACKED_BYTE_ARRAY: {
144 return "PackedByteArray";
145 }
146 case PACKED_INT32_ARRAY: {
147 return "PackedInt32Array";
148 }
149 case PACKED_INT64_ARRAY: {
150 return "PackedInt64Array";
151 }
152 case PACKED_FLOAT32_ARRAY: {
153 return "PackedFloat32Array";
154 }
155 case PACKED_FLOAT64_ARRAY: {
156 return "PackedFloat64Array";
157 }
158 case PACKED_STRING_ARRAY: {
159 return "PackedStringArray";
160 }
161 case PACKED_VECTOR2_ARRAY: {
162 return "PackedVector2Array";
163 }
164 case PACKED_VECTOR3_ARRAY: {
165 return "PackedVector3Array";
166 }
167 case PACKED_COLOR_ARRAY: {
168 return "PackedColorArray";
169 }
170 default: {
171 }
172 }
173
174 return "";
175}
176
177bool Variant::can_convert(Variant::Type p_type_from, Variant::Type p_type_to) {
178 if (p_type_from == p_type_to) {
179 return true;
180 }
181 if (p_type_to == NIL) { //nil can convert to anything
182 return true;
183 }
184
185 if (p_type_from == NIL) {
186 return (p_type_to == OBJECT);
187 }
188
189 const Type *valid_types = nullptr;
190 const Type *invalid_types = nullptr;
191
192 switch (p_type_to) {
193 case BOOL: {
194 static const Type valid[] = {
195 INT,
196 FLOAT,
197 STRING,
198 NIL,
199 };
200
201 valid_types = valid;
202 } break;
203 case INT: {
204 static const Type valid[] = {
205 BOOL,
206 FLOAT,
207 STRING,
208 NIL,
209 };
210
211 valid_types = valid;
212
213 } break;
214 case FLOAT: {
215 static const Type valid[] = {
216 BOOL,
217 INT,
218 STRING,
219 NIL,
220 };
221
222 valid_types = valid;
223
224 } break;
225 case STRING: {
226 static const Type invalid[] = {
227 OBJECT,
228 NIL
229 };
230
231 invalid_types = invalid;
232 } break;
233 case VECTOR2: {
234 static const Type valid[] = {
235 VECTOR2I,
236 NIL,
237 };
238
239 valid_types = valid;
240
241 } break;
242 case VECTOR2I: {
243 static const Type valid[] = {
244 VECTOR2,
245 NIL,
246 };
247
248 valid_types = valid;
249
250 } break;
251 case RECT2: {
252 static const Type valid[] = {
253 RECT2I,
254 NIL,
255 };
256
257 valid_types = valid;
258
259 } break;
260 case RECT2I: {
261 static const Type valid[] = {
262 RECT2,
263 NIL,
264 };
265
266 valid_types = valid;
267
268 } break;
269 case TRANSFORM2D: {
270 static const Type valid[] = {
271 TRANSFORM3D,
272 NIL
273 };
274
275 valid_types = valid;
276 } break;
277 case VECTOR3: {
278 static const Type valid[] = {
279 VECTOR3I,
280 NIL,
281 };
282
283 valid_types = valid;
284
285 } break;
286 case VECTOR3I: {
287 static const Type valid[] = {
288 VECTOR3,
289 NIL,
290 };
291
292 valid_types = valid;
293
294 } break;
295 case VECTOR4: {
296 static const Type valid[] = {
297 VECTOR4I,
298 NIL,
299 };
300
301 valid_types = valid;
302
303 } break;
304 case VECTOR4I: {
305 static const Type valid[] = {
306 VECTOR4,
307 NIL,
308 };
309
310 valid_types = valid;
311
312 } break;
313
314 case QUATERNION: {
315 static const Type valid[] = {
316 BASIS,
317 NIL
318 };
319
320 valid_types = valid;
321
322 } break;
323 case BASIS: {
324 static const Type valid[] = {
325 QUATERNION,
326 NIL
327 };
328
329 valid_types = valid;
330
331 } break;
332 case TRANSFORM3D: {
333 static const Type valid[] = {
334 TRANSFORM2D,
335 QUATERNION,
336 BASIS,
337 PROJECTION,
338 NIL
339 };
340
341 valid_types = valid;
342
343 } break;
344 case PROJECTION: {
345 static const Type valid[] = {
346 TRANSFORM3D,
347 NIL
348 };
349
350 valid_types = valid;
351
352 } break;
353
354 case COLOR: {
355 static const Type valid[] = {
356 STRING,
357 INT,
358 NIL,
359 };
360
361 valid_types = valid;
362
363 } break;
364
365 case RID: {
366 static const Type valid[] = {
367 OBJECT,
368 NIL
369 };
370
371 valid_types = valid;
372 } break;
373 case OBJECT: {
374 static const Type valid[] = {
375 NIL
376 };
377
378 valid_types = valid;
379 } break;
380 case STRING_NAME: {
381 static const Type valid[] = {
382 STRING,
383 NIL
384 };
385
386 valid_types = valid;
387 } break;
388 case NODE_PATH: {
389 static const Type valid[] = {
390 STRING,
391 NIL
392 };
393
394 valid_types = valid;
395 } break;
396 case ARRAY: {
397 static const Type valid[] = {
398 PACKED_BYTE_ARRAY,
399 PACKED_INT32_ARRAY,
400 PACKED_INT64_ARRAY,
401 PACKED_FLOAT32_ARRAY,
402 PACKED_FLOAT64_ARRAY,
403 PACKED_STRING_ARRAY,
404 PACKED_COLOR_ARRAY,
405 PACKED_VECTOR2_ARRAY,
406 PACKED_VECTOR3_ARRAY,
407 NIL
408 };
409
410 valid_types = valid;
411 } break;
412 // arrays
413 case PACKED_BYTE_ARRAY: {
414 static const Type valid[] = {
415 ARRAY,
416 NIL
417 };
418
419 valid_types = valid;
420 } break;
421 case PACKED_INT32_ARRAY: {
422 static const Type valid[] = {
423 ARRAY,
424 NIL
425 };
426 valid_types = valid;
427 } break;
428 case PACKED_INT64_ARRAY: {
429 static const Type valid[] = {
430 ARRAY,
431 NIL
432 };
433 valid_types = valid;
434 } break;
435 case PACKED_FLOAT32_ARRAY: {
436 static const Type valid[] = {
437 ARRAY,
438 NIL
439 };
440
441 valid_types = valid;
442 } break;
443 case PACKED_FLOAT64_ARRAY: {
444 static const Type valid[] = {
445 ARRAY,
446 NIL
447 };
448
449 valid_types = valid;
450 } break;
451 case PACKED_STRING_ARRAY: {
452 static const Type valid[] = {
453 ARRAY,
454 NIL
455 };
456 valid_types = valid;
457 } break;
458 case PACKED_VECTOR2_ARRAY: {
459 static const Type valid[] = {
460 ARRAY,
461 NIL
462 };
463 valid_types = valid;
464
465 } break;
466 case PACKED_VECTOR3_ARRAY: {
467 static const Type valid[] = {
468 ARRAY,
469 NIL
470 };
471 valid_types = valid;
472
473 } break;
474 case PACKED_COLOR_ARRAY: {
475 static const Type valid[] = {
476 ARRAY,
477 NIL
478 };
479
480 valid_types = valid;
481
482 } break;
483 default: {
484 }
485 }
486
487 if (valid_types) {
488 int i = 0;
489 while (valid_types[i] != NIL) {
490 if (p_type_from == valid_types[i]) {
491 return true;
492 }
493 i++;
494 }
495
496 } else if (invalid_types) {
497 int i = 0;
498 while (invalid_types[i] != NIL) {
499 if (p_type_from == invalid_types[i]) {
500 return false;
501 }
502 i++;
503 }
504
505 return true;
506 }
507
508 return false;
509}
510
511bool Variant::can_convert_strict(Variant::Type p_type_from, Variant::Type p_type_to) {
512 if (p_type_from == p_type_to) {
513 return true;
514 }
515 if (p_type_to == NIL) { //nil can convert to anything
516 return true;
517 }
518
519 if (p_type_from == NIL) {
520 return (p_type_to == OBJECT);
521 }
522
523 const Type *valid_types = nullptr;
524
525 switch (p_type_to) {
526 case BOOL: {
527 static const Type valid[] = {
528 INT,
529 FLOAT,
530 //STRING,
531 NIL,
532 };
533
534 valid_types = valid;
535 } break;
536 case INT: {
537 static const Type valid[] = {
538 BOOL,
539 FLOAT,
540 //STRING,
541 NIL,
542 };
543
544 valid_types = valid;
545
546 } break;
547 case FLOAT: {
548 static const Type valid[] = {
549 BOOL,
550 INT,
551 //STRING,
552 NIL,
553 };
554
555 valid_types = valid;
556
557 } break;
558 case STRING: {
559 static const Type valid[] = {
560 NODE_PATH,
561 STRING_NAME,
562 NIL
563 };
564
565 valid_types = valid;
566 } break;
567 case VECTOR2: {
568 static const Type valid[] = {
569 VECTOR2I,
570 NIL,
571 };
572
573 valid_types = valid;
574
575 } break;
576 case VECTOR2I: {
577 static const Type valid[] = {
578 VECTOR2,
579 NIL,
580 };
581
582 valid_types = valid;
583
584 } break;
585 case RECT2: {
586 static const Type valid[] = {
587 RECT2I,
588 NIL,
589 };
590
591 valid_types = valid;
592
593 } break;
594 case RECT2I: {
595 static const Type valid[] = {
596 RECT2,
597 NIL,
598 };
599
600 valid_types = valid;
601
602 } break;
603 case TRANSFORM2D: {
604 static const Type valid[] = {
605 TRANSFORM3D,
606 NIL
607 };
608
609 valid_types = valid;
610 } break;
611 case VECTOR3: {
612 static const Type valid[] = {
613 VECTOR3I,
614 NIL,
615 };
616
617 valid_types = valid;
618
619 } break;
620 case VECTOR3I: {
621 static const Type valid[] = {
622 VECTOR3,
623 NIL,
624 };
625
626 valid_types = valid;
627
628 } break;
629 case VECTOR4: {
630 static const Type valid[] = {
631 VECTOR4I,
632 NIL,
633 };
634
635 valid_types = valid;
636
637 } break;
638 case VECTOR4I: {
639 static const Type valid[] = {
640 VECTOR4,
641 NIL,
642 };
643
644 valid_types = valid;
645
646 } break;
647
648 case QUATERNION: {
649 static const Type valid[] = {
650 BASIS,
651 NIL
652 };
653
654 valid_types = valid;
655
656 } break;
657 case BASIS: {
658 static const Type valid[] = {
659 QUATERNION,
660 NIL
661 };
662
663 valid_types = valid;
664
665 } break;
666 case TRANSFORM3D: {
667 static const Type valid[] = {
668 TRANSFORM2D,
669 QUATERNION,
670 BASIS,
671 PROJECTION,
672 NIL
673 };
674
675 valid_types = valid;
676
677 } break;
678 case PROJECTION: {
679 static const Type valid[] = {
680 TRANSFORM3D,
681 NIL
682 };
683
684 valid_types = valid;
685
686 } break;
687
688 case COLOR: {
689 static const Type valid[] = {
690 STRING,
691 INT,
692 NIL,
693 };
694
695 valid_types = valid;
696
697 } break;
698
699 case RID: {
700 static const Type valid[] = {
701 OBJECT,
702 NIL
703 };
704
705 valid_types = valid;
706 } break;
707 case OBJECT: {
708 static const Type valid[] = {
709 NIL
710 };
711
712 valid_types = valid;
713 } break;
714 case STRING_NAME: {
715 static const Type valid[] = {
716 STRING,
717 NIL
718 };
719
720 valid_types = valid;
721 } break;
722 case NODE_PATH: {
723 static const Type valid[] = {
724 STRING,
725 NIL
726 };
727
728 valid_types = valid;
729 } break;
730 case ARRAY: {
731 static const Type valid[] = {
732 PACKED_BYTE_ARRAY,
733 PACKED_INT32_ARRAY,
734 PACKED_INT64_ARRAY,
735 PACKED_FLOAT32_ARRAY,
736 PACKED_FLOAT64_ARRAY,
737 PACKED_STRING_ARRAY,
738 PACKED_COLOR_ARRAY,
739 PACKED_VECTOR2_ARRAY,
740 PACKED_VECTOR3_ARRAY,
741 NIL
742 };
743
744 valid_types = valid;
745 } break;
746 // arrays
747 case PACKED_BYTE_ARRAY: {
748 static const Type valid[] = {
749 ARRAY,
750 NIL
751 };
752
753 valid_types = valid;
754 } break;
755 case PACKED_INT32_ARRAY: {
756 static const Type valid[] = {
757 ARRAY,
758 NIL
759 };
760 valid_types = valid;
761 } break;
762 case PACKED_INT64_ARRAY: {
763 static const Type valid[] = {
764 ARRAY,
765 NIL
766 };
767 valid_types = valid;
768 } break;
769 case PACKED_FLOAT32_ARRAY: {
770 static const Type valid[] = {
771 ARRAY,
772 NIL
773 };
774
775 valid_types = valid;
776 } break;
777 case PACKED_FLOAT64_ARRAY: {
778 static const Type valid[] = {
779 ARRAY,
780 NIL
781 };
782
783 valid_types = valid;
784 } break;
785 case PACKED_STRING_ARRAY: {
786 static const Type valid[] = {
787 ARRAY,
788 NIL
789 };
790 valid_types = valid;
791 } break;
792 case PACKED_VECTOR2_ARRAY: {
793 static const Type valid[] = {
794 ARRAY,
795 NIL
796 };
797 valid_types = valid;
798
799 } break;
800 case PACKED_VECTOR3_ARRAY: {
801 static const Type valid[] = {
802 ARRAY,
803 NIL
804 };
805 valid_types = valid;
806
807 } break;
808 case PACKED_COLOR_ARRAY: {
809 static const Type valid[] = {
810 ARRAY,
811 NIL
812 };
813
814 valid_types = valid;
815
816 } break;
817 default: {
818 }
819 }
820
821 if (valid_types) {
822 int i = 0;
823 while (valid_types[i] != NIL) {
824 if (p_type_from == valid_types[i]) {
825 return true;
826 }
827 i++;
828 }
829 }
830
831 return false;
832}
833
834bool Variant::operator==(const Variant &p_variant) const {
835 return hash_compare(p_variant);
836}
837
838bool Variant::operator!=(const Variant &p_variant) const {
839 // Don't use `!hash_compare(p_variant)` given it makes use of OP_EQUAL
840 if (type != p_variant.type) { //evaluation of operator== needs to be more strict
841 return true;
842 }
843 bool v;
844 Variant r;
845 evaluate(OP_NOT_EQUAL, *this, p_variant, r, v);
846 return r;
847}
848
849bool Variant::operator<(const Variant &p_variant) const {
850 if (type != p_variant.type) { //if types differ, then order by type first
851 return type < p_variant.type;
852 }
853 bool v;
854 Variant r;
855 evaluate(OP_LESS, *this, p_variant, r, v);
856 return r;
857}
858
859bool Variant::is_zero() const {
860 switch (type) {
861 case NIL: {
862 return true;
863 }
864
865 // Atomic types.
866 case BOOL: {
867 return !(_data._bool);
868 }
869 case INT: {
870 return _data._int == 0;
871 }
872 case FLOAT: {
873 return _data._float == 0;
874 }
875 case STRING: {
876 return *reinterpret_cast<const String *>(_data._mem) == String();
877 }
878
879 // Math types.
880 case VECTOR2: {
881 return *reinterpret_cast<const Vector2 *>(_data._mem) == Vector2();
882 }
883 case VECTOR2I: {
884 return *reinterpret_cast<const Vector2i *>(_data._mem) == Vector2i();
885 }
886 case RECT2: {
887 return *reinterpret_cast<const Rect2 *>(_data._mem) == Rect2();
888 }
889 case RECT2I: {
890 return *reinterpret_cast<const Rect2i *>(_data._mem) == Rect2i();
891 }
892 case TRANSFORM2D: {
893 return *_data._transform2d == Transform2D();
894 }
895 case VECTOR3: {
896 return *reinterpret_cast<const Vector3 *>(_data._mem) == Vector3();
897 }
898 case VECTOR3I: {
899 return *reinterpret_cast<const Vector3i *>(_data._mem) == Vector3i();
900 }
901 case VECTOR4: {
902 return *reinterpret_cast<const Vector4 *>(_data._mem) == Vector4();
903 }
904 case VECTOR4I: {
905 return *reinterpret_cast<const Vector4i *>(_data._mem) == Vector4i();
906 }
907 case PLANE: {
908 return *reinterpret_cast<const Plane *>(_data._mem) == Plane();
909 }
910 case AABB: {
911 return *_data._aabb == ::AABB();
912 }
913 case QUATERNION: {
914 return *reinterpret_cast<const Quaternion *>(_data._mem) == Quaternion();
915 }
916 case BASIS: {
917 return *_data._basis == Basis();
918 }
919 case TRANSFORM3D: {
920 return *_data._transform3d == Transform3D();
921 }
922 case PROJECTION: {
923 return *_data._projection == Projection();
924 }
925
926 // Miscellaneous types.
927 case COLOR: {
928 return *reinterpret_cast<const Color *>(_data._mem) == Color();
929 }
930 case RID: {
931 return *reinterpret_cast<const ::RID *>(_data._mem) == ::RID();
932 }
933 case OBJECT: {
934 return _get_obj().obj == nullptr;
935 }
936 case CALLABLE: {
937 return reinterpret_cast<const Callable *>(_data._mem)->is_null();
938 }
939 case SIGNAL: {
940 return reinterpret_cast<const Signal *>(_data._mem)->is_null();
941 }
942 case STRING_NAME: {
943 return *reinterpret_cast<const StringName *>(_data._mem) == StringName();
944 }
945 case NODE_PATH: {
946 return reinterpret_cast<const NodePath *>(_data._mem)->is_empty();
947 }
948 case DICTIONARY: {
949 return reinterpret_cast<const Dictionary *>(_data._mem)->is_empty();
950 }
951 case ARRAY: {
952 return reinterpret_cast<const Array *>(_data._mem)->is_empty();
953 }
954
955 // Arrays.
956 case PACKED_BYTE_ARRAY: {
957 return PackedArrayRef<uint8_t>::get_array(_data.packed_array).size() == 0;
958 }
959 case PACKED_INT32_ARRAY: {
960 return PackedArrayRef<int32_t>::get_array(_data.packed_array).size() == 0;
961 }
962 case PACKED_INT64_ARRAY: {
963 return PackedArrayRef<int64_t>::get_array(_data.packed_array).size() == 0;
964 }
965 case PACKED_FLOAT32_ARRAY: {
966 return PackedArrayRef<float>::get_array(_data.packed_array).size() == 0;
967 }
968 case PACKED_FLOAT64_ARRAY: {
969 return PackedArrayRef<double>::get_array(_data.packed_array).size() == 0;
970 }
971 case PACKED_STRING_ARRAY: {
972 return PackedArrayRef<String>::get_array(_data.packed_array).size() == 0;
973 }
974 case PACKED_VECTOR2_ARRAY: {
975 return PackedArrayRef<Vector2>::get_array(_data.packed_array).size() == 0;
976 }
977 case PACKED_VECTOR3_ARRAY: {
978 return PackedArrayRef<Vector3>::get_array(_data.packed_array).size() == 0;
979 }
980 case PACKED_COLOR_ARRAY: {
981 return PackedArrayRef<Color>::get_array(_data.packed_array).size() == 0;
982 }
983 default: {
984 }
985 }
986
987 return false;
988}
989
990bool Variant::is_one() const {
991 switch (type) {
992 case NIL: {
993 return true;
994 }
995
996 case BOOL: {
997 return _data._bool;
998 }
999 case INT: {
1000 return _data._int == 1;
1001 }
1002 case FLOAT: {
1003 return _data._float == 1;
1004 }
1005
1006 case VECTOR2: {
1007 return *reinterpret_cast<const Vector2 *>(_data._mem) == Vector2(1, 1);
1008 }
1009 case VECTOR2I: {
1010 return *reinterpret_cast<const Vector2i *>(_data._mem) == Vector2i(1, 1);
1011 }
1012 case RECT2: {
1013 return *reinterpret_cast<const Rect2 *>(_data._mem) == Rect2(1, 1, 1, 1);
1014 }
1015 case RECT2I: {
1016 return *reinterpret_cast<const Rect2i *>(_data._mem) == Rect2i(1, 1, 1, 1);
1017 }
1018 case VECTOR3: {
1019 return *reinterpret_cast<const Vector3 *>(_data._mem) == Vector3(1, 1, 1);
1020 }
1021 case VECTOR3I: {
1022 return *reinterpret_cast<const Vector3i *>(_data._mem) == Vector3i(1, 1, 1);
1023 }
1024 case VECTOR4: {
1025 return *reinterpret_cast<const Vector4 *>(_data._mem) == Vector4(1, 1, 1, 1);
1026 }
1027 case VECTOR4I: {
1028 return *reinterpret_cast<const Vector4i *>(_data._mem) == Vector4i(1, 1, 1, 1);
1029 }
1030 case PLANE: {
1031 return *reinterpret_cast<const Plane *>(_data._mem) == Plane(1, 1, 1, 1);
1032 }
1033
1034 case COLOR: {
1035 return *reinterpret_cast<const Color *>(_data._mem) == Color(1, 1, 1, 1);
1036 }
1037
1038 default: {
1039 return !is_zero();
1040 }
1041 }
1042}
1043
1044bool Variant::is_null() const {
1045 if (type == OBJECT && _get_obj().obj) {
1046 return false;
1047 } else {
1048 return true;
1049 }
1050}
1051
1052bool Variant::initialize_ref(Object *p_object) {
1053 RefCounted *ref_counted = const_cast<RefCounted *>(static_cast<const RefCounted *>(p_object));
1054 if (!ref_counted->init_ref()) {
1055 return false;
1056 }
1057 return true;
1058}
1059void Variant::reference(const Variant &p_variant) {
1060 switch (type) {
1061 case NIL:
1062 case BOOL:
1063 case INT:
1064 case FLOAT:
1065 break;
1066 default:
1067 clear();
1068 }
1069
1070 type = p_variant.type;
1071
1072 switch (p_variant.type) {
1073 case NIL: {
1074 // None.
1075 } break;
1076
1077 // Atomic types.
1078 case BOOL: {
1079 _data._bool = p_variant._data._bool;
1080 } break;
1081 case INT: {
1082 _data._int = p_variant._data._int;
1083 } break;
1084 case FLOAT: {
1085 _data._float = p_variant._data._float;
1086 } break;
1087 case STRING: {
1088 memnew_placement(_data._mem, String(*reinterpret_cast<const String *>(p_variant._data._mem)));
1089 } break;
1090
1091 // Math types.
1092 case VECTOR2: {
1093 memnew_placement(_data._mem, Vector2(*reinterpret_cast<const Vector2 *>(p_variant._data._mem)));
1094 } break;
1095 case VECTOR2I: {
1096 memnew_placement(_data._mem, Vector2i(*reinterpret_cast<const Vector2i *>(p_variant._data._mem)));
1097 } break;
1098 case RECT2: {
1099 memnew_placement(_data._mem, Rect2(*reinterpret_cast<const Rect2 *>(p_variant._data._mem)));
1100 } break;
1101 case RECT2I: {
1102 memnew_placement(_data._mem, Rect2i(*reinterpret_cast<const Rect2i *>(p_variant._data._mem)));
1103 } break;
1104 case TRANSFORM2D: {
1105 _data._transform2d = (Transform2D *)Pools::_bucket_small.alloc();
1106 memnew_placement(_data._transform2d, Transform2D(*p_variant._data._transform2d));
1107 } break;
1108 case VECTOR3: {
1109 memnew_placement(_data._mem, Vector3(*reinterpret_cast<const Vector3 *>(p_variant._data._mem)));
1110 } break;
1111 case VECTOR3I: {
1112 memnew_placement(_data._mem, Vector3i(*reinterpret_cast<const Vector3i *>(p_variant._data._mem)));
1113 } break;
1114 case VECTOR4: {
1115 memnew_placement(_data._mem, Vector4(*reinterpret_cast<const Vector4 *>(p_variant._data._mem)));
1116 } break;
1117 case VECTOR4I: {
1118 memnew_placement(_data._mem, Vector4i(*reinterpret_cast<const Vector4i *>(p_variant._data._mem)));
1119 } break;
1120 case PLANE: {
1121 memnew_placement(_data._mem, Plane(*reinterpret_cast<const Plane *>(p_variant._data._mem)));
1122 } break;
1123 case AABB: {
1124 _data._aabb = (::AABB *)Pools::_bucket_small.alloc();
1125 memnew_placement(_data._aabb, ::AABB(*p_variant._data._aabb));
1126 } break;
1127 case QUATERNION: {
1128 memnew_placement(_data._mem, Quaternion(*reinterpret_cast<const Quaternion *>(p_variant._data._mem)));
1129 } break;
1130 case BASIS: {
1131 _data._basis = (Basis *)Pools::_bucket_medium.alloc();
1132 memnew_placement(_data._basis, Basis(*p_variant._data._basis));
1133 } break;
1134 case TRANSFORM3D: {
1135 _data._transform3d = (Transform3D *)Pools::_bucket_medium.alloc();
1136 memnew_placement(_data._transform3d, Transform3D(*p_variant._data._transform3d));
1137 } break;
1138 case PROJECTION: {
1139 _data._projection = (Projection *)Pools::_bucket_large.alloc();
1140 memnew_placement(_data._projection, Projection(*p_variant._data._projection));
1141 } break;
1142
1143 // Miscellaneous types.
1144 case COLOR: {
1145 memnew_placement(_data._mem, Color(*reinterpret_cast<const Color *>(p_variant._data._mem)));
1146 } break;
1147 case RID: {
1148 memnew_placement(_data._mem, ::RID(*reinterpret_cast<const ::RID *>(p_variant._data._mem)));
1149 } break;
1150 case OBJECT: {
1151 memnew_placement(_data._mem, ObjData);
1152
1153 if (p_variant._get_obj().obj && p_variant._get_obj().id.is_ref_counted()) {
1154 RefCounted *ref_counted = static_cast<RefCounted *>(p_variant._get_obj().obj);
1155 if (!ref_counted->reference()) {
1156 _get_obj().obj = nullptr;
1157 _get_obj().id = ObjectID();
1158 break;
1159 }
1160 }
1161
1162 _get_obj().obj = const_cast<Object *>(p_variant._get_obj().obj);
1163 _get_obj().id = p_variant._get_obj().id;
1164 } break;
1165 case CALLABLE: {
1166 memnew_placement(_data._mem, Callable(*reinterpret_cast<const Callable *>(p_variant._data._mem)));
1167 } break;
1168 case SIGNAL: {
1169 memnew_placement(_data._mem, Signal(*reinterpret_cast<const Signal *>(p_variant._data._mem)));
1170 } break;
1171 case STRING_NAME: {
1172 memnew_placement(_data._mem, StringName(*reinterpret_cast<const StringName *>(p_variant._data._mem)));
1173 } break;
1174 case NODE_PATH: {
1175 memnew_placement(_data._mem, NodePath(*reinterpret_cast<const NodePath *>(p_variant._data._mem)));
1176 } break;
1177 case DICTIONARY: {
1178 memnew_placement(_data._mem, Dictionary(*reinterpret_cast<const Dictionary *>(p_variant._data._mem)));
1179 } break;
1180 case ARRAY: {
1181 memnew_placement(_data._mem, Array(*reinterpret_cast<const Array *>(p_variant._data._mem)));
1182 } break;
1183
1184 // Arrays.
1185 case PACKED_BYTE_ARRAY: {
1186 _data.packed_array = static_cast<PackedArrayRef<uint8_t> *>(p_variant._data.packed_array)->reference();
1187 if (!_data.packed_array) {
1188 _data.packed_array = PackedArrayRef<uint8_t>::create();
1189 }
1190 } break;
1191 case PACKED_INT32_ARRAY: {
1192 _data.packed_array = static_cast<PackedArrayRef<int32_t> *>(p_variant._data.packed_array)->reference();
1193 if (!_data.packed_array) {
1194 _data.packed_array = PackedArrayRef<int32_t>::create();
1195 }
1196 } break;
1197 case PACKED_INT64_ARRAY: {
1198 _data.packed_array = static_cast<PackedArrayRef<int64_t> *>(p_variant._data.packed_array)->reference();
1199 if (!_data.packed_array) {
1200 _data.packed_array = PackedArrayRef<int64_t>::create();
1201 }
1202 } break;
1203 case PACKED_FLOAT32_ARRAY: {
1204 _data.packed_array = static_cast<PackedArrayRef<float> *>(p_variant._data.packed_array)->reference();
1205 if (!_data.packed_array) {
1206 _data.packed_array = PackedArrayRef<float>::create();
1207 }
1208 } break;
1209 case PACKED_FLOAT64_ARRAY: {
1210 _data.packed_array = static_cast<PackedArrayRef<double> *>(p_variant._data.packed_array)->reference();
1211 if (!_data.packed_array) {
1212 _data.packed_array = PackedArrayRef<double>::create();
1213 }
1214 } break;
1215 case PACKED_STRING_ARRAY: {
1216 _data.packed_array = static_cast<PackedArrayRef<String> *>(p_variant._data.packed_array)->reference();
1217 if (!_data.packed_array) {
1218 _data.packed_array = PackedArrayRef<String>::create();
1219 }
1220 } break;
1221 case PACKED_VECTOR2_ARRAY: {
1222 _data.packed_array = static_cast<PackedArrayRef<Vector2> *>(p_variant._data.packed_array)->reference();
1223 if (!_data.packed_array) {
1224 _data.packed_array = PackedArrayRef<Vector2>::create();
1225 }
1226 } break;
1227 case PACKED_VECTOR3_ARRAY: {
1228 _data.packed_array = static_cast<PackedArrayRef<Vector3> *>(p_variant._data.packed_array)->reference();
1229 if (!_data.packed_array) {
1230 _data.packed_array = PackedArrayRef<Vector3>::create();
1231 }
1232 } break;
1233 case PACKED_COLOR_ARRAY: {
1234 _data.packed_array = static_cast<PackedArrayRef<Color> *>(p_variant._data.packed_array)->reference();
1235 if (!_data.packed_array) {
1236 _data.packed_array = PackedArrayRef<Color>::create();
1237 }
1238 } break;
1239 default: {
1240 }
1241 }
1242}
1243
1244void Variant::zero() {
1245 switch (type) {
1246 case NIL:
1247 break;
1248 case BOOL:
1249 this->_data._bool = false;
1250 break;
1251 case INT:
1252 this->_data._int = 0;
1253 break;
1254 case FLOAT:
1255 this->_data._float = 0;
1256 break;
1257
1258 case VECTOR2:
1259 *reinterpret_cast<Vector2 *>(this->_data._mem) = Vector2();
1260 break;
1261 case VECTOR2I:
1262 *reinterpret_cast<Vector2i *>(this->_data._mem) = Vector2i();
1263 break;
1264 case RECT2:
1265 *reinterpret_cast<Rect2 *>(this->_data._mem) = Rect2();
1266 break;
1267 case RECT2I:
1268 *reinterpret_cast<Rect2i *>(this->_data._mem) = Rect2i();
1269 break;
1270 case VECTOR3:
1271 *reinterpret_cast<Vector3 *>(this->_data._mem) = Vector3();
1272 break;
1273 case VECTOR3I:
1274 *reinterpret_cast<Vector3i *>(this->_data._mem) = Vector3i();
1275 break;
1276 case VECTOR4:
1277 *reinterpret_cast<Vector4 *>(this->_data._mem) = Vector4();
1278 break;
1279 case VECTOR4I:
1280 *reinterpret_cast<Vector4i *>(this->_data._mem) = Vector4i();
1281 break;
1282 case PLANE:
1283 *reinterpret_cast<Plane *>(this->_data._mem) = Plane();
1284 break;
1285 case QUATERNION:
1286 *reinterpret_cast<Quaternion *>(this->_data._mem) = Quaternion();
1287 break;
1288
1289 case COLOR:
1290 *reinterpret_cast<Color *>(this->_data._mem) = Color();
1291 break;
1292
1293 default:
1294 this->clear();
1295 break;
1296 }
1297}
1298
1299void Variant::_clear_internal() {
1300 switch (type) {
1301 case STRING: {
1302 reinterpret_cast<String *>(_data._mem)->~String();
1303 } break;
1304
1305 // Math types.
1306 case TRANSFORM2D: {
1307 if (_data._transform2d) {
1308 _data._transform2d->~Transform2D();
1309 Pools::_bucket_small.free((Pools::BucketSmall *)_data._transform2d);
1310 _data._transform2d = nullptr;
1311 }
1312 } break;
1313 case AABB: {
1314 if (_data._aabb) {
1315 _data._aabb->~AABB();
1316 Pools::_bucket_small.free((Pools::BucketSmall *)_data._aabb);
1317 _data._aabb = nullptr;
1318 }
1319 } break;
1320 case BASIS: {
1321 if (_data._basis) {
1322 _data._basis->~Basis();
1323 Pools::_bucket_medium.free((Pools::BucketMedium *)_data._basis);
1324 _data._basis = nullptr;
1325 }
1326 } break;
1327 case TRANSFORM3D: {
1328 if (_data._transform3d) {
1329 _data._transform3d->~Transform3D();
1330 Pools::_bucket_medium.free((Pools::BucketMedium *)_data._transform3d);
1331 _data._transform3d = nullptr;
1332 }
1333 } break;
1334 case PROJECTION: {
1335 if (_data._projection) {
1336 _data._projection->~Projection();
1337 Pools::_bucket_large.free((Pools::BucketLarge *)_data._projection);
1338 _data._projection = nullptr;
1339 }
1340 } break;
1341
1342 // Miscellaneous types.
1343 case STRING_NAME: {
1344 reinterpret_cast<StringName *>(_data._mem)->~StringName();
1345 } break;
1346 case NODE_PATH: {
1347 reinterpret_cast<NodePath *>(_data._mem)->~NodePath();
1348 } break;
1349 case OBJECT: {
1350 if (_get_obj().id.is_ref_counted()) {
1351 // We are safe that there is a reference here.
1352 RefCounted *ref_counted = static_cast<RefCounted *>(_get_obj().obj);
1353 if (ref_counted->unreference()) {
1354 memdelete(ref_counted);
1355 }
1356 }
1357 _get_obj().obj = nullptr;
1358 _get_obj().id = ObjectID();
1359 } break;
1360 case RID: {
1361 // Not much need probably.
1362 // HACK: Can't seem to use destructor + scoping operator, so hack.
1363 typedef ::RID RID_Class;
1364 reinterpret_cast<RID_Class *>(_data._mem)->~RID_Class();
1365 } break;
1366 case CALLABLE: {
1367 reinterpret_cast<Callable *>(_data._mem)->~Callable();
1368 } break;
1369 case SIGNAL: {
1370 reinterpret_cast<Signal *>(_data._mem)->~Signal();
1371 } break;
1372 case DICTIONARY: {
1373 reinterpret_cast<Dictionary *>(_data._mem)->~Dictionary();
1374 } break;
1375 case ARRAY: {
1376 reinterpret_cast<Array *>(_data._mem)->~Array();
1377 } break;
1378
1379 // Arrays.
1380 case PACKED_BYTE_ARRAY: {
1381 PackedArrayRefBase::destroy(_data.packed_array);
1382 } break;
1383 case PACKED_INT32_ARRAY: {
1384 PackedArrayRefBase::destroy(_data.packed_array);
1385 } break;
1386 case PACKED_INT64_ARRAY: {
1387 PackedArrayRefBase::destroy(_data.packed_array);
1388 } break;
1389 case PACKED_FLOAT32_ARRAY: {
1390 PackedArrayRefBase::destroy(_data.packed_array);
1391 } break;
1392 case PACKED_FLOAT64_ARRAY: {
1393 PackedArrayRefBase::destroy(_data.packed_array);
1394 } break;
1395 case PACKED_STRING_ARRAY: {
1396 PackedArrayRefBase::destroy(_data.packed_array);
1397 } break;
1398 case PACKED_VECTOR2_ARRAY: {
1399 PackedArrayRefBase::destroy(_data.packed_array);
1400 } break;
1401 case PACKED_VECTOR3_ARRAY: {
1402 PackedArrayRefBase::destroy(_data.packed_array);
1403 } break;
1404 case PACKED_COLOR_ARRAY: {
1405 PackedArrayRefBase::destroy(_data.packed_array);
1406 } break;
1407 default: {
1408 // Not needed, there is no point. The following do not allocate memory:
1409 // VECTOR2, VECTOR3, RECT2, PLANE, QUATERNION, COLOR.
1410 }
1411 }
1412}
1413
1414Variant::operator signed int() const {
1415 switch (type) {
1416 case NIL:
1417 return 0;
1418 case BOOL:
1419 return _data._bool ? 1 : 0;
1420 case INT:
1421 return _data._int;
1422 case FLOAT:
1423 return _data._float;
1424 case STRING:
1425 return operator String().to_int();
1426 default: {
1427 return 0;
1428 }
1429 }
1430}
1431
1432Variant::operator unsigned int() const {
1433 switch (type) {
1434 case NIL:
1435 return 0;
1436 case BOOL:
1437 return _data._bool ? 1 : 0;
1438 case INT:
1439 return _data._int;
1440 case FLOAT:
1441 return _data._float;
1442 case STRING:
1443 return operator String().to_int();
1444 default: {
1445 return 0;
1446 }
1447 }
1448}
1449
1450Variant::operator int64_t() const {
1451 switch (type) {
1452 case NIL:
1453 return 0;
1454 case BOOL:
1455 return _data._bool ? 1 : 0;
1456 case INT:
1457 return _data._int;
1458 case FLOAT:
1459 return _data._float;
1460 case STRING:
1461 return operator String().to_int();
1462 default: {
1463 return 0;
1464 }
1465 }
1466}
1467
1468Variant::operator uint64_t() const {
1469 switch (type) {
1470 case NIL:
1471 return 0;
1472 case BOOL:
1473 return _data._bool ? 1 : 0;
1474 case INT:
1475 return _data._int;
1476 case FLOAT:
1477 return _data._float;
1478 case STRING:
1479 return operator String().to_int();
1480 default: {
1481 return 0;
1482 }
1483 }
1484}
1485
1486Variant::operator ObjectID() const {
1487 if (type == INT) {
1488 return ObjectID(_data._int);
1489 } else if (type == OBJECT) {
1490 return _get_obj().id;
1491 } else {
1492 return ObjectID();
1493 }
1494}
1495
1496#ifdef NEED_LONG_INT
1497Variant::operator signed long() const {
1498 switch (type) {
1499 case NIL:
1500 return 0;
1501 case BOOL:
1502 return _data._bool ? 1 : 0;
1503 case INT:
1504 return _data._int;
1505 case FLOAT:
1506 return _data._float;
1507 case STRING:
1508 return operator String().to_int();
1509 default: {
1510 return 0;
1511 }
1512 }
1513
1514 return 0;
1515}
1516
1517Variant::operator unsigned long() const {
1518 switch (type) {
1519 case NIL:
1520 return 0;
1521 case BOOL:
1522 return _data._bool ? 1 : 0;
1523 case INT:
1524 return _data._int;
1525 case FLOAT:
1526 return _data._float;
1527 case STRING:
1528 return operator String().to_int();
1529 default: {
1530 return 0;
1531 }
1532 }
1533
1534 return 0;
1535}
1536#endif
1537
1538Variant::operator signed short() const {
1539 switch (type) {
1540 case NIL:
1541 return 0;
1542 case BOOL:
1543 return _data._bool ? 1 : 0;
1544 case INT:
1545 return _data._int;
1546 case FLOAT:
1547 return _data._float;
1548 case STRING:
1549 return operator String().to_int();
1550 default: {
1551 return 0;
1552 }
1553 }
1554}
1555
1556Variant::operator unsigned short() const {
1557 switch (type) {
1558 case NIL:
1559 return 0;
1560 case BOOL:
1561 return _data._bool ? 1 : 0;
1562 case INT:
1563 return _data._int;
1564 case FLOAT:
1565 return _data._float;
1566 case STRING:
1567 return operator String().to_int();
1568 default: {
1569 return 0;
1570 }
1571 }
1572}
1573
1574Variant::operator signed char() const {
1575 switch (type) {
1576 case NIL:
1577 return 0;
1578 case BOOL:
1579 return _data._bool ? 1 : 0;
1580 case INT:
1581 return _data._int;
1582 case FLOAT:
1583 return _data._float;
1584 case STRING:
1585 return operator String().to_int();
1586 default: {
1587 return 0;
1588 }
1589 }
1590}
1591
1592Variant::operator unsigned char() const {
1593 switch (type) {
1594 case NIL:
1595 return 0;
1596 case BOOL:
1597 return _data._bool ? 1 : 0;
1598 case INT:
1599 return _data._int;
1600 case FLOAT:
1601 return _data._float;
1602 case STRING:
1603 return operator String().to_int();
1604 default: {
1605 return 0;
1606 }
1607 }
1608}
1609
1610Variant::operator char32_t() const {
1611 return operator unsigned int();
1612}
1613
1614Variant::operator float() const {
1615 switch (type) {
1616 case NIL:
1617 return 0;
1618 case BOOL:
1619 return _data._bool ? 1.0 : 0.0;
1620 case INT:
1621 return (float)_data._int;
1622 case FLOAT:
1623 return _data._float;
1624 case STRING:
1625 return operator String().to_float();
1626 default: {
1627 return 0;
1628 }
1629 }
1630}
1631
1632Variant::operator double() const {
1633 switch (type) {
1634 case NIL:
1635 return 0;
1636 case BOOL:
1637 return _data._bool ? 1.0 : 0.0;
1638 case INT:
1639 return (double)_data._int;
1640 case FLOAT:
1641 return _data._float;
1642 case STRING:
1643 return operator String().to_float();
1644 default: {
1645 return 0;
1646 }
1647 }
1648}
1649
1650Variant::operator StringName() const {
1651 if (type == STRING_NAME) {
1652 return *reinterpret_cast<const StringName *>(_data._mem);
1653 } else if (type == STRING) {
1654 return *reinterpret_cast<const String *>(_data._mem);
1655 }
1656
1657 return StringName();
1658}
1659
1660struct _VariantStrPair {
1661 String key;
1662 String value;
1663
1664 bool operator<(const _VariantStrPair &p) const {
1665 return key < p.key;
1666 }
1667};
1668
1669Variant::operator String() const {
1670 return stringify(0);
1671}
1672
1673String stringify_variant_clean(const Variant p_variant, int recursion_count) {
1674 String s = p_variant.stringify(recursion_count);
1675
1676 // Wrap strings in quotes to avoid ambiguity.
1677 switch (p_variant.get_type()) {
1678 case Variant::STRING: {
1679 s = s.c_escape().quote();
1680 } break;
1681 case Variant::STRING_NAME: {
1682 s = "&" + s.c_escape().quote();
1683 } break;
1684 case Variant::NODE_PATH: {
1685 s = "^" + s.c_escape().quote();
1686 } break;
1687 default: {
1688 } break;
1689 }
1690
1691 return s;
1692}
1693
1694template <class T>
1695String stringify_vector(const T &vec, int recursion_count) {
1696 String str("[");
1697 for (int i = 0; i < vec.size(); i++) {
1698 if (i > 0) {
1699 str += ", ";
1700 }
1701
1702 str += stringify_variant_clean(vec[i], recursion_count);
1703 }
1704 str += "]";
1705 return str;
1706}
1707
1708String Variant::stringify(int recursion_count) const {
1709 switch (type) {
1710 case NIL:
1711 return "<null>";
1712 case BOOL:
1713 return _data._bool ? "true" : "false";
1714 case INT:
1715 return itos(_data._int);
1716 case FLOAT:
1717 return rtos(_data._float);
1718 case STRING:
1719 return *reinterpret_cast<const String *>(_data._mem);
1720 case VECTOR2:
1721 return operator Vector2();
1722 case VECTOR2I:
1723 return operator Vector2i();
1724 case RECT2:
1725 return operator Rect2();
1726 case RECT2I:
1727 return operator Rect2i();
1728 case TRANSFORM2D:
1729 return operator Transform2D();
1730 case VECTOR3:
1731 return operator Vector3();
1732 case VECTOR3I:
1733 return operator Vector3i();
1734 case VECTOR4:
1735 return operator Vector4();
1736 case VECTOR4I:
1737 return operator Vector4i();
1738 case PLANE:
1739 return operator Plane();
1740 case AABB:
1741 return operator ::AABB();
1742 case QUATERNION:
1743 return operator Quaternion();
1744 case BASIS:
1745 return operator Basis();
1746 case TRANSFORM3D:
1747 return operator Transform3D();
1748 case PROJECTION:
1749 return operator Projection();
1750 case STRING_NAME:
1751 return operator StringName();
1752 case NODE_PATH:
1753 return operator NodePath();
1754 case COLOR:
1755 return operator Color();
1756 case DICTIONARY: {
1757 ERR_FAIL_COND_V_MSG(recursion_count > MAX_RECURSION, "{ ... }", "Maximum dictionary recursion reached!");
1758 recursion_count++;
1759
1760 const Dictionary &d = *reinterpret_cast<const Dictionary *>(_data._mem);
1761
1762 // Add leading and trailing space to Dictionary printing. This distinguishes it
1763 // from array printing on fonts that have similar-looking {} and [] characters.
1764 String str("{ ");
1765 List<Variant> keys;
1766 d.get_key_list(&keys);
1767
1768 Vector<_VariantStrPair> pairs;
1769
1770 for (List<Variant>::Element *E = keys.front(); E; E = E->next()) {
1771 _VariantStrPair sp;
1772 sp.key = stringify_variant_clean(E->get(), recursion_count);
1773 sp.value = stringify_variant_clean(d[E->get()], recursion_count);
1774
1775 pairs.push_back(sp);
1776 }
1777
1778 for (int i = 0; i < pairs.size(); i++) {
1779 if (i > 0) {
1780 str += ", ";
1781 }
1782 str += pairs[i].key + ": " + pairs[i].value;
1783 }
1784 str += " }";
1785
1786 return str;
1787 }
1788 // Packed arrays cannot contain recursive structures, the recursion_count increment is not needed.
1789 case PACKED_VECTOR2_ARRAY: {
1790 return stringify_vector(operator Vector<Vector2>(), recursion_count);
1791 }
1792 case PACKED_VECTOR3_ARRAY: {
1793 return stringify_vector(operator Vector<Vector3>(), recursion_count);
1794 }
1795 case PACKED_COLOR_ARRAY: {
1796 return stringify_vector(operator Vector<Color>(), recursion_count);
1797 }
1798 case PACKED_STRING_ARRAY: {
1799 return stringify_vector(operator Vector<String>(), recursion_count);
1800 }
1801 case PACKED_BYTE_ARRAY: {
1802 return stringify_vector(operator Vector<uint8_t>(), recursion_count);
1803 }
1804 case PACKED_INT32_ARRAY: {
1805 return stringify_vector(operator Vector<int32_t>(), recursion_count);
1806 }
1807 case PACKED_INT64_ARRAY: {
1808 return stringify_vector(operator Vector<int64_t>(), recursion_count);
1809 }
1810 case PACKED_FLOAT32_ARRAY: {
1811 return stringify_vector(operator Vector<float>(), recursion_count);
1812 }
1813 case PACKED_FLOAT64_ARRAY: {
1814 return stringify_vector(operator Vector<double>(), recursion_count);
1815 }
1816 case ARRAY: {
1817 ERR_FAIL_COND_V_MSG(recursion_count > MAX_RECURSION, "[...]", "Maximum array recursion reached!");
1818 recursion_count++;
1819
1820 return stringify_vector(operator Array(), recursion_count);
1821 }
1822 case OBJECT: {
1823 if (_get_obj().obj) {
1824 if (!_get_obj().id.is_ref_counted() && ObjectDB::get_instance(_get_obj().id) == nullptr) {
1825 return "<Freed Object>";
1826 }
1827
1828 return _get_obj().obj->to_string();
1829 } else {
1830 return "<Object#null>";
1831 }
1832 }
1833 case CALLABLE: {
1834 const Callable &c = *reinterpret_cast<const Callable *>(_data._mem);
1835 return c;
1836 }
1837 case SIGNAL: {
1838 const Signal &s = *reinterpret_cast<const Signal *>(_data._mem);
1839 return s;
1840 }
1841 case RID: {
1842 const ::RID &s = *reinterpret_cast<const ::RID *>(_data._mem);
1843 return "RID(" + itos(s.get_id()) + ")";
1844 }
1845 default: {
1846 return "<" + get_type_name(type) + ">";
1847 }
1848 }
1849}
1850
1851String Variant::to_json_string() const {
1852 return JSON::stringify(*this);
1853}
1854
1855Variant::operator Vector2() const {
1856 if (type == VECTOR2) {
1857 return *reinterpret_cast<const Vector2 *>(_data._mem);
1858 } else if (type == VECTOR2I) {
1859 return *reinterpret_cast<const Vector2i *>(_data._mem);
1860 } else if (type == VECTOR3) {
1861 return Vector2(reinterpret_cast<const Vector3 *>(_data._mem)->x, reinterpret_cast<const Vector3 *>(_data._mem)->y);
1862 } else if (type == VECTOR3I) {
1863 return Vector2(reinterpret_cast<const Vector3i *>(_data._mem)->x, reinterpret_cast<const Vector3i *>(_data._mem)->y);
1864 } else if (type == VECTOR4) {
1865 return Vector2(reinterpret_cast<const Vector4 *>(_data._mem)->x, reinterpret_cast<const Vector4 *>(_data._mem)->y);
1866 } else if (type == VECTOR4I) {
1867 return Vector2(reinterpret_cast<const Vector4i *>(_data._mem)->x, reinterpret_cast<const Vector4i *>(_data._mem)->y);
1868 } else {
1869 return Vector2();
1870 }
1871}
1872
1873Variant::operator Vector2i() const {
1874 if (type == VECTOR2I) {
1875 return *reinterpret_cast<const Vector2i *>(_data._mem);
1876 } else if (type == VECTOR2) {
1877 return *reinterpret_cast<const Vector2 *>(_data._mem);
1878 } else if (type == VECTOR3) {
1879 return Vector2(reinterpret_cast<const Vector3 *>(_data._mem)->x, reinterpret_cast<const Vector3 *>(_data._mem)->y);
1880 } else if (type == VECTOR3I) {
1881 return Vector2(reinterpret_cast<const Vector3i *>(_data._mem)->x, reinterpret_cast<const Vector3i *>(_data._mem)->y);
1882 } else if (type == VECTOR4) {
1883 return Vector2(reinterpret_cast<const Vector4 *>(_data._mem)->x, reinterpret_cast<const Vector4 *>(_data._mem)->y);
1884 } else if (type == VECTOR4I) {
1885 return Vector2(reinterpret_cast<const Vector4i *>(_data._mem)->x, reinterpret_cast<const Vector4i *>(_data._mem)->y);
1886 } else {
1887 return Vector2i();
1888 }
1889}
1890
1891Variant::operator Rect2() const {
1892 if (type == RECT2) {
1893 return *reinterpret_cast<const Rect2 *>(_data._mem);
1894 } else if (type == RECT2I) {
1895 return *reinterpret_cast<const Rect2i *>(_data._mem);
1896 } else {
1897 return Rect2();
1898 }
1899}
1900
1901Variant::operator Rect2i() const {
1902 if (type == RECT2I) {
1903 return *reinterpret_cast<const Rect2i *>(_data._mem);
1904 } else if (type == RECT2) {
1905 return *reinterpret_cast<const Rect2 *>(_data._mem);
1906 } else {
1907 return Rect2i();
1908 }
1909}
1910
1911Variant::operator Vector3() const {
1912 if (type == VECTOR3) {
1913 return *reinterpret_cast<const Vector3 *>(_data._mem);
1914 } else if (type == VECTOR3I) {
1915 return *reinterpret_cast<const Vector3i *>(_data._mem);
1916 } else if (type == VECTOR2) {
1917 return Vector3(reinterpret_cast<const Vector2 *>(_data._mem)->x, reinterpret_cast<const Vector2 *>(_data._mem)->y, 0.0);
1918 } else if (type == VECTOR2I) {
1919 return Vector3(reinterpret_cast<const Vector2i *>(_data._mem)->x, reinterpret_cast<const Vector2i *>(_data._mem)->y, 0.0);
1920 } else if (type == VECTOR4) {
1921 return Vector3(reinterpret_cast<const Vector4 *>(_data._mem)->x, reinterpret_cast<const Vector4 *>(_data._mem)->y, reinterpret_cast<const Vector4 *>(_data._mem)->z);
1922 } else if (type == VECTOR4I) {
1923 return Vector3(reinterpret_cast<const Vector4i *>(_data._mem)->x, reinterpret_cast<const Vector4i *>(_data._mem)->y, reinterpret_cast<const Vector4i *>(_data._mem)->z);
1924 } else {
1925 return Vector3();
1926 }
1927}
1928
1929Variant::operator Vector3i() const {
1930 if (type == VECTOR3I) {
1931 return *reinterpret_cast<const Vector3i *>(_data._mem);
1932 } else if (type == VECTOR3) {
1933 return *reinterpret_cast<const Vector3 *>(_data._mem);
1934 } else if (type == VECTOR2) {
1935 return Vector3i(reinterpret_cast<const Vector2 *>(_data._mem)->x, reinterpret_cast<const Vector2 *>(_data._mem)->y, 0.0);
1936 } else if (type == VECTOR2I) {
1937 return Vector3i(reinterpret_cast<const Vector2i *>(_data._mem)->x, reinterpret_cast<const Vector2i *>(_data._mem)->y, 0.0);
1938 } else if (type == VECTOR4) {
1939 return Vector3i(reinterpret_cast<const Vector4 *>(_data._mem)->x, reinterpret_cast<const Vector4 *>(_data._mem)->y, reinterpret_cast<const Vector4 *>(_data._mem)->z);
1940 } else if (type == VECTOR4I) {
1941 return Vector3i(reinterpret_cast<const Vector4i *>(_data._mem)->x, reinterpret_cast<const Vector4i *>(_data._mem)->y, reinterpret_cast<const Vector4i *>(_data._mem)->z);
1942 } else {
1943 return Vector3i();
1944 }
1945}
1946
1947Variant::operator Vector4() const {
1948 if (type == VECTOR4) {
1949 return *reinterpret_cast<const Vector4 *>(_data._mem);
1950 } else if (type == VECTOR4I) {
1951 return *reinterpret_cast<const Vector4i *>(_data._mem);
1952 } else if (type == VECTOR2) {
1953 return Vector4(reinterpret_cast<const Vector2 *>(_data._mem)->x, reinterpret_cast<const Vector2 *>(_data._mem)->y, 0.0, 0.0);
1954 } else if (type == VECTOR2I) {
1955 return Vector4(reinterpret_cast<const Vector2i *>(_data._mem)->x, reinterpret_cast<const Vector2i *>(_data._mem)->y, 0.0, 0.0);
1956 } else if (type == VECTOR3) {
1957 return Vector4(reinterpret_cast<const Vector3 *>(_data._mem)->x, reinterpret_cast<const Vector3 *>(_data._mem)->y, reinterpret_cast<const Vector3 *>(_data._mem)->z, 0.0);
1958 } else if (type == VECTOR3I) {
1959 return Vector4(reinterpret_cast<const Vector3i *>(_data._mem)->x, reinterpret_cast<const Vector3i *>(_data._mem)->y, reinterpret_cast<const Vector3i *>(_data._mem)->z, 0.0);
1960 } else {
1961 return Vector4();
1962 }
1963}
1964
1965Variant::operator Vector4i() const {
1966 if (type == VECTOR4I) {
1967 return *reinterpret_cast<const Vector4i *>(_data._mem);
1968 } else if (type == VECTOR4) {
1969 const Vector4 &v4 = *reinterpret_cast<const Vector4 *>(_data._mem);
1970 return Vector4i(v4.x, v4.y, v4.z, v4.w);
1971 } else if (type == VECTOR2) {
1972 return Vector4i(reinterpret_cast<const Vector2 *>(_data._mem)->x, reinterpret_cast<const Vector2 *>(_data._mem)->y, 0.0, 0.0);
1973 } else if (type == VECTOR2I) {
1974 return Vector4i(reinterpret_cast<const Vector2i *>(_data._mem)->x, reinterpret_cast<const Vector2i *>(_data._mem)->y, 0.0, 0.0);
1975 } else if (type == VECTOR3) {
1976 return Vector4i(reinterpret_cast<const Vector3 *>(_data._mem)->x, reinterpret_cast<const Vector3 *>(_data._mem)->y, reinterpret_cast<const Vector3 *>(_data._mem)->z, 0.0);
1977 } else if (type == VECTOR3I) {
1978 return Vector4i(reinterpret_cast<const Vector3i *>(_data._mem)->x, reinterpret_cast<const Vector3i *>(_data._mem)->y, reinterpret_cast<const Vector3i *>(_data._mem)->z, 0.0);
1979 } else {
1980 return Vector4i();
1981 }
1982}
1983
1984Variant::operator Plane() const {
1985 if (type == PLANE) {
1986 return *reinterpret_cast<const Plane *>(_data._mem);
1987 } else {
1988 return Plane();
1989 }
1990}
1991
1992Variant::operator ::AABB() const {
1993 if (type == AABB) {
1994 return *_data._aabb;
1995 } else {
1996 return ::AABB();
1997 }
1998}
1999
2000Variant::operator Basis() const {
2001 if (type == BASIS) {
2002 return *_data._basis;
2003 } else if (type == QUATERNION) {
2004 return *reinterpret_cast<const Quaternion *>(_data._mem);
2005 } else if (type == TRANSFORM3D) { // unexposed in Variant::can_convert?
2006 return _data._transform3d->basis;
2007 } else {
2008 return Basis();
2009 }
2010}
2011
2012Variant::operator Quaternion() const {
2013 if (type == QUATERNION) {
2014 return *reinterpret_cast<const Quaternion *>(_data._mem);
2015 } else if (type == BASIS) {
2016 return *_data._basis;
2017 } else if (type == TRANSFORM3D) {
2018 return _data._transform3d->basis;
2019 } else {
2020 return Quaternion();
2021 }
2022}
2023
2024Variant::operator Transform3D() const {
2025 if (type == TRANSFORM3D) {
2026 return *_data._transform3d;
2027 } else if (type == BASIS) {
2028 return Transform3D(*_data._basis, Vector3());
2029 } else if (type == QUATERNION) {
2030 return Transform3D(Basis(*reinterpret_cast<const Quaternion *>(_data._mem)), Vector3());
2031 } else if (type == TRANSFORM2D) {
2032 const Transform2D &t = *_data._transform2d;
2033 Transform3D m;
2034 m.basis.rows[0][0] = t.columns[0][0];
2035 m.basis.rows[1][0] = t.columns[0][1];
2036 m.basis.rows[0][1] = t.columns[1][0];
2037 m.basis.rows[1][1] = t.columns[1][1];
2038 m.origin[0] = t.columns[2][0];
2039 m.origin[1] = t.columns[2][1];
2040 return m;
2041 } else if (type == PROJECTION) {
2042 return *_data._projection;
2043 } else {
2044 return Transform3D();
2045 }
2046}
2047
2048Variant::operator Projection() const {
2049 if (type == TRANSFORM3D) {
2050 return *_data._transform3d;
2051 } else if (type == BASIS) {
2052 return Transform3D(*_data._basis, Vector3());
2053 } else if (type == QUATERNION) {
2054 return Transform3D(Basis(*reinterpret_cast<const Quaternion *>(_data._mem)), Vector3());
2055 } else if (type == TRANSFORM2D) {
2056 const Transform2D &t = *_data._transform2d;
2057 Transform3D m;
2058 m.basis.rows[0][0] = t.columns[0][0];
2059 m.basis.rows[1][0] = t.columns[0][1];
2060 m.basis.rows[0][1] = t.columns[1][0];
2061 m.basis.rows[1][1] = t.columns[1][1];
2062 m.origin[0] = t.columns[2][0];
2063 m.origin[1] = t.columns[2][1];
2064 return m;
2065 } else if (type == PROJECTION) {
2066 return *_data._projection;
2067 } else {
2068 return Projection();
2069 }
2070}
2071
2072Variant::operator Transform2D() const {
2073 if (type == TRANSFORM2D) {
2074 return *_data._transform2d;
2075 } else if (type == TRANSFORM3D) {
2076 const Transform3D &t = *_data._transform3d;
2077 Transform2D m;
2078 m.columns[0][0] = t.basis.rows[0][0];
2079 m.columns[0][1] = t.basis.rows[1][0];
2080 m.columns[1][0] = t.basis.rows[0][1];
2081 m.columns[1][1] = t.basis.rows[1][1];
2082 m.columns[2][0] = t.origin[0];
2083 m.columns[2][1] = t.origin[1];
2084 return m;
2085 } else {
2086 return Transform2D();
2087 }
2088}
2089
2090Variant::operator Color() const {
2091 if (type == COLOR) {
2092 return *reinterpret_cast<const Color *>(_data._mem);
2093 } else if (type == STRING) {
2094 return Color(operator String());
2095 } else if (type == INT) {
2096 return Color::hex(operator int());
2097 } else {
2098 return Color();
2099 }
2100}
2101
2102Variant::operator NodePath() const {
2103 if (type == NODE_PATH) {
2104 return *reinterpret_cast<const NodePath *>(_data._mem);
2105 } else if (type == STRING) {
2106 return NodePath(operator String());
2107 } else {
2108 return NodePath();
2109 }
2110}
2111
2112Variant::operator ::RID() const {
2113 if (type == RID) {
2114 return *reinterpret_cast<const ::RID *>(_data._mem);
2115 } else if (type == OBJECT && _get_obj().obj == nullptr) {
2116 return ::RID();
2117 } else if (type == OBJECT && _get_obj().obj) {
2118#ifdef DEBUG_ENABLED
2119 if (EngineDebugger::is_active()) {
2120 ERR_FAIL_COND_V_MSG(ObjectDB::get_instance(_get_obj().id) == nullptr, ::RID(), "Invalid pointer (object was freed).");
2121 }
2122#endif
2123 Callable::CallError ce;
2124 Variant ret = _get_obj().obj->callp(CoreStringNames::get_singleton()->get_rid, nullptr, 0, ce);
2125 if (ce.error == Callable::CallError::CALL_OK && ret.get_type() == Variant::RID) {
2126 return ret;
2127 }
2128 return ::RID();
2129 } else {
2130 return ::RID();
2131 }
2132}
2133
2134Variant::operator Object *() const {
2135 if (type == OBJECT) {
2136 return _get_obj().obj;
2137 } else {
2138 return nullptr;
2139 }
2140}
2141
2142Object *Variant::get_validated_object_with_check(bool &r_previously_freed) const {
2143 if (type == OBJECT) {
2144 Object *instance = ObjectDB::get_instance(_get_obj().id);
2145 r_previously_freed = !instance && _get_obj().id != ObjectID();
2146 return instance;
2147 } else {
2148 r_previously_freed = false;
2149 return nullptr;
2150 }
2151}
2152
2153Object *Variant::get_validated_object() const {
2154 if (type == OBJECT) {
2155 return ObjectDB::get_instance(_get_obj().id);
2156 } else {
2157 return nullptr;
2158 }
2159}
2160
2161Variant::operator Dictionary() const {
2162 if (type == DICTIONARY) {
2163 return *reinterpret_cast<const Dictionary *>(_data._mem);
2164 } else {
2165 return Dictionary();
2166 }
2167}
2168
2169Variant::operator Callable() const {
2170 if (type == CALLABLE) {
2171 return *reinterpret_cast<const Callable *>(_data._mem);
2172 } else {
2173 return Callable();
2174 }
2175}
2176
2177Variant::operator Signal() const {
2178 if (type == SIGNAL) {
2179 return *reinterpret_cast<const Signal *>(_data._mem);
2180 } else {
2181 return Signal();
2182 }
2183}
2184
2185template <class DA, class SA>
2186inline DA _convert_array(const SA &p_array) {
2187 DA da;
2188 da.resize(p_array.size());
2189
2190 for (int i = 0; i < p_array.size(); i++) {
2191 da.set(i, Variant(p_array.get(i)));
2192 }
2193
2194 return da;
2195}
2196
2197template <class DA>
2198inline DA _convert_array_from_variant(const Variant &p_variant) {
2199 switch (p_variant.get_type()) {
2200 case Variant::ARRAY: {
2201 return _convert_array<DA, Array>(p_variant.operator Array());
2202 }
2203 case Variant::PACKED_BYTE_ARRAY: {
2204 return _convert_array<DA, Vector<uint8_t>>(p_variant.operator Vector<uint8_t>());
2205 }
2206 case Variant::PACKED_INT32_ARRAY: {
2207 return _convert_array<DA, Vector<int32_t>>(p_variant.operator Vector<int32_t>());
2208 }
2209 case Variant::PACKED_INT64_ARRAY: {
2210 return _convert_array<DA, Vector<int64_t>>(p_variant.operator Vector<int64_t>());
2211 }
2212 case Variant::PACKED_FLOAT32_ARRAY: {
2213 return _convert_array<DA, Vector<float>>(p_variant.operator Vector<float>());
2214 }
2215 case Variant::PACKED_FLOAT64_ARRAY: {
2216 return _convert_array<DA, Vector<double>>(p_variant.operator Vector<double>());
2217 }
2218 case Variant::PACKED_STRING_ARRAY: {
2219 return _convert_array<DA, Vector<String>>(p_variant.operator Vector<String>());
2220 }
2221 case Variant::PACKED_VECTOR2_ARRAY: {
2222 return _convert_array<DA, Vector<Vector2>>(p_variant.operator Vector<Vector2>());
2223 }
2224 case Variant::PACKED_VECTOR3_ARRAY: {
2225 return _convert_array<DA, Vector<Vector3>>(p_variant.operator Vector<Vector3>());
2226 }
2227 case Variant::PACKED_COLOR_ARRAY: {
2228 return _convert_array<DA, Vector<Color>>(p_variant.operator Vector<Color>());
2229 }
2230 default: {
2231 return DA();
2232 }
2233 }
2234}
2235
2236Variant::operator Array() const {
2237 if (type == ARRAY) {
2238 return *reinterpret_cast<const Array *>(_data._mem);
2239 } else {
2240 return _convert_array_from_variant<Array>(*this);
2241 }
2242}
2243
2244Variant::operator Vector<uint8_t>() const {
2245 if (type == PACKED_BYTE_ARRAY) {
2246 return static_cast<PackedArrayRef<uint8_t> *>(_data.packed_array)->array;
2247 } else {
2248 return _convert_array_from_variant<Vector<uint8_t>>(*this);
2249 }
2250}
2251
2252Variant::operator Vector<int32_t>() const {
2253 if (type == PACKED_INT32_ARRAY) {
2254 return static_cast<PackedArrayRef<int32_t> *>(_data.packed_array)->array;
2255 } else {
2256 return _convert_array_from_variant<Vector<int>>(*this);
2257 }
2258}
2259
2260Variant::operator Vector<int64_t>() const {
2261 if (type == PACKED_INT64_ARRAY) {
2262 return static_cast<PackedArrayRef<int64_t> *>(_data.packed_array)->array;
2263 } else {
2264 return _convert_array_from_variant<Vector<int64_t>>(*this);
2265 }
2266}
2267
2268Variant::operator Vector<float>() const {
2269 if (type == PACKED_FLOAT32_ARRAY) {
2270 return static_cast<PackedArrayRef<float> *>(_data.packed_array)->array;
2271 } else {
2272 return _convert_array_from_variant<Vector<float>>(*this);
2273 }
2274}
2275
2276Variant::operator Vector<double>() const {
2277 if (type == PACKED_FLOAT64_ARRAY) {
2278 return static_cast<PackedArrayRef<double> *>(_data.packed_array)->array;
2279 } else {
2280 return _convert_array_from_variant<Vector<double>>(*this);
2281 }
2282}
2283
2284Variant::operator Vector<String>() const {
2285 if (type == PACKED_STRING_ARRAY) {
2286 return static_cast<PackedArrayRef<String> *>(_data.packed_array)->array;
2287 } else {
2288 return _convert_array_from_variant<Vector<String>>(*this);
2289 }
2290}
2291
2292Variant::operator Vector<Vector3>() const {
2293 if (type == PACKED_VECTOR3_ARRAY) {
2294 return static_cast<PackedArrayRef<Vector3> *>(_data.packed_array)->array;
2295 } else {
2296 return _convert_array_from_variant<Vector<Vector3>>(*this);
2297 }
2298}
2299
2300Variant::operator Vector<Vector2>() const {
2301 if (type == PACKED_VECTOR2_ARRAY) {
2302 return static_cast<PackedArrayRef<Vector2> *>(_data.packed_array)->array;
2303 } else {
2304 return _convert_array_from_variant<Vector<Vector2>>(*this);
2305 }
2306}
2307
2308Variant::operator Vector<Color>() const {
2309 if (type == PACKED_COLOR_ARRAY) {
2310 return static_cast<PackedArrayRef<Color> *>(_data.packed_array)->array;
2311 } else {
2312 return _convert_array_from_variant<Vector<Color>>(*this);
2313 }
2314}
2315
2316/* helpers */
2317
2318Variant::operator Vector<::RID>() const {
2319 Array va = operator Array();
2320 Vector<::RID> rids;
2321 rids.resize(va.size());
2322 for (int i = 0; i < rids.size(); i++) {
2323 rids.write[i] = va[i];
2324 }
2325 return rids;
2326}
2327
2328Variant::operator Vector<Plane>() const {
2329 Array va = operator Array();
2330 Vector<Plane> planes;
2331 int va_size = va.size();
2332 if (va_size == 0) {
2333 return planes;
2334 }
2335
2336 planes.resize(va_size);
2337 Plane *w = planes.ptrw();
2338
2339 for (int i = 0; i < va_size; i++) {
2340 w[i] = va[i];
2341 }
2342
2343 return planes;
2344}
2345
2346Variant::operator Vector<Face3>() const {
2347 Vector<Vector3> va = operator Vector<Vector3>();
2348 Vector<Face3> faces;
2349 int va_size = va.size();
2350 if (va_size == 0) {
2351 return faces;
2352 }
2353
2354 faces.resize(va_size / 3);
2355 Face3 *w = faces.ptrw();
2356 const Vector3 *r = va.ptr();
2357
2358 for (int i = 0; i < va_size; i++) {
2359 w[i / 3].vertex[i % 3] = r[i];
2360 }
2361
2362 return faces;
2363}
2364
2365Variant::operator Vector<Variant>() const {
2366 Array va = operator Array();
2367 Vector<Variant> variants;
2368 int va_size = va.size();
2369 if (va_size == 0) {
2370 return variants;
2371 }
2372
2373 variants.resize(va_size);
2374 Variant *w = variants.ptrw();
2375 for (int i = 0; i < va_size; i++) {
2376 w[i] = va[i];
2377 }
2378
2379 return variants;
2380}
2381
2382Variant::operator Vector<StringName>() const {
2383 Vector<String> from = operator Vector<String>();
2384 Vector<StringName> to;
2385 int len = from.size();
2386 to.resize(len);
2387 for (int i = 0; i < len; i++) {
2388 to.write[i] = from[i];
2389 }
2390 return to;
2391}
2392
2393Variant::operator Side() const {
2394 return (Side) operator int();
2395}
2396
2397Variant::operator Orientation() const {
2398 return (Orientation) operator int();
2399}
2400
2401Variant::operator IPAddress() const {
2402 if (type == PACKED_FLOAT32_ARRAY || type == PACKED_INT32_ARRAY || type == PACKED_FLOAT64_ARRAY || type == PACKED_INT64_ARRAY || type == PACKED_BYTE_ARRAY) {
2403 Vector<int> addr = operator Vector<int>();
2404 if (addr.size() == 4) {
2405 return IPAddress(addr.get(0), addr.get(1), addr.get(2), addr.get(3));
2406 }
2407 }
2408
2409 return IPAddress(operator String());
2410}
2411
2412Variant::Variant(bool p_bool) {
2413 type = BOOL;
2414 _data._bool = p_bool;
2415}
2416
2417Variant::Variant(signed int p_int) {
2418 type = INT;
2419 _data._int = p_int;
2420}
2421
2422Variant::Variant(unsigned int p_int) {
2423 type = INT;
2424 _data._int = p_int;
2425}
2426
2427#ifdef NEED_LONG_INT
2428
2429Variant::Variant(signed long p_int) {
2430 type = INT;
2431 _data._int = p_int;
2432}
2433
2434Variant::Variant(unsigned long p_int) {
2435 type = INT;
2436 _data._int = p_int;
2437}
2438#endif
2439
2440Variant::Variant(int64_t p_int) {
2441 type = INT;
2442 _data._int = p_int;
2443}
2444
2445Variant::Variant(uint64_t p_int) {
2446 type = INT;
2447 _data._int = p_int;
2448}
2449
2450Variant::Variant(signed short p_short) {
2451 type = INT;
2452 _data._int = p_short;
2453}
2454
2455Variant::Variant(unsigned short p_short) {
2456 type = INT;
2457 _data._int = p_short;
2458}
2459
2460Variant::Variant(signed char p_char) {
2461 type = INT;
2462 _data._int = p_char;
2463}
2464
2465Variant::Variant(unsigned char p_char) {
2466 type = INT;
2467 _data._int = p_char;
2468}
2469
2470Variant::Variant(float p_float) {
2471 type = FLOAT;
2472 _data._float = p_float;
2473}
2474
2475Variant::Variant(double p_double) {
2476 type = FLOAT;
2477 _data._float = p_double;
2478}
2479
2480Variant::Variant(const ObjectID &p_id) {
2481 type = INT;
2482 _data._int = p_id;
2483}
2484
2485Variant::Variant(const StringName &p_string) {
2486 type = STRING_NAME;
2487 memnew_placement(_data._mem, StringName(p_string));
2488}
2489
2490Variant::Variant(const String &p_string) {
2491 type = STRING;
2492 memnew_placement(_data._mem, String(p_string));
2493}
2494
2495Variant::Variant(const char *const p_cstring) {
2496 type = STRING;
2497 memnew_placement(_data._mem, String((const char *)p_cstring));
2498}
2499
2500Variant::Variant(const char32_t *p_wstring) {
2501 type = STRING;
2502 memnew_placement(_data._mem, String(p_wstring));
2503}
2504
2505Variant::Variant(const Vector3 &p_vector3) {
2506 type = VECTOR3;
2507 memnew_placement(_data._mem, Vector3(p_vector3));
2508}
2509
2510Variant::Variant(const Vector3i &p_vector3i) {
2511 type = VECTOR3I;
2512 memnew_placement(_data._mem, Vector3i(p_vector3i));
2513}
2514
2515Variant::Variant(const Vector4 &p_vector4) {
2516 type = VECTOR4;
2517 memnew_placement(_data._mem, Vector4(p_vector4));
2518}
2519
2520Variant::Variant(const Vector4i &p_vector4i) {
2521 type = VECTOR4I;
2522 memnew_placement(_data._mem, Vector4i(p_vector4i));
2523}
2524
2525Variant::Variant(const Vector2 &p_vector2) {
2526 type = VECTOR2;
2527 memnew_placement(_data._mem, Vector2(p_vector2));
2528}
2529
2530Variant::Variant(const Vector2i &p_vector2i) {
2531 type = VECTOR2I;
2532 memnew_placement(_data._mem, Vector2i(p_vector2i));
2533}
2534
2535Variant::Variant(const Rect2 &p_rect2) {
2536 type = RECT2;
2537 memnew_placement(_data._mem, Rect2(p_rect2));
2538}
2539
2540Variant::Variant(const Rect2i &p_rect2i) {
2541 type = RECT2I;
2542 memnew_placement(_data._mem, Rect2i(p_rect2i));
2543}
2544
2545Variant::Variant(const Plane &p_plane) {
2546 type = PLANE;
2547 memnew_placement(_data._mem, Plane(p_plane));
2548}
2549
2550Variant::Variant(const ::AABB &p_aabb) {
2551 type = AABB;
2552 _data._aabb = (::AABB *)Pools::_bucket_small.alloc();
2553 memnew_placement(_data._aabb, ::AABB(p_aabb));
2554}
2555
2556Variant::Variant(const Basis &p_matrix) {
2557 type = BASIS;
2558 _data._basis = (Basis *)Pools::_bucket_medium.alloc();
2559 memnew_placement(_data._basis, Basis(p_matrix));
2560}
2561
2562Variant::Variant(const Quaternion &p_quaternion) {
2563 type = QUATERNION;
2564 memnew_placement(_data._mem, Quaternion(p_quaternion));
2565}
2566
2567Variant::Variant(const Transform3D &p_transform) {
2568 type = TRANSFORM3D;
2569 _data._transform3d = (Transform3D *)Pools::_bucket_medium.alloc();
2570 memnew_placement(_data._transform3d, Transform3D(p_transform));
2571}
2572
2573Variant::Variant(const Projection &pp_projection) {
2574 type = PROJECTION;
2575 _data._projection = (Projection *)Pools::_bucket_large.alloc();
2576 memnew_placement(_data._projection, Projection(pp_projection));
2577}
2578
2579Variant::Variant(const Transform2D &p_transform) {
2580 type = TRANSFORM2D;
2581 _data._transform2d = (Transform2D *)Pools::_bucket_small.alloc();
2582 memnew_placement(_data._transform2d, Transform2D(p_transform));
2583}
2584
2585Variant::Variant(const Color &p_color) {
2586 type = COLOR;
2587 memnew_placement(_data._mem, Color(p_color));
2588}
2589
2590Variant::Variant(const NodePath &p_node_path) {
2591 type = NODE_PATH;
2592 memnew_placement(_data._mem, NodePath(p_node_path));
2593}
2594
2595Variant::Variant(const ::RID &p_rid) {
2596 type = RID;
2597 memnew_placement(_data._mem, ::RID(p_rid));
2598}
2599
2600Variant::Variant(const Object *p_object) {
2601 type = OBJECT;
2602
2603 memnew_placement(_data._mem, ObjData);
2604
2605 if (p_object) {
2606 if (p_object->is_ref_counted()) {
2607 RefCounted *ref_counted = const_cast<RefCounted *>(static_cast<const RefCounted *>(p_object));
2608 if (!ref_counted->init_ref()) {
2609 _get_obj().obj = nullptr;
2610 _get_obj().id = ObjectID();
2611 return;
2612 }
2613 }
2614
2615 _get_obj().obj = const_cast<Object *>(p_object);
2616 _get_obj().id = p_object->get_instance_id();
2617 } else {
2618 _get_obj().obj = nullptr;
2619 _get_obj().id = ObjectID();
2620 }
2621}
2622
2623Variant::Variant(const Callable &p_callable) {
2624 type = CALLABLE;
2625 memnew_placement(_data._mem, Callable(p_callable));
2626}
2627
2628Variant::Variant(const Signal &p_callable) {
2629 type = SIGNAL;
2630 memnew_placement(_data._mem, Signal(p_callable));
2631}
2632
2633Variant::Variant(const Dictionary &p_dictionary) {
2634 type = DICTIONARY;
2635 memnew_placement(_data._mem, Dictionary(p_dictionary));
2636}
2637
2638Variant::Variant(const Array &p_array) {
2639 type = ARRAY;
2640 memnew_placement(_data._mem, Array(p_array));
2641}
2642
2643Variant::Variant(const Vector<Plane> &p_array) {
2644 type = ARRAY;
2645
2646 Array *plane_array = memnew_placement(_data._mem, Array);
2647
2648 plane_array->resize(p_array.size());
2649
2650 for (int i = 0; i < p_array.size(); i++) {
2651 plane_array->operator[](i) = Variant(p_array[i]);
2652 }
2653}
2654
2655Variant::Variant(const Vector<::RID> &p_array) {
2656 type = ARRAY;
2657
2658 Array *rid_array = memnew_placement(_data._mem, Array);
2659
2660 rid_array->resize(p_array.size());
2661
2662 for (int i = 0; i < p_array.size(); i++) {
2663 rid_array->set(i, Variant(p_array[i]));
2664 }
2665}
2666
2667Variant::Variant(const Vector<uint8_t> &p_byte_array) {
2668 type = PACKED_BYTE_ARRAY;
2669
2670 _data.packed_array = PackedArrayRef<uint8_t>::create(p_byte_array);
2671}
2672
2673Variant::Variant(const Vector<int32_t> &p_int32_array) {
2674 type = PACKED_INT32_ARRAY;
2675 _data.packed_array = PackedArrayRef<int32_t>::create(p_int32_array);
2676}
2677
2678Variant::Variant(const Vector<int64_t> &p_int64_array) {
2679 type = PACKED_INT64_ARRAY;
2680 _data.packed_array = PackedArrayRef<int64_t>::create(p_int64_array);
2681}
2682
2683Variant::Variant(const Vector<float> &p_float32_array) {
2684 type = PACKED_FLOAT32_ARRAY;
2685 _data.packed_array = PackedArrayRef<float>::create(p_float32_array);
2686}
2687
2688Variant::Variant(const Vector<double> &p_float64_array) {
2689 type = PACKED_FLOAT64_ARRAY;
2690 _data.packed_array = PackedArrayRef<double>::create(p_float64_array);
2691}
2692
2693Variant::Variant(const Vector<String> &p_string_array) {
2694 type = PACKED_STRING_ARRAY;
2695 _data.packed_array = PackedArrayRef<String>::create(p_string_array);
2696}
2697
2698Variant::Variant(const Vector<Vector3> &p_vector3_array) {
2699 type = PACKED_VECTOR3_ARRAY;
2700 _data.packed_array = PackedArrayRef<Vector3>::create(p_vector3_array);
2701}
2702
2703Variant::Variant(const Vector<Vector2> &p_vector2_array) {
2704 type = PACKED_VECTOR2_ARRAY;
2705 _data.packed_array = PackedArrayRef<Vector2>::create(p_vector2_array);
2706}
2707
2708Variant::Variant(const Vector<Color> &p_color_array) {
2709 type = PACKED_COLOR_ARRAY;
2710 _data.packed_array = PackedArrayRef<Color>::create(p_color_array);
2711}
2712
2713Variant::Variant(const Vector<Face3> &p_face_array) {
2714 Vector<Vector3> vertices;
2715 int face_count = p_face_array.size();
2716 vertices.resize(face_count * 3);
2717
2718 if (face_count) {
2719 const Face3 *r = p_face_array.ptr();
2720 Vector3 *w = vertices.ptrw();
2721
2722 for (int i = 0; i < face_count; i++) {
2723 for (int j = 0; j < 3; j++) {
2724 w[i * 3 + j] = r[i].vertex[j];
2725 }
2726 }
2727 }
2728
2729 type = NIL;
2730
2731 *this = vertices;
2732}
2733
2734/* helpers */
2735Variant::Variant(const Vector<Variant> &p_array) {
2736 type = NIL;
2737 Array arr;
2738 arr.resize(p_array.size());
2739 for (int i = 0; i < p_array.size(); i++) {
2740 arr[i] = p_array[i];
2741 }
2742 *this = arr;
2743}
2744
2745Variant::Variant(const Vector<StringName> &p_array) {
2746 type = NIL;
2747 Vector<String> v;
2748 int len = p_array.size();
2749 v.resize(len);
2750 for (int i = 0; i < len; i++) {
2751 v.set(i, p_array[i]);
2752 }
2753 *this = v;
2754}
2755
2756void Variant::operator=(const Variant &p_variant) {
2757 if (unlikely(this == &p_variant)) {
2758 return;
2759 }
2760
2761 if (unlikely(type != p_variant.type)) {
2762 reference(p_variant);
2763 return;
2764 }
2765
2766 switch (p_variant.type) {
2767 case NIL: {
2768 // none
2769 } break;
2770
2771 // atomic types
2772 case BOOL: {
2773 _data._bool = p_variant._data._bool;
2774 } break;
2775 case INT: {
2776 _data._int = p_variant._data._int;
2777 } break;
2778 case FLOAT: {
2779 _data._float = p_variant._data._float;
2780 } break;
2781 case STRING: {
2782 *reinterpret_cast<String *>(_data._mem) = *reinterpret_cast<const String *>(p_variant._data._mem);
2783 } break;
2784
2785 // math types
2786 case VECTOR2: {
2787 *reinterpret_cast<Vector2 *>(_data._mem) = *reinterpret_cast<const Vector2 *>(p_variant._data._mem);
2788 } break;
2789 case VECTOR2I: {
2790 *reinterpret_cast<Vector2i *>(_data._mem) = *reinterpret_cast<const Vector2i *>(p_variant._data._mem);
2791 } break;
2792 case RECT2: {
2793 *reinterpret_cast<Rect2 *>(_data._mem) = *reinterpret_cast<const Rect2 *>(p_variant._data._mem);
2794 } break;
2795 case RECT2I: {
2796 *reinterpret_cast<Rect2i *>(_data._mem) = *reinterpret_cast<const Rect2i *>(p_variant._data._mem);
2797 } break;
2798 case TRANSFORM2D: {
2799 *_data._transform2d = *(p_variant._data._transform2d);
2800 } break;
2801 case VECTOR3: {
2802 *reinterpret_cast<Vector3 *>(_data._mem) = *reinterpret_cast<const Vector3 *>(p_variant._data._mem);
2803 } break;
2804 case VECTOR3I: {
2805 *reinterpret_cast<Vector3i *>(_data._mem) = *reinterpret_cast<const Vector3i *>(p_variant._data._mem);
2806 } break;
2807 case VECTOR4: {
2808 *reinterpret_cast<Vector4 *>(_data._mem) = *reinterpret_cast<const Vector4 *>(p_variant._data._mem);
2809 } break;
2810 case VECTOR4I: {
2811 *reinterpret_cast<Vector4i *>(_data._mem) = *reinterpret_cast<const Vector4i *>(p_variant._data._mem);
2812 } break;
2813 case PLANE: {
2814 *reinterpret_cast<Plane *>(_data._mem) = *reinterpret_cast<const Plane *>(p_variant._data._mem);
2815 } break;
2816
2817 case AABB: {
2818 *_data._aabb = *(p_variant._data._aabb);
2819 } break;
2820 case QUATERNION: {
2821 *reinterpret_cast<Quaternion *>(_data._mem) = *reinterpret_cast<const Quaternion *>(p_variant._data._mem);
2822 } break;
2823 case BASIS: {
2824 *_data._basis = *(p_variant._data._basis);
2825 } break;
2826 case TRANSFORM3D: {
2827 *_data._transform3d = *(p_variant._data._transform3d);
2828 } break;
2829 case PROJECTION: {
2830 *_data._projection = *(p_variant._data._projection);
2831 } break;
2832
2833 // misc types
2834 case COLOR: {
2835 *reinterpret_cast<Color *>(_data._mem) = *reinterpret_cast<const Color *>(p_variant._data._mem);
2836 } break;
2837 case RID: {
2838 *reinterpret_cast<::RID *>(_data._mem) = *reinterpret_cast<const ::RID *>(p_variant._data._mem);
2839 } break;
2840 case OBJECT: {
2841 if (_get_obj().id.is_ref_counted()) {
2842 //we are safe that there is a reference here
2843 RefCounted *ref_counted = static_cast<RefCounted *>(_get_obj().obj);
2844 if (ref_counted->unreference()) {
2845 memdelete(ref_counted);
2846 }
2847 }
2848
2849 if (p_variant._get_obj().obj && p_variant._get_obj().id.is_ref_counted()) {
2850 RefCounted *ref_counted = static_cast<RefCounted *>(p_variant._get_obj().obj);
2851 if (!ref_counted->reference()) {
2852 _get_obj().obj = nullptr;
2853 _get_obj().id = ObjectID();
2854 break;
2855 }
2856 }
2857
2858 _get_obj().obj = const_cast<Object *>(p_variant._get_obj().obj);
2859 _get_obj().id = p_variant._get_obj().id;
2860
2861 } break;
2862 case CALLABLE: {
2863 *reinterpret_cast<Callable *>(_data._mem) = *reinterpret_cast<const Callable *>(p_variant._data._mem);
2864 } break;
2865 case SIGNAL: {
2866 *reinterpret_cast<Signal *>(_data._mem) = *reinterpret_cast<const Signal *>(p_variant._data._mem);
2867 } break;
2868
2869 case STRING_NAME: {
2870 *reinterpret_cast<StringName *>(_data._mem) = *reinterpret_cast<const StringName *>(p_variant._data._mem);
2871 } break;
2872 case NODE_PATH: {
2873 *reinterpret_cast<NodePath *>(_data._mem) = *reinterpret_cast<const NodePath *>(p_variant._data._mem);
2874 } break;
2875 case DICTIONARY: {
2876 *reinterpret_cast<Dictionary *>(_data._mem) = *reinterpret_cast<const Dictionary *>(p_variant._data._mem);
2877 } break;
2878 case ARRAY: {
2879 *reinterpret_cast<Array *>(_data._mem) = *reinterpret_cast<const Array *>(p_variant._data._mem);
2880 } break;
2881
2882 // arrays
2883 case PACKED_BYTE_ARRAY: {
2884 _data.packed_array = PackedArrayRef<uint8_t>::reference_from(_data.packed_array, p_variant._data.packed_array);
2885 } break;
2886 case PACKED_INT32_ARRAY: {
2887 _data.packed_array = PackedArrayRef<int32_t>::reference_from(_data.packed_array, p_variant._data.packed_array);
2888 } break;
2889 case PACKED_INT64_ARRAY: {
2890 _data.packed_array = PackedArrayRef<int64_t>::reference_from(_data.packed_array, p_variant._data.packed_array);
2891 } break;
2892 case PACKED_FLOAT32_ARRAY: {
2893 _data.packed_array = PackedArrayRef<float>::reference_from(_data.packed_array, p_variant._data.packed_array);
2894 } break;
2895 case PACKED_FLOAT64_ARRAY: {
2896 _data.packed_array = PackedArrayRef<double>::reference_from(_data.packed_array, p_variant._data.packed_array);
2897 } break;
2898 case PACKED_STRING_ARRAY: {
2899 _data.packed_array = PackedArrayRef<String>::reference_from(_data.packed_array, p_variant._data.packed_array);
2900 } break;
2901 case PACKED_VECTOR2_ARRAY: {
2902 _data.packed_array = PackedArrayRef<Vector2>::reference_from(_data.packed_array, p_variant._data.packed_array);
2903 } break;
2904 case PACKED_VECTOR3_ARRAY: {
2905 _data.packed_array = PackedArrayRef<Vector3>::reference_from(_data.packed_array, p_variant._data.packed_array);
2906 } break;
2907 case PACKED_COLOR_ARRAY: {
2908 _data.packed_array = PackedArrayRef<Color>::reference_from(_data.packed_array, p_variant._data.packed_array);
2909 } break;
2910 default: {
2911 }
2912 }
2913}
2914
2915Variant::Variant(const IPAddress &p_address) {
2916 type = STRING;
2917 memnew_placement(_data._mem, String(p_address));
2918}
2919
2920Variant::Variant(const Variant &p_variant) {
2921 reference(p_variant);
2922}
2923
2924uint32_t Variant::hash() const {
2925 return recursive_hash(0);
2926}
2927
2928uint32_t Variant::recursive_hash(int recursion_count) const {
2929 switch (type) {
2930 case NIL: {
2931 return 0;
2932 } break;
2933 case BOOL: {
2934 return _data._bool ? 1 : 0;
2935 } break;
2936 case INT: {
2937 return hash_one_uint64((uint64_t)_data._int);
2938 } break;
2939 case FLOAT: {
2940 return hash_murmur3_one_double(_data._float);
2941 } break;
2942 case STRING: {
2943 return reinterpret_cast<const String *>(_data._mem)->hash();
2944 } break;
2945
2946 // math types
2947 case VECTOR2: {
2948 return HashMapHasherDefault::hash(*reinterpret_cast<const Vector2 *>(_data._mem));
2949 } break;
2950 case VECTOR2I: {
2951 return HashMapHasherDefault::hash(*reinterpret_cast<const Vector2i *>(_data._mem));
2952 } break;
2953 case RECT2: {
2954 return HashMapHasherDefault::hash(*reinterpret_cast<const Rect2 *>(_data._mem));
2955 } break;
2956 case RECT2I: {
2957 return HashMapHasherDefault::hash(*reinterpret_cast<const Rect2i *>(_data._mem));
2958 } break;
2959 case TRANSFORM2D: {
2960 uint32_t h = HASH_MURMUR3_SEED;
2961 const Transform2D &t = *_data._transform2d;
2962 h = hash_murmur3_one_real(t[0].x, h);
2963 h = hash_murmur3_one_real(t[0].y, h);
2964 h = hash_murmur3_one_real(t[1].x, h);
2965 h = hash_murmur3_one_real(t[1].y, h);
2966 h = hash_murmur3_one_real(t[2].x, h);
2967 h = hash_murmur3_one_real(t[2].y, h);
2968
2969 return hash_fmix32(h);
2970 } break;
2971 case VECTOR3: {
2972 return HashMapHasherDefault::hash(*reinterpret_cast<const Vector3 *>(_data._mem));
2973 } break;
2974 case VECTOR3I: {
2975 return HashMapHasherDefault::hash(*reinterpret_cast<const Vector3i *>(_data._mem));
2976 } break;
2977 case VECTOR4: {
2978 return HashMapHasherDefault::hash(*reinterpret_cast<const Vector4 *>(_data._mem));
2979 } break;
2980 case VECTOR4I: {
2981 return HashMapHasherDefault::hash(*reinterpret_cast<const Vector4i *>(_data._mem));
2982 } break;
2983 case PLANE: {
2984 uint32_t h = HASH_MURMUR3_SEED;
2985 const Plane &p = *reinterpret_cast<const Plane *>(_data._mem);
2986 h = hash_murmur3_one_real(p.normal.x, h);
2987 h = hash_murmur3_one_real(p.normal.y, h);
2988 h = hash_murmur3_one_real(p.normal.z, h);
2989 h = hash_murmur3_one_real(p.d, h);
2990 return hash_fmix32(h);
2991 } break;
2992 case AABB: {
2993 return HashMapHasherDefault::hash(*_data._aabb);
2994 } break;
2995 case QUATERNION: {
2996 uint32_t h = HASH_MURMUR3_SEED;
2997 const Quaternion &q = *reinterpret_cast<const Quaternion *>(_data._mem);
2998 h = hash_murmur3_one_real(q.x, h);
2999 h = hash_murmur3_one_real(q.y, h);
3000 h = hash_murmur3_one_real(q.z, h);
3001 h = hash_murmur3_one_real(q.w, h);
3002 return hash_fmix32(h);
3003 } break;
3004 case BASIS: {
3005 uint32_t h = HASH_MURMUR3_SEED;
3006 const Basis &b = *_data._basis;
3007 h = hash_murmur3_one_real(b[0].x, h);
3008 h = hash_murmur3_one_real(b[0].y, h);
3009 h = hash_murmur3_one_real(b[0].z, h);
3010 h = hash_murmur3_one_real(b[1].x, h);
3011 h = hash_murmur3_one_real(b[1].y, h);
3012 h = hash_murmur3_one_real(b[1].z, h);
3013 h = hash_murmur3_one_real(b[2].x, h);
3014 h = hash_murmur3_one_real(b[2].y, h);
3015 h = hash_murmur3_one_real(b[2].z, h);
3016 return hash_fmix32(h);
3017 } break;
3018 case TRANSFORM3D: {
3019 uint32_t h = HASH_MURMUR3_SEED;
3020 const Transform3D &t = *_data._transform3d;
3021 h = hash_murmur3_one_real(t.basis[0].x, h);
3022 h = hash_murmur3_one_real(t.basis[0].y, h);
3023 h = hash_murmur3_one_real(t.basis[0].z, h);
3024 h = hash_murmur3_one_real(t.basis[1].x, h);
3025 h = hash_murmur3_one_real(t.basis[1].y, h);
3026 h = hash_murmur3_one_real(t.basis[1].z, h);
3027 h = hash_murmur3_one_real(t.basis[2].x, h);
3028 h = hash_murmur3_one_real(t.basis[2].y, h);
3029 h = hash_murmur3_one_real(t.basis[2].z, h);
3030 h = hash_murmur3_one_real(t.origin.x, h);
3031 h = hash_murmur3_one_real(t.origin.y, h);
3032 h = hash_murmur3_one_real(t.origin.z, h);
3033 return hash_fmix32(h);
3034 } break;
3035 case PROJECTION: {
3036 uint32_t h = HASH_MURMUR3_SEED;
3037 const Projection &t = *_data._projection;
3038 h = hash_murmur3_one_real(t.columns[0].x, h);
3039 h = hash_murmur3_one_real(t.columns[0].y, h);
3040 h = hash_murmur3_one_real(t.columns[0].z, h);
3041 h = hash_murmur3_one_real(t.columns[0].w, h);
3042 h = hash_murmur3_one_real(t.columns[1].x, h);
3043 h = hash_murmur3_one_real(t.columns[1].y, h);
3044 h = hash_murmur3_one_real(t.columns[1].z, h);
3045 h = hash_murmur3_one_real(t.columns[1].w, h);
3046 h = hash_murmur3_one_real(t.columns[2].x, h);
3047 h = hash_murmur3_one_real(t.columns[2].y, h);
3048 h = hash_murmur3_one_real(t.columns[2].z, h);
3049 h = hash_murmur3_one_real(t.columns[2].w, h);
3050 h = hash_murmur3_one_real(t.columns[3].x, h);
3051 h = hash_murmur3_one_real(t.columns[3].y, h);
3052 h = hash_murmur3_one_real(t.columns[3].z, h);
3053 h = hash_murmur3_one_real(t.columns[3].w, h);
3054 return hash_fmix32(h);
3055 } break;
3056 // misc types
3057 case COLOR: {
3058 uint32_t h = HASH_MURMUR3_SEED;
3059 const Color &c = *reinterpret_cast<const Color *>(_data._mem);
3060 h = hash_murmur3_one_float(c.r, h);
3061 h = hash_murmur3_one_float(c.g, h);
3062 h = hash_murmur3_one_float(c.b, h);
3063 h = hash_murmur3_one_float(c.a, h);
3064 return hash_fmix32(h);
3065 } break;
3066 case RID: {
3067 return hash_one_uint64(reinterpret_cast<const ::RID *>(_data._mem)->get_id());
3068 } break;
3069 case OBJECT: {
3070 return hash_one_uint64(hash_make_uint64_t(_get_obj().obj));
3071 } break;
3072 case STRING_NAME: {
3073 return reinterpret_cast<const StringName *>(_data._mem)->hash();
3074 } break;
3075 case NODE_PATH: {
3076 return reinterpret_cast<const NodePath *>(_data._mem)->hash();
3077 } break;
3078 case DICTIONARY: {
3079 return reinterpret_cast<const Dictionary *>(_data._mem)->recursive_hash(recursion_count);
3080
3081 } break;
3082 case CALLABLE: {
3083 return reinterpret_cast<const Callable *>(_data._mem)->hash();
3084
3085 } break;
3086 case SIGNAL: {
3087 const Signal &s = *reinterpret_cast<const Signal *>(_data._mem);
3088 uint32_t hash = s.get_name().hash();
3089 return hash_murmur3_one_64(s.get_object_id(), hash);
3090 } break;
3091 case ARRAY: {
3092 const Array &arr = *reinterpret_cast<const Array *>(_data._mem);
3093 return arr.recursive_hash(recursion_count);
3094
3095 } break;
3096 case PACKED_BYTE_ARRAY: {
3097 const Vector<uint8_t> &arr = PackedArrayRef<uint8_t>::get_array(_data.packed_array);
3098 int len = arr.size();
3099 if (likely(len)) {
3100 const uint8_t *r = arr.ptr();
3101 return hash_murmur3_buffer((uint8_t *)&r[0], len);
3102 } else {
3103 return hash_murmur3_one_64(0);
3104 }
3105
3106 } break;
3107 case PACKED_INT32_ARRAY: {
3108 const Vector<int32_t> &arr = PackedArrayRef<int32_t>::get_array(_data.packed_array);
3109 int len = arr.size();
3110 if (likely(len)) {
3111 const int32_t *r = arr.ptr();
3112 return hash_murmur3_buffer((uint8_t *)&r[0], len * sizeof(int32_t));
3113 } else {
3114 return hash_murmur3_one_64(0);
3115 }
3116
3117 } break;
3118 case PACKED_INT64_ARRAY: {
3119 const Vector<int64_t> &arr = PackedArrayRef<int64_t>::get_array(_data.packed_array);
3120 int len = arr.size();
3121 if (likely(len)) {
3122 const int64_t *r = arr.ptr();
3123 return hash_murmur3_buffer((uint8_t *)&r[0], len * sizeof(int64_t));
3124 } else {
3125 return hash_murmur3_one_64(0);
3126 }
3127
3128 } break;
3129 case PACKED_FLOAT32_ARRAY: {
3130 const Vector<float> &arr = PackedArrayRef<float>::get_array(_data.packed_array);
3131 int len = arr.size();
3132
3133 if (likely(len)) {
3134 const float *r = arr.ptr();
3135 uint32_t h = HASH_MURMUR3_SEED;
3136 for (int32_t i = 0; i < len; i++) {
3137 h = hash_murmur3_one_float(r[i], h);
3138 }
3139 return hash_fmix32(h);
3140 } else {
3141 return hash_murmur3_one_float(0.0);
3142 }
3143
3144 } break;
3145 case PACKED_FLOAT64_ARRAY: {
3146 const Vector<double> &arr = PackedArrayRef<double>::get_array(_data.packed_array);
3147 int len = arr.size();
3148
3149 if (likely(len)) {
3150 const double *r = arr.ptr();
3151 uint32_t h = HASH_MURMUR3_SEED;
3152 for (int32_t i = 0; i < len; i++) {
3153 h = hash_murmur3_one_double(r[i], h);
3154 }
3155 return hash_fmix32(h);
3156 } else {
3157 return hash_murmur3_one_double(0.0);
3158 }
3159
3160 } break;
3161 case PACKED_STRING_ARRAY: {
3162 uint32_t hash = HASH_MURMUR3_SEED;
3163 const Vector<String> &arr = PackedArrayRef<String>::get_array(_data.packed_array);
3164 int len = arr.size();
3165
3166 if (likely(len)) {
3167 const String *r = arr.ptr();
3168
3169 for (int i = 0; i < len; i++) {
3170 hash = hash_murmur3_one_32(r[i].hash(), hash);
3171 }
3172 hash = hash_fmix32(hash);
3173 }
3174
3175 return hash;
3176 } break;
3177 case PACKED_VECTOR2_ARRAY: {
3178 uint32_t hash = HASH_MURMUR3_SEED;
3179 const Vector<Vector2> &arr = PackedArrayRef<Vector2>::get_array(_data.packed_array);
3180 int len = arr.size();
3181
3182 if (likely(len)) {
3183 const Vector2 *r = arr.ptr();
3184
3185 for (int i = 0; i < len; i++) {
3186 hash = hash_murmur3_one_real(r[i].x, hash);
3187 hash = hash_murmur3_one_real(r[i].y, hash);
3188 }
3189 hash = hash_fmix32(hash);
3190 }
3191
3192 return hash;
3193 } break;
3194 case PACKED_VECTOR3_ARRAY: {
3195 uint32_t hash = HASH_MURMUR3_SEED;
3196 const Vector<Vector3> &arr = PackedArrayRef<Vector3>::get_array(_data.packed_array);
3197 int len = arr.size();
3198
3199 if (likely(len)) {
3200 const Vector3 *r = arr.ptr();
3201
3202 for (int i = 0; i < len; i++) {
3203 hash = hash_murmur3_one_real(r[i].x, hash);
3204 hash = hash_murmur3_one_real(r[i].y, hash);
3205 hash = hash_murmur3_one_real(r[i].z, hash);
3206 }
3207 hash = hash_fmix32(hash);
3208 }
3209
3210 return hash;
3211 } break;
3212 case PACKED_COLOR_ARRAY: {
3213 uint32_t hash = HASH_MURMUR3_SEED;
3214 const Vector<Color> &arr = PackedArrayRef<Color>::get_array(_data.packed_array);
3215 int len = arr.size();
3216
3217 if (likely(len)) {
3218 const Color *r = arr.ptr();
3219
3220 for (int i = 0; i < len; i++) {
3221 hash = hash_murmur3_one_float(r[i].r, hash);
3222 hash = hash_murmur3_one_float(r[i].g, hash);
3223 hash = hash_murmur3_one_float(r[i].b, hash);
3224 hash = hash_murmur3_one_float(r[i].a, hash);
3225 }
3226 hash = hash_fmix32(hash);
3227 }
3228
3229 return hash;
3230 } break;
3231 default: {
3232 }
3233 }
3234
3235 return 0;
3236}
3237
3238#define hash_compare_scalar(p_lhs, p_rhs) \
3239 (((p_lhs) == (p_rhs)) || (Math::is_nan(p_lhs) && Math::is_nan(p_rhs)))
3240
3241#define hash_compare_vector2(p_lhs, p_rhs) \
3242 (hash_compare_scalar((p_lhs).x, (p_rhs).x) && \
3243 hash_compare_scalar((p_lhs).y, (p_rhs).y))
3244
3245#define hash_compare_vector3(p_lhs, p_rhs) \
3246 (hash_compare_scalar((p_lhs).x, (p_rhs).x) && \
3247 hash_compare_scalar((p_lhs).y, (p_rhs).y) && \
3248 hash_compare_scalar((p_lhs).z, (p_rhs).z))
3249
3250#define hash_compare_vector4(p_lhs, p_rhs) \
3251 (hash_compare_scalar((p_lhs).x, (p_rhs).x) && \
3252 hash_compare_scalar((p_lhs).y, (p_rhs).y) && \
3253 hash_compare_scalar((p_lhs).z, (p_rhs).z) && \
3254 hash_compare_scalar((p_lhs).w, (p_rhs).w))
3255
3256#define hash_compare_quaternion(p_lhs, p_rhs) \
3257 (hash_compare_scalar((p_lhs).x, (p_rhs).x) && \
3258 hash_compare_scalar((p_lhs).y, (p_rhs).y) && \
3259 hash_compare_scalar((p_lhs).z, (p_rhs).z) && \
3260 hash_compare_scalar((p_lhs).w, (p_rhs).w))
3261
3262#define hash_compare_color(p_lhs, p_rhs) \
3263 (hash_compare_scalar((p_lhs).r, (p_rhs).r) && \
3264 hash_compare_scalar((p_lhs).g, (p_rhs).g) && \
3265 hash_compare_scalar((p_lhs).b, (p_rhs).b) && \
3266 hash_compare_scalar((p_lhs).a, (p_rhs).a))
3267
3268#define hash_compare_packed_array(p_lhs, p_rhs, p_type, p_compare_func) \
3269 const Vector<p_type> &l = PackedArrayRef<p_type>::get_array(p_lhs); \
3270 const Vector<p_type> &r = PackedArrayRef<p_type>::get_array(p_rhs); \
3271 \
3272 if (l.size() != r.size()) \
3273 return false; \
3274 \
3275 const p_type *lr = l.ptr(); \
3276 const p_type *rr = r.ptr(); \
3277 \
3278 for (int i = 0; i < l.size(); ++i) { \
3279 if (!p_compare_func((lr[i]), (rr[i]))) \
3280 return false; \
3281 } \
3282 \
3283 return true
3284
3285bool Variant::hash_compare(const Variant &p_variant, int recursion_count) const {
3286 if (type != p_variant.type) {
3287 return false;
3288 }
3289
3290 switch (type) {
3291 case INT: {
3292 return _data._int == p_variant._data._int;
3293 } break;
3294
3295 case FLOAT: {
3296 return hash_compare_scalar(_data._float, p_variant._data._float);
3297 } break;
3298
3299 case STRING: {
3300 return *reinterpret_cast<const String *>(_data._mem) == *reinterpret_cast<const String *>(p_variant._data._mem);
3301 } break;
3302
3303 case STRING_NAME: {
3304 return *reinterpret_cast<const StringName *>(_data._mem) == *reinterpret_cast<const StringName *>(p_variant._data._mem);
3305 } break;
3306
3307 case VECTOR2: {
3308 const Vector2 *l = reinterpret_cast<const Vector2 *>(_data._mem);
3309 const Vector2 *r = reinterpret_cast<const Vector2 *>(p_variant._data._mem);
3310
3311 return hash_compare_vector2(*l, *r);
3312 } break;
3313 case VECTOR2I: {
3314 const Vector2i *l = reinterpret_cast<const Vector2i *>(_data._mem);
3315 const Vector2i *r = reinterpret_cast<const Vector2i *>(p_variant._data._mem);
3316 return *l == *r;
3317 } break;
3318
3319 case RECT2: {
3320 const Rect2 *l = reinterpret_cast<const Rect2 *>(_data._mem);
3321 const Rect2 *r = reinterpret_cast<const Rect2 *>(p_variant._data._mem);
3322
3323 return hash_compare_vector2(l->position, r->position) &&
3324 hash_compare_vector2(l->size, r->size);
3325 } break;
3326 case RECT2I: {
3327 const Rect2i *l = reinterpret_cast<const Rect2i *>(_data._mem);
3328 const Rect2i *r = reinterpret_cast<const Rect2i *>(p_variant._data._mem);
3329
3330 return *l == *r;
3331 } break;
3332
3333 case TRANSFORM2D: {
3334 Transform2D *l = _data._transform2d;
3335 Transform2D *r = p_variant._data._transform2d;
3336
3337 for (int i = 0; i < 3; i++) {
3338 if (!hash_compare_vector2(l->columns[i], r->columns[i])) {
3339 return false;
3340 }
3341 }
3342
3343 return true;
3344 } break;
3345
3346 case VECTOR3: {
3347 const Vector3 *l = reinterpret_cast<const Vector3 *>(_data._mem);
3348 const Vector3 *r = reinterpret_cast<const Vector3 *>(p_variant._data._mem);
3349
3350 return hash_compare_vector3(*l, *r);
3351 } break;
3352 case VECTOR3I: {
3353 const Vector3i *l = reinterpret_cast<const Vector3i *>(_data._mem);
3354 const Vector3i *r = reinterpret_cast<const Vector3i *>(p_variant._data._mem);
3355
3356 return *l == *r;
3357 } break;
3358 case VECTOR4: {
3359 const Vector4 *l = reinterpret_cast<const Vector4 *>(_data._mem);
3360 const Vector4 *r = reinterpret_cast<const Vector4 *>(p_variant._data._mem);
3361
3362 return hash_compare_vector4(*l, *r);
3363 } break;
3364 case VECTOR4I: {
3365 const Vector4i *l = reinterpret_cast<const Vector4i *>(_data._mem);
3366 const Vector4i *r = reinterpret_cast<const Vector4i *>(p_variant._data._mem);
3367
3368 return *l == *r;
3369 } break;
3370
3371 case PLANE: {
3372 const Plane *l = reinterpret_cast<const Plane *>(_data._mem);
3373 const Plane *r = reinterpret_cast<const Plane *>(p_variant._data._mem);
3374
3375 return hash_compare_vector3(l->normal, r->normal) &&
3376 hash_compare_scalar(l->d, r->d);
3377 } break;
3378
3379 case AABB: {
3380 const ::AABB *l = _data._aabb;
3381 const ::AABB *r = p_variant._data._aabb;
3382
3383 return hash_compare_vector3(l->position, r->position) &&
3384 hash_compare_vector3(l->size, r->size);
3385
3386 } break;
3387
3388 case QUATERNION: {
3389 const Quaternion *l = reinterpret_cast<const Quaternion *>(_data._mem);
3390 const Quaternion *r = reinterpret_cast<const Quaternion *>(p_variant._data._mem);
3391
3392 return hash_compare_quaternion(*l, *r);
3393 } break;
3394
3395 case BASIS: {
3396 const Basis *l = _data._basis;
3397 const Basis *r = p_variant._data._basis;
3398
3399 for (int i = 0; i < 3; i++) {
3400 if (!hash_compare_vector3(l->rows[i], r->rows[i])) {
3401 return false;
3402 }
3403 }
3404
3405 return true;
3406 } break;
3407
3408 case TRANSFORM3D: {
3409 const Transform3D *l = _data._transform3d;
3410 const Transform3D *r = p_variant._data._transform3d;
3411
3412 for (int i = 0; i < 3; i++) {
3413 if (!hash_compare_vector3(l->basis.rows[i], r->basis.rows[i])) {
3414 return false;
3415 }
3416 }
3417
3418 return hash_compare_vector3(l->origin, r->origin);
3419 } break;
3420 case PROJECTION: {
3421 const Projection *l = _data._projection;
3422 const Projection *r = p_variant._data._projection;
3423
3424 for (int i = 0; i < 4; i++) {
3425 if (!hash_compare_vector4(l->columns[i], r->columns[i])) {
3426 return false;
3427 }
3428 }
3429
3430 return true;
3431 } break;
3432
3433 case COLOR: {
3434 const Color *l = reinterpret_cast<const Color *>(_data._mem);
3435 const Color *r = reinterpret_cast<const Color *>(p_variant._data._mem);
3436
3437 return hash_compare_color(*l, *r);
3438 } break;
3439
3440 case ARRAY: {
3441 const Array &l = *(reinterpret_cast<const Array *>(_data._mem));
3442 const Array &r = *(reinterpret_cast<const Array *>(p_variant._data._mem));
3443
3444 if (!l.recursive_equal(r, recursion_count + 1)) {
3445 return false;
3446 }
3447
3448 return true;
3449 } break;
3450
3451 case DICTIONARY: {
3452 const Dictionary &l = *(reinterpret_cast<const Dictionary *>(_data._mem));
3453 const Dictionary &r = *(reinterpret_cast<const Dictionary *>(p_variant._data._mem));
3454
3455 if (!l.recursive_equal(r, recursion_count + 1)) {
3456 return false;
3457 }
3458
3459 return true;
3460 } break;
3461
3462 // This is for floating point comparisons only.
3463 case PACKED_FLOAT32_ARRAY: {
3464 hash_compare_packed_array(_data.packed_array, p_variant._data.packed_array, float, hash_compare_scalar);
3465 } break;
3466
3467 case PACKED_FLOAT64_ARRAY: {
3468 hash_compare_packed_array(_data.packed_array, p_variant._data.packed_array, double, hash_compare_scalar);
3469 } break;
3470
3471 case PACKED_VECTOR2_ARRAY: {
3472 hash_compare_packed_array(_data.packed_array, p_variant._data.packed_array, Vector2, hash_compare_vector2);
3473 } break;
3474
3475 case PACKED_VECTOR3_ARRAY: {
3476 hash_compare_packed_array(_data.packed_array, p_variant._data.packed_array, Vector3, hash_compare_vector3);
3477 } break;
3478
3479 case PACKED_COLOR_ARRAY: {
3480 hash_compare_packed_array(_data.packed_array, p_variant._data.packed_array, Color, hash_compare_color);
3481 } break;
3482
3483 default:
3484 bool v;
3485 Variant r;
3486 evaluate(OP_EQUAL, *this, p_variant, r, v);
3487 return r;
3488 }
3489}
3490
3491bool Variant::identity_compare(const Variant &p_variant) const {
3492 if (type != p_variant.type) {
3493 return false;
3494 }
3495
3496 switch (type) {
3497 case OBJECT: {
3498 return _get_obj().id == p_variant._get_obj().id;
3499 } break;
3500
3501 case DICTIONARY: {
3502 const Dictionary &l = *(reinterpret_cast<const Dictionary *>(_data._mem));
3503 const Dictionary &r = *(reinterpret_cast<const Dictionary *>(p_variant._data._mem));
3504 return l.id() == r.id();
3505 } break;
3506
3507 case ARRAY: {
3508 const Array &l = *(reinterpret_cast<const Array *>(_data._mem));
3509 const Array &r = *(reinterpret_cast<const Array *>(p_variant._data._mem));
3510 return l.id() == r.id();
3511 } break;
3512
3513 case PACKED_BYTE_ARRAY:
3514 case PACKED_INT32_ARRAY:
3515 case PACKED_INT64_ARRAY:
3516 case PACKED_FLOAT32_ARRAY:
3517 case PACKED_FLOAT64_ARRAY:
3518 case PACKED_STRING_ARRAY:
3519 case PACKED_VECTOR2_ARRAY:
3520 case PACKED_VECTOR3_ARRAY:
3521 case PACKED_COLOR_ARRAY: {
3522 return _data.packed_array == p_variant._data.packed_array;
3523 } break;
3524
3525 default: {
3526 return hash_compare(p_variant);
3527 }
3528 }
3529}
3530
3531bool StringLikeVariantComparator::compare(const Variant &p_lhs, const Variant &p_rhs) {
3532 if (p_lhs.hash_compare(p_rhs)) {
3533 return true;
3534 }
3535 if (p_lhs.get_type() == Variant::STRING && p_rhs.get_type() == Variant::STRING_NAME) {
3536 return *VariantInternal::get_string(&p_lhs) == *VariantInternal::get_string_name(&p_rhs);
3537 }
3538 if (p_lhs.get_type() == Variant::STRING_NAME && p_rhs.get_type() == Variant::STRING) {
3539 return *VariantInternal::get_string_name(&p_lhs) == *VariantInternal::get_string(&p_rhs);
3540 }
3541 return false;
3542}
3543
3544bool Variant::is_ref_counted() const {
3545 return type == OBJECT && _get_obj().id.is_ref_counted();
3546}
3547
3548Vector<Variant> varray() {
3549 return Vector<Variant>();
3550}
3551
3552Vector<Variant> varray(const Variant &p_arg1) {
3553 Vector<Variant> v;
3554 v.push_back(p_arg1);
3555 return v;
3556}
3557
3558Vector<Variant> varray(const Variant &p_arg1, const Variant &p_arg2) {
3559 Vector<Variant> v;
3560 v.push_back(p_arg1);
3561 v.push_back(p_arg2);
3562 return v;
3563}
3564
3565Vector<Variant> varray(const Variant &p_arg1, const Variant &p_arg2, const Variant &p_arg3) {
3566 Vector<Variant> v;
3567 v.push_back(p_arg1);
3568 v.push_back(p_arg2);
3569 v.push_back(p_arg3);
3570 return v;
3571}
3572
3573Vector<Variant> varray(const Variant &p_arg1, const Variant &p_arg2, const Variant &p_arg3, const Variant &p_arg4) {
3574 Vector<Variant> v;
3575 v.push_back(p_arg1);
3576 v.push_back(p_arg2);
3577 v.push_back(p_arg3);
3578 v.push_back(p_arg4);
3579 return v;
3580}
3581
3582Vector<Variant> varray(const Variant &p_arg1, const Variant &p_arg2, const Variant &p_arg3, const Variant &p_arg4, const Variant &p_arg5) {
3583 Vector<Variant> v;
3584 v.push_back(p_arg1);
3585 v.push_back(p_arg2);
3586 v.push_back(p_arg3);
3587 v.push_back(p_arg4);
3588 v.push_back(p_arg5);
3589 return v;
3590}
3591
3592void Variant::static_assign(const Variant &p_variant) {
3593}
3594
3595bool Variant::is_type_shared(Variant::Type p_type) {
3596 switch (p_type) {
3597 case OBJECT:
3598 case ARRAY:
3599 case DICTIONARY:
3600 return true;
3601 default: {
3602 }
3603 }
3604
3605 return false;
3606}
3607
3608bool Variant::is_shared() const {
3609 return is_type_shared(type);
3610}
3611
3612void Variant::_variant_call_error(const String &p_method, Callable::CallError &error) {
3613 switch (error.error) {
3614 case Callable::CallError::CALL_ERROR_INVALID_ARGUMENT: {
3615 String err = "Invalid type for argument #" + itos(error.argument) + ", expected '" + Variant::get_type_name(Variant::Type(error.expected)) + "'.";
3616 ERR_PRINT(err.utf8().get_data());
3617
3618 } break;
3619 case Callable::CallError::CALL_ERROR_INVALID_METHOD: {
3620 String err = "Invalid method '" + p_method + "' for type '" + Variant::get_type_name(type) + "'.";
3621 ERR_PRINT(err.utf8().get_data());
3622 } break;
3623 case Callable::CallError::CALL_ERROR_TOO_MANY_ARGUMENTS: {
3624 String err = "Too many arguments for method '" + p_method + "'";
3625 ERR_PRINT(err.utf8().get_data());
3626 } break;
3627 default: {
3628 }
3629 }
3630}
3631
3632void Variant::construct_from_string(const String &p_string, Variant &r_value, ObjectConstruct p_obj_construct, void *p_construct_ud) {
3633 r_value = Variant();
3634}
3635
3636String Variant::get_construct_string() const {
3637 String vars;
3638 VariantWriter::write_to_string(*this, vars);
3639
3640 return vars;
3641}
3642
3643String Variant::get_call_error_text(const StringName &p_method, const Variant **p_argptrs, int p_argcount, const Callable::CallError &ce) {
3644 return get_call_error_text(nullptr, p_method, p_argptrs, p_argcount, ce);
3645}
3646
3647String Variant::get_call_error_text(Object *p_base, const StringName &p_method, const Variant **p_argptrs, int p_argcount, const Callable::CallError &ce) {
3648 String err_text;
3649
3650 if (ce.error == Callable::CallError::CALL_ERROR_INVALID_ARGUMENT) {
3651 int errorarg = ce.argument;
3652 if (p_argptrs) {
3653 err_text = "Cannot convert argument " + itos(errorarg + 1) + " from " + Variant::get_type_name(p_argptrs[errorarg]->get_type()) + " to " + Variant::get_type_name(Variant::Type(ce.expected));
3654 } else {
3655 err_text = "Cannot convert argument " + itos(errorarg + 1) + " from [missing argptr, type unknown] to " + Variant::get_type_name(Variant::Type(ce.expected));
3656 }
3657 } else if (ce.error == Callable::CallError::CALL_ERROR_TOO_MANY_ARGUMENTS) {
3658 err_text = "Method expected " + itos(ce.expected) + " arguments, but called with " + itos(p_argcount);
3659 } else if (ce.error == Callable::CallError::CALL_ERROR_TOO_FEW_ARGUMENTS) {
3660 err_text = "Method expected " + itos(ce.expected) + " arguments, but called with " + itos(p_argcount);
3661 } else if (ce.error == Callable::CallError::CALL_ERROR_INVALID_METHOD) {
3662 err_text = "Method not found";
3663 } else if (ce.error == Callable::CallError::CALL_ERROR_INSTANCE_IS_NULL) {
3664 err_text = "Instance is null";
3665 } else if (ce.error == Callable::CallError::CALL_ERROR_METHOD_NOT_CONST) {
3666 err_text = "Method not const in const instance";
3667 } else if (ce.error == Callable::CallError::CALL_OK) {
3668 return "Call OK";
3669 }
3670
3671 String base_text;
3672 if (p_base) {
3673 base_text = p_base->get_class();
3674 Ref<Resource> script = p_base->get_script();
3675 if (script.is_valid() && script->get_path().is_resource_file()) {
3676 base_text += "(" + script->get_path().get_file() + ")";
3677 }
3678 base_text += "::";
3679 }
3680 return "'" + base_text + String(p_method) + "': " + err_text;
3681}
3682
3683String Variant::get_callable_error_text(const Callable &p_callable, const Variant **p_argptrs, int p_argcount, const Callable::CallError &ce) {
3684 Vector<Variant> binds;
3685 int args_bound;
3686 p_callable.get_bound_arguments_ref(binds, args_bound);
3687 if (args_bound <= 0) {
3688 return get_call_error_text(p_callable.get_object(), p_callable.get_method(), p_argptrs, MAX(0, p_argcount + args_bound), ce);
3689 } else {
3690 Vector<const Variant *> argptrs;
3691 argptrs.resize(p_argcount + binds.size());
3692 for (int i = 0; i < p_argcount; i++) {
3693 argptrs.write[i] = p_argptrs[i];
3694 }
3695 for (int i = 0; i < binds.size(); i++) {
3696 argptrs.write[i + p_argcount] = &binds[i];
3697 }
3698 return get_call_error_text(p_callable.get_object(), p_callable.get_method(), (const Variant **)argptrs.ptr(), argptrs.size(), ce);
3699 }
3700}
3701
3702void Variant::register_types() {
3703 _register_variant_operators();
3704 _register_variant_methods();
3705 _register_variant_setters_getters();
3706 _register_variant_constructors();
3707 _register_variant_destructors();
3708 _register_variant_utility_functions();
3709}
3710void Variant::unregister_types() {
3711 _unregister_variant_operators();
3712 _unregister_variant_methods();
3713 _unregister_variant_setters_getters();
3714 _unregister_variant_destructors();
3715 _unregister_variant_utility_functions();
3716}
3717