extract the button to its own component; start text animations

This commit is contained in:
Pablo Velez Vidal 2022-10-27 18:05:52 +02:00
parent 50b832fbad
commit f4abc5a20f
4 changed files with 105 additions and 69 deletions

View file

@ -0,0 +1,91 @@
// Copyright (c) 2015-present Mattermost, Inc. All Rights Reserved.
// See LICENSE.txt for license information.
import React from 'react';
import {View} from 'react-native';
import Button from 'react-native-button';
import CompassIcon from '@app/components/compass_icon';
import FormattedText from '@app/components/formatted_text';
import {buttonBackgroundStyle, buttonTextStyle} from '@utils/buttonStyles';
import {makeStyleSheetFromTheme} from '@utils/theme';
type Props = {
theme: Theme;
isLastSlide: boolean;
nextSlideHandler: any;
signInHandler: any;
};
const getStyleSheet = makeStyleSheetFromTheme((theme: Theme) => ({
button: {
marginTop: 5,
},
rowIcon: {
color: theme.buttonColor,
fontSize: 12,
marginLeft: 5,
marginTop: 2,
},
}));
const FooterButtons = ({
theme,
nextSlideHandler,
signInHandler,
isLastSlide,
}: Props) => {
const styles = getStyleSheet(theme);
let mainButtonText = (
<View style={{flexDirection: 'row'}}>
<FormattedText
id='mobile.onboarding.next'
defaultMessage='Next'
style={buttonTextStyle(theme, 'm', 'primary', 'default')}
/>
<CompassIcon
name='arrow-forward-ios'
style={styles.rowIcon}
/>
</View>
);
let mainButtonAction = nextSlideHandler;
if (isLastSlide) {
mainButtonText = (
<FormattedText
id='mobile.onboarding.sign_in_to_get_started'
defaultMessage='Sign in to get started'
style={buttonTextStyle(theme, 's', 'primary', 'default')}
/>
);
mainButtonAction = signInHandler;
}
return (
<View style={{flexDirection: 'column', height: 150, marginTop: 15, width: '100%', marginHorizontal: 10, alignItems: 'center'}}>
<Button
testID='mobile.onboaring.next'
onPress={() => mainButtonAction()}
containerStyle={[styles.button, buttonBackgroundStyle(theme, 'm', 'primary', 'default'), {width: isLastSlide ? '90%' : 80}]}
>
{mainButtonText}
</Button>
<Button
testID='mobile.onboaring.sign_in'
onPress={() => signInHandler()}
containerStyle={[styles.button, buttonBackgroundStyle(theme, 'm', 'link', 'default')]}
>
<FormattedText
id='mobile.onboarding.sign_in'
defaultMessage='Sign in'
style={buttonTextStyle(theme, 's', 'primary', 'inverted')}
/>
</Button>
</View>
);
};
export default FooterButtons;

View file

