react-native-reanimated 4.0.1 → 4.0.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (43) hide show
  1. package/Common/cpp/reanimated/Fabric/updates/UpdatesRegistryManager.cpp +13 -14
  2. package/Common/cpp/reanimated/Fabric/updates/UpdatesRegistryManager.h +4 -2
  3. package/Common/cpp/reanimated/LayoutAnimations/LayoutAnimationsProxy.h +2 -2
  4. package/Common/cpp/reanimated/NativeModules/ReanimatedModuleProxy.cpp +207 -23
  5. package/android/build.gradle +11 -15
  6. package/android/src/main/java/com/swmansion/reanimated/NativeProxy.java +93 -8
  7. package/lib/module/animation/spring/springUtils.js +3 -1
  8. package/lib/module/animation/spring/springUtils.js.map +1 -1
  9. package/lib/module/createAnimatedComponent/JSPropsUpdater.js +0 -5
  10. package/lib/module/createAnimatedComponent/JSPropsUpdater.js.map +1 -1
  11. package/lib/module/css/managers/CSSAnimationsManager.web.js +3 -1
  12. package/lib/module/css/managers/CSSAnimationsManager.web.js.map +1 -1
  13. package/lib/module/initializers.js +6 -1
  14. package/lib/module/initializers.js.map +1 -1
  15. package/lib/module/layoutReanimation/animationsManager.js +8 -5
  16. package/lib/module/layoutReanimation/animationsManager.js.map +1 -1
  17. package/lib/module/layoutReanimation/web/animationParser.js.map +1 -1
  18. package/lib/module/layoutReanimation/web/config.js.map +1 -1
  19. package/lib/module/layoutReanimation/web/createAnimation.js +12 -0
  20. package/lib/module/layoutReanimation/web/createAnimation.js.map +1 -1
  21. package/lib/module/platform-specific/jsVersion.js +1 -1
  22. package/lib/typescript/animation/spring/springUtils.d.ts.map +1 -1
  23. package/lib/typescript/createAnimatedComponent/JSPropsUpdater.d.ts +0 -1
  24. package/lib/typescript/createAnimatedComponent/JSPropsUpdater.d.ts.map +1 -1
  25. package/lib/typescript/css/managers/CSSAnimationsManager.web.d.ts.map +1 -1
  26. package/lib/typescript/layoutReanimation/animationsManager.d.ts.map +1 -1
  27. package/lib/typescript/layoutReanimation/web/animationParser.d.ts +3 -0
  28. package/lib/typescript/layoutReanimation/web/animationParser.d.ts.map +1 -1
  29. package/lib/typescript/layoutReanimation/web/config.d.ts +1 -1
  30. package/lib/typescript/layoutReanimation/web/config.d.ts.map +1 -1
  31. package/lib/typescript/layoutReanimation/web/createAnimation.d.ts.map +1 -1
  32. package/lib/typescript/platform-specific/jsVersion.d.ts +1 -1
  33. package/package.json +2 -2
  34. package/scripts/reanimated_utils.rb +1 -1
  35. package/src/animation/spring/springUtils.ts +3 -4
  36. package/src/createAnimatedComponent/JSPropsUpdater.ts +0 -6
  37. package/src/css/managers/CSSAnimationsManager.web.ts +3 -1
  38. package/src/initializers.ts +5 -1
  39. package/src/layoutReanimation/animationsManager.ts +8 -5
  40. package/src/layoutReanimation/web/animationParser.ts +3 -0
  41. package/src/layoutReanimation/web/config.ts +4 -1
  42. package/src/layoutReanimation/web/createAnimation.ts +15 -0
  43. package/src/platform-specific/jsVersion.ts +1 -1
