使用 react-native-community/datetimepicker,如何在 Android 上显示日期时间选择器?

问题描述 投票:0回答:5

对于 iOS,库

react-native-community/datetimepicker
支持日期时间模式,在该模式下它显示日期和时间选择器。

但是,此模式不适用于 Android。

是否有显示 2 个连续选择器的解决方法,一个用于日期,另一个用于时间?

class ShiftTimingScreen extends Component {

    state = {
        dateTimePickerVisible: false, 
        dateOrTimeValue: new Date(), 
    };

    render() {
        return (
            <View>
                <TouchableOpacity
                    onPress={() => this.setState({ dateTimePickerVisible: true, })}
                >
                    <Input
                        label='Shift Starts At'
                        placeholder={"01/01/2019 - 09:00 AM"}
                        editable={false}
                        value={this.state.dateOrTimeValue.toLocaleDateString()}
                    />
                </TouchableOpacity>

                {this.state.dateTimePickerVisible &&
                    (<DateTimePicker
                        mode={"datetime"} // THIS DOES NOT WORK ON ANDROID. IT DISPLAYS ONLY A DATE PICKER.
                        display='default' // Android Only  
                        is24Hour={false} // Android Only 
                        value={defaultShiftStartDateTime}

                        onChange={(event, value) => {
                            this.setState({
                                dateOrTimeValue: value,
                                dateTimePickerVisible: Platform.OS === 'ios' ? true : false,
                            });

                            if (event.type === "set")
                                console.log("value:" , value);
                        }}
                    />)}
            </View>
        );
    } 
} 

export default ShiftTimingScreen;
react-native datetimepicker
5个回答
18
投票

我使用下面的代码来实现使用

react-native-community/datetimepicker
包的日期和时间选择。希望对您有所帮助。有关详细信息,请参阅此处

const [date, setDate] = useState(
  props.item.time ? new Date(props.item.time) : new Date() // to set default from props or current date
);
const [time, setTime] = useState(
  props.item.time ? new Date(props.item.time) : new Date() // to set default from props or current date
);
const [mode, setMode] = useState('date');
const [show, setShow] = useState(false);

const onChange = (event, selectedValue) => {
  setShow(Platform.OS === 'ios');
  if (mode == 'date') {
    const currentDate = selectedValue || new Date();
    setDate(currentDate);
    setMode('time');
    setShow(Platform.OS !== 'ios'); // to show time
  } else {
    const selectedTime = selectedValue || new Date();
    setTime(selectedTime);
    setShow(Platform.OS === 'ios'); // to hide back the picker
    setMode('date'); // defaulting to date for next open
  }
};
const showMode = currentMode => {
  setShow(true);
  setMode(currentMode);
};

const showDatePicker = () => {
  showMode('date');
};
return 
  (<View>
  <TouchableOpacity onPress={showDatePicker}>
    <Text style={styles.title}>{formatDate(date, time)}</Text>
  </TouchableOpacity>
  {show && (
    <DateTimePicker
      value={date}
      minimumDate={Date.parse(new Date())}
      display='default'
      mode={mode}
      onChange={onChange}
    />
  )}
  </View>);
  

const formatDate = (date, time) => {
return `${date.getDate()}/${date.getMonth() +
  1}/${date.getFullYear()} ${time.getHours()}:${time.getMinutes()}`;
};

9
投票

请在下面找到此限制的解决方法。

import React, { Component } from 'react';
import { TouchableOpacity, View } from 'react-native';
import { Input } from 'react-native-elements';

import DateTimePicker from '@react-native-community/datetimepicker';
import XDate from 'xdate'; 

class ShiftTimingScreen extends Component {
    state = {
        // The values, which we get from each of the DateTimePickers. 
        // These values can be saved into your app's state. 
        StartingDateTimeValue: null,
        ToDateValue: null,
        ToTimeValue: null,

        // for iOS & Android: When this flag is true, the relevant <DateTimePicker> is displayed
        isStartingDateTimePickerVisible: false,
        isToDatePickerVisible: false,
        isToTimePickerVisible: false,

        // The value of the <DateTimePicker> is stored in this variable, which is used to pass data between the date & time pickers 
        dateOrTimeValue: null, 

        // ONLY FOR ANDROID: note that the current version of the <DateTimePicker> does NOT support "datetime" mode on Android.
        // So, I am using the following 2 flags (datePickerVisible & timePickerVisible) to provide this functionality.

        // (1) ONLY FOR ANDROID: When the datePickerVisible flag is true, the <DateTimePicker> is displayed in "date" mode
        datePickerVisible: false, 

        // (2) ONLY FOR ANDROID: When the timePickerVisible flag is true, the <DateTimePicker> is displayed in "time" mode
        timePickerVisible: false,
    };