@ -15,6 +15,7 @@ import SlideItem from './slide';
import slidesData from './slides_data';
import type {LaunchProps} from '@typings/launch';
import FooterButtons from './footer_buttons';
interface OnboardingProps extends LaunchProps {
theme: Theme;
@ -34,18 +35,13 @@ const Onboarding = ({
const nextSlide = () => {
const nextSlideIndex = currentIndex + 1;
if (slidesRef.current && currentIndex < lastSlideIndex) {
console.log('*** current slide', currentIndex);
console.log('*** next slide', nextSlideIndex);
moveToSlide(nextSlideIndex);
} else {
console.log('*** end of slide', lastSlideIndex);
}
};
const moveToSlide = (slideIndexToMove: number) => {
if (slideIndexToMove === lastSlideIndex) {
setIsLastSlide(true);
}
setIsLastSlide(slideIndexToMove === lastSlideIndex);
setCurrentIndex(slideIndexToMove);
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
// @ts-ignore
slidesRef?.current?.scrollToIndex({index: slideIndexToMove});
@ -67,6 +63,7 @@ const Onboarding = ({
<SlideItem
item={i}
theme={theme}
scrollX={scrollX}
/>
);
}, []);
@ -75,6 +72,7 @@ const Onboarding = ({
const viewableItemsChanged = useRef(({viewableItems}: any) => {
setCurrentIndex(viewableItems[0].index);
setIsLastSlide(viewableItems[0].index === lastSlideIndex);
}).current;
const viewConfig = useRef({viewAreaCoveragePercentThreshold: 50}).current;
@ -89,7 +87,7 @@ const Onboarding = ({
key={'onboarding_content'}
style={[styles.scrollContainer, transform]}
>
<FlatList
<Animated.FlatList
keyExtractor={(item) => item.id}
data={slidesData}
renderItem={renderSlide}
@ -99,7 +97,7 @@ const Onboarding = ({
pagingEnabled={true}
bounces={false}
onScroll={Animated.event([{nativeEvent: {contentOffset: {x: scrollX}}}], {
useNativeDriver: false,
useNativeDriver: true,
})}
onViewableItemsChanged={viewableItemsChanged}
viewabilityConfig={viewConfig}
@ -111,10 +109,13 @@ const Onboarding = ({
data={slidesData}
theme={theme}
scrollX={scrollX}
moveToSlide={moveToSlide}
/>
<FooterButtons
theme={theme}
isLastSlide={isLastSlide}
nextSlideHandler={nextSlide}
signInHandler={signInHandler}
moveToSlide={moveToSlide}
/>
</View>
);

View file

@ -3,20 +3,13 @@
import React from 'react';
import {View, Animated, useWindowDimensions, TouchableOpacity} from 'react-native';
import Button from 'react-native-button';
import CompassIcon from '@app/components/compass_icon';
import FormattedText from '@app/components/formatted_text';
import {buttonBackgroundStyle, buttonTextStyle} from '@utils/buttonStyles';
import {changeOpacity, makeStyleSheetFromTheme} from '@utils/theme';
type Props = {
data: any;
theme: Theme;
scrollX: any;
isLastSlide: boolean;
nextSlideHandler: any;
signInHandler: any;
moveToSlide: any;
};
@ -49,43 +42,13 @@ const Paginator = ({
theme,
data,
scrollX,
nextSlideHandler,
signInHandler,
moveToSlide,
isLastSlide,
}: Props) => {
const styles = getStyleSheet(theme);
const {width} = useWindowDimensions();
let mainButtonText = (
<>
<FormattedText
id='mobile.onboarding.next'
defaultMessage='Next'
style={buttonTextStyle(theme, 'm', 'primary', 'default')}
/>
<CompassIcon
name='arrow-forward-ios'
style={styles.rowIcon}
/>
</>
);
let mainButtonAction = nextSlideHandler;
if (isLastSlide) {
mainButtonText = (
<FormattedText
id='mobile.onboarding.sign_in_to_get_started'
defaultMessage='Sign in to get started'
style={buttonTextStyle(theme, 'm', 'primary', 'default')}
/>
);
mainButtonAction = signInHandler;
}
return (
<View style={{flexDirection: 'column', height: 150}}>
<View style={{flexDirection: 'column', height: 10}}>
<View style={{flexDirection: 'row', height: 5}}>
{data.map((item: any, i: number) => {
const inputRange = [(i - 1) * width, i * width, (i + 1) * width];
@ -116,26 +79,6 @@ const Paginator = ({
);
})}
</View>
<View style={{marginTop: 15}}>
<Button
testID='mobile.onboaring.next'
onPress={() => mainButtonAction()}
containerStyle={[styles.button, buttonBackgroundStyle(theme, 'lg', 'primary', 'default')]}
>
{mainButtonText}
</Button>
<Button
testID='mobile.onboaring.sign_in'
onPress={() => signInHandler()}
containerStyle={[styles.button, buttonBackgroundStyle(theme, 'lg', 'link', 'default')]}
>
<FormattedText
id='mobile.onboarding.sign_in'
defaultMessage='Sign in'
style={buttonTextStyle(theme, 'm', 'primary', 'inverted')}
/>
</Button>
</View>
</View>
);
};

View file

@ -10,6 +10,7 @@ import {typography} from '@utils/typography';
type Props = {
item: any;
theme: Theme;
scrollX: any;
};
const getStyleSheet = makeStyleSheetFromTheme((theme: Theme) => ({
@ -43,7 +44,7 @@ const getStyleSheet = makeStyleSheetFromTheme((theme: Theme) => ({
},
}));
const SlideItem = ({theme, item}: Props) => {
const SlideItem = ({theme, item, scrollX}: Props) => {
const {width} = useWindowDimensions();
const styles = getStyleSheet(theme);
const SvgImg = item.image;