@@ -57,25 +57,24 @@ void UpdatesRegistryManager::unmarkNodeAsRemovable(Tag viewTag) {
57
57
 
58
58
  void UpdatesRegistryManager::handleNodeRemovals(
59
59
  const RootShadowNode &rootShadowNode) {
60
- for (auto it = removableShadowNodes_.begin();
61
- it != removableShadowNodes_.end();) {
62
- const auto &shadowNode = it->second;
63
- const auto &family = shadowNode->getFamily();
64
- const auto &ancestors = family.getAncestors(rootShadowNode);
65
-
66
- // Skip if the node hasn't been removed
67
- if (!ancestors.empty()) {
68
- ++it;
60
+ RemovableShadowNodes remainingShadowNodes;
61
+
62
+ for (const auto &[tag, shadowNode] : removableShadowNodes_) {
63
+ if (!shadowNode) {
69
64
  continue;
70
65
  }
71
66
 
72
- const auto tag = shadowNode->getTag();
73
- for (auto &registry : registries_) {
74
- registry->remove(tag);
67
+ if (shadowNode->getFamily().getAncestors(rootShadowNode).empty()) {
68
+ for (auto &registry : registries_) {
69
+ registry->remove(tag);
70
+ }
71
+ staticPropsRegistry_->remove(tag);
72
+ } else {
73
+ remainingShadowNodes.emplace(tag, shadowNode);
75
74
  }
76
- staticPropsRegistry_->remove(tag);
77
- it = removableShadowNodes_.erase(it);
78
75
  }
76
+
77
+ removableShadowNodes_ = std::move(remainingShadowNodes);
79
78
  }
80
79
 
81
80
  PropsMap UpdatesRegistryManager::collectProps() {
@@ -45,11 +45,13 @@ class UpdatesRegistryManager {
45
45
  #endif
46
46
 
47
47
  private:
48
+ using RemovableShadowNodes =
49
+ std::unordered_map<Tag, std::shared_ptr<const ShadowNode>>;
50
+
48
51
  mutable std::mutex mutex_;
49
52
  std::atomic<bool> isPaused_;
50
53
  std::atomic<bool> shouldCommitAfterPause_;
51
- std::unordered_map<Tag, std::shared_ptr<const ShadowNode>>
52
- removableShadowNodes_;
54
+ RemovableShadowNodes removableShadowNodes_;
53
55
  std::vector<std::shared_ptr<UpdatesRegistry>> registries_;
54
56
  const std::shared_ptr<StaticPropsRegistry> staticPropsRegistry_;
55
57
 
@@ -44,14 +44,14 @@ struct LayoutAnimationsProxy
44
44
  mutable std::unordered_map<Tag, int> leastRemoved;
45
45
  mutable std::vector<Tag> finishedAnimationTags_;
46
46
  std::shared_ptr<LayoutAnimationsManager> layoutAnimationsManager_;
47
- ContextContainer::Shared contextContainer_;
47
+ std::shared_ptr<const ContextContainer> contextContainer_;
48
48
  SharedComponentDescriptorRegistry componentDescriptorRegistry_;
49
49
  jsi::Runtime &uiRuntime_;
50
50
  const std::shared_ptr<UIScheduler> uiScheduler_;
51
51
  LayoutAnimationsProxy(
52
52
  std::shared_ptr<LayoutAnimationsManager> layoutAnimationsManager,
53
53
  SharedComponentDescriptorRegistry componentDescriptorRegistry,
54
- ContextContainer::Shared contextContainer,
54
+ std::shared_ptr<const ContextContainer> contextContainer,
55
55
  jsi::Runtime &uiRuntime,
56
56
  const std::shared_ptr<UIScheduler> uiScheduler)
57
57
  : layoutAnimationsManager_(layoutAnimationsManager),
@@ -408,6 +408,7 @@ void ReanimatedModuleProxy::setViewStyle(
408
408
  void ReanimatedModuleProxy::markNodeAsRemovable(
409
409
  jsi::Runtime &rt,
410
410
  const jsi::Value &shadowNodeWrapper) {
411
+ auto lock = updatesRegistryManager_->lock();
411
412
  auto shadowNode = shadowNodeFromValue(rt, shadowNodeWrapper);
412
413
  updatesRegistryManager_->markNodeAsRemovable(shadowNode);
413
414
  }
@@ -415,6 +416,7 @@ void ReanimatedModuleProxy::markNodeAsRemovable(
415
416
  void ReanimatedModuleProxy::unmarkNodeAsRemovable(
416
417
  jsi::Runtime &rt,
417
418
  const jsi::Value &viewTag) {
419
+ auto lock = updatesRegistryManager_->lock();
418
420
  updatesRegistryManager_->unmarkNodeAsRemovable(viewTag.asNumber());
419
421
  }
420
422
 
@@ -674,12 +676,35 @@ void ReanimatedModuleProxy::performOperations() {
674
676
  if constexpr (StaticFeatureFlags::getFlag(
675
677
  "ANDROID_SYNCHRONOUSLY_UPDATE_UI_PROPS")) {
676
678
  static const std::unordered_set<std::string> synchronousProps = {
677
- "transform",
678
679
  "opacity",
679
- "borderRadius",
680
+ "elevation",
681
+ "zIndex",
682
+ // "shadowOpacity", // not supported on Android
683
+ // "shadowRadius", // not supported on Android
680
684
  "backgroundColor",
681
- "borderColor",
682
685
  // "color", // TODO: fix animating color of Animated.Text
686
+ "tintColor",
687
+ "borderRadius",
688
+ "borderTopLeftRadius",
689
+ "borderTopRightRadius",
690
+ "borderTopStartRadius",
691
+ "borderTopEndRadius",
692
+ "borderBottomLeftRadius",
693
+ "borderBottomRightRadius",
694
+ "borderBottomStartRadius",
695
+ "borderBottomEndRadius",
696
+ "borderStartStartRadius",
697
+ "borderStartEndRadius",
698
+ "borderEndStartRadius",
699
+ "borderEndEndRadius",
700
+ "borderColor",
701
+ "borderTopColor",
702
+ "borderBottomColor",
703
+ "borderLeftColor",
704
+ "borderRightColor",
705
+ "borderStartColor",
706
+ "borderEndColor",
707
+ "transform",
683
708
  };
684
709
 
685
710
  // NOTE: Keep in sync with NativeProxy.java
@@ -687,11 +712,38 @@ void ReanimatedModuleProxy::performOperations() {
687
712
  static constexpr auto CMD_START_OF_TRANSFORM = 2;
688
713
  static constexpr auto CMD_END_OF_TRANSFORM = 3;
689
714
  static constexpr auto CMD_END_OF_VIEW = 4;
715
+
690
716
  static constexpr auto CMD_OPACITY = 10;
691
- static constexpr auto CMD_BORDER_RADIUS = 11;
692
- static constexpr auto CMD_BACKGROUND_COLOR = 12;
693
- static constexpr auto CMD_BORDER_COLOR = 13;
694
- static constexpr auto CMD_COLOR = 14;
717
+ static constexpr auto CMD_ELEVATION = 11;
718
+ static constexpr auto CMD_Z_INDEX = 12;
719
+ static constexpr auto CMD_SHADOW_OPACITY = 13;
720
+ static constexpr auto CMD_SHADOW_RADIUS = 14;
721
+ static constexpr auto CMD_BACKGROUND_COLOR = 15;
722
+ static constexpr auto CMD_COLOR = 16;
723
+ static constexpr auto CMD_TINT_COLOR = 17;
724
+
725
+ static constexpr auto CMD_BORDER_RADIUS = 20;
726
+ static constexpr auto CMD_BORDER_TOP_LEFT_RADIUS = 21;
727
+ static constexpr auto CMD_BORDER_TOP_RIGHT_RADIUS = 22;
728
+ static constexpr auto CMD_BORDER_TOP_START_RADIUS = 23;
729
+ static constexpr auto CMD_BORDER_TOP_END_RADIUS = 24;
730
+ static constexpr auto CMD_BORDER_BOTTOM_LEFT_RADIUS = 25;
731
+ static constexpr auto CMD_BORDER_BOTTOM_RIGHT_RADIUS = 26;
732
+ static constexpr auto CMD_BORDER_BOTTOM_START_RADIUS = 27;
733
+ static constexpr auto CMD_BORDER_BOTTOM_END_RADIUS = 28;
734
+ static constexpr auto CMD_BORDER_START_START_RADIUS = 29;
735
+ static constexpr auto CMD_BORDER_START_END_RADIUS = 30;
736
+ static constexpr auto CMD_BORDER_END_START_RADIUS = 31;
737
+ static constexpr auto CMD_BORDER_END_END_RADIUS = 32;
738
+
739
+ static constexpr auto CMD_BORDER_COLOR = 40;
740
+ static constexpr auto CMD_BORDER_TOP_COLOR = 41;
741
+ static constexpr auto CMD_BORDER_BOTTOM_COLOR = 42;
742
+ static constexpr auto CMD_BORDER_LEFT_COLOR = 43;
743
+ static constexpr auto CMD_BORDER_RIGHT_COLOR = 44;
744
+ static constexpr auto CMD_BORDER_START_COLOR = 45;
745
+ static constexpr auto CMD_BORDER_END_COLOR = 46;
746
+
695
747
  static constexpr auto CMD_TRANSFORM_TRANSLATE_X = 100;
696
748
  static constexpr auto CMD_TRANSFORM_TRANSLATE_Y = 101;
697
749
  static constexpr auto CMD_TRANSFORM_SCALE = 102;
@@ -705,6 +757,7 @@ void ReanimatedModuleProxy::performOperations() {
705
757
  static constexpr auto CMD_TRANSFORM_SKEW_Y = 110;
706
758
  static constexpr auto CMD_TRANSFORM_MATRIX = 111;
707
759
  static constexpr auto CMD_TRANSFORM_PERSPECTIVE = 112;
760
+
708
761
  static constexpr auto CMD_UNIT_DEG = 200;
709
762
  static constexpr auto CMD_UNIT_RAD = 201;
710
763
  static constexpr auto CMD_UNIT_PX = 202;
@@ -713,47 +766,135 @@ void ReanimatedModuleProxy::performOperations() {
713
766
  const auto propNameToCommand = [](const std::string &name) {
714
767
  if (name == "opacity")
715
768
  return CMD_OPACITY;
716
- if (name == "borderRadius")
717
- return CMD_BORDER_RADIUS;
769
+
770
+ if (name == "elevation")
771
+ return CMD_ELEVATION;
772
+
773
+ if (name == "zIndex")
774
+ return CMD_Z_INDEX;
775
+
776
+ if (name == "shadowOpacity")
777
+ return CMD_SHADOW_OPACITY;
778
+
779
+ if (name == "shadowRadius")
780
+ return CMD_SHADOW_RADIUS;
781
+
718
782
  if (name == "backgroundColor")
719
783
  return CMD_BACKGROUND_COLOR;
720
- if (name == "borderColor")
721
- return CMD_BORDER_COLOR;
784
+
722
785
  if (name == "color")
723
786
  return CMD_COLOR;
787
+
788
+ if (name == "tintColor")
789
+ return CMD_TINT_COLOR;
790
+
791
+ if (name == "borderRadius")
792
+ return CMD_BORDER_RADIUS;
793
+
794
+ if (name == "borderTopLeftRadius")
795
+ return CMD_BORDER_TOP_LEFT_RADIUS;
796
+
797
+ if (name == "borderTopRightRadius")
798
+ return CMD_BORDER_TOP_RIGHT_RADIUS;
799
+
800
+ if (name == "borderTopStartRadius")
801
+ return CMD_BORDER_TOP_START_RADIUS;
802
+
803
+ if (name == "borderTopEndRadius")
804
+ return CMD_BORDER_TOP_END_RADIUS;
805
+
806
+ if (name == "borderBottomLeftRadius")
807
+ return CMD_BORDER_BOTTOM_LEFT_RADIUS;
808
+
809
+ if (name == "borderBottomRightRadius")
810
+ return CMD_BORDER_BOTTOM_RIGHT_RADIUS;
811
+
812
+ if (name == "borderBottomStartRadius")
813
+ return CMD_BORDER_BOTTOM_START_RADIUS;
814
+
815
+ if (name == "borderBottomEndRadius")
816
+ return CMD_BORDER_BOTTOM_END_RADIUS;
817
+
818
+ if (name == "borderStartStartRadius")
819
+ return CMD_BORDER_START_START_RADIUS;
820
+
821
+ if (name == "borderStartEndRadius")
822
+ return CMD_BORDER_START_END_RADIUS;
823
+
824
+ if (name == "borderEndStartRadius")
825
+ return CMD_BORDER_END_START_RADIUS;
826
+
827
+ if (name == "borderEndEndRadius")
828
+ return CMD_BORDER_END_END_RADIUS;
829
+
830
+ if (name == "borderColor")
831
+ return CMD_BORDER_COLOR;
832
+
833
+ if (name == "borderTopColor")
834
+ return CMD_BORDER_TOP_COLOR;
835
+
836
+ if (name == "borderBottomColor")
837
+ return CMD_BORDER_BOTTOM_COLOR;
838
+
839
+ if (name == "borderLeftColor")
840
+ return CMD_BORDER_LEFT_COLOR;
841
+
842
+ if (name == "borderRightColor")
843
+ return CMD_BORDER_RIGHT_COLOR;
844
+
845
+ if (name == "borderStartColor")
846
+ return CMD_BORDER_START_COLOR;
847
+
848
+ if (name == "borderEndColor")
849
+ return CMD_BORDER_END_COLOR;
850
+
724
851
  if (name == "transform")
725
852
  return CMD_START_OF_TRANSFORM; // TODO: use CMD_TRANSFORM?
726
- throw std::runtime_error("Unsupported style: " + name);
853
+
854
+ throw std::runtime_error("[Reanimated] Unsupported style: " + name);
727
855
  };
728
856
 
729
857
  const auto transformNameToCommand = [](const std::string &name) {
730
858
  if (name == "translateX")
731
859
  return CMD_TRANSFORM_TRANSLATE_X;
860
+
732
861
  if (name == "translateY")
733
862
  return CMD_TRANSFORM_TRANSLATE_Y;
863
+
734
864
  if (name == "scale")
735
865
  return CMD_TRANSFORM_SCALE;
866
+
736
867
  if (name == "scaleX")
737
868
  return CMD_TRANSFORM_SCALE_X;
869
+
738
870
  if (name == "scaleY")
739
871
  return CMD_TRANSFORM_SCALE_Y;
872
+
740
873
  if (name == "rotate")
741
874
  return CMD_TRANSFORM_ROTATE;
875
+
742
876
  if (name == "rotateX")
743
877
  return CMD_TRANSFORM_ROTATE_X;
878
+
744
879
  if (name == "rotateY")
745
880
  return CMD_TRANSFORM_ROTATE_Y;
881
+
746
882
  if (name == "rotateZ")
747
883
  return CMD_TRANSFORM_ROTATE_Z;
884
+
748
885
  if (name == "skewX")
749
886
  return CMD_TRANSFORM_SKEW_X;
887
+
750
888
  if (name == "skewY")
751
889
  return CMD_TRANSFORM_SKEW_Y;
890
+
752
891
  if (name == "matrix")
753
892
  return CMD_TRANSFORM_MATRIX;
893
+
754
894
  if (name == "perspective")
755
895
  return CMD_TRANSFORM_PERSPECTIVE;
756
- throw std::runtime_error("Unsupported transform: " + name);
896
+
897
+ throw std::runtime_error("[Reanimated] Unsupported transform: " + name);
757
898
  };
758
899
 
759
900
  UpdatesBatch synchronousUpdatesBatch, shadowTreeUpdatesBatch;
@@ -787,29 +928,71 @@ void ReanimatedModuleProxy::performOperations() {
787
928
  const auto command = propNameToCommand(key.getString());
788
929
  switch (command) {
789
930
  case CMD_OPACITY:
790
- case CMD_BORDER_RADIUS:
931
+ case CMD_ELEVATION:
932
+ case CMD_Z_INDEX:
933
+ case CMD_SHADOW_OPACITY:
934
+ case CMD_SHADOW_RADIUS:
791
935
  intBuffer.push_back(command);
792
936
  doubleBuffer.push_back(value.asDouble());
793
937
  break;
794
938
 
795
939
  case CMD_BACKGROUND_COLOR:
796
- case CMD_BORDER_COLOR:
797
940
  case CMD_COLOR:
941
+ case CMD_TINT_COLOR:
942
+ case CMD_BORDER_COLOR:
943
+ case CMD_BORDER_TOP_COLOR:
944
+ case CMD_BORDER_BOTTOM_COLOR:
945
+ case CMD_BORDER_LEFT_COLOR:
946
+ case CMD_BORDER_RIGHT_COLOR:
947
+ case CMD_BORDER_START_COLOR:
948
+ case CMD_BORDER_END_COLOR:
798
949
  intBuffer.push_back(command);
799
950
  intBuffer.push_back(value.asInt());
800
951
  break;
801
952
 
953
+ case CMD_BORDER_RADIUS:
954
+ case CMD_BORDER_TOP_LEFT_RADIUS:
955
+ case CMD_BORDER_TOP_RIGHT_RADIUS:
956
+ case CMD_BORDER_TOP_START_RADIUS:
957
+ case CMD_BORDER_TOP_END_RADIUS:
958
+ case CMD_BORDER_BOTTOM_LEFT_RADIUS:
959
+ case CMD_BORDER_BOTTOM_RIGHT_RADIUS:
960
+ case CMD_BORDER_BOTTOM_START_RADIUS:
961
+ case CMD_BORDER_BOTTOM_END_RADIUS:
962
+ case CMD_BORDER_START_START_RADIUS:
963
+ case CMD_BORDER_START_END_RADIUS:
964
+ case CMD_BORDER_END_START_RADIUS:
965
+ case CMD_BORDER_END_END_RADIUS:
966
+ intBuffer.push_back(command);
967
+ if (value.isDouble()) {
968
+ intBuffer.push_back(CMD_UNIT_PX);
969
+ doubleBuffer.push_back(value.getDouble());
970
+ } else if (value.isString()) {
971
+ const auto &valueStr = value.getString();
972
+ if (!valueStr.ends_with("%")) {
973
+ throw std::runtime_error(
974
+ "[Reanimated] Border radius string must be a percentage");
975
+ }
976
+ intBuffer.push_back(CMD_UNIT_PERCENT);
977
+ doubleBuffer.push_back(std::stof(valueStr.substr(0, -1)));
978
+ } else {
979
+ throw std::runtime_error(
980
+ "[Reanimated] Border radius value must be either a number or a string");
981
+ }
982
+ break;
983
+
802
984
  case CMD_START_OF_TRANSFORM:
803
985
  intBuffer.push_back(command);
804
986
  react_native_assert(
805
- value.isArray() && "Transform value must be an array");
987
+ value.isArray() &&
988
+ "[Reanimated] Transform value must be an array");
806
989
  for (const auto &item : value) {
807
990
  react_native_assert(
808
991
  item.isObject() &&
809
- "Transform array item must be an object");
992
+ "[Reanimated] Transform array item must be an object");
810
993
  react_native_assert(
811
994
  item.size() == 1 &&
812
- "Transform array item must have exactly one key-value pair");
995
+ "[Reanimated] Transform array item must have exactly one key-value pair");
813
996
  const auto transformCommand =
814
997
  transformNameToCommand(item.keys().begin()->getString());
815
998
  const auto &transformValue = *item.values().begin();
@@ -828,20 +1011,20 @@ void ReanimatedModuleProxy::performOperations() {
828
1011
  intBuffer.push_back(transformCommand);
829
1012
  if (transformValue.isDouble()) {
830
1013
  intBuffer.push_back(CMD_UNIT_PX);
831
- doubleBuffer.push_back(transformValue.asDouble());
1014
+ doubleBuffer.push_back(transformValue.getDouble());
832
1015
  } else if (transformValue.isString()) {
833
1016
  const auto &transformValueStr =
834
1017
  transformValue.getString();
835
1018
  if (!transformValueStr.ends_with("%")) {
836
1019
  throw std::runtime_error(
837
- "String translate must be a percentage");
1020
+ "[Reanimated] String translate must be a percentage");
838
1021
  }
839
1022
  intBuffer.push_back(CMD_UNIT_PERCENT);
840
1023
  doubleBuffer.push_back(
841
1024
  std::stof(transformValueStr.substr(0, -1)));
842
1025
  } else {
843
1026
  throw std::runtime_error(
844
- "Translate value must be a number or a string");
1027
+ "[Reanimated] Translate value must be either a number or a string");
845
1028
  }
846
1029
  break;
847
1030
  }
@@ -861,7 +1044,8 @@ void ReanimatedModuleProxy::performOperations() {
861
1044
  intBuffer.push_back(CMD_UNIT_RAD);
862
1045
  } else {
863
1046
  throw std::runtime_error(
864
- "Unsupported rotation unit: " + transformValueStr);
1047
+ "[Reanimated] Unsupported rotation unit: " +
1048
+ transformValueStr);
865
1049
  }
866
1050
  doubleBuffer.push_back(
867
1051
  std::stof(transformValueStr.substr(0, -3)));
@@ -872,7 +1056,7 @@ void ReanimatedModuleProxy::performOperations() {
872
1056
  intBuffer.push_back(transformCommand);
873
1057
  react_native_assert(
874
1058
  transformValue.isArray() &&
875
- "Matrix must be an array");
1059
+ "[Reanimated] Matrix must be an array");
876
1060
  int size = transformValue.size();
877
1061
  intBuffer.push_back(size);
878
1062
  for (int i = 0; i < size; i++) {
@@ -85,18 +85,6 @@ def toPlatformFileString(String path) {
85
85
  return path
86
86
  }
87
87
 
88
- def validateWorkletsVersion() {
89
- def result = providers.exec {
90
- workingDir(projectDir.path)
91
- commandLine("node", "./../scripts/validate-worklets-build.js")
92
- ignoreExitValue = true
93
- }
94
-
95
- if (result.getResult().get().exitValue != 0) {
96
- throw new GradleException(result.getStandardError().getAsText().get().trim())
97
- }
98
- }
99
-
100
88
  def getReanimatedStaticFeatureFlags() {
101
89
  def featureFlags = new HashMap<String, String>()
102
90
 
@@ -123,6 +111,7 @@ if (isNewArchitectureEnabled()) {
123
111
  apply plugin: "com.facebook.react"
124
112
  }
125
113
 
114
+ def packageDir = project.projectDir.parentFile
126
115
  def reactNativeRootDir = resolveReactNativeDirectory()
127
116
  def reactNativeWorkletsRootDir = resolveReactNativeWorkletsDirectory()
128
117
  def REACT_NATIVE_MINOR_VERSION = getReactNativeMinorVersion()
@@ -270,7 +259,6 @@ android {
270
259
  if (!IS_REANIMATED_EXAMPLE_APP) {
271
260
  return
272
261
  }
273
- def packageDir = new File("${project.projectDir}/..")
274
262
 
275
263
  def generated = new File("${compileTask.abi.getCxxBuildFolder()}/compile_commands.json")
276
264
  def output = new File("${packageDir}/compile_commands.json")
@@ -284,7 +272,7 @@ android {
284
272
 
285
273
  task assertMinimalReactNativeVersionTask {
286
274
  // If you change the minimal React Native version remember to update Compatibility Table in docs
287
- def minimalReactNativeVersion = 75
275
+ def minimalReactNativeVersion = 78
288
276
  onlyIf { REACT_NATIVE_MINOR_VERSION < minimalReactNativeVersion }
289
277
  doFirst {
290
278
  throw new GradleException("[Reanimated] Unsupported React Native version. Please use React Native 0.$minimalReactNativeVersion or newer.")
@@ -302,9 +290,17 @@ task assertNewArchitectureEnabledTask {
302
290
 
303
291
  preBuild.dependsOn(assertNewArchitectureEnabledTask)
304
292
 
293
+ def validateWorkletsBuildResult = providers.exec {
294
+ workingDir(projectDir.path)
295
+ commandLine("node", "./../scripts/validate-worklets-build.js")
296
+ ignoreExitValue = true
297
+ }
298
+
305
299
  task assertWorkletsVersionTask {
306
300
  doFirst {
307
- validateWorkletsVersion()
301
+ if (validateWorkletsBuildResult.getResult().get().exitValue != 0) {
302
+ throw new GradleException(validateWorkletsBuildResult.getStandardError().getAsText().get().trim())
303
+ }
308
304
  }
309
305
  }
310
306
 
@@ -185,11 +185,38 @@ public class NativeProxy {
185
185
  private static final int CMD_START_OF_TRANSFORM = 2;
186
186
  private static final int CMD_END_OF_TRANSFORM = 3;
187
187
  private static final int CMD_END_OF_VIEW = 4;
188
+
188
189
  private static final int CMD_OPACITY = 10;
189
- private static final int CMD_BORDER_RADIUS = 11;
190
- private static final int CMD_BACKGROUND_COLOR = 12;
191
- private static final int CMD_BORDER_COLOR = 13;
192
- private static final int CMD_COLOR = 14;
190
+ private static final int CMD_ELEVATION = 11;
191
+ private static final int CMD_Z_INDEX = 12;
192
+ private static final int CMD_SHADOW_OPACITY = 13;
193
+ private static final int CMD_SHADOW_RADIUS = 14;
194
+ private static final int CMD_BACKGROUND_COLOR = 15;
195
+ private static final int CMD_COLOR = 16;
196
+ private static final int CMD_TINT_COLOR = 17;
197
+
198
+ private static final int CMD_BORDER_RADIUS = 20;
199
+ private static final int CMD_BORDER_TOP_LEFT_RADIUS = 21;
200
+ private static final int CMD_BORDER_TOP_RIGHT_RADIUS = 22;
201
+ private static final int CMD_BORDER_TOP_START_RADIUS = 23;
202
+ private static final int CMD_BORDER_TOP_END_RADIUS = 24;
203
+ private static final int CMD_BORDER_BOTTOM_LEFT_RADIUS = 25;
204
+ private static final int CMD_BORDER_BOTTOM_RIGHT_RADIUS = 26;
205
+ private static final int CMD_BORDER_BOTTOM_START_RADIUS = 27;
206
+ private static final int CMD_BORDER_BOTTOM_END_RADIUS = 28;
207
+ private static final int CMD_BORDER_START_START_RADIUS = 29;
208
+ private static final int CMD_BORDER_START_END_RADIUS = 30;
209
+ private static final int CMD_BORDER_END_START_RADIUS = 31;
210
+ private static final int CMD_BORDER_END_END_RADIUS = 32;
211
+
212
+ private static final int CMD_BORDER_COLOR = 40;
213
+ private static final int CMD_BORDER_TOP_COLOR = 41;
214
+ private static final int CMD_BORDER_BOTTOM_COLOR = 42;
215
+ private static final int CMD_BORDER_LEFT_COLOR = 43;
216
+ private static final int CMD_BORDER_RIGHT_COLOR = 44;
217
+ private static final int CMD_BORDER_START_COLOR = 45;
218
+ private static final int CMD_BORDER_END_COLOR = 46;
219
+
193
220
  private static final int CMD_TRANSFORM_TRANSLATE_X = 100;
194
221
  private static final int CMD_TRANSFORM_TRANSLATE_Y = 101;
195
222
  private static final int CMD_TRANSFORM_SCALE = 102;
@@ -203,6 +230,7 @@ public class NativeProxy {
203
230
  private static final int CMD_TRANSFORM_SKEW_Y = 110;
204
231
  private static final int CMD_TRANSFORM_MATRIX = 111;
205
232
  private static final int CMD_TRANSFORM_PERSPECTIVE = 112;
233
+
206
234
  private static final int CMD_UNIT_DEG = 200;
207
235
  private static final int CMD_UNIT_RAD = 201;
208
236
  private static final int CMD_UNIT_PX = 202;
@@ -211,10 +239,33 @@ public class NativeProxy {
211
239
  private static String commandToString(int command) {
212
240
  return switch (command) {
213
241
  case CMD_OPACITY -> "opacity";
214
- case CMD_BORDER_RADIUS -> "borderRadius";
242
+ case CMD_ELEVATION -> "elevation";
243
+ case CMD_Z_INDEX -> "zIndex";
244
+ case CMD_SHADOW_OPACITY -> "shadowOpacity";
245
+ case CMD_SHADOW_RADIUS -> "shadowRadius";
215
246
  case CMD_BACKGROUND_COLOR -> "backgroundColor";
216
- case CMD_BORDER_COLOR -> "borderColor";
217
247
  case CMD_COLOR -> "color";
248
+ case CMD_TINT_COLOR -> "tintColor";
249
+ case CMD_BORDER_RADIUS -> "borderRadius";
250
+ case CMD_BORDER_TOP_LEFT_RADIUS -> "borderTopLeftRadius";
251
+ case CMD_BORDER_TOP_RIGHT_RADIUS -> "borderTopRightRadius";
252
+ case CMD_BORDER_TOP_START_RADIUS -> "borderTopStartRadius";
253
+ case CMD_BORDER_TOP_END_RADIUS -> "borderTopEndRadius";
254
+ case CMD_BORDER_BOTTOM_LEFT_RADIUS -> "borderBottomLeftRadius";
255
+ case CMD_BORDER_BOTTOM_RIGHT_RADIUS -> "borderBottomRightRadius";
256
+ case CMD_BORDER_BOTTOM_START_RADIUS -> "borderBottomStartRadius";
257
+ case CMD_BORDER_BOTTOM_END_RADIUS -> "borderBottomEndRadius";
258
+ case CMD_BORDER_START_START_RADIUS -> "borderStartStartRadius";
259
+ case CMD_BORDER_START_END_RADIUS -> "borderStartEndRadius";
260
+ case CMD_BORDER_END_START_RADIUS -> "borderEndStartRadius";
261
+ case CMD_BORDER_END_END_RADIUS -> "borderEndEndRadius";
262
+ case CMD_BORDER_COLOR -> "borderColor";
263
+ case CMD_BORDER_TOP_COLOR -> "borderTopColor";
264
+ case CMD_BORDER_BOTTOM_COLOR -> "borderBottomColor";
265
+ case CMD_BORDER_LEFT_COLOR -> "borderLeftColor";
266
+ case CMD_BORDER_RIGHT_COLOR -> "borderRightColor";
267
+ case CMD_BORDER_START_COLOR -> "borderStartColor";
268
+ case CMD_BORDER_END_COLOR -> "borderEndColor";
218
269
  default -> throw new RuntimeException("Unknown command: " + command);
219
270
  };
220
271
  }
@@ -253,7 +304,10 @@ public class NativeProxy {
253
304
  break;
254
305
 
255
306
  case CMD_OPACITY:
256
- case CMD_BORDER_RADIUS:
307
+ case CMD_ELEVATION:
308
+ case CMD_Z_INDEX:
309
+ case CMD_SHADOW_OPACITY:
310
+ case CMD_SHADOW_RADIUS:
257
311
  {
258
312
  String name = commandToString(command);
259
313
  props.putDouble(name, doubleIterator.nextDouble());
@@ -261,14 +315,45 @@ public class NativeProxy {
261
315
  }
262
316
 
263
317
  case CMD_BACKGROUND_COLOR:
264
- case CMD_BORDER_COLOR:
265
318
  case CMD_COLOR:
319
+ case CMD_TINT_COLOR:
320
+ case CMD_BORDER_COLOR:
321
+ case CMD_BORDER_TOP_COLOR:
322
+ case CMD_BORDER_BOTTOM_COLOR:
323
+ case CMD_BORDER_LEFT_COLOR:
324
+ case CMD_BORDER_RIGHT_COLOR:
325
+ case CMD_BORDER_START_COLOR:
326
+ case CMD_BORDER_END_COLOR:
266
327
  {
267
328
  String name = commandToString(command);
268
329
  props.putInt(name, intIterator.nextInt());
269
330
  break;
270
331
  }
271
332
 
333
+ case CMD_BORDER_RADIUS:
334
+ case CMD_BORDER_TOP_LEFT_RADIUS:
335
+ case CMD_BORDER_TOP_RIGHT_RADIUS:
336
+ case CMD_BORDER_TOP_START_RADIUS:
337
+ case CMD_BORDER_TOP_END_RADIUS:
338
+ case CMD_BORDER_BOTTOM_LEFT_RADIUS:
339
+ case CMD_BORDER_BOTTOM_RIGHT_RADIUS:
340
+ case CMD_BORDER_BOTTOM_START_RADIUS:
341
+ case CMD_BORDER_BOTTOM_END_RADIUS:
342
+ case CMD_BORDER_START_START_RADIUS:
343
+ case CMD_BORDER_START_END_RADIUS:
344
+ case CMD_BORDER_END_START_RADIUS:
345
+ case CMD_BORDER_END_END_RADIUS:
346
+ {
347
+ String name = commandToString(command);
348
+ double value = doubleIterator.nextDouble();
349
+ switch (intIterator.nextInt()) {
350
+ case CMD_UNIT_PX -> props.putDouble(name, value);
351
+ case CMD_UNIT_PERCENT -> props.putString(name, value + "%");
352
+ default -> throw new RuntimeException("Unknown unit command");
353
+ }
354
+ break;
355
+ }
356
+
272
357
  case CMD_START_OF_TRANSFORM:
273
358
  JavaOnlyArray transform = new JavaOnlyArray();
274
359
  while (true) {
@@ -262,7 +262,9 @@ export function isAnimationTerminatingCalculation(animation, config) {
262
262
  initialEnergy
263
263
  } = animation;
264
264
  if (config.overshootClamping) {
265
- if (current > toValue && startValue < toValue || current < toValue && startValue > toValue) {
265
+ const leftBound = startValue >= 0 ? toValue : toValue + startValue;
266
+ const rightBound = leftBound + Math.abs(startValue);
267
+ if (current < leftBound || current > rightBound) {
266
268
  return true;
267
269
  }
268
270
  }