mirror of
https://github.com/facebook/react-native.git
synced 2025-11-01 09:14:26 +00:00
Compare commits
100
Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
aaff0d37e2 | ||
|
|
16a89816fc | ||
|
|
04858ecbab | ||
|
|
d8e00f0bb1 | ||
|
|
07f6f70aef | ||
|
|
ece8ca82cd | ||
|
|
08a59c59e0 | ||
|
|
fbd44ade3a | ||
|
|
4f94028ca6 | ||
|
|
0a567a63cd | ||
|
|
19ebd4c188 | ||
|
|
a2a72e239d | ||
|
|
fedceecc37 | ||
|
|
e3047db0dc | ||
|
|
1e212f91bc | ||
|
|
4f1f72ea34 | ||
|
|
fe1aacae6d | ||
|
|
a82b5acf3d | ||
|
|
8cc2874d3f | ||
|
|
d012b2c19b | ||
|
|
cfc6960bc4 | ||
|
|
ef742dbc68 | ||
|
|
11a1ad7a98 | ||
|
|
b01a5f91fe | ||
|
|
65ae3dafcd | ||
|
|
d3495fd162 | ||
|
|
252e1345bf | ||
|
|
dd1b795abe | ||
|
|
c125f306c2 | ||
|
|
03ab6a3098 | ||
|
|
46b562b9b3 | ||
|
|
c1bf39bfdf | ||
|
|
f238b74658 | ||
|
|
76e2ab4ac8 | ||
|
|
35dba09724 | ||
|
|
9e96acbd0f | ||
|
|
40b8f4ad22 | ||
|
|
3306691d64 | ||
|
|
f184b591cf | ||
|
|
62d8d30652 | ||
|
|
60967fdffb | ||
|
|
4b91b63094 | ||
|
|
7f7655d711 | ||
|
|
76e04fac82 | ||
|
|
18f4db44ef | ||
|
|
251eb3fd4c | ||
|
|
3782fe865d | ||
|
|
5742227dd8 | ||
|
|
90654e4ba2 | ||
|
|
60c01b4715 | ||
|
|
69e028da45 | ||
|
|
152cb538f6 | ||
|
|
2ec6e3d901 | ||
|
|
1a86ee17fb | ||
|
|
8888cf9a2d | ||
|
|
27c97ac942 | ||
|
|
e69f0726cd | ||
|
|
1ced97fbe6 | ||
|
|
ff7e24f19a | ||
|
|
d9ec57a3b9 | ||
|
|
33fed54a16 | ||
|
|
7b7b538d6b | ||
|
|
9612d2e225 | ||
|
|
ee8b66e278 | ||
|
|
f214a52a9a | ||
|
|
f338db9c17 | ||
|
|
fe4047fe3a | ||
|
|
9f479ff8d6 | ||
|
|
dda8ab69d4 | ||
|
|
f04d1f1ef7 | ||
|
|
54a1e41694 | ||
|
|
269cf58140 | ||
|
|
941853974b | ||
|
|
36c0826f56 | ||
|
|
7970f79078 | ||
|
|
37e863e866 | ||
|
|
5961edd825 | ||
|
|
71d6d86ed6 | ||
|
|
0a7e1342cd | ||
|
|
891656d055 | ||
|
|
abbef4a0b8 | ||
|
|
e888329e9a | ||
|
|
1f8374e1dd | ||
|
|
a10ee5808b | ||
|
|
ab2ce4f2d8 | ||
|
|
ee256d11ae | ||
|
|
1f53d51e64 | ||
|
|
4f71a9434d | ||
|
|
ed9969b3d0 | ||
|
|
04da4800da | ||
|
|
bc093b8fa9 | ||
|
|
fbbd20dd63 | ||
|
|
710e08cd54 | ||
|
|
cc442eb8c8 | ||
|
|
aaad7e083d | ||
|
|
999f437b02 | ||
|
|
ffb37373ba | ||
|
|
e297fe1582 | ||
|
|
386a930afb | ||
|
|
281f48daf4 |
+3
-1
@@ -47,6 +47,8 @@ packages/react-native/flow/
|
||||
|
||||
[options]
|
||||
enums=true
|
||||
experimental.pattern_matching=true
|
||||
experimental.pattern_matching.includes=<PROJECT_ROOT>/packages/react-native/src/private/components/virtualview/
|
||||
casting_syntax=both
|
||||
component_syntax=true
|
||||
|
||||
@@ -103,4 +105,4 @@ untyped-import
|
||||
untyped-type-import
|
||||
|
||||
[version]
|
||||
^0.273.1
|
||||
^0.274.0
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
+260
-5133
File diff suppressed because it is too large
Load Diff
+6
-6
@@ -58,7 +58,7 @@
|
||||
"@typescript-eslint/parser": "^7.1.1",
|
||||
"ansi-styles": "^4.2.1",
|
||||
"babel-plugin-minify-dead-code-elimination": "^0.5.2",
|
||||
"babel-plugin-syntax-hermes-parser": "0.28.1",
|
||||
"babel-plugin-syntax-hermes-parser": "0.29.0",
|
||||
"babel-plugin-transform-define": "^2.1.4",
|
||||
"babel-plugin-transform-flow-enums": "^0.0.2",
|
||||
"clang-format": "^1.8.0",
|
||||
@@ -76,11 +76,11 @@
|
||||
"eslint-plugin-react-native": "^4.0.0",
|
||||
"eslint-plugin-redundant-undefined": "^0.4.0",
|
||||
"eslint-plugin-relay": "^1.8.3",
|
||||
"flow-api-translator": "0.28.1",
|
||||
"flow-bin": "^0.273.1",
|
||||
"flow-api-translator": "0.29.0",
|
||||
"flow-bin": "^0.274.0",
|
||||
"glob": "^7.1.1",
|
||||
"hermes-eslint": "0.28.1",
|
||||
"hermes-transform": "0.28.1",
|
||||
"hermes-eslint": "0.29.0",
|
||||
"hermes-transform": "0.29.0",
|
||||
"inquirer": "^7.1.0",
|
||||
"jest": "^29.7.0",
|
||||
"jest-config": "^29.7.0",
|
||||
@@ -96,7 +96,7 @@
|
||||
"node-fetch": "^2.2.0",
|
||||
"nullthrows": "^1.1.1",
|
||||
"prettier": "2.8.8",
|
||||
"prettier-plugin-hermes-parser": "0.28.1",
|
||||
"prettier-plugin-hermes-parser": "0.29.0",
|
||||
"react": "19.1.0",
|
||||
"react-test-renderer": "19.1.0",
|
||||
"rimraf": "^3.0.2",
|
||||
|
||||
@@ -81,6 +81,7 @@ export default function createDevMiddleware({
|
||||
projectRoot,
|
||||
serverBaseUrl,
|
||||
logger,
|
||||
// $FlowFixMe[prop-missing]
|
||||
unstable_browserLauncher = DefaultBrowserLauncher,
|
||||
unstable_eventReporter,
|
||||
unstable_experiments: experimentConfig = {},
|
||||
|
||||
@@ -18,8 +18,8 @@
|
||||
"bugs": "https://github.com/facebook/react-native/issues",
|
||||
"main": "index.js",
|
||||
"devDependencies": {
|
||||
"babel-plugin-syntax-hermes-parser": "0.28.1",
|
||||
"hermes-eslint": "0.28.1"
|
||||
"babel-plugin-syntax-hermes-parser": "0.29.0",
|
||||
"hermes-eslint": "0.29.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">= 22.14.0"
|
||||
|
||||
@@ -32,8 +32,8 @@
|
||||
"source-map-support": "0.5.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"babel-plugin-syntax-hermes-parser": "0.28.1",
|
||||
"hermes-eslint": "0.28.1"
|
||||
"babel-plugin-syntax-hermes-parser": "0.29.0",
|
||||
"hermes-eslint": "0.29.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">= 22.14.0"
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
[versions]
|
||||
agp = "8.10.1"
|
||||
agp = "8.11.0"
|
||||
gson = "2.8.9"
|
||||
guava = "31.0.1-jre"
|
||||
javapoet = "1.13.0"
|
||||
|
||||
@@ -67,7 +67,7 @@
|
||||
"@babel/plugin-transform-unicode-regex": "^7.24.7",
|
||||
"@babel/template": "^7.25.0",
|
||||
"@react-native/babel-plugin-codegen": "0.80.0-main",
|
||||
"babel-plugin-syntax-hermes-parser": "0.28.1",
|
||||
"babel-plugin-syntax-hermes-parser": "0.29.0",
|
||||
"babel-plugin-transform-flow-enums": "^0.0.2",
|
||||
"react-refresh": "^0.14.0"
|
||||
},
|
||||
|
||||
@@ -28,7 +28,7 @@
|
||||
"dependencies": {
|
||||
"@babel/core": "^7.25.2",
|
||||
"@react-native/babel-preset": "0.80.0-main",
|
||||
"hermes-parser": "0.28.1",
|
||||
"hermes-parser": "0.29.0",
|
||||
"nullthrows": "^1.1.1"
|
||||
},
|
||||
"peerDependencies": {
|
||||
|
||||
@@ -30,7 +30,7 @@
|
||||
],
|
||||
"dependencies": {
|
||||
"glob": "^7.1.1",
|
||||
"hermes-parser": "0.28.1",
|
||||
"hermes-parser": "0.29.0",
|
||||
"invariant": "^2.2.4",
|
||||
"nullthrows": "^1.1.1",
|
||||
"yargs": "^17.6.2"
|
||||
@@ -43,7 +43,7 @@
|
||||
"@babel/plugin-transform-nullish-coalescing-operator": "^7.24.7",
|
||||
"@babel/plugin-transform-optional-chaining": "^7.24.8",
|
||||
"@babel/preset-env": "^7.25.3",
|
||||
"hermes-estree": "0.28.1",
|
||||
"hermes-estree": "0.29.0",
|
||||
"micromatch": "^4.0.4",
|
||||
"prettier": "2.8.8",
|
||||
"rimraf": "^3.0.2"
|
||||
|
||||
@@ -9,6 +9,8 @@
|
||||
#import <React/RCTUIManager.h>
|
||||
#import <React/RCTViewManager.h>
|
||||
|
||||
#import <string>
|
||||
|
||||
static UIColor *UIColorFromHexString(const std::string hexString)
|
||||
{
|
||||
unsigned rgbValue = 0;
|
||||
|
||||
@@ -26,7 +26,7 @@ Pod::Spec.new do |s|
|
||||
s.author = "Meta Platforms, Inc. and its affiliates"
|
||||
s.platforms = min_supported_versions
|
||||
s.source = source
|
||||
s.source_files = "*.{m}"
|
||||
s.source_files = podspec_sources("*.{m}", "")
|
||||
s.preserve_paths = "package.json", "LICENSE", "LICENSE-docs"
|
||||
s.header_dir = "RCTActionSheet"
|
||||
|
||||
|
||||
@@ -29,7 +29,7 @@ export type EventConfig<T> = {
|
||||
platformConfig?: PlatformConfig,
|
||||
};
|
||||
|
||||
export function attachNativeEvent(
|
||||
export function attachNativeEventImpl(
|
||||
viewRef: any,
|
||||
eventName: string,
|
||||
argMapping: $ReadOnlyArray<?Mapping>,
|
||||
@@ -181,7 +181,7 @@ export class AnimatedEvent {
|
||||
'Only native driven events need to be attached.',
|
||||
);
|
||||
|
||||
this._attachedEvent = attachNativeEvent(
|
||||
this._attachedEvent = attachNativeEventImpl(
|
||||
viewRef,
|
||||
eventName,
|
||||
this._argMapping,
|
||||
|
||||
@@ -10,6 +10,10 @@
|
||||
|
||||
import AnimatedImplementation from './AnimatedImplementation';
|
||||
|
||||
export type {DecayAnimationConfig} from './animations/DecayAnimation';
|
||||
export type {SpringAnimationConfig} from './animations/SpringAnimation';
|
||||
export type {TimingAnimationConfig} from './animations/TimingAnimation';
|
||||
|
||||
export {default as FlatList} from './components/AnimatedFlatList';
|
||||
export {default as Image} from './components/AnimatedImage';
|
||||
export {default as ScrollView} from './components/AnimatedScrollView';
|
||||
@@ -33,6 +37,7 @@ export type {default as AnimatedNode} from './nodes/AnimatedNode';
|
||||
export type {default as AnimatedAddition} from './nodes/AnimatedAddition';
|
||||
export type {default as AnimatedDiffClamp} from './nodes/AnimatedDiffClamp';
|
||||
export type {default as AnimatedDivision} from './nodes/AnimatedDivision';
|
||||
export type {InterpolationConfigType as InterpolationConfig} from './nodes/AnimatedInterpolation';
|
||||
export type {default as AnimatedModulo} from './nodes/AnimatedModulo';
|
||||
export type {default as AnimatedMultiplication} from './nodes/AnimatedMultiplication';
|
||||
export type {default as AnimatedSubtraction} from './nodes/AnimatedSubtraction';
|
||||
|
||||
@@ -20,7 +20,7 @@ import type {DecayAnimationConfig} from './animations/DecayAnimation';
|
||||
import type {SpringAnimationConfig} from './animations/SpringAnimation';
|
||||
import type {TimingAnimationConfig} from './animations/TimingAnimation';
|
||||
|
||||
import {AnimatedEvent, attachNativeEvent} from './AnimatedEvent';
|
||||
import {AnimatedEvent, attachNativeEventImpl} from './AnimatedEvent';
|
||||
import DecayAnimation from './animations/DecayAnimation';
|
||||
import SpringAnimation from './animations/SpringAnimation';
|
||||
import TimingAnimation from './animations/TimingAnimation';
|
||||
@@ -47,39 +47,39 @@ export type CompositeAnimation = {
|
||||
...
|
||||
};
|
||||
|
||||
const add = function (
|
||||
const addImpl = function (
|
||||
a: AnimatedNode | number,
|
||||
b: AnimatedNode | number,
|
||||
): AnimatedAddition {
|
||||
return new AnimatedAddition(a, b);
|
||||
};
|
||||
|
||||
const subtract = function (
|
||||
const subtractImpl = function (
|
||||
a: AnimatedNode | number,
|
||||
b: AnimatedNode | number,
|
||||
): AnimatedSubtraction {
|
||||
return new AnimatedSubtraction(a, b);
|
||||
};
|
||||
|
||||
const divide = function (
|
||||
const divideImpl = function (
|
||||
a: AnimatedNode | number,
|
||||
b: AnimatedNode | number,
|
||||
): AnimatedDivision {
|
||||
return new AnimatedDivision(a, b);
|
||||
};
|
||||
|
||||
const multiply = function (
|
||||
const multiplyImpl = function (
|
||||
a: AnimatedNode | number,
|
||||
b: AnimatedNode | number,
|
||||
): AnimatedMultiplication {
|
||||
return new AnimatedMultiplication(a, b);
|
||||
};
|
||||
|
||||
const modulo = function (a: AnimatedNode, modulus: number): AnimatedModulo {
|
||||
const moduloImpl = function (a: AnimatedNode, modulus: number): AnimatedModulo {
|
||||
return new AnimatedModulo(a, modulus);
|
||||
};
|
||||
|
||||
const diffClamp = function (
|
||||
const diffClampImpl = function (
|
||||
a: AnimatedNode,
|
||||
min: number,
|
||||
max: number,
|
||||
@@ -120,7 +120,7 @@ const maybeVectorAnim = function (
|
||||
const aY = anim((value: AnimatedValueXY).y, configY);
|
||||
// We use `stopTogether: false` here because otherwise tracking will break
|
||||
// because the second animation will get stopped before it can update.
|
||||
return parallel([aX, aY], {stopTogether: false});
|
||||
return parallelImpl([aX, aY], {stopTogether: false});
|
||||
} else if (value instanceof AnimatedColor) {
|
||||
const configR = {...config};
|
||||
const configG = {...config};
|
||||
@@ -146,12 +146,12 @@ const maybeVectorAnim = function (
|
||||
const aA = anim((value: AnimatedColor).a, configA);
|
||||
// We use `stopTogether: false` here because otherwise tracking will break
|
||||
// because the second animation will get stopped before it can update.
|
||||
return parallel([aR, aG, aB, aA], {stopTogether: false});
|
||||
return parallelImpl([aR, aG, aB, aA], {stopTogether: false});
|
||||
}
|
||||
return null;
|
||||
};
|
||||
|
||||
const spring = function (
|
||||
const springImpl = function (
|
||||
value: AnimatedValue | AnimatedValueXY | AnimatedColor,
|
||||
config: SpringAnimationConfig,
|
||||
): CompositeAnimation {
|
||||
@@ -179,7 +179,7 @@ const spring = function (
|
||||
}
|
||||
};
|
||||
return (
|
||||
maybeVectorAnim(value, config, spring) || {
|
||||
maybeVectorAnim(value, config, springImpl) || {
|
||||
start: function (callback?: ?EndCallback): void {
|
||||
start(value, config, callback);
|
||||
},
|
||||
@@ -204,7 +204,7 @@ const spring = function (
|
||||
);
|
||||
};
|
||||
|
||||
const timing = function (
|
||||
const timingImpl = function (
|
||||
value: AnimatedValue | AnimatedValueXY | AnimatedColor,
|
||||
config: TimingAnimationConfig,
|
||||
): CompositeAnimation {
|
||||
@@ -233,7 +233,7 @@ const timing = function (
|
||||
};
|
||||
|
||||
return (
|
||||
maybeVectorAnim(value, config, timing) || {
|
||||
maybeVectorAnim(value, config, timingImpl) || {
|
||||
start: function (callback?: ?EndCallback, isLooping?: boolean): void {
|
||||
start(value, {...config, isLooping}, callback);
|
||||
},
|
||||
@@ -258,7 +258,7 @@ const timing = function (
|
||||
);
|
||||
};
|
||||
|
||||
const decay = function (
|
||||
const decayImpl = function (
|
||||
value: AnimatedValue | AnimatedValueXY | AnimatedColor,
|
||||
config: DecayAnimationConfig,
|
||||
): CompositeAnimation {
|
||||
@@ -275,7 +275,7 @@ const decay = function (
|
||||
};
|
||||
|
||||
return (
|
||||
maybeVectorAnim(value, config, decay) || {
|
||||
maybeVectorAnim(value, config, decayImpl) || {
|
||||
start: function (callback?: ?EndCallback): void {
|
||||
start(value, config, callback);
|
||||
},
|
||||
@@ -300,7 +300,7 @@ const decay = function (
|
||||
);
|
||||
};
|
||||
|
||||
const sequence = function (
|
||||
const sequenceImpl = function (
|
||||
animations: Array<CompositeAnimation>,
|
||||
): CompositeAnimation {
|
||||
let current = 0;
|
||||
@@ -363,7 +363,7 @@ type ParallelConfig = {
|
||||
stopTogether?: boolean,
|
||||
...
|
||||
};
|
||||
const parallel = function (
|
||||
const parallelImpl = function (
|
||||
animations: Array<CompositeAnimation>,
|
||||
config?: ?ParallelConfig,
|
||||
): CompositeAnimation {
|
||||
@@ -431,9 +431,9 @@ const parallel = function (
|
||||
return result;
|
||||
};
|
||||
|
||||
const delay = function (time: number): CompositeAnimation {
|
||||
const delayImpl = function (time: number): CompositeAnimation {
|
||||
// Would be nice to make a specialized implementation
|
||||
return timing(new AnimatedValue(0), {
|
||||
return timingImpl(new AnimatedValue(0), {
|
||||
toValue: 0,
|
||||
delay: time,
|
||||
duration: 0,
|
||||
@@ -441,13 +441,13 @@ const delay = function (time: number): CompositeAnimation {
|
||||
});
|
||||
};
|
||||
|
||||
const stagger = function (
|
||||
const staggerImpl = function (
|
||||
time: number,
|
||||
animations: Array<CompositeAnimation>,
|
||||
): CompositeAnimation {
|
||||
return parallel(
|
||||
return parallelImpl(
|
||||
animations.map((animation, i) => {
|
||||
return sequence([delay(time * i), animation]);
|
||||
return sequenceImpl([delayImpl(time * i), animation]);
|
||||
}),
|
||||
);
|
||||
};
|
||||
@@ -458,7 +458,7 @@ type LoopAnimationConfig = {
|
||||
...
|
||||
};
|
||||
|
||||
const loop = function (
|
||||
const loopImpl = function (
|
||||
animation: CompositeAnimation,
|
||||
// $FlowFixMe[prop-missing]
|
||||
{iterations = -1, resetBeforeIteration = true}: LoopAnimationConfig = {},
|
||||
@@ -514,7 +514,7 @@ const loop = function (
|
||||
};
|
||||
};
|
||||
|
||||
function forkEvent(
|
||||
function forkEventImpl(
|
||||
event: ?AnimatedEvent | ?Function,
|
||||
listener: Function,
|
||||
): AnimatedEvent | Function {
|
||||
@@ -531,7 +531,7 @@ function forkEvent(
|
||||
}
|
||||
}
|
||||
|
||||
function unforkEvent(
|
||||
function unforkEventImpl(
|
||||
event: ?AnimatedEvent | ?Function,
|
||||
listener: Function,
|
||||
): void {
|
||||
@@ -540,7 +540,7 @@ function unforkEvent(
|
||||
}
|
||||
}
|
||||
|
||||
const event = function <T>(
|
||||
const eventImpl = function <T>(
|
||||
argMapping: $ReadOnlyArray<?Mapping>,
|
||||
config: EventConfig<T>,
|
||||
): any {
|
||||
@@ -606,25 +606,25 @@ export default {
|
||||
* See https://reactnative.dev/docs/animated#node
|
||||
*/
|
||||
Node: AnimatedNode,
|
||||
decay,
|
||||
timing,
|
||||
spring,
|
||||
add,
|
||||
subtract,
|
||||
divide,
|
||||
multiply,
|
||||
modulo,
|
||||
diffClamp,
|
||||
delay,
|
||||
sequence,
|
||||
parallel,
|
||||
stagger,
|
||||
loop,
|
||||
event,
|
||||
decay: decayImpl,
|
||||
timing: timingImpl,
|
||||
spring: springImpl,
|
||||
add: addImpl,
|
||||
subtract: subtractImpl,
|
||||
divide: divideImpl,
|
||||
multiply: multiplyImpl,
|
||||
modulo: moduloImpl,
|
||||
diffClamp: diffClampImpl,
|
||||
delay: delayImpl,
|
||||
sequence: sequenceImpl,
|
||||
parallel: parallelImpl,
|
||||
stagger: staggerImpl,
|
||||
loop: loopImpl,
|
||||
event: eventImpl,
|
||||
createAnimatedComponent,
|
||||
attachNativeEvent,
|
||||
forkEvent,
|
||||
unforkEvent,
|
||||
attachNativeEvent: attachNativeEventImpl,
|
||||
forkEvent: forkEventImpl,
|
||||
unforkEvent: unforkEventImpl,
|
||||
|
||||
/**
|
||||
* Expose Event class, so it can be used as a type for type checkers.
|
||||
|
||||
@@ -17,7 +17,7 @@ import type {DecayAnimationConfig} from './animations/DecayAnimation';
|
||||
import type {SpringAnimationConfig} from './animations/SpringAnimation';
|
||||
import type {TimingAnimationConfig} from './animations/TimingAnimation';
|
||||
|
||||
import {AnimatedEvent, attachNativeEvent} from './AnimatedEvent';
|
||||
import {AnimatedEvent, attachNativeEventImpl} from './AnimatedEvent';
|
||||
import AnimatedImplementation from './AnimatedImplementation';
|
||||
import createAnimatedComponent from './createAnimatedComponent';
|
||||
import AnimatedColor from './nodes/AnimatedColor';
|
||||
@@ -188,7 +188,7 @@ export default {
|
||||
loop,
|
||||
event: AnimatedImplementation.event,
|
||||
createAnimatedComponent,
|
||||
attachNativeEvent,
|
||||
attachNativeEvent: attachNativeEventImpl,
|
||||
forkEvent: AnimatedImplementation.forkEvent,
|
||||
unforkEvent: AnimatedImplementation.unforkEvent,
|
||||
Event: AnimatedEvent,
|
||||
|
||||
@@ -17,6 +17,7 @@ import ensureInstance from '../../../src/private/__tests__/utilities/ensureInsta
|
||||
import * as Fantom from '@react-native/fantom';
|
||||
import {createRef} from 'react';
|
||||
import {Animated, View, useAnimatedValue} from 'react-native';
|
||||
import {allowStyleProp} from 'react-native/Libraries/Animated/NativeAnimatedAllowlist';
|
||||
import * as ReactNativeFeatureFlags from 'react-native/src/private/featureflags/ReactNativeFeatureFlags';
|
||||
import ReactNativeElement from 'react-native/src/private/webapis/dom/nodes/ReactNativeElement';
|
||||
|
||||
@@ -152,6 +153,7 @@ test('animation driven by onScroll event', () => {
|
||||
|
||||
test('animated opacity', () => {
|
||||
let _opacity;
|
||||
let _opacityAnimation;
|
||||
const viewRef = createRef<HostInstance>();
|
||||
|
||||
function MyApp() {
|
||||
@@ -182,7 +184,7 @@ test('animated opacity', () => {
|
||||
expect(viewElement.getBoundingClientRect().x).toBe(0);
|
||||
|
||||
Fantom.runTask(() => {
|
||||
Animated.timing(_opacity, {
|
||||
_opacityAnimation = Animated.timing(_opacity, {
|
||||
toValue: 0,
|
||||
duration: 30,
|
||||
useNativeDriver: true,
|
||||
@@ -194,8 +196,10 @@ test('animated opacity', () => {
|
||||
0,
|
||||
);
|
||||
|
||||
// TODO(T223344928): this shouldn't be neccessary with cxxNativeAnimatedRemoveJsSync:true
|
||||
Fantom.runWorkLoop();
|
||||
// TODO: this shouldn't be neccessary since animation should be stopped after duration
|
||||
Fantom.runTask(() => {
|
||||
_opacityAnimation?.stop();
|
||||
});
|
||||
|
||||
expect(root.getRenderedOutput({props: ['opacity']}).toJSX()).toEqual(
|
||||
<rn-view opacity="0" />,
|
||||
@@ -475,3 +479,61 @@ describe('Value.extractOffset', () => {
|
||||
Fantom.runWorkLoop();
|
||||
});
|
||||
});
|
||||
|
||||
test('animate layout props', () => {
|
||||
const viewRef = createRef<HostInstance>();
|
||||
allowStyleProp('height');
|
||||
|
||||
let _animatedHeight;
|
||||
let _heightAnimation;
|
||||
|
||||
function MyApp() {
|
||||
const animatedHeight = useAnimatedValue(0);
|
||||
_animatedHeight = animatedHeight;
|
||||
return (
|
||||
<Animated.View
|
||||
ref={viewRef}
|
||||
style={[
|
||||
{
|
||||
width: 100,
|
||||
height: animatedHeight,
|
||||
},
|
||||
]}
|
||||
/>
|
||||
);
|
||||
}
|
||||
|
||||
const root = Fantom.createRoot();
|
||||
|
||||
Fantom.runTask(() => {
|
||||
root.render(<MyApp />);
|
||||
});
|
||||
|
||||
const viewElement = ensureInstance(viewRef.current, ReactNativeElement);
|
||||
|
||||
Fantom.runTask(() => {
|
||||
_heightAnimation = Animated.timing(_animatedHeight, {
|
||||
toValue: 100,
|
||||
duration: 10,
|
||||
useNativeDriver: true,
|
||||
}).start();
|
||||
});
|
||||
|
||||
Fantom.unstable_produceFramesForDuration(10);
|
||||
|
||||
// TODO: this shouldn't be neccessary since animation should be stopped after duration
|
||||
Fantom.runTask(() => {
|
||||
_heightAnimation?.stop();
|
||||
});
|
||||
|
||||
// $FlowFixMe[incompatible-use]
|
||||
expect(Fantom.unstable_getDirectManipulationProps(viewElement).height).toBe(
|
||||
100,
|
||||
);
|
||||
|
||||
expect(Fantom.unstable_getFabricUpdateProps(viewElement).height).toBe(100);
|
||||
|
||||
expect(root.getRenderedOutput({props: ['height']}).toJSX()).toEqual(
|
||||
<rn-view height="100.000000" />,
|
||||
);
|
||||
});
|
||||
|
||||
@@ -15,7 +15,9 @@ import type {
|
||||
} from '../createAnimatedComponent';
|
||||
|
||||
import RefreshControl from '../../Components/RefreshControl/RefreshControl';
|
||||
import ScrollView from '../../Components/ScrollView/ScrollView';
|
||||
import ScrollView, {
|
||||
type ScrollViewProps,
|
||||
} from '../../Components/ScrollView/ScrollView';
|
||||
import flattenStyle from '../../StyleSheet/flattenStyle';
|
||||
import splitLayoutProps from '../../StyleSheet/splitLayoutProps';
|
||||
import StyleSheet from '../../StyleSheet/StyleSheet';
|
||||
@@ -26,21 +28,20 @@ import useAnimatedProps from '../useAnimatedProps';
|
||||
import * as React from 'react';
|
||||
import {cloneElement, useMemo} from 'react';
|
||||
|
||||
type AnimatedScrollViewProps = React.ElementConfig<typeof ScrollView>;
|
||||
type AnimatedScrollViewInstance = React.ElementRef<typeof ScrollView>;
|
||||
|
||||
/**
|
||||
* @see https://github.com/facebook/react-native/commit/b8c8562
|
||||
*/
|
||||
const AnimatedScrollView: AnimatedComponentType<
|
||||
AnimatedScrollViewProps,
|
||||
ScrollViewProps,
|
||||
AnimatedScrollViewInstance,
|
||||
> = function AnimatedScrollViewWithOrWithoutInvertedRefreshControl({
|
||||
ref: forwardedRef,
|
||||
...props
|
||||
}: {
|
||||
ref?: React.RefSetter<AnimatedScrollViewInstance>,
|
||||
...AnimatedProps<AnimatedScrollViewProps>,
|
||||
...AnimatedProps<ScrollViewProps>,
|
||||
}) {
|
||||
// (Android only) When a ScrollView has a RefreshControl and
|
||||
// any `style` property set with an Animated.Value, the CSS
|
||||
@@ -111,7 +112,7 @@ const AnimatedScrollViewWithInvertedRefreshControl =
|
||||
|
||||
// Handle animated props on `NativeDirectionalScrollView`.
|
||||
const [scrollViewAnimatedProps, scrollViewRef] = useAnimatedProps<
|
||||
AnimatedScrollViewProps,
|
||||
ScrollViewProps,
|
||||
AnimatedScrollViewInstance,
|
||||
>(intermediatePropsForScrollView);
|
||||
const ref = useMergeRefs<AnimatedScrollViewInstance>(
|
||||
|
||||
@@ -10,13 +10,10 @@
|
||||
|
||||
import type {AnimatedComponentType} from '../createAnimatedComponent';
|
||||
|
||||
import Text from '../../Text/Text';
|
||||
import Text, {type TextProps} from '../../Text/Text';
|
||||
import createAnimatedComponent from '../createAnimatedComponent';
|
||||
import * as React from 'react';
|
||||
|
||||
export default (createAnimatedComponent(
|
||||
(Text: $FlowFixMe),
|
||||
): AnimatedComponentType<
|
||||
React.ElementConfig<typeof Text>,
|
||||
React.ElementRef<typeof Text>,
|
||||
>);
|
||||
): AnimatedComponentType<TextProps, React.ElementRef<typeof Text>>);
|
||||
|
||||
@@ -8,6 +8,7 @@
|
||||
* @format
|
||||
*/
|
||||
|
||||
import type {ViewProps} from '../../Components/View/ViewPropTypes';
|
||||
import type {AnimatedComponentType} from '../createAnimatedComponent';
|
||||
|
||||
import View from '../../Components/View/View';
|
||||
@@ -15,6 +16,6 @@ import createAnimatedComponent from '../createAnimatedComponent';
|
||||
import * as React from 'react';
|
||||
|
||||
export default (createAnimatedComponent(View): AnimatedComponentType<
|
||||
React.ElementConfig<typeof View>,
|
||||
ViewProps,
|
||||
React.ElementRef<typeof View>,
|
||||
>);
|
||||
|
||||
@@ -21,7 +21,7 @@ import type AnimatedValue from './nodes/AnimatedValue';
|
||||
|
||||
import createAnimatedPropsHook from '../../src/private/animated/createAnimatedPropsHook';
|
||||
import composeStyles from '../../src/private/styles/composeStyles';
|
||||
import View from '../Components/View/View';
|
||||
import {type ViewProps} from '../Components/View/ViewPropTypes';
|
||||
import useMergeRefs from '../Utilities/useMergeRefs';
|
||||
import * as React from 'react';
|
||||
import {useMemo} from 'react';
|
||||
@@ -60,9 +60,7 @@ type NonAnimatedProps =
|
||||
| 'disabled'
|
||||
| 'accessibilityLabel';
|
||||
type PassThroughProps = $ReadOnly<{
|
||||
passthroughAnimatedPropExplicitValues?: React.ElementConfig<
|
||||
typeof View,
|
||||
> | null,
|
||||
passthroughAnimatedPropExplicitValues?: ViewProps | null,
|
||||
}>;
|
||||
|
||||
export type AnimatedProps<Props: {...}> = {
|
||||
|
||||
@@ -42,7 +42,7 @@ Pod::Spec.new do |s|
|
||||
s.author = "Meta Platforms, Inc. and its affiliates"
|
||||
s.platforms = min_supported_versions
|
||||
s.source = source
|
||||
s.source_files = "**/*.{c,h,m,mm,S,cpp}"
|
||||
s.source_files = podspec_sources("**/*.{c,h,m,mm,S,cpp}", "**/*.h")
|
||||
|
||||
# This guard prevent to install the dependencies when we run `pod install` in the old architecture.
|
||||
s.compiler_flags = other_cflags
|
||||
|
||||
@@ -30,7 +30,7 @@ Pod::Spec.new do |s|
|
||||
s.platforms = min_supported_versions
|
||||
s.compiler_flags = '-Wno-nullability-completeness'
|
||||
s.source = source
|
||||
s.source_files = "*.{h,m,mm}"
|
||||
s.source_files = podspec_sources("*.{h,m,mm}", "**/*.h")
|
||||
s.preserve_paths = "package.json", "LICENSE", "LICENSE-docs"
|
||||
s.header_dir = "RCTBlob"
|
||||
s.pod_target_xcconfig = {
|
||||
|
||||
+6
-4
@@ -281,10 +281,12 @@ export type ButtonProps = $ReadOnly<{
|
||||
```
|
||||
*/
|
||||
|
||||
const Touchable: typeof TouchableNativeFeedback | typeof TouchableOpacity =
|
||||
const NativeTouchable:
|
||||
| typeof TouchableNativeFeedback
|
||||
| typeof TouchableOpacity =
|
||||
Platform.OS === 'android' ? TouchableNativeFeedback : TouchableOpacity;
|
||||
|
||||
type ButtonRef = React.ElementRef<typeof Touchable>;
|
||||
type ButtonRef = React.ElementRef<typeof NativeTouchable>;
|
||||
|
||||
const Button: component(
|
||||
ref?: React.RefSetter<ButtonRef>,
|
||||
@@ -362,7 +364,7 @@ const Button: component(
|
||||
: importantForAccessibility;
|
||||
|
||||
return (
|
||||
<Touchable
|
||||
<NativeTouchable
|
||||
accessible={accessible}
|
||||
accessibilityActions={accessibilityActions}
|
||||
onAccessibilityAction={onAccessibilityAction}
|
||||
@@ -391,7 +393,7 @@ const Button: component(
|
||||
{formattedTitle}
|
||||
</Text>
|
||||
</View>
|
||||
</Touchable>
|
||||
</NativeTouchable>
|
||||
);
|
||||
};
|
||||
|
||||
|
||||
@@ -8,6 +8,7 @@
|
||||
* @format
|
||||
*/
|
||||
|
||||
import type {ViewStyleProp} from '../../StyleSheet/StyleSheet';
|
||||
import type {
|
||||
GestureResponderEvent,
|
||||
LayoutChangeEvent,
|
||||
@@ -26,8 +27,6 @@ import useAndroidRippleForView, {
|
||||
import * as React from 'react';
|
||||
import {memo, useMemo, useRef, useState} from 'react';
|
||||
|
||||
type ViewStyleProp = React.ElementConfig<typeof View>['style'];
|
||||
|
||||
export type {PressableAndroidRippleConfig};
|
||||
|
||||
export type PressableStateCallbackType = $ReadOnly<{
|
||||
|
||||
@@ -24,7 +24,7 @@ import * as React from 'react';
|
||||
* sensor housing area on iPhone X).
|
||||
* @deprecated Use `react-native-safe-area-context` instead. This component will be removed in a future release.
|
||||
*/
|
||||
const exported: component(
|
||||
const SafeAreaView: component(
|
||||
ref?: React.RefSetter<React.ElementRef<typeof View>>,
|
||||
...props: ViewProps
|
||||
) = Platform.select({
|
||||
@@ -32,4 +32,4 @@ const exported: component(
|
||||
default: View,
|
||||
});
|
||||
|
||||
export default exported;
|
||||
export default SafeAreaView;
|
||||
|
||||
@@ -10,6 +10,7 @@
|
||||
import type * as React from 'react';
|
||||
import {Constructor} from '../../../types/private/Utilities';
|
||||
import {Insets} from '../../../types/public/Insets';
|
||||
import {HostInstance} from '../../../types/public/ReactNativeTypes';
|
||||
import {ColorValue, StyleProp} from '../../StyleSheet/StyleSheet';
|
||||
import {ViewStyle} from '../../StyleSheet/StyleSheetTypes';
|
||||
import {
|
||||
@@ -878,6 +879,12 @@ export class ScrollView extends ScrollViewBase {
|
||||
// Undocumented
|
||||
getInnerViewNode(): any;
|
||||
|
||||
/**
|
||||
* Returns a reference to the underlying native scroll view, or null if the
|
||||
* native instance is not mounted.
|
||||
*/
|
||||
getNativeScrollRef: () => HostInstance | null;
|
||||
|
||||
/**
|
||||
* @deprecated Use scrollTo instead
|
||||
*/
|
||||
|
||||
@@ -1480,6 +1480,7 @@ class ScrollView extends React.Component<ScrollViewProps, ScrollViewState> {
|
||||
// then the second tap goes to the actual interior view)
|
||||
const {keyboardShouldPersistTaps} = this.props;
|
||||
const keyboardNeverPersistTaps =
|
||||
// $FlowFixMe[sketchy-null-bool]
|
||||
!keyboardShouldPersistTaps || keyboardShouldPersistTaps === 'never';
|
||||
|
||||
if (typeof e.target === 'number') {
|
||||
@@ -1562,6 +1563,7 @@ class ScrollView extends React.Component<ScrollViewProps, ScrollViewState> {
|
||||
|
||||
const {keyboardShouldPersistTaps} = this.props;
|
||||
const keyboardNeverPersistsTaps =
|
||||
// $FlowFixMe[sketchy-null-bool]
|
||||
!keyboardShouldPersistTaps || keyboardShouldPersistTaps === 'never';
|
||||
|
||||
// Dismiss the keyboard now if we didn't become responder in capture phase
|
||||
|
||||
@@ -32,7 +32,7 @@ export type {EventSubscription, EmitterSubscription};
|
||||
export type NativeEventSubscription = EventSubscription;
|
||||
|
||||
// $FlowFixMe[unclear-type] unclear type of events
|
||||
type UnsafeObject = Object;
|
||||
type UnsafeNativeEventObject = Object;
|
||||
|
||||
/**
|
||||
* `NativeEventEmitter` is intended for use by Native Modules to emit events to
|
||||
@@ -46,8 +46,8 @@ type UnsafeObject = Object;
|
||||
*/
|
||||
export default class NativeEventEmitter<
|
||||
TEventToArgsMap: $ReadOnly<
|
||||
Record<string, $ReadOnlyArray<UnsafeObject>>,
|
||||
> = $ReadOnly<Record<string, $ReadOnlyArray<UnsafeObject>>>,
|
||||
Record<string, $ReadOnlyArray<UnsafeNativeEventObject>>,
|
||||
> = $ReadOnly<Record<string, $ReadOnlyArray<UnsafeNativeEventObject>>>,
|
||||
> implements IEventEmitter<TEventToArgsMap>
|
||||
{
|
||||
_nativeModule: ?NativeModule;
|
||||
|
||||
@@ -25,7 +25,7 @@ Pod::Spec.new do |s|
|
||||
s.author = "Meta Platforms, Inc. and its affiliates"
|
||||
s.platforms = min_supported_versions
|
||||
s.source = source
|
||||
s.source_files = "**/*.{c,h,m,mm,cpp}"
|
||||
s.source_files = podspec_sources("**/*.{c,h,m,mm,cpp}", "**/*.h")
|
||||
s.header_dir = "FBLazyVector"
|
||||
|
||||
end
|
||||
|
||||
@@ -8,9 +8,10 @@
|
||||
#import <React/RCTImageLoaderLoggable.h>
|
||||
#import <React/RCTImageLoaderProtocol.h>
|
||||
#import <React/RCTImageURLLoader.h>
|
||||
|
||||
// TODO (T61325135): Remove C++ checks
|
||||
#ifdef __cplusplus
|
||||
#import <string>
|
||||
|
||||
namespace facebook::react {
|
||||
|
||||
struct ImageURLLoaderAttribution {
|
||||
|
||||
@@ -7,7 +7,7 @@
|
||||
|
||||
#import <React/RCTImageUtils.h>
|
||||
|
||||
#import <tgmath.h>
|
||||
#import <cmath>
|
||||
|
||||
#import <ImageIO/ImageIO.h>
|
||||
#import <MobileCoreServices/UTCoreTypes.h>
|
||||
|
||||
@@ -32,7 +32,7 @@ Pod::Spec.new do |s|
|
||||
s.platforms = min_supported_versions
|
||||
s.compiler_flags = '-Wno-nullability-completeness'
|
||||
s.source = source
|
||||
s.source_files = "*.{m,mm}"
|
||||
s.source_files = podspec_sources("*.{m,mm}", "**/*.h")
|
||||
s.preserve_paths = "package.json", "LICENSE", "LICENSE-docs"
|
||||
s.header_dir = "RCTImage"
|
||||
s.pod_target_xcconfig = {
|
||||
|
||||
@@ -229,7 +229,8 @@ function _processUpdate() {
|
||||
*/
|
||||
const InteractionManager = (
|
||||
ReactNativeFeatureFlags.disableInteractionManager()
|
||||
? require('./InteractionManagerStub').default
|
||||
? // $FlowFixMe[incompatible-variance]
|
||||
require('./InteractionManagerStub').default
|
||||
: InteractionManagerImpl
|
||||
) as typeof InteractionManagerImpl;
|
||||
|
||||
|
||||
@@ -45,7 +45,7 @@ type OnAnimationDidFailCallback = () => void;
|
||||
let isLayoutAnimationEnabled: boolean =
|
||||
ReactNativeFeatureFlags.isLayoutAnimationEnabled();
|
||||
|
||||
function setEnabled(value: boolean) {
|
||||
function setLayoutAnimationEnabled(value: boolean) {
|
||||
isLayoutAnimationEnabled = isLayoutAnimationEnabled;
|
||||
}
|
||||
|
||||
@@ -115,7 +115,7 @@ function configureNext(
|
||||
}
|
||||
}
|
||||
|
||||
function create(
|
||||
function createLayoutAnimation(
|
||||
duration: number,
|
||||
type?: LayoutAnimationType,
|
||||
property?: LayoutAnimationProperty,
|
||||
@@ -129,12 +129,16 @@ function create(
|
||||
}
|
||||
|
||||
const Presets = {
|
||||
easeInEaseOut: (create(
|
||||
easeInEaseOut: (createLayoutAnimation(
|
||||
300,
|
||||
'easeInEaseOut',
|
||||
'opacity',
|
||||
): LayoutAnimationConfig),
|
||||
linear: (create(500, 'linear', 'opacity'): LayoutAnimationConfig),
|
||||
linear: (createLayoutAnimation(
|
||||
500,
|
||||
'linear',
|
||||
'opacity',
|
||||
): LayoutAnimationConfig),
|
||||
spring: ({
|
||||
duration: 700,
|
||||
create: {
|
||||
@@ -180,7 +184,7 @@ const LayoutAnimation = {
|
||||
/**
|
||||
* Helper for creating a config for `configureNext`.
|
||||
*/
|
||||
create,
|
||||
create: createLayoutAnimation,
|
||||
Types: Object.freeze({
|
||||
spring: 'spring',
|
||||
linear: 'linear',
|
||||
@@ -208,7 +212,7 @@ const LayoutAnimation = {
|
||||
spring: (configureNext.bind(null, Presets.spring): (
|
||||
onAnimationDidEnd?: OnAnimationDidEndCallback,
|
||||
) => void),
|
||||
setEnabled,
|
||||
setEnabled: setLayoutAnimationEnabled,
|
||||
};
|
||||
|
||||
export default LayoutAnimation;
|
||||
|
||||
@@ -31,7 +31,7 @@ Pod::Spec.new do |s|
|
||||
s.platforms = min_supported_versions
|
||||
s.compiler_flags = '-Wno-nullability-completeness'
|
||||
s.source = source
|
||||
s.source_files = "*.{m,mm}"
|
||||
s.source_files = podspec_sources("*.{m,mm}", "")
|
||||
s.preserve_paths = "package.json", "LICENSE", "LICENSE-docs"
|
||||
s.header_dir = "RCTLinking"
|
||||
s.pod_target_xcconfig = {
|
||||
|
||||
+1
-2
@@ -15,6 +15,7 @@ import type {
|
||||
ListRenderItemInfo,
|
||||
ViewabilityConfigCallbackPair,
|
||||
ViewToken,
|
||||
VirtualizedListProps,
|
||||
} from '@react-native/virtualized-lists';
|
||||
|
||||
import * as ReactNativeFeatureFlags from '../../src/private/featureflags/ReactNativeFeatureFlags';
|
||||
@@ -181,8 +182,6 @@ type FlatListBaseProps<ItemT> = {
|
||||
...OptionalProps<ItemT>,
|
||||
};
|
||||
|
||||
type VirtualizedListProps = React.ElementConfig<typeof VirtualizedList>;
|
||||
|
||||
export type FlatListProps<ItemT> = {
|
||||
...Omit<
|
||||
VirtualizedListProps,
|
||||
|
||||
@@ -30,7 +30,7 @@ Pod::Spec.new do |s|
|
||||
s.platforms = min_supported_versions
|
||||
s.compiler_flags = '-Wno-nullability-completeness'
|
||||
s.source = source
|
||||
s.source_files = "**/*.{h,m,mm}"
|
||||
s.source_files = podspec_sources("**/*.{h,m,mm}", "**/*.h")
|
||||
s.preserve_paths = "package.json", "LICENSE", "LICENSE-docs"
|
||||
s.header_dir = "RCTAnimation"
|
||||
s.pod_target_xcconfig = {
|
||||
|
||||
@@ -30,7 +30,7 @@ Pod::Spec.new do |s|
|
||||
s.platforms = min_supported_versions
|
||||
s.compiler_flags = '-Wno-nullability-completeness'
|
||||
s.source = source
|
||||
s.source_files = "*.{m,mm}"
|
||||
s.source_files = podspec_sources("*.{m,mm}", "")
|
||||
s.preserve_paths = "package.json", "LICENSE", "LICENSE-docs"
|
||||
s.header_dir = "RCTNetwork"
|
||||
s.pod_target_xcconfig = {
|
||||
|
||||
@@ -130,7 +130,7 @@ const PERMISSIONS = Object.freeze({
|
||||
*
|
||||
* See https://reactnative.dev/docs/permissionsandroid
|
||||
*/
|
||||
class PermissionsAndroid {
|
||||
class PermissionsAndroidImpl {
|
||||
PERMISSIONS: PermissionsType = PERMISSIONS;
|
||||
RESULTS: $ReadOnly<{
|
||||
DENIED: 'denied',
|
||||
@@ -297,5 +297,6 @@ class PermissionsAndroid {
|
||||
}
|
||||
}
|
||||
|
||||
const PermissionsAndroidInstance: PermissionsAndroid = new PermissionsAndroid();
|
||||
const PermissionsAndroidInstance: PermissionsAndroidImpl =
|
||||
new PermissionsAndroidImpl();
|
||||
export default PermissionsAndroidInstance;
|
||||
|
||||
@@ -13,8 +13,8 @@ import type {RootTag} from '../Types/RootTagTypes';
|
||||
import type {IPerformanceLogger} from '../Utilities/createPerformanceLogger';
|
||||
import type {DisplayModeType} from './DisplayMode';
|
||||
|
||||
type Task = (taskData: any) => Promise<void>;
|
||||
export type TaskProvider = () => Task;
|
||||
type HeadlessTask = (taskData: any) => Promise<void>;
|
||||
export type TaskProvider = () => HeadlessTask;
|
||||
|
||||
export type ComponentProvider = () => React.ComponentType<any>;
|
||||
export type ComponentProviderInstrumentationHook = (
|
||||
|
||||
@@ -25,6 +25,6 @@ Pod::Spec.new do |s|
|
||||
s.author = "Meta Platforms, Inc. and its affiliates"
|
||||
s.platforms = min_supported_versions
|
||||
s.source = source
|
||||
s.source_files = "**/*.{c,h,m,mm,cpp}"
|
||||
s.source_files = podspec_sources("**/*.{c,h,m,mm,cpp}", "**/*.h")
|
||||
s.header_dir = "RCTRequired"
|
||||
end
|
||||
|
||||
@@ -31,7 +31,7 @@ Pod::Spec.new do |s|
|
||||
s.platforms = min_supported_versions
|
||||
s.compiler_flags = '-Wno-nullability-completeness'
|
||||
s.source = source
|
||||
s.source_files = "*.{m,mm}"
|
||||
s.source_files = podspec_sources("*.{m,mm}", "**/*.h")
|
||||
s.preserve_paths = "package.json", "LICENSE", "LICENSE-docs"
|
||||
s.header_dir = "RCTSettings"
|
||||
s.pod_target_xcconfig = {
|
||||
|
||||
@@ -26,7 +26,7 @@ Pod::Spec.new do |s|
|
||||
s.author = "Meta Platforms, Inc. and its affiliates"
|
||||
s.platforms = min_supported_versions
|
||||
s.source = source
|
||||
s.source_files = "**/*.{h,m,mm}"
|
||||
s.source_files = podspec_sources("**/*.{h,m,mm}", "**/*.h")
|
||||
s.preserve_paths = "package.json", "LICENSE", "LICENSE-docs"
|
||||
s.header_dir = "RCTText"
|
||||
s.framework = ["MobileCoreServices"]
|
||||
|
||||
@@ -25,7 +25,7 @@ Pod::Spec.new do |s|
|
||||
s.author = "Meta Platforms, Inc. and its affiliates"
|
||||
s.platforms = min_supported_versions
|
||||
s.source = source
|
||||
s.source_files = "**/*.{c,h,m,mm,cpp}"
|
||||
s.source_files = podspec_sources("**/*.{c,h,m,mm,cpp}", "**/*.h")
|
||||
s.header_dir = "RCTTypeSafety"
|
||||
s.pod_target_xcconfig = {
|
||||
"USE_HEADERMAP" => "YES",
|
||||
|
||||
@@ -9,6 +9,4 @@
|
||||
*/
|
||||
|
||||
export * from '../../src/private/specs_DEPRECATED/modules/NativeDeviceInfo';
|
||||
import NativeDeviceInfo from '../../src/private/specs_DEPRECATED/modules/NativeDeviceInfo';
|
||||
|
||||
export default NativeDeviceInfo;
|
||||
export {default} from '../../src/private/specs_DEPRECATED/modules/NativeDeviceInfo';
|
||||
|
||||
@@ -23,7 +23,7 @@ type Options = $ReadOnly<{
|
||||
excludedPlatforms?: $ReadOnlyArray<'iOS' | 'android'>,
|
||||
}>;
|
||||
|
||||
export type NativeComponentType<T> = HostComponent<T>;
|
||||
export type NativeComponentType<T: {...}> = HostComponent<T>;
|
||||
|
||||
// If this function runs then that means the view configs were not
|
||||
// generated at build time using `GenerateViewConfigJs.js`. Thus
|
||||
|
||||
@@ -31,7 +31,7 @@ Pod::Spec.new do |s|
|
||||
s.platforms = min_supported_versions
|
||||
s.compiler_flags = '-Wno-nullability-completeness'
|
||||
s.source = source
|
||||
s.source_files = "*.{m,mm}"
|
||||
s.source_files = podspec_sources("*.{m,mm}", "**/*.h")
|
||||
s.preserve_paths = "package.json", "LICENSE", "LICENSE-docs"
|
||||
s.header_dir = "RCTVibration"
|
||||
s.pod_target_xcconfig = {
|
||||
|
||||
@@ -136,7 +136,7 @@ export type EventConfig<T> = {
|
||||
useNativeDriver: boolean,
|
||||
platformConfig?: PlatformConfig,
|
||||
};
|
||||
declare export function attachNativeEvent(
|
||||
declare export function attachNativeEventImpl(
|
||||
viewRef: any,
|
||||
eventName: string,
|
||||
argMapping: $ReadOnlyArray<?Mapping>,
|
||||
@@ -166,7 +166,10 @@ declare export default {
|
||||
`;
|
||||
|
||||
exports[`public API should not change unintentionally Libraries/Animated/AnimatedExports.js.flow 1`] = `
|
||||
"export { default as FlatList } from \\"./components/AnimatedFlatList\\";
|
||||
"export type { DecayAnimationConfig } from \\"./animations/DecayAnimation\\";
|
||||
export type { SpringAnimationConfig } from \\"./animations/SpringAnimation\\";
|
||||
export type { TimingAnimationConfig } from \\"./animations/TimingAnimation\\";
|
||||
export { default as FlatList } from \\"./components/AnimatedFlatList\\";
|
||||
export { default as Image } from \\"./components/AnimatedImage\\";
|
||||
export { default as ScrollView } from \\"./components/AnimatedScrollView\\";
|
||||
export { default as SectionList } from \\"./components/AnimatedSectionList\\";
|
||||
@@ -185,6 +188,7 @@ export type { default as AnimatedNode } from \\"./nodes/AnimatedNode\\";
|
||||
export type { default as AnimatedAddition } from \\"./nodes/AnimatedAddition\\";
|
||||
export type { default as AnimatedDiffClamp } from \\"./nodes/AnimatedDiffClamp\\";
|
||||
export type { default as AnimatedDivision } from \\"./nodes/AnimatedDivision\\";
|
||||
export type { InterpolationConfigType as InterpolationConfig } from \\"./nodes/AnimatedInterpolation\\";
|
||||
export type { default as AnimatedModulo } from \\"./nodes/AnimatedModulo\\";
|
||||
export type { default as AnimatedMultiplication } from \\"./nodes/AnimatedMultiplication\\";
|
||||
export type { default as AnimatedSubtraction } from \\"./nodes/AnimatedSubtraction\\";
|
||||
@@ -222,53 +226,53 @@ exports[`public API should not change unintentionally Libraries/Animated/Animate
|
||||
reset: () => void,
|
||||
...
|
||||
};
|
||||
declare const add: (
|
||||
declare const addImpl: (
|
||||
a: AnimatedNode | number,
|
||||
b: AnimatedNode | number
|
||||
) => AnimatedAddition;
|
||||
declare const subtract: (
|
||||
declare const subtractImpl: (
|
||||
a: AnimatedNode | number,
|
||||
b: AnimatedNode | number
|
||||
) => AnimatedSubtraction;
|
||||
declare const divide: (
|
||||
declare const divideImpl: (
|
||||
a: AnimatedNode | number,
|
||||
b: AnimatedNode | number
|
||||
) => AnimatedDivision;
|
||||
declare const multiply: (
|
||||
declare const multiplyImpl: (
|
||||
a: AnimatedNode | number,
|
||||
b: AnimatedNode | number
|
||||
) => AnimatedMultiplication;
|
||||
declare const modulo: (a: AnimatedNode, modulus: number) => AnimatedModulo;
|
||||
declare const diffClamp: (
|
||||
declare const moduloImpl: (a: AnimatedNode, modulus: number) => AnimatedModulo;
|
||||
declare const diffClampImpl: (
|
||||
a: AnimatedNode,
|
||||
min: number,
|
||||
max: number
|
||||
) => AnimatedDiffClamp;
|
||||
declare const spring: (
|
||||
declare const springImpl: (
|
||||
value: AnimatedValue | AnimatedValueXY | AnimatedColor,
|
||||
config: SpringAnimationConfig
|
||||
) => CompositeAnimation;
|
||||
declare const timing: (
|
||||
declare const timingImpl: (
|
||||
value: AnimatedValue | AnimatedValueXY | AnimatedColor,
|
||||
config: TimingAnimationConfig
|
||||
) => CompositeAnimation;
|
||||
declare const decay: (
|
||||
declare const decayImpl: (
|
||||
value: AnimatedValue | AnimatedValueXY | AnimatedColor,
|
||||
config: DecayAnimationConfig
|
||||
) => CompositeAnimation;
|
||||
declare const sequence: (
|
||||
declare const sequenceImpl: (
|
||||
animations: Array<CompositeAnimation>
|
||||
) => CompositeAnimation;
|
||||
type ParallelConfig = {
|
||||
stopTogether?: boolean,
|
||||
...
|
||||
};
|
||||
declare const parallel: (
|
||||
declare const parallelImpl: (
|
||||
animations: Array<CompositeAnimation>,
|
||||
config?: ?ParallelConfig
|
||||
) => CompositeAnimation;
|
||||
declare const delay: (time: number) => CompositeAnimation;
|
||||
declare const stagger: (
|
||||
declare const delayImpl: (time: number) => CompositeAnimation;
|
||||
declare const staggerImpl: (
|
||||
time: number,
|
||||
animations: Array<CompositeAnimation>
|
||||
) => CompositeAnimation;
|
||||
@@ -277,19 +281,19 @@ type LoopAnimationConfig = {
|
||||
resetBeforeIteration?: boolean,
|
||||
...
|
||||
};
|
||||
declare const loop: (
|
||||
declare const loopImpl: (
|
||||
animation: CompositeAnimation,
|
||||
$$PARAM_1$$?: LoopAnimationConfig
|
||||
) => CompositeAnimation;
|
||||
declare function forkEvent(
|
||||
declare function forkEventImpl(
|
||||
event: ?AnimatedEvent | ?Function,
|
||||
listener: Function
|
||||
): AnimatedEvent | Function;
|
||||
declare function unforkEvent(
|
||||
declare function unforkEventImpl(
|
||||
event: ?AnimatedEvent | ?Function,
|
||||
listener: Function
|
||||
): void;
|
||||
declare const event: <T>(
|
||||
declare const eventImpl: <T>(
|
||||
argMapping: $ReadOnlyArray<?Mapping>,
|
||||
config: EventConfig<T>
|
||||
) => any;
|
||||
@@ -309,25 +313,25 @@ declare export default {
|
||||
Color: typeof AnimatedColor,
|
||||
Interpolation: typeof AnimatedInterpolation,
|
||||
Node: typeof AnimatedNode,
|
||||
decay: typeof decay,
|
||||
timing: typeof timing,
|
||||
spring: typeof spring,
|
||||
add: typeof add,
|
||||
subtract: typeof subtract,
|
||||
divide: typeof divide,
|
||||
multiply: typeof multiply,
|
||||
modulo: typeof modulo,
|
||||
diffClamp: typeof diffClamp,
|
||||
delay: typeof delay,
|
||||
sequence: typeof sequence,
|
||||
parallel: typeof parallel,
|
||||
stagger: typeof stagger,
|
||||
loop: typeof loop,
|
||||
event: typeof event,
|
||||
decay: typeof decayImpl,
|
||||
timing: typeof timingImpl,
|
||||
spring: typeof springImpl,
|
||||
add: typeof addImpl,
|
||||
subtract: typeof subtractImpl,
|
||||
divide: typeof divideImpl,
|
||||
multiply: typeof multiplyImpl,
|
||||
modulo: typeof moduloImpl,
|
||||
diffClamp: typeof diffClampImpl,
|
||||
delay: typeof delayImpl,
|
||||
sequence: typeof sequenceImpl,
|
||||
parallel: typeof parallelImpl,
|
||||
stagger: typeof staggerImpl,
|
||||
loop: typeof loopImpl,
|
||||
event: typeof eventImpl,
|
||||
createAnimatedComponent: typeof createAnimatedComponent,
|
||||
attachNativeEvent: typeof attachNativeEvent,
|
||||
forkEvent: typeof forkEvent,
|
||||
unforkEvent: typeof unforkEvent,
|
||||
attachNativeEvent: typeof attachNativeEventImpl,
|
||||
forkEvent: typeof forkEventImpl,
|
||||
unforkEvent: typeof unforkEventImpl,
|
||||
Event: typeof AnimatedEvent,
|
||||
};
|
||||
"
|
||||
@@ -628,10 +632,9 @@ exports[`public API should not change unintentionally Libraries/Animated/compone
|
||||
`;
|
||||
|
||||
exports[`public API should not change unintentionally Libraries/Animated/components/AnimatedScrollView.js 1`] = `
|
||||
"type AnimatedScrollViewProps = React.ElementConfig<typeof ScrollView>;
|
||||
type AnimatedScrollViewInstance = React.ElementRef<typeof ScrollView>;
|
||||
"type AnimatedScrollViewInstance = React.ElementRef<typeof ScrollView>;
|
||||
declare const AnimatedScrollView: AnimatedComponentType<
|
||||
AnimatedScrollViewProps,
|
||||
ScrollViewProps,
|
||||
AnimatedScrollViewInstance,
|
||||
>;
|
||||
declare export default typeof AnimatedScrollView;
|
||||
@@ -648,7 +651,7 @@ exports[`public API should not change unintentionally Libraries/Animated/compone
|
||||
|
||||
exports[`public API should not change unintentionally Libraries/Animated/components/AnimatedText.js 1`] = `
|
||||
"declare export default AnimatedComponentType<
|
||||
React.ElementConfig<typeof Text>,
|
||||
TextProps,
|
||||
React.ElementRef<typeof Text>,
|
||||
>;
|
||||
"
|
||||
@@ -656,7 +659,7 @@ exports[`public API should not change unintentionally Libraries/Animated/compone
|
||||
|
||||
exports[`public API should not change unintentionally Libraries/Animated/components/AnimatedView.js 1`] = `
|
||||
"declare export default AnimatedComponentType<
|
||||
React.ElementConfig<typeof View>,
|
||||
ViewProps,
|
||||
React.ElementRef<typeof View>,
|
||||
>;
|
||||
"
|
||||
@@ -695,9 +698,7 @@ type NonAnimatedProps =
|
||||
| \\"disabled\\"
|
||||
| \\"accessibilityLabel\\";
|
||||
type PassThroughProps = $ReadOnly<{
|
||||
passthroughAnimatedPropExplicitValues?: React.ElementConfig<
|
||||
typeof View,
|
||||
> | null,
|
||||
passthroughAnimatedPropExplicitValues?: ViewProps | null,
|
||||
}>;
|
||||
export type AnimatedProps<Props: { ... }> = {
|
||||
[K in keyof Props]: K extends NonAnimatedProps
|
||||
@@ -1538,10 +1539,10 @@ exports[`public API should not change unintentionally Libraries/Components/Butto
|
||||
accessibilityHint?: ?string,
|
||||
accessibilityLanguage?: ?Stringish,
|
||||
}>;
|
||||
declare const Touchable:
|
||||
declare const NativeTouchable:
|
||||
| typeof TouchableNativeFeedback
|
||||
| typeof TouchableOpacity;
|
||||
type ButtonRef = React.ElementRef<typeof Touchable>;
|
||||
type ButtonRef = React.ElementRef<typeof NativeTouchable>;
|
||||
declare const Button: component(
|
||||
ref?: React.RefSetter<ButtonRef>,
|
||||
...props: ButtonProps
|
||||
@@ -1757,8 +1758,7 @@ declare export default typeof LayoutConformanceNativeComponent;
|
||||
`;
|
||||
|
||||
exports[`public API should not change unintentionally Libraries/Components/Pressable/Pressable.js 1`] = `
|
||||
"type ViewStyleProp = React.ElementConfig<typeof View>[\\"style\\"];
|
||||
export type { PressableAndroidRippleConfig };
|
||||
"export type { PressableAndroidRippleConfig };
|
||||
export type PressableStateCallbackType = $ReadOnly<{
|
||||
pressed: boolean,
|
||||
}>;
|
||||
@@ -1932,11 +1932,11 @@ export { default } from \\"../../../src/private/specs_DEPRECATED/components/RCTS
|
||||
`;
|
||||
|
||||
exports[`public API should not change unintentionally Libraries/Components/SafeAreaView/SafeAreaView.js 1`] = `
|
||||
"declare const exported: component(
|
||||
"declare const SafeAreaView: component(
|
||||
ref?: React.RefSetter<React.ElementRef<typeof View>>,
|
||||
...props: ViewProps
|
||||
);
|
||||
declare export default typeof exported;
|
||||
declare export default typeof SafeAreaView;
|
||||
"
|
||||
`;
|
||||
|
||||
@@ -4179,11 +4179,11 @@ exports[`public API should not change unintentionally Libraries/EventEmitter/Nat
|
||||
type EmitterSubscription = EventSubscription;
|
||||
export type { EventSubscription, EmitterSubscription };
|
||||
export type NativeEventSubscription = EventSubscription;
|
||||
type UnsafeObject = Object;
|
||||
type UnsafeNativeEventObject = Object;
|
||||
declare export default class NativeEventEmitter<
|
||||
TEventToArgsMap: $ReadOnly<
|
||||
Record<string, $ReadOnlyArray<UnsafeObject>>,
|
||||
> = $ReadOnly<Record<string, $ReadOnlyArray<UnsafeObject>>>,
|
||||
Record<string, $ReadOnlyArray<UnsafeNativeEventObject>>,
|
||||
> = $ReadOnly<Record<string, $ReadOnlyArray<UnsafeNativeEventObject>>>,
|
||||
> implements IEventEmitter<TEventToArgsMap>
|
||||
{
|
||||
constructor(nativeModule?: ?NativeModule): void;
|
||||
@@ -4859,13 +4859,13 @@ export type LayoutAnimationProperties = $ReadOnly<{
|
||||
}>;
|
||||
type OnAnimationDidEndCallback = () => void;
|
||||
type OnAnimationDidFailCallback = () => void;
|
||||
declare function setEnabled(value: boolean): void;
|
||||
declare function setLayoutAnimationEnabled(value: boolean): void;
|
||||
declare function configureNext(
|
||||
config: LayoutAnimationConfig,
|
||||
onAnimationDidEnd?: OnAnimationDidEndCallback,
|
||||
onAnimationDidFail?: OnAnimationDidFailCallback
|
||||
): void;
|
||||
declare function create(
|
||||
declare function createLayoutAnimation(
|
||||
duration: number,
|
||||
type?: LayoutAnimationType,
|
||||
property?: LayoutAnimationProperty
|
||||
@@ -4877,7 +4877,7 @@ declare const Presets: {
|
||||
};
|
||||
declare const LayoutAnimation: {
|
||||
configureNext: typeof configureNext,
|
||||
create: typeof create,
|
||||
create: typeof createLayoutAnimation,
|
||||
Types: LayoutAnimationTypes,
|
||||
Properties: LayoutAnimationProperties,
|
||||
checkConfig(...args: Array<mixed>): void,
|
||||
@@ -4885,7 +4885,7 @@ declare const LayoutAnimation: {
|
||||
easeInEaseOut: (onAnimationDidEnd?: OnAnimationDidEndCallback) => void,
|
||||
linear: (onAnimationDidEnd?: OnAnimationDidEndCallback) => void,
|
||||
spring: (onAnimationDidEnd?: OnAnimationDidEndCallback) => void,
|
||||
setEnabled: typeof setEnabled,
|
||||
setEnabled: typeof setLayoutAnimationEnabled,
|
||||
};
|
||||
declare export default typeof LayoutAnimation;
|
||||
"
|
||||
@@ -4940,8 +4940,7 @@ declare export default typeof FillRateHelper;
|
||||
`;
|
||||
|
||||
exports[`public API should not change unintentionally Libraries/Lists/FlatList.js 1`] = `
|
||||
"declare const VirtualizedList: typeof VirtualizedLists.VirtualizedList;
|
||||
type RequiredProps<ItemT> = {
|
||||
"type RequiredProps<ItemT> = {
|
||||
data: ?$ReadOnly<$ArrayLike<ItemT>>,
|
||||
};
|
||||
type OptionalProps<ItemT> = {
|
||||
@@ -4971,7 +4970,6 @@ type FlatListBaseProps<ItemT> = {
|
||||
...RequiredProps<ItemT>,
|
||||
...OptionalProps<ItemT>,
|
||||
};
|
||||
type VirtualizedListProps = React.ElementConfig<typeof VirtualizedList>;
|
||||
export type FlatListProps<ItemT> = {
|
||||
...Omit<
|
||||
VirtualizedListProps,
|
||||
@@ -6147,7 +6145,7 @@ type PermissionsType = $ReadOnly<{
|
||||
}>;
|
||||
export type PermissionStatus = \\"granted\\" | \\"denied\\" | \\"never_ask_again\\";
|
||||
export type Permission = $Values<PermissionsType>;
|
||||
declare class PermissionsAndroid {
|
||||
declare class PermissionsAndroidImpl {
|
||||
PERMISSIONS: PermissionsType;
|
||||
RESULTS: $ReadOnly<{
|
||||
DENIED: \\"denied\\",
|
||||
@@ -6168,7 +6166,7 @@ declare class PermissionsAndroid {
|
||||
permissions: Array<Permission>
|
||||
): Promise<{ [permission: Permission]: PermissionStatus, ... }>;
|
||||
}
|
||||
declare const PermissionsAndroidInstance: PermissionsAndroid;
|
||||
declare const PermissionsAndroidInstance: PermissionsAndroidImpl;
|
||||
declare export default typeof PermissionsAndroidInstance;
|
||||
"
|
||||
`;
|
||||
@@ -6434,8 +6432,8 @@ declare export default typeof AppContainer;
|
||||
`;
|
||||
|
||||
exports[`public API should not change unintentionally Libraries/ReactNative/AppRegistry.flow.js 1`] = `
|
||||
"type Task = (taskData: any) => Promise<void>;
|
||||
export type TaskProvider = () => Task;
|
||||
"type HeadlessTask = (taskData: any) => Promise<void>;
|
||||
export type TaskProvider = () => HeadlessTask;
|
||||
export type ComponentProvider = () => React.ComponentType<any>;
|
||||
export type ComponentProviderInstrumentationHook = (
|
||||
component_: ComponentProvider,
|
||||
@@ -8365,7 +8363,7 @@ declare export default typeof NativeDevLoadingView;
|
||||
|
||||
exports[`public API should not change unintentionally Libraries/Utilities/NativeDeviceInfo.js 1`] = `
|
||||
"export * from \\"../../src/private/specs_DEPRECATED/modules/NativeDeviceInfo\\";
|
||||
declare export default typeof NativeDeviceInfo;
|
||||
export { default } from \\"../../src/private/specs_DEPRECATED/modules/NativeDeviceInfo\\";
|
||||
"
|
||||
`;
|
||||
|
||||
@@ -8656,7 +8654,7 @@ exports[`public API should not change unintentionally Libraries/Utilities/codege
|
||||
paperComponentNameDeprecated?: string,
|
||||
excludedPlatforms?: $ReadOnlyArray<\\"iOS\\" | \\"android\\">,
|
||||
}>;
|
||||
export type NativeComponentType<T> = HostComponent<T>;
|
||||
export type NativeComponentType<T: { ... }> = HostComponent<T>;
|
||||
declare function codegenNativeComponent<Props: { ... }>(
|
||||
componentName: string,
|
||||
options?: Options
|
||||
@@ -8961,12 +8959,12 @@ declare export default ErrorUtils;
|
||||
`;
|
||||
|
||||
exports[`public API should not change unintentionally Libraries/vendor/emitter/EventEmitter.js 1`] = `
|
||||
"type UnsafeObject = Object;
|
||||
"type UnsafeEventObject = Object;
|
||||
export interface EventSubscription {
|
||||
remove(): void;
|
||||
}
|
||||
export interface IEventEmitter<
|
||||
TEventToArgsMap: $ReadOnly<Record<string, $ReadOnlyArray<UnsafeObject>>>,
|
||||
TEventToArgsMap: $ReadOnly<Record<string, $ReadOnlyArray<UnsafeEventObject>>>,
|
||||
> {
|
||||
addListener<TEvent: $Keys<TEventToArgsMap>>(
|
||||
eventType: TEvent,
|
||||
@@ -8982,8 +8980,8 @@ export interface IEventEmitter<
|
||||
}
|
||||
declare export default class EventEmitter<
|
||||
TEventToArgsMap: $ReadOnly<
|
||||
Record<string, $ReadOnlyArray<UnsafeObject>>,
|
||||
> = $ReadOnly<Record<string, $ReadOnlyArray<UnsafeObject>>>,
|
||||
Record<string, $ReadOnlyArray<UnsafeEventObject>>,
|
||||
> = $ReadOnly<Record<string, $ReadOnlyArray<UnsafeEventObject>>>,
|
||||
> implements IEventEmitter<TEventToArgsMap>
|
||||
{
|
||||
constructor(): void;
|
||||
@@ -9063,6 +9061,8 @@ export type {
|
||||
export { default as RefreshControl } from \\"./Libraries/Components/RefreshControl/RefreshControl\\";
|
||||
export { default as SafeAreaView } from \\"./Libraries/Components/SafeAreaView/SafeAreaView\\";
|
||||
export type {
|
||||
ScrollViewImperativeMethods,
|
||||
ScrollViewScrollToOptions,
|
||||
ScrollResponderType,
|
||||
ScrollViewProps,
|
||||
ScrollViewPropsAndroid,
|
||||
|
||||
@@ -12,7 +12,7 @@ import type {TransformVisitor} from 'hermes-transform';
|
||||
|
||||
const {
|
||||
visitors: stripPrivateProperties,
|
||||
} = require('../../../../scripts/build-types/transforms/stripPrivateProperties');
|
||||
} = require('../../../../scripts/build-types/transforms/flow/stripPrivateProperties');
|
||||
const translate = require('flow-api-translator');
|
||||
const {existsSync, promises: fs} = require('fs');
|
||||
const glob = require('glob');
|
||||
|
||||
@@ -9,14 +9,14 @@
|
||||
*/
|
||||
|
||||
// $FlowFixMe[unclear-type] unclear type of events
|
||||
type UnsafeObject = Object;
|
||||
type UnsafeEventObject = Object;
|
||||
|
||||
export interface EventSubscription {
|
||||
remove(): void;
|
||||
}
|
||||
|
||||
export interface IEventEmitter<
|
||||
TEventToArgsMap: $ReadOnly<Record<string, $ReadOnlyArray<UnsafeObject>>>,
|
||||
TEventToArgsMap: $ReadOnly<Record<string, $ReadOnlyArray<UnsafeEventObject>>>,
|
||||
> {
|
||||
addListener<TEvent: $Keys<TEventToArgsMap>>(
|
||||
eventType: TEvent,
|
||||
@@ -41,7 +41,7 @@ interface Registration<TArgs> {
|
||||
}
|
||||
|
||||
type Registry<
|
||||
TEventToArgsMap: $ReadOnly<Record<string, $ReadOnlyArray<UnsafeObject>>>,
|
||||
TEventToArgsMap: $ReadOnly<Record<string, $ReadOnlyArray<UnsafeEventObject>>>,
|
||||
> = {
|
||||
[K in keyof TEventToArgsMap]: Set<Registration<TEventToArgsMap[K]>>,
|
||||
};
|
||||
@@ -68,8 +68,8 @@ type Registry<
|
||||
*/
|
||||
export default class EventEmitter<
|
||||
TEventToArgsMap: $ReadOnly<
|
||||
Record<string, $ReadOnlyArray<UnsafeObject>>,
|
||||
> = $ReadOnly<Record<string, $ReadOnlyArray<UnsafeObject>>>,
|
||||
Record<string, $ReadOnlyArray<UnsafeEventObject>>,
|
||||
> = $ReadOnly<Record<string, $ReadOnlyArray<UnsafeEventObject>>>,
|
||||
> implements IEventEmitter<TEventToArgsMap>
|
||||
{
|
||||
#registry: Registry<TEventToArgsMap>;
|
||||
@@ -157,7 +157,7 @@ export default class EventEmitter<
|
||||
}
|
||||
|
||||
function allocate<
|
||||
TEventToArgsMap: $ReadOnly<Record<string, $ReadOnlyArray<UnsafeObject>>>,
|
||||
TEventToArgsMap: $ReadOnly<Record<string, $ReadOnlyArray<UnsafeEventObject>>>,
|
||||
TEvent: $Keys<TEventToArgsMap>,
|
||||
TEventArgs: TEventToArgsMap[TEvent],
|
||||
>(
|
||||
|
||||
@@ -495,6 +495,14 @@ let reactRCTNetwork = RNTarget(
|
||||
dependencies: [.yoga, .jsi, .reactTurboModuleCore]
|
||||
)
|
||||
|
||||
/// React-RCTVibration.podspec
|
||||
let reactRCTVibration = RNTarget(
|
||||
name: .reactRCTVibration,
|
||||
path: "Libraries/Vibration",
|
||||
linkedFrameworks: ["AudioToolbox"],
|
||||
dependencies: [.yoga, .jsi, .reactTurboModuleCore]
|
||||
)
|
||||
|
||||
/// React-RCTAppDelegate.podspec
|
||||
let reactAppDelegate = RNTarget(
|
||||
name: .reactAppDelegate,
|
||||
@@ -560,6 +568,7 @@ let targets = [
|
||||
reactRCTText,
|
||||
reactRCTBlob,
|
||||
reactRCTNetwork,
|
||||
reactRCTVibration,
|
||||
reactRCTLinking,
|
||||
reactCoreModules,
|
||||
reactTurboModuleBridging,
|
||||
@@ -731,6 +740,7 @@ extension String {
|
||||
static let reactRCTText = "React-RCTText"
|
||||
static let reactRCTBlob = "React-RCTBlob"
|
||||
static let reactRCTNetwork = "React-RCTNetwork"
|
||||
static let reactRCTVibration = "React-RCTVibration"
|
||||
static let reactRCTActionSheet = "React-RCTActionSheet" // Empty target
|
||||
static let reactRCTLinking = "React-RCTLinking"
|
||||
static let reactCoreModules = "React-CoreModules"
|
||||
|
||||
@@ -0,0 +1,79 @@
|
||||
# Copyright (c) Meta Platforms, Inc. and affiliates.
|
||||
#
|
||||
# This source code is licensed under the MIT license found in the
|
||||
# LICENSE file in the root directory of this source tree.
|
||||
|
||||
require "json"
|
||||
package = JSON.parse(File.read(File.join(__dir__, "package.json")))
|
||||
version = package['version']
|
||||
|
||||
source = ReactNativeCoreUtils.resolve_podspec_source()
|
||||
Pod::Spec.new do |s|
|
||||
s.name = "React-Core-prebuilt"
|
||||
s.version = version
|
||||
s.summary = "The core of React Native prebuilt frameworks."
|
||||
s.homepage = "https://reactnative.dev/"
|
||||
s.license = package["license"]
|
||||
s.author = "Meta Platforms, Inc. and its affiliates"
|
||||
s.platforms = min_supported_versions
|
||||
s.source = source
|
||||
s.vendored_frameworks = "React.xcframework"
|
||||
|
||||
s.preserve_paths = '**/*.*'
|
||||
s.header_mappings_dir = 'React.xcframework/Headers'
|
||||
s.source_files = 'React.xcframework/Headers/**/*.{h,hpp}'
|
||||
|
||||
s.module_name = 'React'
|
||||
s.module_map = 'React.xcframework/Modules/module.modulemap'
|
||||
s.public_header_files = 'React.xcframework/Headers/**/*.h'
|
||||
|
||||
add_rn_third_party_dependencies(s)
|
||||
|
||||
# We need to make sure that the React.xcframework is copied correctly - in the downloaded tarball
|
||||
# the root directory is the framework, but when using it we need to have it in a subdirectory
|
||||
# called React.xcframework, so we need to move the contents of the tarball into that directory.
|
||||
# This is done in the prepare_command.
|
||||
# We need to make sure that the headers are copied to the right place - local tar.gz has a different structure
|
||||
# than the one from the maven repo
|
||||
s.prepare_command = <<~'CMD'
|
||||
CURRENT_PATH=$(pwd)
|
||||
XCFRAMEWORK_PATH="${CURRENT_PATH}/React.xcframework"
|
||||
|
||||
# Check if XCFRAMEWORK_PATH is empty
|
||||
if [ -z "$XCFRAMEWORK_PATH" ]; then
|
||||
echo "ERROR: XCFRAMEWORK_PATH is empty."
|
||||
exit 0
|
||||
fi
|
||||
|
||||
mkdir -p "${XCFRAMEWORK_PATH}"
|
||||
find "$CURRENT_PATH" -mindepth 1 -maxdepth 1 ! -name "$(basename "$XCFRAMEWORK_PATH")" -exec mv {} "$XCFRAMEWORK_PATH" \;
|
||||
CMD
|
||||
|
||||
# If we are passing a local tarball, we don't want to switch between Debug and Release
|
||||
if !ENV["RCT_TESTONLY_RNCORE_TARBALL_PATH"]
|
||||
script_phase = {
|
||||
:name => "[RNDeps] Replace React Native Core for the right configuration, if needed",
|
||||
:execution_position => :before_compile,
|
||||
:script => <<-EOS
|
||||
. "$REACT_NATIVE_PATH/scripts/xcode/with-environment.sh"
|
||||
|
||||
CONFIG="Release"
|
||||
if echo $GCC_PREPROCESSOR_DEFINITIONS | grep -q "DEBUG=1"; then
|
||||
CONFIG="Debug"
|
||||
fi
|
||||
|
||||
# TODO(T228219721): Add this for React Native Core as well
|
||||
##### "$NODE_BINARY" "$REACT_NATIVE_PATH/third-party-podspecs/replace_dependencies_version.js" -c "$CONFIG" -r "#{version}" -p "$PODS_ROOT"
|
||||
EOS
|
||||
}
|
||||
|
||||
|
||||
# :always_out_of_date is only available in CocoaPods 1.13.0 and later
|
||||
if Gem::Version.new(Pod::VERSION) >= Gem::Version.new('1.13.0')
|
||||
# always run the script without warning
|
||||
script_phase[:always_out_of_date] = "1"
|
||||
end
|
||||
|
||||
s.script_phase = script_phase
|
||||
end
|
||||
end
|
||||
@@ -66,7 +66,7 @@ Pod::Spec.new do |s|
|
||||
s.default_subspec = "Default"
|
||||
|
||||
s.subspec "Default" do |ss|
|
||||
ss.source_files = "React/**/*.{c,h,m,mm,S,cpp}"
|
||||
ss.source_files = podspec_sources("React/**/*.{c,h,m,mm,S,cpp}", "React/**/*.h")
|
||||
exclude_files = [
|
||||
"React/CoreModules/**/*",
|
||||
"React/DevSupport/**/*",
|
||||
@@ -76,17 +76,24 @@ Pod::Spec.new do |s|
|
||||
"React/Inspector/**/*",
|
||||
"React/Runtime/**/*",
|
||||
]
|
||||
|
||||
|
||||
# The default is use hermes, we don't have jsc installed
|
||||
exclude_files = exclude_files.append("React/CxxBridge/JSCExecutorFactory.{h,mm}")
|
||||
|
||||
ss.exclude_files = exclude_files
|
||||
ss.private_header_files = "React/Cxx*/*.h"
|
||||
|
||||
# Include prebuilt if we're not building from source
|
||||
if !ReactNativeCoreUtils.build_rncore_from_source()
|
||||
ss.dependency "React-Core-prebuilt", version
|
||||
end
|
||||
end
|
||||
|
||||
s.subspec "DevSupport" do |ss|
|
||||
ss.source_files = "React/DevSupport/*.{h,mm,m}",
|
||||
"React/Inspector/*.{h,mm,m}"
|
||||
ss.source_files = podspec_sources(["React/DevSupport/*.{h,mm,m}",
|
||||
"React/Inspector/*.{h,mm,m}"],
|
||||
["React/DevSupport/*.h",
|
||||
"React/Inspector/*.h"])
|
||||
|
||||
ss.dependency "React-Core/Default", version
|
||||
ss.dependency "React-Core/RCTWebSocket", version
|
||||
@@ -94,7 +101,7 @@ Pod::Spec.new do |s|
|
||||
end
|
||||
|
||||
s.subspec "RCTWebSocket" do |ss|
|
||||
ss.source_files = "Libraries/WebSocket/*.{h,m}"
|
||||
ss.source_files = podspec_sources("Libraries/WebSocket/*.{h,m}", "Libraries/WebSocket/*.h")
|
||||
ss.dependency "React-Core/Default", version
|
||||
end
|
||||
|
||||
|
||||
@@ -5,8 +5,6 @@
|
||||
* LICENSE file in the root directory of this source tree.
|
||||
*/
|
||||
|
||||
#import <tgmath.h>
|
||||
|
||||
#import <CoreGraphics/CoreGraphics.h>
|
||||
#import <Foundation/Foundation.h>
|
||||
#import <UIKit/UIKit.h>
|
||||
|
||||
@@ -32,7 +32,7 @@ Pod::Spec.new do |s|
|
||||
s.compiler_flags = '-Wno-nullability-completeness'
|
||||
s.source = source
|
||||
|
||||
s.source_files = "**/*.{c,m,mm,cpp}"
|
||||
s.source_files = podspec_sources("**/*.{c,m,mm,cpp}", "**/*.h")
|
||||
|
||||
s.ios.exclude_files = "PlatformStubs/**/*"
|
||||
exclude_files = ["RCTStatusBarManager.mm"]
|
||||
|
||||
+37
-2
@@ -32,6 +32,12 @@ typedef NS_ENUM(NSInteger, RCTVirtualViewMode) {
|
||||
RCTVirtualViewModeHidden = 2,
|
||||
};
|
||||
|
||||
typedef NS_ENUM(NSInteger, RCTVirtualViewRenderState) {
|
||||
RCTVirtualViewRenderStateUnknown = 0,
|
||||
RCTVirtualViewRenderStateRendered = 1,
|
||||
RCTVirtualViewRenderStateNone = 2,
|
||||
};
|
||||
|
||||
/**
|
||||
* Checks whether one CGRect overlaps with another CGRect.
|
||||
*
|
||||
@@ -67,6 +73,7 @@ static BOOL CGRectOverlaps(CGRect rect1, CGRect rect2)
|
||||
@implementation RCTVirtualViewComponentView {
|
||||
RCTScrollViewComponentView *_lastParentScrollViewComponentView;
|
||||
std::optional<enum RCTVirtualViewMode> _mode;
|
||||
enum RCTVirtualViewRenderState _renderState;
|
||||
std::optional<CGRect> _targetRect;
|
||||
}
|
||||
|
||||
@@ -74,6 +81,7 @@ static BOOL CGRectOverlaps(CGRect rect1, CGRect rect2)
|
||||
{
|
||||
if (self = [super initWithFrame:frame]) {
|
||||
_props = VirtualViewShadowNode::defaultSharedProps();
|
||||
_renderState = RCTVirtualViewRenderStateUnknown;
|
||||
}
|
||||
|
||||
return self;
|
||||
@@ -81,11 +89,27 @@ static BOOL CGRectOverlaps(CGRect rect1, CGRect rect2)
|
||||
|
||||
- (void)updateProps:(const Props::Shared &)props oldProps:(const Props::Shared &)oldProps
|
||||
{
|
||||
const auto &newViewProps = static_cast<const VirtualViewProps &>(*props);
|
||||
|
||||
if (!_mode.has_value()) {
|
||||
const auto &newViewProps = static_cast<const VirtualViewProps &>(*props);
|
||||
_mode = newViewProps.initialHidden ? RCTVirtualViewModeHidden : RCTVirtualViewModeVisible;
|
||||
}
|
||||
|
||||
// If disabled, `_renderState` will always be `RCTVirtualViewRenderStateUnknown`.
|
||||
if (ReactNativeFeatureFlags::enableVirtualViewRenderState()) {
|
||||
switch (newViewProps.renderState) {
|
||||
case 1:
|
||||
_renderState = RCTVirtualViewRenderStateRendered;
|
||||
break;
|
||||
case 2:
|
||||
_renderState = RCTVirtualViewRenderStateNone;
|
||||
break;
|
||||
default:
|
||||
_renderState = RCTVirtualViewRenderStateUnknown;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
[super updateProps:props oldProps:oldProps];
|
||||
}
|
||||
|
||||
@@ -219,7 +243,18 @@ static BOOL CGRectOverlaps(CGRect rect1, CGRect rect2)
|
||||
|
||||
switch (newMode) {
|
||||
case RCTVirtualViewModeVisible:
|
||||
[self dispatchSyncModeChange:event];
|
||||
if (_renderState == RCTVirtualViewRenderStateUnknown) {
|
||||
// Feature flag is disabled, so use the former logic.
|
||||
[self dispatchSyncModeChange:event];
|
||||
} else {
|
||||
// If the previous mode was prerender and the result of dispatching that event was committed, we do not need to
|
||||
// dispatch an event for visible.
|
||||
const auto wasPrerenderCommitted = oldMode.has_value() && oldMode == RCTVirtualViewModePrerender &&
|
||||
_renderState == RCTVirtualViewRenderStateRendered;
|
||||
if (!wasPrerenderCommitted) {
|
||||
[self dispatchSyncModeChange:event];
|
||||
}
|
||||
}
|
||||
break;
|
||||
case RCTVirtualViewModePrerender:
|
||||
if (!oldMode.has_value() || oldMode != RCTVirtualViewModeVisible) {
|
||||
|
||||
@@ -72,6 +72,12 @@ class SchedulerDelegateProxy : public SchedulerDelegate {
|
||||
[scheduler.delegate schedulerDidSynchronouslyUpdateViewOnUIThread:tag props:props];
|
||||
}
|
||||
|
||||
void schedulerDidUpdateShadowTree(const std::unordered_map<Tag, folly::dynamic> &tagToProps) override
|
||||
{
|
||||
// Does nothing.
|
||||
// This delegate method is not currently used on iOS.
|
||||
}
|
||||
|
||||
private:
|
||||
void *scheduler_;
|
||||
};
|
||||
|
||||
@@ -16,6 +16,7 @@ NS_ASSUME_NONNULL_BEGIN
|
||||
+ (std::vector<facebook::react::ProcessedColorStop>)getFixedColorStops:
|
||||
(const std::vector<facebook::react::ColorStop> &)colorStops
|
||||
gradientLineLength:(CGFloat)gradientLineLength;
|
||||
|
||||
// CAGradientLayer linear gradient squishes the non-square gradient to square gradient.
|
||||
// This function fixes the "squished" effect.
|
||||
// See https://stackoverflow.com/a/43176174 for more information.
|
||||
|
||||
@@ -153,75 +153,42 @@ static RadiusVector GetRadialGradientRadius(
|
||||
|
||||
+ (CALayer *)gradientLayerWithSize:(CGSize)size gradient:(const RadialGradient &)gradient
|
||||
{
|
||||
UIGraphicsImageRenderer *renderer = [[UIGraphicsImageRenderer alloc] initWithSize:size];
|
||||
UIImage *gradientImage = [renderer imageWithActions:^(UIGraphicsImageRendererContext *_Nonnull rendererContext) {
|
||||
CGContextRef context = rendererContext.CGContext;
|
||||
CAGradientLayer *gradientLayer = [CAGradientLayer layer];
|
||||
gradientLayer.type = kCAGradientLayerRadial;
|
||||
CGPoint centerPoint = CGPointMake(size.width / 2.0, size.height / 2.0);
|
||||
|
||||
CGPoint centerPoint = CGPointMake(size.width / 2.0, size.height / 2.0);
|
||||
if (gradient.position.top) {
|
||||
centerPoint.y = gradient.position.top->resolve(size.height);
|
||||
} else if (gradient.position.bottom) {
|
||||
centerPoint.y = size.height - gradient.position.bottom->resolve(size.height);
|
||||
}
|
||||
|
||||
if (gradient.position.top) {
|
||||
centerPoint.y = gradient.position.top->resolve(size.height);
|
||||
} else if (gradient.position.bottom) {
|
||||
centerPoint.y = size.height - gradient.position.bottom->resolve(size.height);
|
||||
}
|
||||
if (gradient.position.left) {
|
||||
centerPoint.x = gradient.position.left->resolve(size.width);
|
||||
} else if (gradient.position.right) {
|
||||
centerPoint.x = size.width - gradient.position.right->resolve(size.width);
|
||||
}
|
||||
|
||||
if (gradient.position.left) {
|
||||
centerPoint.x = gradient.position.left->resolve(size.width);
|
||||
} else if (gradient.position.right) {
|
||||
centerPoint.x = size.width - gradient.position.right->resolve(size.width);
|
||||
}
|
||||
bool isCircle = (gradient.shape == RadialGradientShape::Circle);
|
||||
auto [radiusX, radiusY] =
|
||||
GetRadialGradientRadius(isCircle, gradient.size, centerPoint.x, centerPoint.y, size.width, size.height);
|
||||
const auto gradientLineLength = std::max(radiusX, radiusY);
|
||||
const auto colorStops = [RCTGradientUtils getFixedColorStops:gradient.colorStops
|
||||
gradientLineLength:gradientLineLength];
|
||||
gradientLayer.startPoint = CGPointMake(centerPoint.x / size.width, centerPoint.y / size.height);
|
||||
// endpoint.x is horizontal length and endpoint.y is vertical length
|
||||
gradientLayer.endPoint = CGPointMake(
|
||||
gradientLayer.startPoint.x + radiusX / size.width, gradientLayer.startPoint.y + radiusY / size.height);
|
||||
|
||||
bool isCircle = (gradient.shape == RadialGradientShape::Circle);
|
||||
auto [radiusX, radiusY] =
|
||||
GetRadialGradientRadius(isCircle, gradient.size, centerPoint.x, centerPoint.y, size.width, size.height);
|
||||
NSMutableArray<id> *colors = [NSMutableArray array];
|
||||
NSMutableArray<NSNumber *> *locations = [NSMutableArray array];
|
||||
for (const auto &colorStop : colorStops) {
|
||||
[colors addObject:(id)RCTUIColorFromSharedColor(colorStop.color).CGColor];
|
||||
[locations addObject:@(std::max(std::min(colorStop.position.value(), 1.0), 0.0))];
|
||||
}
|
||||
|
||||
CGFloat scale = 1.0;
|
||||
if (radiusX != radiusY && gradient.shape != RadialGradientShape::Circle) {
|
||||
scale = radiusX / radiusY;
|
||||
CGContextSaveGState(context);
|
||||
// Scale the context to make the circular gradient appear elliptical
|
||||
CGContextTranslateCTM(context, centerPoint.x, centerPoint.y);
|
||||
CGContextScaleCTM(context, 1.0, 1.0 / scale);
|
||||
CGContextTranslateCTM(context, -centerPoint.x, -centerPoint.y);
|
||||
radiusX = std::max(radiusX, radiusY * scale);
|
||||
}
|
||||
|
||||
const auto colorStops = [RCTGradientUtils getFixedColorStops:gradient.colorStops gradientLineLength:radiusX];
|
||||
|
||||
NSMutableArray *colors = [NSMutableArray array];
|
||||
CGFloat locations[colorStops.size()];
|
||||
|
||||
for (size_t i = 0; i < colorStops.size(); ++i) {
|
||||
const auto &colorStop = colorStops[i];
|
||||
CGColorRef cgColor = RCTCreateCGColorRefFromSharedColor(colorStop.color);
|
||||
[colors addObject:(__bridge id)cgColor];
|
||||
locations[i] = std::max(std::min(colorStop.position.value(), 1.0), 0.0);
|
||||
}
|
||||
|
||||
CGGradientRef cgGradient = CGGradientCreateWithColors(NULL, (__bridge CFArrayRef)colors, locations);
|
||||
|
||||
CGContextDrawRadialGradient(
|
||||
context,
|
||||
cgGradient,
|
||||
centerPoint,
|
||||
0,
|
||||
centerPoint,
|
||||
radiusX,
|
||||
kCGGradientDrawsBeforeStartLocation | kCGGradientDrawsAfterEndLocation);
|
||||
|
||||
// Restore the context state if we scaled it
|
||||
if (radiusX != radiusY && gradient.shape != RadialGradientShape::Circle) {
|
||||
CGContextRestoreGState(context);
|
||||
}
|
||||
|
||||
for (id color in colors) {
|
||||
CGColorRelease((__bridge CGColorRef)color);
|
||||
}
|
||||
CGGradientRelease(cgGradient);
|
||||
}];
|
||||
|
||||
CALayer *gradientLayer = [CALayer layer];
|
||||
gradientLayer.contents = (__bridge id)gradientImage.CGImage;
|
||||
gradientLayer.colors = colors;
|
||||
gradientLayer.locations = locations;
|
||||
|
||||
return gradientLayer;
|
||||
}
|
||||
|
||||
@@ -35,7 +35,7 @@ Pod::Spec.new do |s|
|
||||
s.author = "Meta Platforms, Inc. and its affiliates"
|
||||
s.platforms = min_supported_versions
|
||||
s.source = source
|
||||
s.source_files = "FBReactNativeSpec/**/*.{c,h,m,mm,cpp}"
|
||||
s.source_files = podspec_sources("FBReactNativeSpec/**/*.{c,h,m,mm,cpp}", "FBReactNativeSpec/**/*.{h}")
|
||||
s.exclude_files = "FBReactNativeSpec/react/renderer/components",
|
||||
s.compiler_flags = new_arch_flags
|
||||
s.header_dir = 'FBReactNativeSpec'
|
||||
@@ -63,7 +63,7 @@ Pod::Spec.new do |s|
|
||||
add_rn_third_party_dependencies(s)
|
||||
|
||||
s.subspec "components" do |ss|
|
||||
ss.source_files = "FBReactNativeSpec/react/renderer/components/FBReactNativeSpec/**/*.{m,mm,cpp,h}"
|
||||
ss.source_files = podspec_sources("FBReactNativeSpec/react/renderer/components/FBReactNativeSpec/**/*.{m,mm,cpp,h}", "FBReactNativeSpec/react/renderer/components/FBReactNativeSpec/**/*.{h}")
|
||||
ss.header_dir = "react/renderer/components/FBReactNativeSpec"
|
||||
|
||||
add_dependency(ss, "React-featureflags")
|
||||
|
||||
@@ -42,7 +42,7 @@ Pod::Spec.new do |s|
|
||||
s.author = "Meta Platforms, Inc. and its affiliates"
|
||||
s.platforms = min_supported_versions
|
||||
s.source = source
|
||||
s.source_files = "Fabric/**/*.{c,h,m,mm,S,cpp}"
|
||||
s.source_files = podspec_sources("Fabric/**/*.{c,h,m,mm,S,cpp}", "Fabric/**/*.{h}")
|
||||
s.exclude_files = "**/tests/*",
|
||||
"**/android/*",
|
||||
s.compiler_flags = new_arch_flags
|
||||
@@ -99,7 +99,7 @@ Pod::Spec.new do |s|
|
||||
add_rn_third_party_dependencies(s)
|
||||
|
||||
s.test_spec 'Tests' do |test_spec|
|
||||
test_spec.source_files = "Tests/**/*.{mm}"
|
||||
test_spec.source_files = podspec_sources("Tests/**/*.{mm}", "")
|
||||
test_spec.framework = "XCTest"
|
||||
end
|
||||
end
|
||||
|
||||
@@ -30,7 +30,7 @@ Pod::Spec.new do |s|
|
||||
s.author = "Meta Platforms, Inc. and its affiliates"
|
||||
s.platforms = min_supported_versions
|
||||
s.source = source
|
||||
s.source_files = "*.{h,mm}"
|
||||
s.source_files = podspec_sources("*.{h,mm}", "*.h")
|
||||
s.compiler_flags = new_arch_flags
|
||||
s.header_dir = header_dir
|
||||
s.module_name = module_name
|
||||
|
||||
@@ -3659,6 +3659,7 @@ public class com/facebook/react/uimanager/ReactAccessibilityDelegate : androidx/
|
||||
public static final field TOP_ACCESSIBILITY_ACTION_EVENT Ljava/lang/String;
|
||||
public static final field sActionIdMap Ljava/util/HashMap;
|
||||
public fun <init> (Landroid/view/View;ZI)V
|
||||
public fun cleanUp ()V
|
||||
public static fun createNodeInfoFromView (Landroid/view/View;)Landroidx/core/view/accessibility/AccessibilityNodeInfoCompat;
|
||||
public fun getAccessibilityNodeProvider (Landroid/view/View;)Landroidx/core/view/accessibility/AccessibilityNodeProviderCompat;
|
||||
protected fun getHostView ()Landroid/view/View;
|
||||
@@ -4339,20 +4340,20 @@ public abstract interface class com/facebook/react/uimanager/UIImplementation$La
|
||||
public abstract fun onLayoutUpdated (Lcom/facebook/react/uimanager/ReactShadowNode;)V
|
||||
}
|
||||
|
||||
public class com/facebook/react/uimanager/UIManagerHelper {
|
||||
public final class com/facebook/react/uimanager/UIManagerHelper {
|
||||
public static final field INSTANCE Lcom/facebook/react/uimanager/UIManagerHelper;
|
||||
public static final field PADDING_BOTTOM_INDEX I
|
||||
public static final field PADDING_END_INDEX I
|
||||
public static final field PADDING_START_INDEX I
|
||||
public static final field PADDING_TOP_INDEX I
|
||||
public fun <init> ()V
|
||||
public static fun getDefaultTextInputPadding (Landroid/content/Context;)[F
|
||||
public static fun getEventDispatcher (Lcom/facebook/react/bridge/ReactContext;I)Lcom/facebook/react/uimanager/events/EventDispatcher;
|
||||
public static fun getEventDispatcherForReactTag (Lcom/facebook/react/bridge/ReactContext;I)Lcom/facebook/react/uimanager/events/EventDispatcher;
|
||||
public static fun getReactContext (Landroid/view/View;)Lcom/facebook/react/bridge/ReactContext;
|
||||
public static fun getSurfaceId (Landroid/content/Context;)I
|
||||
public static fun getSurfaceId (Landroid/view/View;)I
|
||||
public static fun getUIManager (Lcom/facebook/react/bridge/ReactContext;I)Lcom/facebook/react/bridge/UIManager;
|
||||
public static fun getUIManagerForReactTag (Lcom/facebook/react/bridge/ReactContext;I)Lcom/facebook/react/bridge/UIManager;
|
||||
public static final fun getDefaultTextInputPadding (Landroid/content/Context;)[F
|
||||
public static final fun getEventDispatcher (Lcom/facebook/react/bridge/ReactContext;I)Lcom/facebook/react/uimanager/events/EventDispatcher;
|
||||
public static final fun getEventDispatcherForReactTag (Lcom/facebook/react/bridge/ReactContext;I)Lcom/facebook/react/uimanager/events/EventDispatcher;
|
||||
public static final fun getReactContext (Landroid/view/View;)Lcom/facebook/react/bridge/ReactContext;
|
||||
public static final fun getSurfaceId (Landroid/content/Context;)I
|
||||
public static final fun getSurfaceId (Landroid/view/View;)I
|
||||
public static final fun getUIManager (Lcom/facebook/react/bridge/ReactContext;I)Lcom/facebook/react/bridge/UIManager;
|
||||
public static final fun getUIManagerForReactTag (Lcom/facebook/react/bridge/ReactContext;I)Lcom/facebook/react/bridge/UIManager;
|
||||
}
|
||||
|
||||
public class com/facebook/react/uimanager/UIManagerModule : com/facebook/react/bridge/ReactContextBaseJavaModule, com/facebook/react/bridge/LifecycleEventListener, com/facebook/react/bridge/OnBatchCompleteListener, com/facebook/react/bridge/UIManager {
|
||||
@@ -4866,20 +4867,6 @@ public abstract interface class com/facebook/react/uimanager/events/EventDispatc
|
||||
public abstract fun removeListener (Lcom/facebook/react/uimanager/events/EventDispatcherListener;)V
|
||||
}
|
||||
|
||||
public class com/facebook/react/uimanager/events/EventDispatcherImpl : com/facebook/react/bridge/LifecycleEventListener, com/facebook/react/uimanager/events/EventDispatcher {
|
||||
public fun <init> (Lcom/facebook/react/bridge/ReactApplicationContext;)V
|
||||
public fun addBatchEventDispatchedListener (Lcom/facebook/react/uimanager/events/BatchEventDispatchedListener;)V
|
||||
public fun addListener (Lcom/facebook/react/uimanager/events/EventDispatcherListener;)V
|
||||
public fun dispatchAllEvents ()V
|
||||
public fun dispatchEvent (Lcom/facebook/react/uimanager/events/Event;)V
|
||||
public fun onCatalystInstanceDestroyed ()V
|
||||
public fun onHostDestroy ()V
|
||||
public fun onHostPause ()V
|
||||
public fun onHostResume ()V
|
||||
public fun removeBatchEventDispatchedListener (Lcom/facebook/react/uimanager/events/BatchEventDispatchedListener;)V
|
||||
public fun removeListener (Lcom/facebook/react/uimanager/events/EventDispatcherListener;)V
|
||||
}
|
||||
|
||||
public abstract interface class com/facebook/react/uimanager/events/EventDispatcherListener {
|
||||
public abstract fun onEventDispatch (Lcom/facebook/react/uimanager/events/Event;)V
|
||||
}
|
||||
@@ -5303,6 +5290,7 @@ public class com/facebook/react/viewmanagers/VirtualViewManagerDelegate : com/fa
|
||||
|
||||
public abstract interface class com/facebook/react/viewmanagers/VirtualViewManagerInterface : com/facebook/react/uimanager/ViewManagerWithGeneratedInterface {
|
||||
public abstract fun setInitialHidden (Landroid/view/View;Z)V
|
||||
public abstract fun setRenderState (Landroid/view/View;I)V
|
||||
}
|
||||
|
||||
public final class com/facebook/react/views/drawer/ReactDrawerLayout : androidx/drawerlayout/widget/DrawerLayout {
|
||||
|
||||
+3
-3
@@ -37,15 +37,15 @@ public class MemoryPressureRouter(context: Context) : ComponentCallbacks2 {
|
||||
listeners.remove(listener)
|
||||
}
|
||||
|
||||
override public fun onTrimMemory(level: Int) {
|
||||
public override fun onTrimMemory(level: Int) {
|
||||
dispatchMemoryPressure(level)
|
||||
}
|
||||
|
||||
override public fun onConfigurationChanged(newConfig: Configuration): Unit = Unit
|
||||
public override fun onConfigurationChanged(newConfig: Configuration): Unit = Unit
|
||||
|
||||
@Deprecated(
|
||||
"onLowMemory is deprecated, use onTrimMemory instead.", ReplaceWith("onTrimMemory(level)"))
|
||||
override public fun onLowMemory(): Unit = Unit
|
||||
public override fun onLowMemory(): Unit = Unit
|
||||
|
||||
private fun dispatchMemoryPressure(level: Int) {
|
||||
for (listener in listeners) {
|
||||
|
||||
+2
-1
@@ -111,7 +111,8 @@ public open class ReactDelegate {
|
||||
|
||||
public fun onHostResume() {
|
||||
if (activity !is DefaultHardwareBackBtnHandler) {
|
||||
throw ClassCastException("Host Activity does not implement DefaultHardwareBackBtnHandler")
|
||||
throw ClassCastException(
|
||||
"Host Activity `${activity.javaClass.simpleName}` does not implement DefaultHardwareBackBtnHandler")
|
||||
}
|
||||
if (ReactNativeNewArchitectureFeatureFlags.enableBridgelessArchitecture() &&
|
||||
reactHost != null) {
|
||||
|
||||
+45
-59
@@ -80,7 +80,7 @@ import kotlin.concurrent.Volatile
|
||||
*/
|
||||
@OptIn(UnstableReactNativeAPI::class)
|
||||
@ReactModule(name = NativeAnimatedModuleSpec.NAME)
|
||||
public class NativeAnimatedModule(reactContext: ReactApplicationContext?) :
|
||||
public class NativeAnimatedModule(reactContext: ReactApplicationContext) :
|
||||
NativeAnimatedModuleSpec(reactContext), LifecycleEventListener, UIManagerListener {
|
||||
|
||||
// For `queueAndExecuteBatchedOperations`
|
||||
@@ -163,12 +163,13 @@ public class NativeAnimatedModule(reactContext: ReactApplicationContext?) :
|
||||
// Due to a race condition, we manually "carry-over" a polled item from previous batch
|
||||
// instead of peeking the queue itself for consistency.
|
||||
// TODO(T112522554): Clean up the queue access
|
||||
val peekedOperation = peekedOperation
|
||||
if (peekedOperation != null) {
|
||||
if (checkNotNull(peekedOperation).batchNumber > maxBatchNumber) {
|
||||
if (peekedOperation.batchNumber > maxBatchNumber) {
|
||||
break
|
||||
}
|
||||
operations.add(checkNotNull(peekedOperation))
|
||||
peekedOperation = null
|
||||
operations.add(peekedOperation)
|
||||
this.peekedOperation = null
|
||||
}
|
||||
|
||||
val polledOperation =
|
||||
@@ -179,7 +180,7 @@ public class NativeAnimatedModule(reactContext: ReactApplicationContext?) :
|
||||
if (polledOperation.batchNumber > maxBatchNumber) {
|
||||
// Because the operation is already retrieved from the queue, there's no way of placing it
|
||||
// back as the head element, so we remember it manually here
|
||||
peekedOperation = polledOperation
|
||||
this.peekedOperation = polledOperation
|
||||
break
|
||||
}
|
||||
operations.add(polledOperation)
|
||||
@@ -189,8 +190,7 @@ public class NativeAnimatedModule(reactContext: ReactApplicationContext?) :
|
||||
}
|
||||
}
|
||||
|
||||
private val animatedFrameCallback: GuardedFrameCallback
|
||||
private val reactChoreographer: ReactChoreographer? = ReactChoreographer.getInstance()
|
||||
private val reactChoreographer: ReactChoreographer = ReactChoreographer.getInstance()
|
||||
|
||||
private val operations = ConcurrentOperationQueue()
|
||||
private val preOperations = ConcurrentOperationQueue()
|
||||
@@ -205,7 +205,6 @@ public class NativeAnimatedModule(reactContext: ReactApplicationContext?) :
|
||||
|
||||
private var initializedForFabric = false
|
||||
private var initializedForNonFabric = false
|
||||
private var enqueuedAnimationOnFrame = false
|
||||
|
||||
@UIManagerType private var uiManagerType = UIManagerType.LEGACY
|
||||
private var numFabricAnimations = 0
|
||||
@@ -302,8 +301,8 @@ public class NativeAnimatedModule(reactContext: ReactApplicationContext?) :
|
||||
}
|
||||
}
|
||||
|
||||
checkNotNull(preOperations).executeBatch(batchNumber, nodesManager)
|
||||
checkNotNull(operations).executeBatch(batchNumber, nodesManager)
|
||||
preOperations.executeBatch(batchNumber, nodesManager)
|
||||
operations.executeBatch(batchNumber, nodesManager)
|
||||
}
|
||||
|
||||
// For non-FabricUIManager only
|
||||
@@ -322,11 +321,9 @@ public class NativeAnimatedModule(reactContext: ReactApplicationContext?) :
|
||||
// might be stripped out.
|
||||
val frameNo = currentBatchNumber++
|
||||
|
||||
val preOperationsUIBlock = UIBlock {
|
||||
checkNotNull(preOperations).executeBatch(frameNo, nodesManager)
|
||||
}
|
||||
val preOperationsUIBlock = UIBlock { preOperations.executeBatch(frameNo, nodesManager) }
|
||||
|
||||
val operationsUIBlock = UIBlock { checkNotNull(operations).executeBatch(frameNo, nodesManager) }
|
||||
val operationsUIBlock = UIBlock { operations.executeBatch(frameNo, nodesManager) }
|
||||
|
||||
assert(uiManager is UIManagerModule)
|
||||
val uiManagerModule = uiManager as UIManagerModule
|
||||
@@ -366,41 +363,34 @@ public class NativeAnimatedModule(reactContext: ReactApplicationContext?) :
|
||||
nodesManagerRef.set(nodesManager)
|
||||
}
|
||||
|
||||
init {
|
||||
animatedFrameCallback =
|
||||
object : GuardedFrameCallback(checkNotNull(reactContext)) {
|
||||
override fun doFrameGuarded(frameTimeNanos: Long) {
|
||||
try {
|
||||
enqueuedAnimationOnFrame = false
|
||||
val nodesManager = nodesManager
|
||||
if (nodesManager?.hasActiveAnimations() == true) {
|
||||
nodesManager.runUpdates(frameTimeNanos)
|
||||
}
|
||||
// This is very unlikely to ever be hit.
|
||||
if (nodesManager == null || reactChoreographer == null) {
|
||||
return
|
||||
}
|
||||
|
||||
enqueueFrameCallback()
|
||||
} catch (ex: Exception) {
|
||||
throw RuntimeException(ex)
|
||||
private var enqueuedAnimationOnFrame = false
|
||||
private val animatedFrameCallback =
|
||||
object : GuardedFrameCallback(reactContext) {
|
||||
override fun doFrameGuarded(frameTimeNanos: Long) {
|
||||
try {
|
||||
enqueuedAnimationOnFrame = false
|
||||
val nodesManager = nodesManager ?: return
|
||||
if (nodesManager.hasActiveAnimations()) {
|
||||
nodesManager.runUpdates(frameTimeNanos)
|
||||
}
|
||||
|
||||
enqueueFrameCallback()
|
||||
} catch (ex: Exception) {
|
||||
throw RuntimeException(ex)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private fun clearFrameCallback() {
|
||||
checkNotNull(reactChoreographer)
|
||||
.removeFrameCallback(
|
||||
ReactChoreographer.CallbackType.NATIVE_ANIMATED_MODULE, animatedFrameCallback)
|
||||
reactChoreographer.removeFrameCallback(
|
||||
ReactChoreographer.CallbackType.NATIVE_ANIMATED_MODULE, animatedFrameCallback)
|
||||
enqueuedAnimationOnFrame = false
|
||||
}
|
||||
|
||||
private fun enqueueFrameCallback() {
|
||||
if (!enqueuedAnimationOnFrame) {
|
||||
checkNotNull(reactChoreographer)
|
||||
.postFrameCallback(
|
||||
ReactChoreographer.CallbackType.NATIVE_ANIMATED_MODULE, animatedFrameCallback)
|
||||
reactChoreographer.postFrameCallback(
|
||||
ReactChoreographer.CallbackType.NATIVE_ANIMATED_MODULE, animatedFrameCallback)
|
||||
enqueuedAnimationOnFrame = true
|
||||
}
|
||||
}
|
||||
@@ -431,8 +421,9 @@ public class NativeAnimatedModule(reactContext: ReactApplicationContext?) :
|
||||
}
|
||||
|
||||
// Subscribe to UIManager (Fabric or non-Fabric) lifecycle events if we haven't yet
|
||||
if (if (uiManagerType == UIManagerType.FABRIC) initializedForFabric
|
||||
else initializedForNonFabric) {
|
||||
val initialized =
|
||||
if (uiManagerType == UIManagerType.FABRIC) initializedForFabric else initializedForNonFabric
|
||||
if (initialized) {
|
||||
return
|
||||
}
|
||||
|
||||
@@ -494,16 +485,14 @@ public class NativeAnimatedModule(reactContext: ReactApplicationContext?) :
|
||||
override fun createAnimatedNode(tagDouble: Double, config: ReadableMap) {
|
||||
val tag = tagDouble.toInt()
|
||||
if (ANIMATED_MODULE_DEBUG) {
|
||||
FLog.d(NAME, "queue createAnimatedNode: ${tag} config: ${config.toHashMap().toString()}")
|
||||
FLog.d(NAME, "queue createAnimatedNode: $tag config: ${config.toHashMap()}")
|
||||
}
|
||||
|
||||
addOperation(
|
||||
object : UIThreadOperation() {
|
||||
override fun execute(animatedNodesManager: NativeAnimatedNodesManager) {
|
||||
if (ANIMATED_MODULE_DEBUG) {
|
||||
FLog.d(
|
||||
NAME,
|
||||
("execute createAnimatedNode: ${tag} config: ${config.toHashMap().toString()}"))
|
||||
FLog.d(NAME, ("execute createAnimatedNode: $tag config: ${config.toHashMap()}"))
|
||||
}
|
||||
animatedNodesManager.createAnimatedNode(tag, config)
|
||||
}
|
||||
@@ -513,17 +502,14 @@ public class NativeAnimatedModule(reactContext: ReactApplicationContext?) :
|
||||
override fun updateAnimatedNodeConfig(tagDouble: Double, config: ReadableMap) {
|
||||
val tag = tagDouble.toInt()
|
||||
if (ANIMATED_MODULE_DEBUG) {
|
||||
FLog.d(
|
||||
NAME, "queue updateAnimatedNodeConfig: ${tag} config: ${config.toHashMap().toString()}")
|
||||
FLog.d(NAME, "queue updateAnimatedNodeConfig: $tag config: ${config.toHashMap()}")
|
||||
}
|
||||
|
||||
addOperation(
|
||||
object : UIThreadOperation() {
|
||||
override fun execute(animatedNodesManager: NativeAnimatedNodesManager) {
|
||||
if (ANIMATED_MODULE_DEBUG) {
|
||||
FLog.d(
|
||||
NAME,
|
||||
("execute updateAnimatedNodeConfig: ${tag} config: ${config.toHashMap().toString()}"))
|
||||
FLog.d(NAME, ("execute updateAnimatedNodeConfig: $tag config: ${config.toHashMap()}"))
|
||||
}
|
||||
animatedNodesManager.updateAnimatedNodeConfig(tag, config)
|
||||
}
|
||||
@@ -714,7 +700,7 @@ public class NativeAnimatedModule(reactContext: ReactApplicationContext?) :
|
||||
if (ANIMATED_MODULE_DEBUG) {
|
||||
FLog.d(
|
||||
NAME,
|
||||
("execute connectAnimatedNodes: parent: ${parentNodeTag} child: ${childNodeTag}"))
|
||||
("execute connectAnimatedNodes: parent: $parentNodeTag child: $childNodeTag"))
|
||||
}
|
||||
animatedNodesManager.connectAnimatedNodes(parentNodeTag, childNodeTag)
|
||||
}
|
||||
@@ -734,7 +720,7 @@ public class NativeAnimatedModule(reactContext: ReactApplicationContext?) :
|
||||
if (ANIMATED_MODULE_DEBUG) {
|
||||
FLog.d(
|
||||
NAME,
|
||||
("execute disconnectAnimatedNodes: parent: ${parentNodeTag} child: ${childNodeTag}"))
|
||||
("execute disconnectAnimatedNodes: parent: $parentNodeTag child: $childNodeTag"))
|
||||
}
|
||||
animatedNodesManager.disconnectAnimatedNodes(parentNodeTag, childNodeTag)
|
||||
}
|
||||
@@ -747,7 +733,7 @@ public class NativeAnimatedModule(reactContext: ReactApplicationContext?) :
|
||||
if (ANIMATED_MODULE_DEBUG) {
|
||||
FLog.d(
|
||||
NAME,
|
||||
("queue connectAnimatedNodeToView: animatedNodeTag: ${animatedNodeTag} viewTag: ${viewTag}"))
|
||||
("queue connectAnimatedNodeToView: animatedNodeTag: $animatedNodeTag viewTag: $viewTag"))
|
||||
}
|
||||
|
||||
initializeLifecycleEventListenersForViewTag(viewTag)
|
||||
@@ -758,7 +744,7 @@ public class NativeAnimatedModule(reactContext: ReactApplicationContext?) :
|
||||
if (ANIMATED_MODULE_DEBUG) {
|
||||
FLog.d(
|
||||
NAME,
|
||||
("execute connectAnimatedNodeToView: animatedNodeTag: ${animatedNodeTag} viewTag: ${viewTag}"))
|
||||
("execute connectAnimatedNodeToView: animatedNodeTag: $animatedNodeTag viewTag: $viewTag"))
|
||||
}
|
||||
animatedNodesManager.connectAnimatedNodeToView(animatedNodeTag, viewTag)
|
||||
}
|
||||
@@ -783,7 +769,7 @@ public class NativeAnimatedModule(reactContext: ReactApplicationContext?) :
|
||||
if (ANIMATED_MODULE_DEBUG) {
|
||||
FLog.d(
|
||||
NAME,
|
||||
("execute disconnectAnimatedNodeFromView: ${animatedNodeTag} viewTag: ${viewTag}"))
|
||||
("execute disconnectAnimatedNodeFromView: $animatedNodeTag viewTag: $viewTag"))
|
||||
}
|
||||
animatedNodesManager.disconnectAnimatedNodeFromView(animatedNodeTag, viewTag)
|
||||
}
|
||||
@@ -816,7 +802,7 @@ public class NativeAnimatedModule(reactContext: ReactApplicationContext?) :
|
||||
if (ANIMATED_MODULE_DEBUG) {
|
||||
FLog.d(
|
||||
NAME,
|
||||
("queue addAnimatedEventToView: ${viewTag} eventName: ${eventName} eventMapping: ${eventMapping.toHashMap().toString()}"))
|
||||
("queue addAnimatedEventToView: $viewTag eventName: $eventName eventMapping: ${eventMapping.toHashMap()}"))
|
||||
}
|
||||
|
||||
initializeLifecycleEventListenersForViewTag(viewTag)
|
||||
@@ -827,7 +813,7 @@ public class NativeAnimatedModule(reactContext: ReactApplicationContext?) :
|
||||
if (ANIMATED_MODULE_DEBUG) {
|
||||
FLog.d(
|
||||
NAME,
|
||||
("execute addAnimatedEventToView: ${viewTag} eventName: ${eventName} eventMapping: ${eventMapping.toHashMap().toString()}"))
|
||||
("execute addAnimatedEventToView: $viewTag eventName: $eventName eventMapping: ${eventMapping.toHashMap()}"))
|
||||
}
|
||||
animatedNodesManager.addAnimatedEventToView(viewTag, eventName, eventMapping)
|
||||
}
|
||||
@@ -844,7 +830,7 @@ public class NativeAnimatedModule(reactContext: ReactApplicationContext?) :
|
||||
if (ANIMATED_MODULE_DEBUG) {
|
||||
FLog.d(
|
||||
NAME,
|
||||
("queue removeAnimatedEventFromView: viewTag: ${viewTag} eventName: ${eventName} animatedValueTag: ${animatedValueTag}"))
|
||||
("queue removeAnimatedEventFromView: viewTag: $viewTag eventName: $eventName animatedValueTag: $animatedValueTag"))
|
||||
}
|
||||
|
||||
decrementInFlightAnimationsForViewTag(viewTag)
|
||||
@@ -855,7 +841,7 @@ public class NativeAnimatedModule(reactContext: ReactApplicationContext?) :
|
||||
if (ANIMATED_MODULE_DEBUG) {
|
||||
FLog.d(
|
||||
NAME,
|
||||
("execute removeAnimatedEventFromView: viewTag: ${viewTag} eventName: ${eventName} animatedValueTag: ${animatedValueTag}"))
|
||||
("execute removeAnimatedEventFromView: viewTag: $viewTag eventName: $eventName animatedValueTag: $animatedValueTag"))
|
||||
}
|
||||
animatedNodesManager.removeAnimatedEventFromView(viewTag, eventName, animatedValueTag)
|
||||
}
|
||||
|
||||
+3
-3
@@ -381,7 +381,7 @@ public class NativeAnimatedNodesManager(
|
||||
("connectAnimatedNodeToView: Animated node connected to view [${viewTag}] should be of type ${PropsAnimatedNode::class.java.name}"))
|
||||
}
|
||||
checkNotNull(reactApplicationContext) {
|
||||
("connectAnimatedNodeToView: Animated node could not be connected, no ReactApplicationContext: ${viewTag}")
|
||||
("connectAnimatedNodeToView: Animated node could not be connected, no ReactApplicationContext: $viewTag")
|
||||
}
|
||||
|
||||
val uiManager = UIManagerHelper.getUIManagerForReactTag(reactApplicationContext, viewTag)
|
||||
@@ -389,7 +389,7 @@ public class NativeAnimatedNodesManager(
|
||||
ReactSoftExceptionLogger.logSoftException(
|
||||
TAG,
|
||||
ReactNoCrashSoftException(
|
||||
("connectAnimatedNodeToView: Animated node could not be connected to UIManager - uiManager disappeared for tag: ${viewTag}")))
|
||||
("connectAnimatedNodeToView: Animated node could not be connected to UIManager - uiManager disappeared for tag: $viewTag")))
|
||||
return
|
||||
}
|
||||
|
||||
@@ -751,7 +751,7 @@ public class NativeAnimatedNodesManager(
|
||||
val reason = if (cyclesDetected > 0) ("cycles ($cyclesDetected)") else "disconnected regions"
|
||||
val ex =
|
||||
IllegalStateException(
|
||||
("Looks like animated nodes graph has ${reason}, there are ${activeNodesCount} but toposort visited only ${updatedNodesCount}"))
|
||||
("Looks like animated nodes graph has ${reason}, there are $activeNodesCount but toposort visited only $updatedNodesCount"))
|
||||
if (eventListenerInitializedForFabric && cyclesDetected == 0) {
|
||||
// TODO T71377544: investigate these SoftExceptions and see if we can remove entirely
|
||||
// or fix the root cause
|
||||
|
||||
+2
-2
@@ -18,12 +18,12 @@ public open class BaseActivityEventListener : ActivityEventListener {
|
||||
ReplaceWith("onActivityResult(activity, requestCode, resultCode, data)"))
|
||||
public open fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent): Unit = Unit
|
||||
|
||||
override public fun onActivityResult(
|
||||
public override fun onActivityResult(
|
||||
activity: Activity,
|
||||
requestCode: Int,
|
||||
resultCode: Int,
|
||||
data: Intent?
|
||||
): Unit = Unit
|
||||
|
||||
override public fun onNewIntent(intent: Intent): Unit = Unit
|
||||
public override fun onNewIntent(intent: Intent): Unit = Unit
|
||||
}
|
||||
|
||||
+1
-1
@@ -25,7 +25,7 @@ protected constructor(private val exceptionHandler: JSExceptionHandler) :
|
||||
protected constructor(reactContext: ReactContext) : this(reactContext.exceptionHandler)
|
||||
|
||||
@Deprecated("AsyncTask is deprecated.")
|
||||
override protected final fun doInBackground(vararg params: Params): Void? {
|
||||
protected final override fun doInBackground(vararg params: Params): Void? {
|
||||
try {
|
||||
doInBackgroundGuarded(*params)
|
||||
} catch (e: RuntimeException) {
|
||||
|
||||
+8
-9
@@ -134,15 +134,14 @@ public class JavaOnlyArray : ReadableArray, WritableArray {
|
||||
|
||||
override fun toString(): String = backingList.toString()
|
||||
|
||||
override fun equals(other: Any?): Boolean {
|
||||
if (this === other) {
|
||||
return true
|
||||
} else if (other == null || javaClass != other.javaClass) {
|
||||
return false
|
||||
} else {
|
||||
return backingList == (other as JavaOnlyArray).backingList
|
||||
}
|
||||
}
|
||||
override fun equals(other: Any?): Boolean =
|
||||
if (this === other) {
|
||||
true
|
||||
} else if (other == null || javaClass != other.javaClass) {
|
||||
false
|
||||
} else {
|
||||
backingList == (other as JavaOnlyArray).backingList
|
||||
}
|
||||
|
||||
override fun hashCode(): Int = backingList.hashCode()
|
||||
}
|
||||
|
||||
-25
@@ -1,25 +0,0 @@
|
||||
/*
|
||||
* Copyright (c) Meta Platforms, Inc. and affiliates.
|
||||
*
|
||||
* This source code is licensed under the MIT license found in the
|
||||
* LICENSE file in the root directory of this source tree.
|
||||
*/
|
||||
|
||||
package com.facebook.react.bridge;
|
||||
|
||||
import android.content.Context;
|
||||
import com.facebook.infer.annotation.Nullsafe;
|
||||
|
||||
/**
|
||||
* A context wrapper that always wraps Android Application {@link Context} and {@link
|
||||
* CatalystInstance} by extending {@link ReactContext}
|
||||
*/
|
||||
@Nullsafe(Nullsafe.Mode.LOCAL)
|
||||
public abstract class ReactApplicationContext extends ReactContext {
|
||||
// We want to wrap ApplicationContext, since there is no easy way to verify that application
|
||||
// context is passed as a param, we use {@link Context#getApplicationContext} to ensure that
|
||||
// the context we're wrapping is in fact an application context.
|
||||
public ReactApplicationContext(Context context) {
|
||||
super(context.getApplicationContext());
|
||||
}
|
||||
}
|
||||
+20
@@ -0,0 +1,20 @@
|
||||
/*
|
||||
* Copyright (c) Meta Platforms, Inc. and affiliates.
|
||||
*
|
||||
* This source code is licensed under the MIT license found in the
|
||||
* LICENSE file in the root directory of this source tree.
|
||||
*/
|
||||
|
||||
package com.facebook.react.bridge
|
||||
|
||||
import android.content.Context
|
||||
|
||||
/**
|
||||
* A context wrapper that always wraps Android Application [Context] and [CatalystInstance] by
|
||||
* extending [ReactContext].
|
||||
*/
|
||||
public abstract class ReactApplicationContext(context: Context) :
|
||||
// We want to wrap ApplicationContext, since there is no easy way to verify that application
|
||||
// context is passed as a param, we use [Context.getApplicationContext] to ensure that
|
||||
// the context we're wrapping is in fact an application context.
|
||||
ReactContext(context.applicationContext)
|
||||
+3
-3
@@ -79,10 +79,10 @@ public open class ReadableNativeMap protected constructor() : NativeMap(), Reada
|
||||
|
||||
private inline fun <reified T> getNullableValue(name: String, type: Class<T>): T? {
|
||||
val res = getNullableValue(name)
|
||||
if (res == null) {
|
||||
return null
|
||||
return if (res == null) {
|
||||
null
|
||||
} else {
|
||||
return checkInstance(name, res, type)
|
||||
checkInstance(name, res, type)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
+2
-1
@@ -12,6 +12,7 @@ import android.hardware.SensorEvent
|
||||
import android.hardware.SensorEventListener
|
||||
import android.hardware.SensorManager
|
||||
import java.util.concurrent.TimeUnit
|
||||
import kotlin.math.abs
|
||||
|
||||
/** Listens for the user shaking their phone. Allocation-less once it starts listening. */
|
||||
public class ShakeDetector
|
||||
@@ -63,7 +64,7 @@ constructor(private val shakeListener: ShakeListener, private val minNumShakes:
|
||||
* @return true if the magnitude of the force exceeds the minimum required amount of force. false
|
||||
* otherwise.
|
||||
*/
|
||||
private fun atLeastRequiredForce(a: Float): Boolean = Math.abs(a) > REQUIRED_FORCE
|
||||
private fun atLeastRequiredForce(a: Float): Boolean = abs(a) > REQUIRED_FORCE
|
||||
|
||||
/**
|
||||
* Save data about last shake
|
||||
|
||||
+1
-3
@@ -465,9 +465,7 @@ public abstract class DevSupportManagerBase(
|
||||
devOptionsDialog?.show()
|
||||
|
||||
val reactContext = currentReactContext
|
||||
if (reactContext != null) {
|
||||
reactContext.getJSModule(RCTNativeAppEventEmitter::class.java).emit("RCTDevMenuShown", null)
|
||||
}
|
||||
reactContext?.getJSModule(RCTNativeAppEventEmitter::class.java)?.emit("RCTDevMenuShown", null)
|
||||
}
|
||||
|
||||
override fun onNewReactContextCreated(reactContext: ReactContext) {
|
||||
|
||||
+1
-1
@@ -76,7 +76,7 @@ internal class PackagerStatusCheck {
|
||||
if (PACKAGER_OK_STATUS != bodyString) {
|
||||
FLog.e(
|
||||
ReactConstants.TAG,
|
||||
"Got unexpected response from packager when requesting status: ${bodyString}")
|
||||
"Got unexpected response from packager when requesting status: $bodyString")
|
||||
callback.onPackagerStatusFetched(false)
|
||||
return
|
||||
}
|
||||
|
||||
+6
-5
@@ -37,11 +37,12 @@ internal class LongStreamingStats {
|
||||
}
|
||||
|
||||
len++
|
||||
if (len == 1) {
|
||||
average = n.toDouble()
|
||||
} else {
|
||||
average = (average / (len / (len - 1))) + (n / len)
|
||||
}
|
||||
average =
|
||||
if (len == 1) {
|
||||
n.toDouble()
|
||||
} else {
|
||||
(average / (len / (len - 1))) + (n / len)
|
||||
}
|
||||
|
||||
max = (if (n > max) n else max)
|
||||
}
|
||||
|
||||
+49
-50
@@ -21,6 +21,7 @@ import androidx.collection.SparseArrayCompat;
|
||||
import com.facebook.common.logging.FLog;
|
||||
import com.facebook.infer.annotation.Assertions;
|
||||
import com.facebook.infer.annotation.ThreadConfined;
|
||||
import com.facebook.react.bridge.GuardedRunnable;
|
||||
import com.facebook.react.bridge.ReactNoCrashSoftException;
|
||||
import com.facebook.react.bridge.ReactSoftExceptionLogger;
|
||||
import com.facebook.react.bridge.ReadableArray;
|
||||
@@ -189,57 +190,55 @@ public class SurfaceMountingManager {
|
||||
mTagToViewState.put(mSurfaceId, new ViewState(mSurfaceId, rootView, mRootViewManager, true));
|
||||
|
||||
Runnable runnable =
|
||||
() -> {
|
||||
// The CPU has ticked since `addRootView` was called, so the surface could technically
|
||||
// have already stopped here.
|
||||
if (isStopped()) {
|
||||
return;
|
||||
new GuardedRunnable(Assertions.assertNotNull(mThemedReactContext)) {
|
||||
@Override
|
||||
public void runGuarded() {
|
||||
// The CPU has ticked since `addRootView` was called, so the surface could technically
|
||||
// have already stopped here.
|
||||
if (isStopped()) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (rootView.getId() == mSurfaceId) {
|
||||
ReactSoftExceptionLogger.logSoftException(
|
||||
TAG,
|
||||
new IllegalViewOperationException(
|
||||
"Race condition in addRootView detected. Trying to set an id of ["
|
||||
+ mSurfaceId
|
||||
+ "] on the RootView, but that id has already been set. "));
|
||||
} else if (rootView.getId() != View.NO_ID) {
|
||||
FLog.e(
|
||||
TAG,
|
||||
"Trying to add RootTag to RootView that already has a tag: existing tag: [%d] new"
|
||||
+ " tag: [%d]",
|
||||
rootView.getId(),
|
||||
mSurfaceId);
|
||||
// This behavior can not be guaranteed in hybrid apps that have a native android layer
|
||||
// over which reactRootViews are added and the native views need to have ids on them
|
||||
// in order to work. Hence this can cause unnecessary crashes at runtime for hybrid
|
||||
// apps. So converting this to a soft exception such that pure react-native devs can
|
||||
// still see the warning while hybrid apps continue to run without crashes
|
||||
ReactSoftExceptionLogger.logSoftException(
|
||||
TAG,
|
||||
new IllegalViewOperationException(
|
||||
"Trying to add a root view with an explicit id already set. React Native uses"
|
||||
+ " the id field to track react tags and will overwrite this field. If"
|
||||
+ " that is fine, explicitly overwrite the id field to View.NO_ID before"
|
||||
+ " calling addRootView."));
|
||||
}
|
||||
rootView.setId(mSurfaceId);
|
||||
|
||||
if (rootView instanceof ReactRoot) {
|
||||
((ReactRoot) rootView).setRootViewTag(mSurfaceId);
|
||||
}
|
||||
|
||||
executeMountItemsOnViewAttach();
|
||||
|
||||
// By doing this after `executeMountItemsOnViewAttach`, we ensure that any operations
|
||||
// scheduled while processing this queue are also added to the queue, instead of being
|
||||
// processed immediately through the queue in `MountItemDispatcher`.
|
||||
mRootViewAttached = true;
|
||||
}
|
||||
|
||||
if (rootView.getId() == mSurfaceId) {
|
||||
ReactSoftExceptionLogger.logSoftException(
|
||||
TAG,
|
||||
new IllegalViewOperationException(
|
||||
"Race condition in addRootView detected. Trying to set an id of ["
|
||||
+ mSurfaceId
|
||||
+ "] on the RootView, but that id has already been set. "));
|
||||
} else if (rootView.getId() != View.NO_ID) {
|
||||
FLog.e(
|
||||
TAG,
|
||||
"Trying to add RootTag to RootView that already has a tag: existing tag: [%d] new"
|
||||
+ " tag: [%d]",
|
||||
rootView.getId(),
|
||||
mSurfaceId);
|
||||
// This behavior can not be guaranteed in hybrid apps that have a native android layer
|
||||
// over
|
||||
// which reactRootViews are added and the native views need to have ids on them in order
|
||||
// to
|
||||
// work.
|
||||
// Hence this can cause unnecessary crashes at runtime for hybrid apps.
|
||||
// So converting this to a soft exception such that pure react-native devs can still see
|
||||
// the
|
||||
// warning while hybrid apps continue to run without crashes
|
||||
ReactSoftExceptionLogger.logSoftException(
|
||||
TAG,
|
||||
new IllegalViewOperationException(
|
||||
"Trying to add a root view with an explicit id already set. React Native uses"
|
||||
+ " the id field to track react tags and will overwrite this field. If that"
|
||||
+ " is fine, explicitly overwrite the id field to View.NO_ID before calling"
|
||||
+ " addRootView."));
|
||||
}
|
||||
rootView.setId(mSurfaceId);
|
||||
|
||||
if (rootView instanceof ReactRoot) {
|
||||
((ReactRoot) rootView).setRootViewTag(mSurfaceId);
|
||||
}
|
||||
|
||||
executeMountItemsOnViewAttach();
|
||||
|
||||
// By doing this after `executeMountItemsOnViewAttach`, we ensure
|
||||
// that any operations scheduled while processing this queue are
|
||||
// also added to the queue, instead of being processed immediately
|
||||
// through the queue in `MountItemDispatcher`.
|
||||
mRootViewAttached = true;
|
||||
};
|
||||
|
||||
if (UiThreadUtil.isOnUiThread()) {
|
||||
|
||||
+13
-1
@@ -4,7 +4,7 @@
|
||||
* This source code is licensed under the MIT license found in the
|
||||
* LICENSE file in the root directory of this source tree.
|
||||
*
|
||||
* @generated SignedSource<<dee97293bfeab942c9cd0ba8622a5f86>>
|
||||
* @generated SignedSource<<442cbf571b5654c5d322ca1b5542db7d>>
|
||||
*/
|
||||
|
||||
/**
|
||||
@@ -258,6 +258,18 @@ public object ReactNativeFeatureFlags {
|
||||
@JvmStatic
|
||||
public fun enableVirtualViewDebugFeatures(): Boolean = accessor.enableVirtualViewDebugFeatures()
|
||||
|
||||
/**
|
||||
* Enables reading render state when dispatching VirtualView events.
|
||||
*/
|
||||
@JvmStatic
|
||||
public fun enableVirtualViewRenderState(): Boolean = accessor.enableVirtualViewRenderState()
|
||||
|
||||
/**
|
||||
* Enables window focus detection for prioritizing VirtualView events.
|
||||
*/
|
||||
@JvmStatic
|
||||
public fun enableVirtualViewWindowFocusDetection(): Boolean = accessor.enableVirtualViewWindowFocusDetection()
|
||||
|
||||
/**
|
||||
* Uses the default event priority instead of the discreet event priority by default when dispatching events from Fabric to React.
|
||||
*/
|
||||
|
||||
+21
-1
@@ -4,7 +4,7 @@
|
||||
* This source code is licensed under the MIT license found in the
|
||||
* LICENSE file in the root directory of this source tree.
|
||||
*
|
||||
* @generated SignedSource<<c46464d2d10ac0c8a6b7869ae5b3cd2b>>
|
||||
* @generated SignedSource<<166a7cc18f83861c6c4d7f96a55c5843>>
|
||||
*/
|
||||
|
||||
/**
|
||||
@@ -58,6 +58,8 @@ internal class ReactNativeFeatureFlagsCxxAccessor : ReactNativeFeatureFlagsAcces
|
||||
private var enableViewRecyclingForTextCache: Boolean? = null
|
||||
private var enableViewRecyclingForViewCache: Boolean? = null
|
||||
private var enableVirtualViewDebugFeaturesCache: Boolean? = null
|
||||
private var enableVirtualViewRenderStateCache: Boolean? = null
|
||||
private var enableVirtualViewWindowFocusDetectionCache: Boolean? = null
|
||||
private var fixMappingOfEventPrioritiesBetweenFabricAndReactCache: Boolean? = null
|
||||
private var fuseboxEnabledReleaseCache: Boolean? = null
|
||||
private var fuseboxNetworkInspectionEnabledCache: Boolean? = null
|
||||
@@ -415,6 +417,24 @@ internal class ReactNativeFeatureFlagsCxxAccessor : ReactNativeFeatureFlagsAcces
|
||||
return cached
|
||||
}
|
||||
|
||||
override fun enableVirtualViewRenderState(): Boolean {
|
||||
var cached = enableVirtualViewRenderStateCache
|
||||
if (cached == null) {
|
||||
cached = ReactNativeFeatureFlagsCxxInterop.enableVirtualViewRenderState()
|
||||
enableVirtualViewRenderStateCache = cached
|
||||
}
|
||||
return cached
|
||||
}
|
||||
|
||||
override fun enableVirtualViewWindowFocusDetection(): Boolean {
|
||||
var cached = enableVirtualViewWindowFocusDetectionCache
|
||||
if (cached == null) {
|
||||
cached = ReactNativeFeatureFlagsCxxInterop.enableVirtualViewWindowFocusDetection()
|
||||
enableVirtualViewWindowFocusDetectionCache = cached
|
||||
}
|
||||
return cached
|
||||
}
|
||||
|
||||
override fun fixMappingOfEventPrioritiesBetweenFabricAndReact(): Boolean {
|
||||
var cached = fixMappingOfEventPrioritiesBetweenFabricAndReactCache
|
||||
if (cached == null) {
|
||||
|
||||
+5
-1
@@ -4,7 +4,7 @@
|
||||
* This source code is licensed under the MIT license found in the
|
||||
* LICENSE file in the root directory of this source tree.
|
||||
*
|
||||
* @generated SignedSource<<62c548a9bfbf777a40b1b9e9d52b1de2>>
|
||||
* @generated SignedSource<<27e8fa8139901c1decaba5bfcbced221>>
|
||||
*/
|
||||
|
||||
/**
|
||||
@@ -104,6 +104,10 @@ public object ReactNativeFeatureFlagsCxxInterop {
|
||||
|
||||
@DoNotStrip @JvmStatic public external fun enableVirtualViewDebugFeatures(): Boolean
|
||||
|
||||
@DoNotStrip @JvmStatic public external fun enableVirtualViewRenderState(): Boolean
|
||||
|
||||
@DoNotStrip @JvmStatic public external fun enableVirtualViewWindowFocusDetection(): Boolean
|
||||
|
||||
@DoNotStrip @JvmStatic public external fun fixMappingOfEventPrioritiesBetweenFabricAndReact(): Boolean
|
||||
|
||||
@DoNotStrip @JvmStatic public external fun fuseboxEnabledRelease(): Boolean
|
||||
|
||||
+5
-1
@@ -4,7 +4,7 @@
|
||||
* This source code is licensed under the MIT license found in the
|
||||
* LICENSE file in the root directory of this source tree.
|
||||
*
|
||||
* @generated SignedSource<<de8775978e15479830fb215c6f15b144>>
|
||||
* @generated SignedSource<<5efae3bf30e8acf69f0682372c39f7b2>>
|
||||
*/
|
||||
|
||||
/**
|
||||
@@ -99,6 +99,10 @@ public open class ReactNativeFeatureFlagsDefaults : ReactNativeFeatureFlagsProvi
|
||||
|
||||
override fun enableVirtualViewDebugFeatures(): Boolean = false
|
||||
|
||||
override fun enableVirtualViewRenderState(): Boolean = false
|
||||
|
||||
override fun enableVirtualViewWindowFocusDetection(): Boolean = false
|
||||
|
||||
override fun fixMappingOfEventPrioritiesBetweenFabricAndReact(): Boolean = false
|
||||
|
||||
override fun fuseboxEnabledRelease(): Boolean = false
|
||||
|
||||
+23
-1
@@ -4,7 +4,7 @@
|
||||
* This source code is licensed under the MIT license found in the
|
||||
* LICENSE file in the root directory of this source tree.
|
||||
*
|
||||
* @generated SignedSource<<220b0cff47d2eadddf8a36646852d619>>
|
||||
* @generated SignedSource<<498e9a51a9a0d0c0c4eb69c84bb33dd1>>
|
||||
*/
|
||||
|
||||
/**
|
||||
@@ -62,6 +62,8 @@ internal class ReactNativeFeatureFlagsLocalAccessor : ReactNativeFeatureFlagsAcc
|
||||
private var enableViewRecyclingForTextCache: Boolean? = null
|
||||
private var enableViewRecyclingForViewCache: Boolean? = null
|
||||
private var enableVirtualViewDebugFeaturesCache: Boolean? = null
|
||||
private var enableVirtualViewRenderStateCache: Boolean? = null
|
||||
private var enableVirtualViewWindowFocusDetectionCache: Boolean? = null
|
||||
private var fixMappingOfEventPrioritiesBetweenFabricAndReactCache: Boolean? = null
|
||||
private var fuseboxEnabledReleaseCache: Boolean? = null
|
||||
private var fuseboxNetworkInspectionEnabledCache: Boolean? = null
|
||||
@@ -457,6 +459,26 @@ internal class ReactNativeFeatureFlagsLocalAccessor : ReactNativeFeatureFlagsAcc
|
||||
return cached
|
||||
}
|
||||
|
||||
override fun enableVirtualViewRenderState(): Boolean {
|
||||
var cached = enableVirtualViewRenderStateCache
|
||||
if (cached == null) {
|
||||
cached = currentProvider.enableVirtualViewRenderState()
|
||||
accessedFeatureFlags.add("enableVirtualViewRenderState")
|
||||
enableVirtualViewRenderStateCache = cached
|
||||
}
|
||||
return cached
|
||||
}
|
||||
|
||||
override fun enableVirtualViewWindowFocusDetection(): Boolean {
|
||||
var cached = enableVirtualViewWindowFocusDetectionCache
|
||||
if (cached == null) {
|
||||
cached = currentProvider.enableVirtualViewWindowFocusDetection()
|
||||
accessedFeatureFlags.add("enableVirtualViewWindowFocusDetection")
|
||||
enableVirtualViewWindowFocusDetectionCache = cached
|
||||
}
|
||||
return cached
|
||||
}
|
||||
|
||||
override fun fixMappingOfEventPrioritiesBetweenFabricAndReact(): Boolean {
|
||||
var cached = fixMappingOfEventPrioritiesBetweenFabricAndReactCache
|
||||
if (cached == null) {
|
||||
|
||||
+5
-1
@@ -4,7 +4,7 @@
|
||||
* This source code is licensed under the MIT license found in the
|
||||
* LICENSE file in the root directory of this source tree.
|
||||
*
|
||||
* @generated SignedSource<<d2ab95a5f7bf0dfc52428a90bee2fc10>>
|
||||
* @generated SignedSource<<fce6841e89beec5be32b76fc0941ef95>>
|
||||
*/
|
||||
|
||||
/**
|
||||
@@ -99,6 +99,10 @@ public interface ReactNativeFeatureFlagsProvider {
|
||||
|
||||
@DoNotStrip public fun enableVirtualViewDebugFeatures(): Boolean
|
||||
|
||||
@DoNotStrip public fun enableVirtualViewRenderState(): Boolean
|
||||
|
||||
@DoNotStrip public fun enableVirtualViewWindowFocusDetection(): Boolean
|
||||
|
||||
@DoNotStrip public fun fixMappingOfEventPrioritiesBetweenFabricAndReact(): Boolean
|
||||
|
||||
@DoNotStrip public fun fuseboxEnabledRelease(): Boolean
|
||||
|
||||
+18
-27
@@ -121,14 +121,13 @@ internal class AccessibilityInfoModule(context: ReactApplicationContext) :
|
||||
}
|
||||
|
||||
private val isInvertColorsEnabledValue: Boolean
|
||||
get() {
|
||||
try {
|
||||
return Settings.Secure.getInt(
|
||||
contentResolver, Settings.Secure.ACCESSIBILITY_DISPLAY_INVERSION_ENABLED) == 1
|
||||
} catch (e: Settings.SettingNotFoundException) {
|
||||
return false
|
||||
}
|
||||
}
|
||||
get() =
|
||||
try {
|
||||
Settings.Secure.getInt(
|
||||
contentResolver, Settings.Secure.ACCESSIBILITY_DISPLAY_INVERSION_ENABLED) == 1
|
||||
} catch (e: Settings.SettingNotFoundException) {
|
||||
false
|
||||
}
|
||||
|
||||
private val isGrayscaleEnabledValue: Boolean
|
||||
get() {
|
||||
@@ -181,10 +180,8 @@ internal class AccessibilityInfoModule(context: ReactApplicationContext) :
|
||||
val isReduceMotionEnabled = isReduceMotionEnabledValue
|
||||
if (reduceMotionEnabled != isReduceMotionEnabled) {
|
||||
reduceMotionEnabled = isReduceMotionEnabled
|
||||
val reactApplicationContext = getReactApplicationContextIfActiveOrWarn()
|
||||
if (reactApplicationContext != null) {
|
||||
reactApplicationContext.emitDeviceEvent(REDUCE_MOTION_EVENT_NAME, reduceMotionEnabled)
|
||||
}
|
||||
getReactApplicationContextIfActiveOrWarn()
|
||||
?.emitDeviceEvent(REDUCE_MOTION_EVENT_NAME, reduceMotionEnabled)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -192,10 +189,8 @@ internal class AccessibilityInfoModule(context: ReactApplicationContext) :
|
||||
val isInvertColorsEnabled = isInvertColorsEnabledValue
|
||||
if (invertColorsEnabled != isInvertColorsEnabled) {
|
||||
invertColorsEnabled = isInvertColorsEnabled
|
||||
val reactApplicationContext = getReactApplicationContextIfActiveOrWarn()
|
||||
if (reactApplicationContext != null) {
|
||||
reactApplicationContext.emitDeviceEvent(INVERT_COLOR_EVENT_NAME, invertColorsEnabled)
|
||||
}
|
||||
getReactApplicationContextIfActiveOrWarn()
|
||||
?.emitDeviceEvent(INVERT_COLOR_EVENT_NAME, invertColorsEnabled)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -203,13 +198,11 @@ internal class AccessibilityInfoModule(context: ReactApplicationContext) :
|
||||
val isHighTextContrastEnabled = isHighTextContrastEnabledValue
|
||||
if (highTextContrastEnabled != isHighTextContrastEnabled) {
|
||||
highTextContrastEnabled = isHighTextContrastEnabled
|
||||
val reactApplicationContext = getReactApplicationContextIfActiveOrWarn()
|
||||
if (reactApplicationContext != null) {
|
||||
reactApplicationContext.emitDeviceEvent(
|
||||
HIGH_TEXT_CONTRAST_EVENT_NAME,
|
||||
highTextContrastEnabled,
|
||||
)
|
||||
}
|
||||
getReactApplicationContextIfActiveOrWarn()
|
||||
?.emitDeviceEvent(
|
||||
HIGH_TEXT_CONTRAST_EVENT_NAME,
|
||||
highTextContrastEnabled,
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -239,10 +232,8 @@ internal class AccessibilityInfoModule(context: ReactApplicationContext) :
|
||||
val isGrayscaleModeEnabled = isGrayscaleEnabledValue
|
||||
if (grayscaleModeEnabled != isGrayscaleModeEnabled) {
|
||||
grayscaleModeEnabled = isGrayscaleModeEnabled
|
||||
val reactApplicationContext = getReactApplicationContextIfActiveOrWarn()
|
||||
if (reactApplicationContext != null) {
|
||||
reactApplicationContext.emitDeviceEvent(GRAYSCALE_MODE_EVENT_NAME, grayscaleModeEnabled)
|
||||
}
|
||||
getReactApplicationContextIfActiveOrWarn()
|
||||
?.emitDeviceEvent(GRAYSCALE_MODE_EVENT_NAME, grayscaleModeEnabled)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
+2
-2
@@ -9,6 +9,7 @@ package com.facebook.react.modules.clipboard
|
||||
|
||||
import android.content.ClipData
|
||||
import android.content.ClipboardManager
|
||||
import android.content.Context
|
||||
import com.facebook.fbreact.specs.NativeClipboardSpec
|
||||
import com.facebook.react.bridge.Promise
|
||||
import com.facebook.react.bridge.ReactApplicationContext
|
||||
@@ -20,8 +21,7 @@ internal class ClipboardModule(context: ReactApplicationContext) : NativeClipboa
|
||||
|
||||
private val clipboardService: ClipboardManager
|
||||
get() =
|
||||
getReactApplicationContext().getSystemService(ReactApplicationContext.CLIPBOARD_SERVICE)
|
||||
as ClipboardManager
|
||||
getReactApplicationContext().getSystemService(Context.CLIPBOARD_SERVICE) as ClipboardManager
|
||||
|
||||
override fun getString(promise: Promise) {
|
||||
try {
|
||||
|
||||
+3
-6
@@ -108,7 +108,7 @@ public open class IntentModule(reactContext: ReactApplicationContext) :
|
||||
* @param url the URL to open
|
||||
*/
|
||||
override fun openURL(url: String?, promise: Promise) {
|
||||
if (url == null || url.isEmpty()) {
|
||||
if (url.isNullOrEmpty()) {
|
||||
promise.reject(JSApplicationIllegalArgumentException("Invalid URL: $url"))
|
||||
return
|
||||
}
|
||||
@@ -131,7 +131,7 @@ public open class IntentModule(reactContext: ReactApplicationContext) :
|
||||
* @param promise a promise that is always resolved with a boolean argument
|
||||
*/
|
||||
override fun canOpenURL(url: String?, promise: Promise) {
|
||||
if (url == null || url.isEmpty()) {
|
||||
if (url.isNullOrEmpty()) {
|
||||
promise.reject(JSApplicationIllegalArgumentException("Invalid URL: $url"))
|
||||
return
|
||||
}
|
||||
@@ -189,7 +189,7 @@ public open class IntentModule(reactContext: ReactApplicationContext) :
|
||||
* @param extras An array of extras [{ String, String | Number | Boolean }]
|
||||
*/
|
||||
override fun sendIntent(action: String?, extras: ReadableArray?, promise: Promise) {
|
||||
if (action == null || action.isEmpty()) {
|
||||
if (action.isNullOrEmpty()) {
|
||||
promise.reject(JSApplicationIllegalArgumentException("Invalid Action: $action."))
|
||||
return
|
||||
}
|
||||
@@ -214,7 +214,6 @@ public open class IntentModule(reactContext: ReactApplicationContext) :
|
||||
ReadableType.String -> {
|
||||
intent.putExtra(name, map.getString(EXTRA_MAP_KEY_FOR_VALUE))
|
||||
}
|
||||
|
||||
ReadableType.Number -> {
|
||||
// We cannot know from JS if is an Integer or Double
|
||||
// See: https://github.com/facebook/react-native/issues/4141
|
||||
@@ -222,11 +221,9 @@ public open class IntentModule(reactContext: ReactApplicationContext) :
|
||||
val number = map.getDouble(EXTRA_MAP_KEY_FOR_VALUE)
|
||||
intent.putExtra(name, number)
|
||||
}
|
||||
|
||||
ReadableType.Boolean -> {
|
||||
intent.putExtra(name, map.getBoolean(EXTRA_MAP_KEY_FOR_VALUE))
|
||||
}
|
||||
|
||||
else -> {
|
||||
promise.reject(
|
||||
JSApplicationIllegalArgumentException("Extra type for $name not supported."))
|
||||
|
||||
+5
-5
@@ -62,14 +62,14 @@ internal class ProgressiveStringDecoder(charset: Charset) {
|
||||
}
|
||||
|
||||
val hasRemainder = decoded && remainderLength > 0
|
||||
if (hasRemainder) {
|
||||
remainder =
|
||||
remainder =
|
||||
if (hasRemainder) {
|
||||
ByteArray(remainderLength).apply {
|
||||
System.arraycopy(decodeData, length - remainderLength, this, 0, remainderLength)
|
||||
}
|
||||
} else {
|
||||
remainder = null
|
||||
}
|
||||
} else {
|
||||
null
|
||||
}
|
||||
|
||||
if (!decoded) {
|
||||
FLog.w(ReactConstants.TAG, "failed to decode string from byte array")
|
||||
|
||||
+1
-1
@@ -80,7 +80,7 @@ public class PermissionsModule(reactContext: ReactApplicationContext?) :
|
||||
object : Callback {
|
||||
override operator fun invoke(vararg args: Any?) {
|
||||
val results = args[0] as IntArray
|
||||
if (results.size > 0 && results[0] == PackageManager.PERMISSION_GRANTED) {
|
||||
if (results.isNotEmpty() && results[0] == PackageManager.PERMISSION_GRANTED) {
|
||||
promise.resolve(GRANTED)
|
||||
} else {
|
||||
val callbackActivity = args[1] as PermissionAwareActivity
|
||||
|
||||
+1
-1
@@ -131,7 +131,7 @@ public class WebSocketModule(context: ReactApplicationContext) :
|
||||
protocolsValue.append(",")
|
||||
}
|
||||
}
|
||||
if (protocolsValue.length > 0) {
|
||||
if (protocolsValue.isNotEmpty()) {
|
||||
protocolsValue.replace(protocolsValue.length - 1, protocolsValue.length, "")
|
||||
builder.addHeader("Sec-WebSocket-Protocol", protocolsValue.toString())
|
||||
}
|
||||
|
||||
+3
-2
@@ -26,6 +26,7 @@ import com.facebook.react.uimanager.JSTouchDispatcher
|
||||
import com.facebook.react.uimanager.common.UIManagerType
|
||||
import com.facebook.systrace.Systrace
|
||||
import java.util.Objects
|
||||
import kotlin.math.max
|
||||
|
||||
/**
|
||||
* A view created by [com.facebook.react.interfaces.fabric.ReactSurface] that's responsible for
|
||||
@@ -55,7 +56,7 @@ public class ReactSurfaceView(context: Context?, private val surface: ReactSurfa
|
||||
for (i in 0 until childCount) {
|
||||
val child = getChildAt(i)
|
||||
val childSize = (child.left + child.measuredWidth + child.paddingLeft + child.paddingRight)
|
||||
width = Math.max(width, childSize)
|
||||
width = max(width, childSize)
|
||||
}
|
||||
} else {
|
||||
width = MeasureSpec.getSize(widthMeasureSpec)
|
||||
@@ -65,7 +66,7 @@ public class ReactSurfaceView(context: Context?, private val surface: ReactSurfa
|
||||
for (i in 0 until childCount) {
|
||||
val child = getChildAt(i)
|
||||
val childSize = (child.top + child.measuredHeight + child.paddingTop + child.paddingBottom)
|
||||
height = Math.max(height, childSize)
|
||||
height = max(height, childSize)
|
||||
}
|
||||
} else {
|
||||
height = MeasureSpec.getSize(heightMeasureSpec)
|
||||
|
||||
+11
@@ -19,6 +19,7 @@ import android.view.accessibility.AccessibilityEvent;
|
||||
import androidx.annotation.ColorInt;
|
||||
import androidx.annotation.NonNull;
|
||||
import androidx.annotation.Nullable;
|
||||
import androidx.core.view.AccessibilityDelegateCompat;
|
||||
import androidx.core.view.ViewCompat;
|
||||
import com.facebook.common.logging.FLog;
|
||||
import com.facebook.react.R;
|
||||
@@ -186,6 +187,16 @@ public abstract class BaseViewManager<T extends View, C extends LayoutShadowNode
|
||||
if (focusChangeListener instanceof BaseVMFocusChangeListener) {
|
||||
((BaseVMFocusChangeListener) focusChangeListener).detach(view);
|
||||
}
|
||||
|
||||
AccessibilityDelegateCompat axDelegate = ViewCompat.getAccessibilityDelegate(view);
|
||||
|
||||
if (axDelegate instanceof ReactAccessibilityDelegate) {
|
||||
((ReactAccessibilityDelegate) axDelegate).cleanUp();
|
||||
}
|
||||
|
||||
if (view instanceof ViewGroup) {
|
||||
((ViewGroup) view).setOnHierarchyChangeListener(null);
|
||||
}
|
||||
}
|
||||
|
||||
// Currently, layout listener is only attached when transform or transformOrigin is set.
|
||||
|
||||
+25
-20
@@ -8,6 +8,12 @@
|
||||
package com.facebook.react.uimanager
|
||||
|
||||
import com.facebook.infer.annotation.Assertions
|
||||
import kotlin.math.abs
|
||||
import kotlin.math.atan2
|
||||
import kotlin.math.cos
|
||||
import kotlin.math.sin
|
||||
import kotlin.math.sqrt
|
||||
import kotlin.math.tan
|
||||
|
||||
/**
|
||||
* Provides helper methods for converting transform operations into a matrix and then into a list of
|
||||
@@ -19,7 +25,7 @@ public object MatrixMathHelper {
|
||||
private fun isZero(d: Double): Boolean {
|
||||
return if (java.lang.Double.isNaN(d)) {
|
||||
false
|
||||
} else Math.abs(d) < EPSILON
|
||||
} else abs(d) < EPSILON
|
||||
}
|
||||
|
||||
@JvmStatic
|
||||
@@ -181,12 +187,11 @@ public object MatrixMathHelper {
|
||||
// Now, get the rotations out
|
||||
// Based on: http://nghiaho.com/?page_id=846
|
||||
val conv = 180 / Math.PI
|
||||
rotationDegrees[0] = roundTo3Places(-Math.atan2(row[2][1], row[2][2]) * conv)
|
||||
rotationDegrees[0] = roundTo3Places(-atan2(row[2][1], row[2][2]) * conv)
|
||||
rotationDegrees[1] =
|
||||
roundTo3Places(
|
||||
-Math.atan2(-row[2][0], Math.sqrt(row[2][1] * row[2][1] + row[2][2] * row[2][2])) *
|
||||
conv)
|
||||
rotationDegrees[2] = roundTo3Places(-Math.atan2(row[1][0], row[0][0]) * conv)
|
||||
-atan2(-row[2][0], sqrt(row[2][1] * row[2][1] + row[2][2] * row[2][2])) * conv)
|
||||
rotationDegrees[2] = roundTo3Places(-atan2(row[1][0], row[0][0]) * conv)
|
||||
}
|
||||
|
||||
@JvmStatic
|
||||
@@ -322,7 +327,7 @@ public object MatrixMathHelper {
|
||||
/** From: https://code.google.com/p/webgl-mjs/source/browse/mjs.js */
|
||||
@JvmStatic
|
||||
public fun v3Length(a: DoubleArray): Double {
|
||||
return Math.sqrt(a[0] * a[0] + a[1] * a[1] + a[2] * a[2])
|
||||
return sqrt(a[0] * a[0] + a[1] * a[1] + a[2] * a[2])
|
||||
}
|
||||
|
||||
/** Based on: https://code.google.com/p/webgl-mjs/source/browse/mjs.js */
|
||||
@@ -437,37 +442,37 @@ public object MatrixMathHelper {
|
||||
|
||||
@JvmStatic
|
||||
public fun applySkewX(m: DoubleArray, radians: Double) {
|
||||
m[4] = Math.tan(radians)
|
||||
m[4] = tan(radians)
|
||||
}
|
||||
|
||||
@JvmStatic
|
||||
public fun applySkewY(m: DoubleArray, radians: Double) {
|
||||
m[1] = Math.tan(radians)
|
||||
m[1] = tan(radians)
|
||||
}
|
||||
|
||||
@JvmStatic
|
||||
public fun applyRotateX(m: DoubleArray, radians: Double) {
|
||||
m[5] = Math.cos(radians)
|
||||
m[6] = Math.sin(radians)
|
||||
m[9] = -Math.sin(radians)
|
||||
m[10] = Math.cos(radians)
|
||||
m[5] = cos(radians)
|
||||
m[6] = sin(radians)
|
||||
m[9] = -sin(radians)
|
||||
m[10] = cos(radians)
|
||||
}
|
||||
|
||||
@JvmStatic
|
||||
public fun applyRotateY(m: DoubleArray, radians: Double) {
|
||||
m[0] = Math.cos(radians)
|
||||
m[2] = -Math.sin(radians)
|
||||
m[8] = Math.sin(radians)
|
||||
m[10] = Math.cos(radians)
|
||||
m[0] = cos(radians)
|
||||
m[2] = -sin(radians)
|
||||
m[8] = sin(radians)
|
||||
m[10] = cos(radians)
|
||||
}
|
||||
|
||||
// http://www.w3.org/TR/css3-transforms/#recomposing-to-a-2d-matrix
|
||||
@JvmStatic
|
||||
public fun applyRotateZ(m: DoubleArray, radians: Double) {
|
||||
m[0] = Math.cos(radians)
|
||||
m[1] = Math.sin(radians)
|
||||
m[4] = -Math.sin(radians)
|
||||
m[5] = Math.cos(radians)
|
||||
m[0] = cos(radians)
|
||||
m[1] = sin(radians)
|
||||
m[4] = -sin(radians)
|
||||
m[5] = cos(radians)
|
||||
}
|
||||
|
||||
public open class MatrixDecompositionContext {
|
||||
|
||||
+6
-7
@@ -29,13 +29,12 @@ public enum class PointerEvents {
|
||||
public companion object {
|
||||
|
||||
@JvmStatic
|
||||
public fun parsePointerEvents(pointerEventsStr: String?): PointerEvents {
|
||||
if (pointerEventsStr == null) {
|
||||
return AUTO
|
||||
} else {
|
||||
return PointerEvents.valueOf(pointerEventsStr.uppercase(Locale.US).replace("-", "_"))
|
||||
}
|
||||
}
|
||||
public fun parsePointerEvents(pointerEventsStr: String?): PointerEvents =
|
||||
if (pointerEventsStr == null) {
|
||||
AUTO
|
||||
} else {
|
||||
PointerEvents.valueOf(pointerEventsStr.uppercase(Locale.US).replace("-", "_"))
|
||||
}
|
||||
|
||||
@JvmStatic
|
||||
public fun canBeTouchTarget(pointerEvents: PointerEvents): Boolean {
|
||||
|
||||
+37
-1
@@ -16,6 +16,7 @@ import android.text.TextUtils;
|
||||
import android.view.View;
|
||||
import android.view.ViewGroup;
|
||||
import android.view.accessibility.AccessibilityEvent;
|
||||
import android.view.accessibility.AccessibilityManager;
|
||||
import android.widget.EditText;
|
||||
import androidx.annotation.NonNull;
|
||||
import androidx.annotation.Nullable;
|
||||
@@ -72,6 +73,10 @@ public class ReactAccessibilityDelegate extends ExploreByTouchHelper {
|
||||
private Handler mHandler;
|
||||
private final HashMap<Integer, String> mAccessibilityActionsMap;
|
||||
|
||||
@Nullable
|
||||
private AccessibilityManager.AccessibilityStateChangeListener accessibilityStateChangeListener =
|
||||
null;
|
||||
|
||||
@Nullable View mAccessibilityLabelledBy;
|
||||
|
||||
static {
|
||||
@@ -256,10 +261,29 @@ public class ReactAccessibilityDelegate extends ExploreByTouchHelper {
|
||||
|
||||
@Override
|
||||
public void onInitializeAccessibilityNodeInfo(View host, AccessibilityNodeInfoCompat info) {
|
||||
super.onInitializeAccessibilityNodeInfo(host, info);
|
||||
// If we set an accessibility order then all the focusing logic should go through our custom
|
||||
// virtual view tree hierarchy and ignore the default path
|
||||
ReadableArray axOrderIds = (ReadableArray) mView.getTag(R.id.accessibility_order);
|
||||
if (axOrderIds != null && axOrderIds.size() != 0) {
|
||||
info.setContentDescription("");
|
||||
info.setFocusable(false);
|
||||
|
||||
AccessibilityManager am =
|
||||
(AccessibilityManager) host.getContext().getSystemService(Context.ACCESSIBILITY_SERVICE);
|
||||
|
||||
if (accessibilityStateChangeListener == null && am != null) {
|
||||
AccessibilityManager.AccessibilityStateChangeListener newAccessibilityStateChangeListener =
|
||||
enabled -> {
|
||||
if (!enabled) {
|
||||
ReactAxOrderHelper.restoreSubtreeFocusability(host);
|
||||
host.setTag(R.id.accessibility_order_dirty, true);
|
||||
}
|
||||
};
|
||||
|
||||
am.addAccessibilityStateChangeListener(newAccessibilityStateChangeListener);
|
||||
accessibilityStateChangeListener = newAccessibilityStateChangeListener;
|
||||
}
|
||||
|
||||
Boolean isAxOrderDirty = (Boolean) mView.getTag(R.id.accessibility_order_dirty);
|
||||
if (isAxOrderDirty != null && isAxOrderDirty) {
|
||||
@@ -278,7 +302,6 @@ public class ReactAccessibilityDelegate extends ExploreByTouchHelper {
|
||||
return;
|
||||
}
|
||||
|
||||
super.onInitializeAccessibilityNodeInfo(host, info);
|
||||
populateAccessibilityNodeInfo(host, info);
|
||||
}
|
||||
|
||||
@@ -1098,4 +1121,17 @@ public class ReactAccessibilityDelegate extends ExploreByTouchHelper {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// In case a view with accessibilityOrder is unmounted we need a way to clean up the listener on
|
||||
// this delegate
|
||||
public void cleanUp() {
|
||||
if (accessibilityStateChangeListener != null) {
|
||||
AccessibilityManager am =
|
||||
(AccessibilityManager) mView.getContext().getSystemService(Context.ACCESSIBILITY_SERVICE);
|
||||
if (am != null) {
|
||||
am.removeAccessibilityStateChangeListener(accessibilityStateChangeListener);
|
||||
}
|
||||
accessibilityStateChangeListener = null;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
+24
-5
@@ -10,7 +10,6 @@ package com.facebook.react.uimanager
|
||||
import android.graphics.Rect
|
||||
import android.view.View
|
||||
import android.view.ViewGroup
|
||||
import android.widget.TextView
|
||||
import com.facebook.react.R
|
||||
import com.facebook.react.bridge.ReadableArray
|
||||
|
||||
@@ -76,10 +75,6 @@ private object ReactAxOrderHelper {
|
||||
}
|
||||
}
|
||||
|
||||
if (!isIncluded && !isContained && parent != view && view !is TextView) {
|
||||
view.importantForAccessibility = View.IMPORTANT_FOR_ACCESSIBILITY_NO
|
||||
}
|
||||
|
||||
// Don't traverse the children of a nested accessibility order
|
||||
if (view is ViewGroup) {
|
||||
val axChildren: ArrayList<View> = getAxChildren(view)
|
||||
@@ -100,6 +95,13 @@ private object ReactAxOrderHelper {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!isIncluded && !isContained && parent != view) {
|
||||
if (view.getTag(R.id.original_focusability) == null) {
|
||||
view.setTag(R.id.original_focusability, view.isFocusable)
|
||||
}
|
||||
view.isFocusable = false
|
||||
}
|
||||
}
|
||||
|
||||
traverseAndBuildAxOrder(
|
||||
@@ -159,4 +161,21 @@ private object ReactAxOrderHelper {
|
||||
}
|
||||
return axChildren
|
||||
}
|
||||
|
||||
@JvmStatic
|
||||
public fun restoreSubtreeFocusability(view: View) {
|
||||
val originalFocusability = view.getTag(R.id.original_focusability)
|
||||
if (originalFocusability is Boolean) {
|
||||
view.isFocusable = originalFocusability
|
||||
}
|
||||
|
||||
if (view is ViewGroup) {
|
||||
for (i in 0 until view.childCount) {
|
||||
val child = view.getChildAt(i)
|
||||
if (child != null) {
|
||||
restoreSubtreeFocusability(child)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
+1
-1
@@ -32,7 +32,7 @@ public interface ReactClippingViewGroup {
|
||||
*/
|
||||
public fun updateClippingRect()
|
||||
|
||||
public fun updateClippingRect(excludedView: Set<Int>?)
|
||||
public fun updateClippingRect(excludedViews: Set<Int>?)
|
||||
|
||||
/**
|
||||
* Get rectangular bounds to which view is currently clipped to. Called only on views that has set
|
||||
|
||||
-235
@@ -1,235 +0,0 @@
|
||||
/*
|
||||
* Copyright (c) Meta Platforms, Inc. and affiliates.
|
||||
*
|
||||
* This source code is licensed under the MIT license found in the
|
||||
* LICENSE file in the root directory of this source tree.
|
||||
*/
|
||||
|
||||
package com.facebook.react.uimanager;
|
||||
|
||||
import static com.facebook.react.uimanager.common.UIManagerType.FABRIC;
|
||||
import static com.facebook.react.uimanager.common.ViewUtil.getUIManagerType;
|
||||
|
||||
import android.content.Context;
|
||||
import android.content.ContextWrapper;
|
||||
import android.view.View;
|
||||
import android.widget.EditText;
|
||||
import androidx.annotation.Nullable;
|
||||
import androidx.core.view.ViewCompat;
|
||||
import com.facebook.infer.annotation.Nullsafe;
|
||||
import com.facebook.react.bridge.CatalystInstance;
|
||||
import com.facebook.react.bridge.ReactContext;
|
||||
import com.facebook.react.bridge.ReactNoCrashSoftException;
|
||||
import com.facebook.react.bridge.ReactSoftExceptionLogger;
|
||||
import com.facebook.react.bridge.UIManager;
|
||||
import com.facebook.react.common.annotations.internal.LegacyArchitectureLogLevel;
|
||||
import com.facebook.react.common.annotations.internal.LegacyArchitectureLogger;
|
||||
import com.facebook.react.common.build.ReactBuildConfig;
|
||||
import com.facebook.react.uimanager.common.UIManagerType;
|
||||
import com.facebook.react.uimanager.events.EventDispatcher;
|
||||
import com.facebook.react.uimanager.events.EventDispatcherProvider;
|
||||
|
||||
/** Helper class for {@link UIManager}. */
|
||||
@Nullsafe(Nullsafe.Mode.LOCAL)
|
||||
public class UIManagerHelper {
|
||||
|
||||
private static final String TAG = "UIManagerHelper";
|
||||
public static final int PADDING_START_INDEX = 0;
|
||||
public static final int PADDING_END_INDEX = 1;
|
||||
public static final int PADDING_TOP_INDEX = 2;
|
||||
public static final int PADDING_BOTTOM_INDEX = 3;
|
||||
|
||||
/**
|
||||
* @return a {@link UIManager} that can handle the react tag received by parameter.
|
||||
*/
|
||||
@Nullable
|
||||
public static UIManager getUIManagerForReactTag(ReactContext context, int reactTag) {
|
||||
return getUIManager(context, getUIManagerType(reactTag));
|
||||
}
|
||||
|
||||
/**
|
||||
* @return a {@link UIManager} that can handle the react tag received by parameter.
|
||||
*/
|
||||
@Nullable
|
||||
public static UIManager getUIManager(ReactContext context, @UIManagerType int uiManagerType) {
|
||||
return getUIManager(context, uiManagerType, true);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
private static UIManager getUIManager(
|
||||
ReactContext context,
|
||||
@UIManagerType int uiManagerType,
|
||||
boolean returnNullIfCatalystIsInactive) {
|
||||
if (ReactBuildConfig.UNSTABLE_ENABLE_MINIFY_LEGACY_ARCHITECTURE || context.isBridgeless()) {
|
||||
@Nullable UIManager uiManager = context.getFabricUIManager();
|
||||
if (uiManager == null) {
|
||||
ReactSoftExceptionLogger.logSoftException(
|
||||
TAG,
|
||||
new ReactNoCrashSoftException(
|
||||
"Cannot get UIManager because the instance hasn't been initialized yet."));
|
||||
return null;
|
||||
}
|
||||
return uiManager;
|
||||
}
|
||||
|
||||
// The following code is compiled-out when `context.isBridgeless() == true &&
|
||||
// ReactBuildConfig.UNSTABLE_ENABLE_MINIFY_LEGACY_ARCHITECTURE == true ` because:
|
||||
// - BridgelessReactContext.isBridgeless() is set to true statically
|
||||
// - BridgeReactContext is compiled-out when UNSTABLE_ENABLE_MINIFY_LEGACY_ARCHITECTURE == true
|
||||
//
|
||||
// To detect a potential regression we add the following assertion ERROR
|
||||
LegacyArchitectureLogger.assertLegacyArchitecture(
|
||||
"UIManagerHelper.getUIManager(context, uiManagerType)", LegacyArchitectureLogLevel.ERROR);
|
||||
if (!context.hasCatalystInstance()) {
|
||||
ReactSoftExceptionLogger.logSoftException(
|
||||
TAG,
|
||||
new ReactNoCrashSoftException(
|
||||
"Cannot get UIManager because the context doesn't contain a CatalystInstance."));
|
||||
return null;
|
||||
}
|
||||
// TODO T60461551: add tests to verify emission of events when the ReactContext is being turn
|
||||
// down.
|
||||
if (!context.hasActiveReactInstance()) {
|
||||
ReactSoftExceptionLogger.logSoftException(
|
||||
TAG,
|
||||
new ReactNoCrashSoftException(
|
||||
"Cannot get UIManager because the context doesn't contain an active"
|
||||
+ " CatalystInstance."));
|
||||
if (returnNullIfCatalystIsInactive) {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
CatalystInstance catalystInstance = context.getCatalystInstance();
|
||||
try {
|
||||
return uiManagerType == FABRIC
|
||||
? context.getFabricUIManager()
|
||||
: catalystInstance.getNativeModule(UIManagerModule.class);
|
||||
} catch (IllegalArgumentException ex) {
|
||||
// TODO T67518514 Clean this up once we migrate everything over to bridgeless mode
|
||||
ReactSoftExceptionLogger.logSoftException(
|
||||
TAG,
|
||||
new ReactNoCrashSoftException(
|
||||
"Cannot get UIManager for UIManagerType: " + uiManagerType));
|
||||
return catalystInstance.getNativeModule(UIManagerModule.class);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the {@link EventDispatcher} that handles events for the reactTag received as a
|
||||
* parameter.
|
||||
*/
|
||||
@Nullable
|
||||
public static EventDispatcher getEventDispatcherForReactTag(ReactContext context, int reactTag) {
|
||||
EventDispatcher eventDispatcher = getEventDispatcher(context, getUIManagerType(reactTag));
|
||||
if (eventDispatcher == null) {
|
||||
ReactSoftExceptionLogger.logSoftException(
|
||||
TAG, new IllegalStateException("Cannot get EventDispatcher for reactTag " + reactTag));
|
||||
}
|
||||
return eventDispatcher;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the {@link EventDispatcher} that handles events for the {@link UIManagerType} received
|
||||
* as a parameter.
|
||||
*/
|
||||
@Nullable
|
||||
public static EventDispatcher getEventDispatcher(
|
||||
ReactContext context, @UIManagerType int uiManagerType) {
|
||||
// TODO T67518514 Clean this up once we migrate everything over to bridgeless mode
|
||||
if (context.isBridgeless()) {
|
||||
if (context instanceof ThemedReactContext) {
|
||||
context = ((ThemedReactContext) context).getReactApplicationContext();
|
||||
}
|
||||
return ((EventDispatcherProvider) context).getEventDispatcher();
|
||||
}
|
||||
UIManager uiManager = getUIManager(context, uiManagerType, false);
|
||||
if (uiManager == null) {
|
||||
ReactSoftExceptionLogger.logSoftException(
|
||||
TAG,
|
||||
new ReactNoCrashSoftException(
|
||||
"Unable to find UIManager for UIManagerType " + uiManagerType));
|
||||
return null;
|
||||
}
|
||||
EventDispatcher eventDispatcher = (EventDispatcher) uiManager.getEventDispatcher();
|
||||
if (eventDispatcher == null) {
|
||||
ReactSoftExceptionLogger.logSoftException(
|
||||
TAG,
|
||||
new IllegalStateException(
|
||||
"Cannot get EventDispatcher for UIManagerType " + uiManagerType));
|
||||
}
|
||||
return eventDispatcher;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return The {@link ReactContext} associated to the {@link View} received as a parameter.
|
||||
* <p>We can't rely that the method View.getContext() will return the same context that was
|
||||
* passed as a parameter during the construction of the View.
|
||||
* <p>For example the AppCompatEditText class wraps the context received as a parameter in the
|
||||
* constructor of the View into a TintContextWrapper object. See:
|
||||
* https://android.googlesource.com/platform/frameworks/support/+/dd55716/v7/appcompat/src/android/support/v7/widget/AppCompatEditText.java#55
|
||||
*/
|
||||
public static ReactContext getReactContext(View view) {
|
||||
Context context = view.getContext();
|
||||
if (!(context instanceof ReactContext) && context instanceof ContextWrapper) {
|
||||
context = ((ContextWrapper) context).getBaseContext();
|
||||
}
|
||||
return (ReactContext) context;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return Gets the surfaceId for the {@link ThemedReactContext} associated with a View, if
|
||||
* possible, and then call getSurfaceId on it. See above (getReactContext) for additional
|
||||
* context.
|
||||
* <p>For RootViews, the root's rootViewTag is returned
|
||||
* <p>Returns -1 for non-Fabric views
|
||||
*/
|
||||
public static int getSurfaceId(View view) {
|
||||
if (view instanceof ReactRoot) {
|
||||
ReactRoot rootView = (ReactRoot) view;
|
||||
return rootView.getUIManagerType() == UIManagerType.FABRIC ? rootView.getRootViewTag() : -1;
|
||||
}
|
||||
|
||||
int reactTag = view.getId();
|
||||
|
||||
// In non-Fabric we don't have (or use) SurfaceId
|
||||
if (getUIManagerType(reactTag) == UIManagerType.LEGACY) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
Context context = view.getContext();
|
||||
if (!(context instanceof ThemedReactContext) && context instanceof ContextWrapper) {
|
||||
context = ((ContextWrapper) context).getBaseContext();
|
||||
}
|
||||
|
||||
int surfaceId = getSurfaceId(context);
|
||||
if (surfaceId == -1) {
|
||||
// All Fabric-managed Views (should) have a ThemedReactContext attached.
|
||||
ReactSoftExceptionLogger.logSoftException(
|
||||
TAG,
|
||||
new IllegalStateException(
|
||||
"Fabric View [" + reactTag + "] does not have SurfaceId associated with it"));
|
||||
}
|
||||
return surfaceId;
|
||||
}
|
||||
|
||||
public static int getSurfaceId(Context context) {
|
||||
if (context instanceof ThemedReactContext) {
|
||||
return ((ThemedReactContext) context).getSurfaceId();
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the default padding used by Android EditText's. This method returns the padding in an
|
||||
* array to avoid extra classloading during hot-path of RN Android.
|
||||
*/
|
||||
public static float[] getDefaultTextInputPadding(Context context) {
|
||||
EditText editText = new EditText(context);
|
||||
float[] padding = new float[4];
|
||||
padding[PADDING_START_INDEX] = PixelUtil.toDIPFromPixel(ViewCompat.getPaddingStart(editText));
|
||||
padding[PADDING_END_INDEX] = PixelUtil.toDIPFromPixel(ViewCompat.getPaddingEnd(editText));
|
||||
padding[PADDING_TOP_INDEX] = PixelUtil.toDIPFromPixel(editText.getPaddingTop());
|
||||
padding[PADDING_BOTTOM_INDEX] = PixelUtil.toDIPFromPixel(editText.getPaddingBottom());
|
||||
return padding;
|
||||
}
|
||||
}
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user