Фокусный стиль для TextInput в реагировании
В React Native, как вы изменяете стиль textInput
когда он получает фокус? Скажи у меня что то типа
class MyInput extends Component {
render () {
return <TextInput style={styles.textInput} />;
}
};
const stylesObj = {
textInput: {
height: 50,
fontSize: 15,
backgroundColor: 'yellow',
color: 'black',
}
};
const styles = StyleSheet.create(stylesObj);
И я хочу изменить цвет фона на фокусе на green
.
Эта документация заставляет меня поверить, что решение является чем-то вроде
class MyInput extends Component {
constructor (props) {
super(props);
this.state = {hasFocus: false};
}
render () {
return (<TextInput
style={this.state.hasFocus ? styles.focusedTextInput : styles.textInput}
onFocus={this.setFocus.bind(this, true)}
onBlur={this.setFocus.bind(this, false)}
/>);
}
setFocus (hasFocus) {
this.setState({hasFocus});
}
};
const stylesObj = {
textInput: {
height: 50,
fontSize: 15,
backgroundColor: 'yellow',
color: 'black',
}
};
const styles = StyleSheet.create({
...stylesObj,
focusedTextInput: {
...stylesObj,
backgroundColor: 'green',
}
});
Игнорируя потенциальные ошибки в структурировании стилей, будет ли это правильным решением? Это кажется мне очень многословным.
Ответы
Ответ 1
Вы можете добиться этого, передав события onFocus и onBlur для установки и отмены стилей при фокусировке и размытии:
onFocus() {
this.setState({
backgroundColor: 'green'
})
},
onBlur() {
this.setState({
backgroundColor: '#ededed'
})
},
И затем в TextInput выполните следующее:
<TextInput
onBlur={ () => this.onBlur() }
onFocus={ () => this.onFocus() }
style={{ height:60, backgroundColor: this.state.backgroundColor, color: this.state.color }} />
Я создал полный рабочий проект здесь. Надеюсь, это поможет!
https://rnplay.org/apps/hYrKmQ
'use strict';
var React = require('react-native');
var {
AppRegistry,
StyleSheet,
Text,
View,
TextInput
} = React;
var SampleApp = React.createClass({
getInitialState() {
return {
backgroundColor: '#ededed',
color: 'white'
}
},
onFocus() {
this.setState({
backgroundColor: 'green'
})
},
onBlur() {
this.setState({
backgroundColor: '#ededed'
})
},
render: function() {
return (
<View style={styles.container}>
<TextInput
onBlur={ () => this.onBlur() }
onFocus={ () => this.onFocus() }
style={{ height:60, backgroundColor: this.state.backgroundColor, color: this.state.color }} />
</View>
);
}
});
var styles = StyleSheet.create({
container: {
flex: 1,
marginTop:60
}
});
AppRegistry.registerComponent('SampleApp', () => SampleApp);
Ответ 2
Nader Dabit указал мне сделать что-то подобное - используя состояние для стилей - но я думаю, что это можно сделать чище, если вы создали отдельные стили для сфокусированного и не сфокусированного стиля и передали только идентификатор стиля следующим образом:
getInitialState() {
return { style: styles.textinput_unfocused }
}
onFocus() {
this.setState({ style: styles.textinput_focused })
}
onBlur() {
this.setState({ style: styles.textinput_unfocused })
}
в render - ссылка по идентификатору styleID в this.state.style
, обратите внимание, как разные стили передаются как массив:
<TextInput
onBlur={ () => this.onBlur() }
onFocus={ () => this.onFocus() }
style={ [styles.textinput, this.state.style] } />
+ Ваша таблица стилей по меню:
textinput_focused: {
backgroundColor: 'red',
color: 'white'
}
textinput_unfocused: {
backgroundColor: 'green'
}
Ответ 3
Используйте refs, DirectManipulation и setNativeProps для большей производительности: https://facebook.github.io/react-native/docs/direct-manipulation.
class MyInput extends Component {
focusedInput = () => {
this.textInput.setNativeProps({
style: { backgroundColor: 'green' }
})
}
blurredInput = () => {
this.textInput.setNativeProps({
style: { backgroundColor: 'yellow' }
})
}
render () {
return <TextInput
ref={c => { this.textInput = c}}
style={styles.textInput}
onFocus={this.focusedInput}
onBlur={this.blurredInput} />
}
}
const stylesObj = { ввод текста: { высота: 50, fontSize: 15, backgroundColor: "желтый", черный цвет', } }
const styles = StyleSheet.create(stylesObj)
Это обновляет компонент TextInput напрямую, без повторного рендеринга иерархии компонентов.
Ответ 4
Эй, ребята, я вроде использовал идею всякого: р
@Феликс дал мне идею, которая может быть даже чище. (Хотелось бы, чтобы в этом статическом компоненте не было включено состояние, просто чтобы изменить стиль... Но я новичок в этом, чтобы понять это.
вот мое решение:
import React, { Component } from 'react';
import { StyleSheet, TextInput } from 'react-native';
class TxtInput extends Component {
constructor(props) {
super(props);
this.state = {
style: {},
};
}
onFocus = () => {
const state = { ...this.state };
state.style = {
borderStyle: 'solid',
borderColor: '#e74712',
};
this.setState(state);
}
onBlur = () => {
console.log('on ONBLUR')
const state = { ...this.state };
state.style = {};
this.setState(state);
}
render = () => <TextInput style={[styles.input, this.state.style]} onFocus={() => this.onFocus()} onBlur={() => this.onBlur()} />;
}
const styles = StyleSheet.create({
input: {
color: '#000000',
fontFamily: 'MuseoSans 700 Italic',
fontSize: 22,
borderRadius: 34,
borderStyle: 'solid',
borderColor: 'transparent',
borderWidth: 5,
backgroundColor: '#ffffff',
textAlign: 'center',
width: '25%',
},
});
export default TxtInput;
Я добавил стиль в массив, чтобы все фактические стили ввода были выполнены для первого свойства массива, а для второго - выделения фокуса и синего цвета.
Надеюсь, поможет
Ответ 5
<TextInput
style={{ backgroundColor: 'white', height: 40, width: 100, alignItems: 'center'
}}
theme={{ colors: { placeholder: 'white', text: 'white', primary: 'white',
underlineColor: 'transparent', background: '#003489' } }}
/>