mirror of
https://github.com/status-im/rn-emoji-keyboard.git
synced 2025-01-27 08:34:48 +00:00
fix: android RNGH
This commit is contained in:
parent
5cab329d57
commit
9b91d392b7
@ -1,6 +1,9 @@
|
|||||||
package com.example.reactnativeemojikeyboard;
|
package com.example.reactnativeemojikeyboard;
|
||||||
|
|
||||||
import com.facebook.react.ReactActivity;
|
import com.facebook.react.ReactActivity;
|
||||||
|
import com.facebook.react.ReactActivityDelegate;
|
||||||
|
import com.facebook.react.ReactRootView;
|
||||||
|
import com.swmansion.gesturehandler.react.RNGestureHandlerEnabledRootView;
|
||||||
|
|
||||||
public class MainActivity extends ReactActivity {
|
public class MainActivity extends ReactActivity {
|
||||||
|
|
||||||
@ -12,4 +15,13 @@ public class MainActivity extends ReactActivity {
|
|||||||
protected String getMainComponentName() {
|
protected String getMainComponentName() {
|
||||||
return "EmojiKeyboardExample";
|
return "EmojiKeyboardExample";
|
||||||
}
|
}
|
||||||
|
@Override
|
||||||
|
protected ReactActivityDelegate createReactActivityDelegate() {
|
||||||
|
return new ReactActivityDelegate(this, getMainComponentName()) {
|
||||||
|
@Override
|
||||||
|
protected ReactRootView createRootView() {
|
||||||
|
return new RNGestureHandlerEnabledRootView(MainActivity.this);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -17,13 +17,18 @@ export default function App() {
|
|||||||
<SafeAreaView style={styles.container}>
|
<SafeAreaView style={styles.container}>
|
||||||
<Text style={styles.text}>Result: {result}</Text>
|
<Text style={styles.text}>Result: {result}</Text>
|
||||||
<TouchableOpacity onPress={() => setIsModalOpen(true)}>
|
<TouchableOpacity onPress={() => setIsModalOpen(true)}>
|
||||||
<Text>Open</Text>
|
<Text style={styles.text}>Open</Text>
|
||||||
</TouchableOpacity>
|
</TouchableOpacity>
|
||||||
|
|
||||||
|
{/* //////////////////////////////////////////// */}
|
||||||
|
|
||||||
<EmojiPicker
|
<EmojiPicker
|
||||||
onEmojiSelected={handlePick}
|
onEmojiSelected={handlePick}
|
||||||
open={isModalOpen}
|
open={isModalOpen}
|
||||||
onClose={() => setIsModalOpen(false)}
|
onClose={() => setIsModalOpen(false)}
|
||||||
/>
|
/>
|
||||||
|
|
||||||
|
{/* //////////////////////////////////////////// */}
|
||||||
</SafeAreaView>
|
</SafeAreaView>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -37,10 +42,4 @@ const styles = StyleSheet.create({
|
|||||||
margin: 64,
|
margin: 64,
|
||||||
fontSize: 18,
|
fontSize: 18,
|
||||||
},
|
},
|
||||||
containerStyles: {
|
|
||||||
backgroundColor: '#efefef',
|
|
||||||
borderTopLeftRadius: 24,
|
|
||||||
borderTopRightRadius: 24,
|
|
||||||
elevation: 20,
|
|
||||||
},
|
|
||||||
});
|
});
|
||||||
|
@ -6,8 +6,6 @@ import {
|
|||||||
FlatList,
|
FlatList,
|
||||||
useWindowDimensions,
|
useWindowDimensions,
|
||||||
Animated,
|
Animated,
|
||||||
// NativeSyntheticEvent,
|
|
||||||
// NativeScrollEvent,
|
|
||||||
} from 'react-native';
|
} from 'react-native';
|
||||||
import { CATEGORIES, CategoryTypes } from './types';
|
import { CATEGORIES, CategoryTypes } from './types';
|
||||||
import { EmojiCategory } from './components/EmojiCategory';
|
import { EmojiCategory } from './components/EmojiCategory';
|
||||||
@ -80,6 +78,9 @@ export const EmojiKeyboard = () => {
|
|||||||
getItemLayout={getItemLayout}
|
getItemLayout={getItemLayout}
|
||||||
scrollEnabled={false}
|
scrollEnabled={false}
|
||||||
// onScroll={onScroll}
|
// onScroll={onScroll}
|
||||||
|
initialNumToRender={1}
|
||||||
|
windowSize={7}
|
||||||
|
maxToRenderPerBatch={1}
|
||||||
/>
|
/>
|
||||||
<Categories flatListRef={flatListRef} scrollNav={scrollNav} />
|
<Categories flatListRef={flatListRef} scrollNav={scrollNav} />
|
||||||
</View>
|
</View>
|
||||||
|
@ -12,21 +12,33 @@ import type { CategoryTypes, EmojiType } from 'src/types';
|
|||||||
import { SingleEmoji } from './SingleEmoji';
|
import { SingleEmoji } from './SingleEmoji';
|
||||||
import { KeyboardContext } from '../KeyboardContext';
|
import { KeyboardContext } from '../KeyboardContext';
|
||||||
|
|
||||||
|
const emptyEmoji = {
|
||||||
|
emoji: '',
|
||||||
|
name: 'blank emoji',
|
||||||
|
slug: 'blank_emoji',
|
||||||
|
skin_tone_support: false,
|
||||||
|
unicode_version: '0',
|
||||||
|
emoji_version: '0',
|
||||||
|
};
|
||||||
|
|
||||||
export const EmojiCategory = ({ item }: { item: CategoryTypes }) => {
|
export const EmojiCategory = ({ item }: { item: CategoryTypes }) => {
|
||||||
const { width } = useWindowDimensions();
|
const { width } = useWindowDimensions();
|
||||||
const ctx = React.useContext(KeyboardContext);
|
const ctx = React.useContext(KeyboardContext);
|
||||||
const numberOfColumns = React.useRef<number>(
|
const numberOfColumns = React.useRef<number>(
|
||||||
Math.floor(width / (ctx.emojiSize + 20))
|
Math.floor(width / (ctx.emojiSize + 20))
|
||||||
);
|
);
|
||||||
const [data, setData] = React.useState<EmojiType[]>([]);
|
const [empty, setEmpty] = React.useState<EmojiType[]>([]);
|
||||||
|
|
||||||
React.useEffect(() => {
|
React.useEffect(() => {
|
||||||
const newData = emojisByGroup[item];
|
console.log(
|
||||||
|
numberOfColumns.current -
|
||||||
|
(emojisByGroup[item].length % numberOfColumns.current)
|
||||||
|
);
|
||||||
const fillWithEmpty = new Array(
|
const fillWithEmpty = new Array(
|
||||||
numberOfColumns.current -
|
numberOfColumns.current -
|
||||||
(emojisByGroup[item].length % numberOfColumns.current)
|
(emojisByGroup[item].length % numberOfColumns.current)
|
||||||
).fill('a');
|
).fill(emptyEmoji);
|
||||||
setData([...newData, ...fillWithEmpty]);
|
setEmpty(fillWithEmpty);
|
||||||
}, [item]);
|
}, [item]);
|
||||||
|
|
||||||
const getItemLayout = (_: EmojiType[] | null | undefined, index: number) => ({
|
const getItemLayout = (_: EmojiType[] | null | undefined, index: number) => ({
|
||||||
@ -36,8 +48,30 @@ export const EmojiCategory = ({ item }: { item: CategoryTypes }) => {
|
|||||||
});
|
});
|
||||||
|
|
||||||
const renderItem = React.useCallback(
|
const renderItem = React.useCallback(
|
||||||
(props) => <SingleEmoji {...props} />,
|
// (props) => {
|
||||||
[]
|
// if (props.item.slug === 'blank_emoji')
|
||||||
|
// return (
|
||||||
|
// <View
|
||||||
|
// {...props}
|
||||||
|
// style={{ backgroundColor: 'blue', width: 10, height: 10 }}
|
||||||
|
// />
|
||||||
|
// );
|
||||||
|
// else
|
||||||
|
// return (
|
||||||
|
// <View
|
||||||
|
// {...props}
|
||||||
|
// style={{ backgroundColor: 'red', width: 10, height: 10 }}
|
||||||
|
// />
|
||||||
|
// );
|
||||||
|
// },
|
||||||
|
(props) => (
|
||||||
|
<SingleEmoji
|
||||||
|
{...props}
|
||||||
|
onPress={() => ctx.onEmojiSelected(props.item)}
|
||||||
|
emojiSize={ctx.emojiSize}
|
||||||
|
/>
|
||||||
|
),
|
||||||
|
[ctx]
|
||||||
);
|
);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
@ -46,7 +80,7 @@ export const EmojiCategory = ({ item }: { item: CategoryTypes }) => {
|
|||||||
<Text style={[styles.sectionTitle, ctx.headerStyles]}>{item}</Text>
|
<Text style={[styles.sectionTitle, ctx.headerStyles]}>{item}</Text>
|
||||||
)}
|
)}
|
||||||
<FlatList
|
<FlatList
|
||||||
data={data}
|
data={[...emojisByGroup[item], ...empty]}
|
||||||
keyExtractor={(emoji) => emoji.name}
|
keyExtractor={(emoji) => emoji.name}
|
||||||
numColumns={numberOfColumns.current}
|
numColumns={numberOfColumns.current}
|
||||||
renderItem={renderItem}
|
renderItem={renderItem}
|
||||||
|
@ -52,6 +52,7 @@ export const Knob = ({ offsetY, height, onClose }: KnobProps) => {
|
|||||||
<PanGestureHandler
|
<PanGestureHandler
|
||||||
onGestureEvent={handleGesture}
|
onGestureEvent={handleGesture}
|
||||||
onHandlerStateChange={handleGesture}
|
onHandlerStateChange={handleGesture}
|
||||||
|
hitSlop={{ vertical: 20, horizontal: 40 }}
|
||||||
>
|
>
|
||||||
<Animated.View style={[styles.knob, ctx.knobStyles]} />
|
<Animated.View style={[styles.knob, ctx.knobStyles]} />
|
||||||
</PanGestureHandler>
|
</PanGestureHandler>
|
||||||
|
@ -9,6 +9,7 @@ import {
|
|||||||
View,
|
View,
|
||||||
} from 'react-native';
|
} from 'react-native';
|
||||||
import { KeyboardContext } from '../KeyboardContext';
|
import { KeyboardContext } from '../KeyboardContext';
|
||||||
|
import { GestureHandlerRootView } from 'react-native-gesture-handler';
|
||||||
|
|
||||||
type ModalWithBackdropProps = {
|
type ModalWithBackdropProps = {
|
||||||
isOpen: boolean;
|
isOpen: boolean;
|
||||||
@ -35,30 +36,32 @@ export const ModalWithBackdrop = ({
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<Modal visible={isOpen} animationType="fade" transparent={true}>
|
<Modal visible={isOpen} animationType="fade" transparent={true}>
|
||||||
<TouchableOpacity
|
<GestureHandlerRootView style={styles.modalContainer}>
|
||||||
style={styles.modalContainer}
|
<TouchableOpacity
|
||||||
activeOpacity={1}
|
style={styles.modalContainer}
|
||||||
onPress={backdropPress}
|
activeOpacity={1}
|
||||||
>
|
onPress={backdropPress}
|
||||||
<View
|
|
||||||
style={[
|
|
||||||
styles.modalContainer,
|
|
||||||
{ backgroundColor: ctx.backdropColor },
|
|
||||||
]}
|
|
||||||
>
|
>
|
||||||
<SafeAreaView style={styles.modalContainer}>
|
<View
|
||||||
<TouchableOpacity activeOpacity={1}>
|
style={[
|
||||||
<Animated.View
|
styles.modalContainer,
|
||||||
style={{
|
{ backgroundColor: ctx.backdropColor },
|
||||||
transform: [{ translateY }],
|
]}
|
||||||
}}
|
>
|
||||||
>
|
<SafeAreaView style={styles.modalContainer}>
|
||||||
{children}
|
<TouchableOpacity activeOpacity={1}>
|
||||||
</Animated.View>
|
<Animated.View
|
||||||
</TouchableOpacity>
|
style={{
|
||||||
</SafeAreaView>
|
transform: [{ translateY }],
|
||||||
</View>
|
}}
|
||||||
</TouchableOpacity>
|
>
|
||||||
|
{children}
|
||||||
|
</Animated.View>
|
||||||
|
</TouchableOpacity>
|
||||||
|
</SafeAreaView>
|
||||||
|
</View>
|
||||||
|
</TouchableOpacity>
|
||||||
|
</GestureHandlerRootView>
|
||||||
</Modal>
|
</Modal>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
@ -1,20 +1,25 @@
|
|||||||
import * as React from 'react';
|
import * as React from 'react';
|
||||||
import { View, Text, TouchableOpacity, StyleSheet } from 'react-native';
|
import { View, Text, TouchableOpacity, StyleSheet } from 'react-native';
|
||||||
import { KeyboardContext } from '../KeyboardContext';
|
|
||||||
import type { EmojiType } from '../types';
|
import type { EmojiType } from '../types';
|
||||||
|
|
||||||
export const SingleEmoji = ({ item }: { item: EmojiType }) => {
|
export const SingleEmoji = ({
|
||||||
const ctx = React.useContext(KeyboardContext);
|
item,
|
||||||
return (
|
onPress,
|
||||||
<TouchableOpacity
|
emojiSize,
|
||||||
onPress={() => ctx?.onEmojiSelected(item)}
|
}: {
|
||||||
style={styles.container}
|
item: EmojiType;
|
||||||
>
|
onPress: (emojiObject: EmojiType) => void;
|
||||||
<View>
|
emojiSize: number;
|
||||||
<Text style={{ fontSize: ctx?.emojiSize }}>{item.emoji}</Text>
|
}) => {
|
||||||
</View>
|
if (item.slug !== 'blank_emoji')
|
||||||
</TouchableOpacity>
|
return (
|
||||||
);
|
<TouchableOpacity onPress={() => onPress(item)} style={styles.container}>
|
||||||
|
<View>
|
||||||
|
<Text style={{ fontSize: emojiSize }}>{item.emoji}</Text>
|
||||||
|
</View>
|
||||||
|
</TouchableOpacity>
|
||||||
|
);
|
||||||
|
else return <View style={styles.container} />;
|
||||||
};
|
};
|
||||||
|
|
||||||
const styles = StyleSheet.create({
|
const styles = StyleSheet.create({
|
||||||
|
Loading…
x
Reference in New Issue
Block a user