    saveStartingDateTime = (value) => { 
        console.log("saveStartingDateTime - value:", value); 
        this.setState({
            StartingDateTimeValue: value,
        });
    }; 

    saveEndingDate = (value) => { 
        console.log("saveEndingDate - value:", value);
        this.setState({
            ToDateValue: value,
        });
    }; 

    saveEndingTime = (value) => {
        console.log("saveEndingTime - value:", value);
        this.setState({
            ToTimeValue: value,
        });
    };

    fRenderDateTimePicker = (dateTimePickerVisible, visibilityVariableName, dateTimePickerMode, defaultValue, saveValueFunctionName ) => {
        // dateTimePickerVisible:   a flag, which is used to show/hide this DateTimePicker
        // visibilityVariableName:              the name of the state variable, which controls showing/hiding this DateTimePicker. 
            // The name of the variable is received in (visibilityVariableName), and the value of it is received in the argument (dateTimePickerVisible).
        // dateTimePickerMode:      the mode mode of this DateTimePicker
        // defaultValue:                the default value, which should be selected initially when the DatTimePicker is displayed 
        // saveValueFunctionName:   the function, which would be called after the user selects a value. 
            // In my case it is a Redux's action creator, which saves the selected value in the app's state. 

        return (
            <View>
                {/* A. For iOS, display the picker in "date", "time" or "datetime" mode - No need for any customisation */}
                {Platform.OS === 'ios' && dateTimePickerVisible &&
                    (<DateTimePicker
                        mode={dateTimePickerMode}
                        value={defaultValue}

                        onChange={ (event, value) => {
                            this.setState({
                                dateOrTimeValue: value,

                                // We are done. Hide the <DatTimePicker>
                                // Technically speaking, since this part of the script is only relevant to a certain platform, I don't need to check for the platform (below). 
                                // Note that [visibilityVariableName] refers to the NAME of a state variable
                                [visibilityVariableName]: Platform.OS === 'ios' ? true : false,
                            });

                            if (event.type === "set") {
                                saveValueFunctionName(value);
                                // console.log("visibilityVariableName:", [visibilityVariableName], " - value:", value); 
                            }

                        }}
                    />)}

                {/* B.1 For Android - "date" mode:      display the picker in "date" mode */}
                {/*       For Android - "datetime" mode: display the picker in "date" mode (to be followed by another picker (below) in "time" mode) */}
                {Platform.OS === 'android' && dateTimePickerVisible && this.state.datePickerVisible &&
                    (<DateTimePicker
                        mode={"date"}
                        display='default' // 'default', 'spinner', 'calendar', 'clock' // Android Only 
                        value={defaultValue}

                        onChange={ (event, value) => {
                            this.setState({
                                // In case of (mode == datetime), the TIME part will be added to "dateOrTimeValue" using another DateTimePicker (below).
                                dateOrTimeValue: value,
                                datePickerVisible: false,
                            });

                            // When the mode is "datetime" & this picker was set (the user clicked on OK, rather than cancel), 
                            // we need to display another DateTimePicker in TIME mode (below) 
                            if (event.type === "set" && dateTimePickerMode === "datetime") {
                                this.setState({
                                    timePickerVisible: true,
                                });
                            }

                            // When the mode is "date" & this picker was set (the user clicked on OK, rather than cancel), 
                            // (1) We need to hide this picker. 
                            // (2) Save the data. Otherwise, do nothing. Date will be saved after the TIME picker is launched (below). 
                            else if (event.type === "set" && dateTimePickerMode === "date") {
                                // console.log("saveValueFunctionName: ", saveValueFunctionName); 
                                this.setState({ 
                                    [visibilityVariableName]: Platform.OS === 'ios' ? true : false, 
                                }); 

                                saveValueFunctionName(value);
                                // console.log("visibilityVariableName:", [visibilityVariableName], " - value:", value); 
                            }

                        }}
                    />)}

                {/* B.2 For Android - "time" mode:      display the picker in "time" mode */}
                {/*       For Android - "datetime" mode: display the picker in "time" mode (following another picker (above) in "date" mode) */}
                {Platform.OS === 'android' && dateTimePickerVisible && this.state.timePickerVisible &&
                    (<DateTimePicker
                        mode={"time"}
                        display='spinner' // 'default', 'spinner', 'calendar', 'clock' // Android Only 
                        is24Hour={false} // Android Only 
                        value={defaultValue}

                        onChange={(event, value) => {
                            // 1. In case of (mode == "time"), (value) is assigned to (newDateTime), which will be used below (as is with no additions)
                            let newDateTime = value;

                            // 2. In case of (mode == "datetime"), 
                            if (event.type === "set" && dateTimePickerMode === "datetime") {

                                // 2.1. Get the (date) part from the previously displayed DATE picker, which saved its value into (this.state.dateValue)
                                newDateTime = this.state.dateOrTimeValue;

                                // 2.2. Get the (hours & minutes) parts from this TIME Picker, which saved its value into (value) 
                                const newHours = value.getHours();
                                const newMinutes = value.getMinutes();

                                // 2.3 Combine 2.1 & 2.2 (above) into (newDateTime).
                                newDateTime.setHours(newHours);
                                newDateTime.setMinutes(newMinutes);
                                newDateTime.setSeconds(0);
                            }

                            this.setState({
                                dateOrTimeValue: newDateTime,
                                datePickerVisible: false,
                                timePickerVisible: false,

                                // We are done. Hide the <DatTimePicker>
                                // Technically speaking, since this part of the script is only relevant to a certain platform, I don't need to check for the platform (below). 
                                [visibilityVariableName]: Platform.OS === 'ios' ? true : false,
                            });

                            if (event.type === "set") {
                                saveValueFunctionName(newDateTime);
                                // console.log("visibilityVariableName:", [visibilityVariableName], " - newDateTime:", newDateTime); 
                            } 
                        }}

                    />)} 
            </View>
        );      
    }; 

