basic app

This commit is contained in:
2025-07-03 19:40:32 +05:00
commit 2a597df2d3
29 changed files with 17379 additions and 0 deletions

84
src/components/Button.js Normal file
View File

@@ -0,0 +1,84 @@
import React from 'react';
import { TouchableOpacity, Text, StyleSheet, ActivityIndicator } from 'react-native';
import { COLORS } from '../constants/colors';
const Button = ({
title,
onPress,
loading = false,
disabled = false,
variant = 'primary',
style,
textStyle
}) => {
const buttonStyles = [
styles.button,
styles[variant],
disabled && styles.disabled,
style,
];
const textStyles = [
styles.text,
styles[`${variant}Text`],
textStyle,
];
return (
<TouchableOpacity
style={buttonStyles}
onPress={onPress}
disabled={disabled || loading}
activeOpacity={0.8}
>
{loading ? (
<ActivityIndicator color={variant === 'primary' ? COLORS.white : COLORS.primary} />
) : (
<Text style={textStyles}>{title}</Text>
)}
</TouchableOpacity>
);
};
const styles = StyleSheet.create({
button: {
paddingVertical: 16,
paddingHorizontal: 24,
borderRadius: 12,
alignItems: 'center',
justifyContent: 'center',
minHeight: 52,
},
primary: {
backgroundColor: COLORS.primary,
},
secondary: {
backgroundColor: COLORS.backgroundSecondary,
borderWidth: 1,
borderColor: COLORS.gray[300],
},
outline: {
backgroundColor: 'transparent',
borderWidth: 1,
borderColor: COLORS.primary,
},
disabled: {
opacity: 0.5,
},
text: {
fontSize: 16,
fontWeight: '600',
textAlign: 'center',
},
primaryText: {
color: COLORS.textOnPrimary,
},
secondaryText: {
color: COLORS.textPrimary,
},
outlineText: {
color: COLORS.primary,
},
});
export default Button;

128
src/components/Input.js Normal file
View File

@@ -0,0 +1,128 @@
import React, { useState } from 'react';
import { View, TextInput, Text, StyleSheet, TouchableOpacity } from 'react-native';
import { Ionicons } from '@expo/vector-icons';
import { COLORS } from '../constants/colors';
const Input = ({
label,
value,
onChangeText,
placeholder,
secureTextEntry = false,
keyboardType = 'default',
error,
disabled = false,
leftIcon,
style,
returnKeyType = 'done',
onSubmitEditing,
...props
}) => {
const [isPasswordVisible, setIsPasswordVisible] = useState(false);
const [isFocused, setIsFocused] = useState(false);
const togglePasswordVisibility = () => {
setIsPasswordVisible(!isPasswordVisible);
};
return (
<View style={[styles.container, style]}>
{label && <Text style={styles.label}>{label}</Text>}
<View style={[
styles.inputContainer,
isFocused && styles.focused,
error && styles.error,
disabled && styles.disabled,
]}>
{leftIcon && (
<View style={styles.leftIconContainer}>
<Ionicons name={leftIcon} size={20} color={COLORS.gray[400]} />
</View>
)}
<TextInput
style={[styles.input, leftIcon && styles.inputWithLeftIcon]}
value={value}
onChangeText={onChangeText}
placeholder={placeholder}
placeholderTextColor={COLORS.gray[400]}
secureTextEntry={secureTextEntry && !isPasswordVisible}
keyboardType={keyboardType}
editable={!disabled}
onFocus={() => setIsFocused(true)}
onBlur={() => setIsFocused(false)}
returnKeyType={returnKeyType}
onSubmitEditing={onSubmitEditing}
{...props}
/>
{secureTextEntry && (
<TouchableOpacity
style={styles.eyeIcon}
onPress={togglePasswordVisibility}
>
<Ionicons
name={isPasswordVisible ? 'eye-off' : 'eye'}
size={20}
color={COLORS.gray[400]}
/>
</TouchableOpacity>
)}
</View>
{error && <Text style={styles.errorText}>{error}</Text>}
</View>
);
};
const styles = StyleSheet.create({
container: {
marginBottom: 20,
},
label: {
fontSize: 14,
fontWeight: '600',
color: COLORS.textPrimary,
marginBottom: 8,
},
inputContainer: {
flexDirection: 'row',
alignItems: 'center',
borderWidth: 1,
borderColor: COLORS.gray[300],
borderRadius: 12,
backgroundColor: COLORS.white,
paddingHorizontal: 16,
minHeight: 52,
},
focused: {
borderColor: COLORS.primary,
borderWidth: 2,
},
error: {
borderColor: COLORS.error,
},
disabled: {
backgroundColor: COLORS.gray[100],
opacity: 0.6,
},
leftIconContainer: {
marginRight: 12,
},
input: {
flex: 1,
fontSize: 16,
color: COLORS.textPrimary,
paddingVertical: 16,
},
inputWithLeftIcon: {
paddingLeft: 0,
},
eyeIcon: {
padding: 4,
},
errorText: {
fontSize: 12,
color: COLORS.error,
marginTop: 4,
},
});
export default Input;

21
src/components/Logo.js Normal file
View File

@@ -0,0 +1,21 @@
import React from 'react';
import { Image } from 'react-native';
const Logo = ({ width = 120, height = 120, style = {} }) => {
return (
<Image
source={require('../../resources/logo.png')} // You'll need to add logo.png to resources folder
style={[
{
width,
height,
resizeMode: 'contain',
marginBottom: 20,
},
style,
]}
/>
);
};
export default Logo;