    // This function formats date values. Obviously, using it is optional. 
    // If you decide to use it, remember that it needs the XDate library: 
    // import XDate from 'xdate';
    fFormatDateTime = (date1, format1 = "datetime") => {
        // date1:   the date to be formatted 
        // format1: the date mode - "datetime" , "date" OR "time"
        if (date1 === null) {
            return null;
        }

        // else:
        const format2 = format1.toLowerCase();
        let dateFormatted;
        const date2 = new XDate(date1);

        switch (format2) {
            case "datetime": {
                dateFormatted = date2.toString('dd/MM/yyyy - hh:mm TT');
                return dateFormatted;
            }
            case "date": {
                dateFormatted = date2.toString('dd/MM/yyyy');
                return dateFormatted;
            }
            case "time": {
                dateFormatted = date2.toString('hh:mm TT');
                return dateFormatted;
            }
            default:
                return null;
        } 
    };

    // This function shows/hides the initial DateTimePicker 
    // If the mode is "datetime", another picker will be displayed by the DATE picker 
    fRenderDatePicker = (mode, visibilityVariableName) => {
        // mode:                        specifies the mode of the <DateTimePicker> 
        // visibilityVariableName:  the name of the state variable, which controls showing/hiding this DateTimePicker. 
        switch (mode) {
            case "datetime":
                return this.setState({ [visibilityVariableName]: true, datePickerVisible: true, timePickerVisible: false });
            case "date":
                return this.setState({ [visibilityVariableName]: true, datePickerVisible: true, timePickerVisible: false });
            case "time":
                return this.setState({ [visibilityVariableName]: true, datePickerVisible: false, timePickerVisible: true });
        }
    }

    render() {
        // 1. For the "Shift Start", Initial/Default value for the DateTimePicker 
        // // defaultShiftStartDateTime: (tomorrow's date at 9 AM)
        let defaultShiftStartDateTime = new Date();
        defaultShiftStartDateTime.setDate(defaultShiftStartDateTime.getDate() + 1);
        defaultShiftStartDateTime.setHours(9);
        defaultShiftStartDateTime.setMinutes(0);
        defaultShiftStartDateTime.setSeconds(0);

        // 2. For the "Shift End", Initial/Default value for the DateTimePicker 
        let defaultShiftEndDateTime = new Date();
        defaultShiftEndDateTime.setDate(defaultShiftEndDateTime.getDate() + 1);
        defaultShiftEndDateTime.setHours(17);
        defaultShiftEndDateTime.setMinutes(0);
        defaultShiftEndDateTime.setSeconds(0);

        return (
                <View>
                    <TouchableOpacity
                        // THE FOLLOWING ARGUMENT VALUE IS THE (1st place OF 2) PLACES, WHICH DIFFERENTIATE BETWEEN THE DIFFERENT MODES (DATETIME, DATE & TIME)
                        onPress={() => {
                            // this.setState({ isStartingDateTimePickerVisible: true, });
                            this.fRenderDatePicker("datetime", "isStartingDateTimePickerVisible");
                        }}>
                        <Input
                            label='Starting Date & Time'
                            placeholder={"01/01/2019 - 09:00 AM"}
                            editable={false}
                            value={this.fFormatDateTime(this.state.StartingDateTimeValue)}
                        />
                    </TouchableOpacity>

                    {// This function would render the necessary DateTimePicker only if the relevant state variable is set (above)
                    this.fRenderDateTimePicker(
                        this.state.isStartingDateTimePickerVisible,
                        "isStartingDateTimePickerVisible",

                        // THE FOLLOWING ARGUMENT VALUE IS THE (2nd place OF 2) PLACES, WHICH DIFFERENTIATE BETWEEN THE DIFFERENT MODES (DATETIME, DATE & TIME)
                        "datetime",

                        defaultShiftStartDateTime,

                        // This is my function, which saves the selected value to my app's state. 
                        // YOU NEED TO REPLACE IT WITH SOMETHING RELEVANT TO YOUR APP. 
                        this.saveStartingDateTime,
                    )}


                    <TouchableOpacity
                        onPress={() => {
                            // this.setState({ isToDatePickerVisible: true, });
                            this.fRenderDatePicker("date", "isToDatePickerVisible");
                        }}>
                        <Input
                            label='Ending Date'
                            placeholder={"01/01/2019"}
                            editable={false}
                            value={this.fFormatDateTime(this.state.ToDateValue, "date")}
                        />
                    </TouchableOpacity>
                    {this.fRenderDateTimePicker(
                        this.state.isToDatePickerVisible,
                        "isToDatePickerVisible",
                        "date",
                        defaultShiftEndDateTime,

                        // This is my function, which saves the selected value to my app's state. 
                        // YOU NEED TO REPLACE IT WITH SOMETHING RELEVANT TO YOUR APP. 
                        this.saveEndingDate,
                    )}

                    <TouchableOpacity
                        onPress={() => {
                            // this.setState({ isToTimePickerVisible: true, });
                            this.fRenderDatePicker("time", "isToTimePickerVisible");
                        }}>
                        <Input
                            label='Ending Time'
                            placeholder={"09:00 AM"}
                            editable={false}
                            value={this.fFormatDateTime(this.state.ToTimeValue, "time")}
                        />
                    </TouchableOpacity>
                    {this.fRenderDateTimePicker(
                        this.state.isToTimePickerVisible,
                        "isToTimePickerVisible",
                        "time",
                        defaultShiftEndDateTime,

                        // This is my function, which saves the selected value to my app's state. 
                        // YOU NEED TO REPLACE IT WITH SOMETHING RELEVANT TO YOUR APP. 
                        this.saveEndingTime,
                    )}
                </View>
        );
    } // end of: render()
} // end of: component

export default ShiftTimingScreen;


3
投票
import React, {Component} from 'react';
import {View, Button, Platform} from 'react-native';
import DateTimePicker from '@react-native-community/datetimepicker';

export default class App extends Component {
  state = {
    date: new Date('2020-06-12T14:42:42'),
    mode: 'date',
    show: false,
  }

  setDate = (event, date) => {
    date = date || this.state.date;

    this.setState({
      show: Platform.OS === 'ios' ? true : false,
      date,
    });
  }

  show = mode => {
    this.setState({
      show: true,
      mode,
    });
  }

  datepicker = () => {
    this.show('date');
  }

  timepicker = () => {
    this.show('time');
  }

  render() {
    const { show, date, mode } = this.state;

    return (
      <View>
        <View>
          <Button onPress={this.datepicker} title="Show date picker!" />
        </View>
        <View>
          <Button onPress={this.timepicker} title="Show time picker!" />
        </View>
        { show && <DateTimePicker value={date}
                    mode={mode}
                    is24Hour={true}
                    display="default"
                    onChange={this.setDate} />
        }
      </View>
    );
  }
}

1
投票

你可以简单地用命令式api来做

import { DateTimePickerAndroid } from '@react-native-community/datetimepicker';




const Demo () => {
  const [date, setDate] = useState<Date>(new Date());

  const openDatePickHandler:VoidFunction = () => {
    DateTimePickerAndroid.open({
      mode: 'date',
      value: date,
      onChange: (event, newDate) => {
        if (newDate) {
          DateTimePickerAndroid.open({
            mode: 'time',
            value: newDate,
            onChange: (_, newDateTime) => {
              if (newDateTime) {
                setDate(newDateTime);              
              }
            },
          });
        }
      },
    });
  };

  return(
    <>
      <Text>{date.getTime()}</Text>
      <Button title="click for change" onPress={openDatePickHandler} />
    </>
  )

}


0
投票
 Use This code for date picker in react native

 import DateTimePickerModal from 'react-native-modal-datetime-picker';


 const App()=>{

  const [isDatePickerVisible, setDatePickerVisibility] =useState(false);
  const [date, setDate] = useState();
  const showDatePicker = () => {
   setDatePickerVisibility(true);
 };


const hideDatePicker = () => {
 setDatePickerVisibility(false);
 };

 const handleConfirm = data => {
  setDate(data.toLocaleDateString());
   hideDatePicker();

  };

 <DateTimePickerModal
    isVisible={isDatePickerVisible}
    mode="date"
    onConfirm={handleConfirm}
    onCancel={hideDatePicker}
  />
 }
© www.soinside.com 2019 - 2024. All rights reserved.