Why won't my placeholder show up properly? (react-native-datepicker) - javascript

I'm having a really hard time getting a placeholder to show up properly in this datepicker package I'm using for react native...
Here's how I have the component setup:
The _onDateChange function:
const _onDateChange = (startTime) => {
pickDate(props.setPatrolStartTime, startTime)
this.setState({startTime: props.setPatrolStartTime})
}
The datepicker component:
<DatePicker
//date={props.startTime}
mode="datetime"
iconComponent={ <Icon name='chevron-down' type='font-awesome' color='green'/> }
style={ styles.datePickerStyle }
placeholder={`Select Start Time`}
confirmBtnText='Confirm'
cancelBtnText='Cancel'
customStyles={{
dateInput:{
borderWidth: 0,
},
dateText: {
color: 'white',
textAlign: 'left',
fontSize: 20
},
}}
onDateChange={this._onDateChange(props.startTime) }
/>
Expected behavior: I thought it would show the placeholder until I changed the date, but it would not show the placeholder until I commented out the date prop, and after googling and searching stackoverflow for a while, I saw various posts, some saying that I need to bind the onDateChange prop, and some requesting that I make a separate onDateChange function and call it from the prop.
Actual behavior:
I can't seem to figure out how to bind it, and when I try to call it as shown above, it red screens, saying that undefined is not a function, referencing _onDateChange. When I try to use the placeholder prop, the placeholder will not show unless I comment out the date prop, and when I do that, it shows the placeholder, except when I set the date, the placeholder doesn't change to the date I set.
At this point, I can't really figure out what I'm doing wrong. Can anyone give me some input?
Thanks!

Try to use placeholderText instead of placeholder
You can get reference from here

You have used backticks instead of normal quotes, it should be
placeholder="Select start time"
You can check the example on github https://github.com/xgfe/react-native-datepicker

placeholder does not take an object, however, it takes a string like this:
placeholder="select date"
not like this:
placeholder={"select date"}
also, the placeholder value only shows up when this.props.date is false

Seems to be a bug in the library, and it hasn't been updated in a year. If you want to prevent the current date from showing up by using a placeholder, you will need to set placeholder to be a non-empty string and it should work.
The input value still needs to be falsy for the placeholder to appear (e.g. an empty string as date/time).

Update 2022,
there still is a bug trying to display a placeholder, the work around I found is to use the customInput to return a div and use the ::after CSS pseudoelement to insert whatever text you like

Related

Im using AntD components library. i have 2 <Form.List> nested inside another <Form.List> and im having trouble to setFieldsValue to nested inputs

I've created a reproducable example. Here is the link: https://codesandbox.io/s/size-antd-5-1-6-forked-315hum?file=/demo.tsx
So i have to set the fields value, but the last nested
<Form.List name={[concatenationName, "options"]}>
is kind of bugged. Because if we watch the logs, the value is set properly. But the value is not rendered in the input.
Here is how it´s rendered:
And here are the values that shows the form watcher:
What im expecting is that those options, actually shows the value of the input. It's like it gets the value, but it doesnt render the value. I had no problems with other <Form.List>, but this one seems to be kind of bugged.
Any suggestions why is not rendering the value in the input. And why all the other inputs, when i do the setFieldsValue.
I've added a DEBUG button to do easier debugging. It basically setFieldsValue to all inputs, and with it we can see how the last nested inputs dont render its value, but other inputs do render the value.
I found the error, and it was <Form.Item></Form.Item> not wrapping directly the input, so it wasnt able to set the value
<Form.Item
{...concatenationOptionRestField}
name={[concatenationOptionsName, 'content']}
rules={[
{
required: true,
message: 'Porfavor complete el campo',
},
]}
>
<Input
style={{
width: '100%',
}}
placeholder="Ingresa opción de respuesta"
/>
</Form.Item>

How to use setTimeout in react for if statement?

I like to use only placeholder without label for inputs/forms. Therefore i created a onClick -> set type from text to date.
But if someone has a bad memory and dont know what date to fill in, I created a onMouseleave -> set type from date to text, if its empty.
But if someone want to fill his birthday and the mouse leaves accendently, they will give me a text instead of a date.
Therefore I want to use a setTmeout but it doesn't work as planned.
const [type, setType] = useState("text")
const handleDate = () => {
setType("date")
}
const handleText = () =>{
if(values.birthday === ""){
setType("text")}
}
<input
onChange={handleChange}
value={values.birthday}
type={type}
name="birthday"
placeholder="birthday"
onClick={handleDate}
onMouseLeave={setTimeout(handleText, 3000)}/>
by using onMouseLeave={setTimeout(handleText, 3000)}/> the input field is deselected and i can't type anything in.
I want that the if-query will be checked after 3 seconds and am able to type something in
try this:
<input
onChange={handleChange}
value={values.birthday}
type={type}
name="birthday"
placeholder="birthday"
onClick={handleDate}
onMouseLeave={() => setTimeout(handleText, 3000)}/>
the way you're doing currently it is immediately calling the setTimeout on render, you need to put it as a function
This is very weird UX design, I doubt your users will like it. No one expects that moving the mouse out of the input would replace the contents of the input a few seconds later. And did you consider that people may use a touch screen? Or move to the next input with the Tab key?
How about using a more conventional UX, for example title if you don't want labels?

timepicker: how to change the time with the keyboard

i am using boostrap timepicker : https://bootstrap-vue.org/docs/components/form-timepicker#form-timepicker
I entered this code:
<b-form-timepicker
v-model="timeSlot.timeStart"
minutes-step="15"
#input="getCurrentTime(timeSlot)"
></b-form-timepicker>
I can't find a method that can make me change the time via the pc keyboard
You could use button-only mode and add an input where you type time :
<b-input-group class="mb-3">
<b-form-input
id="example-input"
v-model="timeSlot.timeStart"
type="text"
placeholder="HH:mm:ss"
></b-form-input>
<b-input-group-append>
<b-form-timepicker
v-model="timeSlot.timeStart"
button-only
right
show-seconds
locale="en"
aria-controls="example-input"
></b-form-timepicker>
</b-input-group-append">
</b-input-group>
The documentation says the following:
always returns a string in the format of 'HH:mm:ss' which is the same format returned by native browser controls. The value will be in the range of '00:00:00' up to '23:59:59' (24-hour clock using the 'h23' hour cycle syntax). If no time is selected, then returns an empty string ('').
https://bootstrap-vue.org/docs/components/form-timepicker#form-timepicker
So you need to implement something which only edits the value in timeslot.timeStart by keyboard. For an easy example you could add another simple input-field and also give it timeslot.timeStart as v-model.
<input type="text" v-model="timeslot.timeStart" />
You should see your b-form-timepicker change if you change the value in the input-field and other way round. After you have understood this, it should be easy to implement some base event-handlers, which changes your timeSlot.timeStart while having your b-form-timepicker in focus, based on your keyboard input.
You can find an example for that in the documentation:
https://bootstrap-vue.org/docs/components/form-timepicker#button-only-mode

Material UI Autocomplete component not showing values from react state

I am trying to get value from the state for materialUI's autocomplete component.
I am facing the following problem : -
Autocomplte working fine for selecting the value and with onChange function it saving it into the state too.
But when I refresh my page/ re-render it is not showing value on the textfeild(from saved state):
<Autocomplete
name={"TideLocation"}
disabled={p.disabled}
options={data_source}
getOptionLabel={option => option.text}
inputValue={this.state.tidelocation_searchtext}
onChange={_this.handleUpdateTideLocationField}
onNewRequest={_this.handleChangeTideLocation}
onBlur={_this.handleBlurTideLocationField}
onUpdateInput={_this.handleUpdateTideLocationField}
renderInput={(params) => (
<TextField className="autoCompleteTxt"{...params} label="Location" />
)}
/>
I tried with the debugger and found its getting value in this.state.tidelocation_searchtext
but failed to set it with params.
Thanks in advance !!
Ps: I tried with defaultValue and search text nothing worked for me
following is my ONchangeFunction
handleUpdateTideLocationField = (str, value) => {
debugger
this.setState({tidelocation_searchtext: value.text});
}
after selecting a value,following value saved in sate :
tidelocation_searchtext: "Auckland"
So I found the solution all by myself by doing research and several hit and try, following is the solution of my problem:
<Autocomplete
name={"TideLocation"}
disabled={p.disabled}
options={data_source.map(option=>option.text)}
defaultValue={this.state.tidelocation_searchtext}
onChange={_this.handleUpdateTideLocationField}
onNewRequest={_this.handleChangeTideLocation}
onBlur={_this.handleBlurTideLocationField}
onUpdateInput={_this.handleUpdateTideLocationField}
renderInput={(params) => (
<TextField className="autoCompleteTxt"{...params} label="Location" />
)}
/>
Basically I was doing the following things wrong :
1.There is no need of using input inputValue={this.state.tidelocation_searchtext}& getOptionLabel={option => option.text}
2.as my data is in object form I have to convert it into a string so default value can match this from the state value
options={data_source.map(option=>option.text)}
Thank you all for your valuable support and solution !!
Removing inputValue has worked for me, even when passing object as options.
Using: "#material-ui/core": "^4.12.3"
If data/state not saved externally f.e. in local storage then it will be lost on page refresh, always. It's normal - like RAM memory without power - it (page/app state) only exists in memory !!
It's like using using cookie to keep you logged in.
If you really need such functionality then use f.e. redux-persist
You are right, if object type options are passed, material-ui's AutoComplete component does not seem to reflect the value when mounted. (Perhaps a bug?)
I was able to get around this by passing the proper characters to inputValue.
#RebelCoder
Maybe you should have initialized tidelocation_searchtext.
For me it was coming from the dropdown z-index which was hidden by another css behaviour.
I added this in a css file :
/* Dropdown MUI Component Autocomplete*/
div[role="presentation"].MuiAutocomplete-popper {
z-index: 1000000;
}
And it appeared finally. A bit hacky, but I think it was caused by another library that had something of that kind.
Note that I added several css elements to the selector, because just using the class wasn't enough.

Display tooltip/message while input is invalid HTML/JS/CSS/Angularjs

I have an HTML input field where certain characters shouldn't be allowed. The functional part is solved, but I would like to display a tooltip/message next to the input field while it contains illegal characters.
I have a boolean which keeps track of this, but I've been unable to make a satisfactory tooltip/message.
I've tried tweaking uib-tooltip, but It requires the user to hover over the input area. I've tried making a span/div/label that's hidden/displayed based on the boolean, but my CSS skills aren't strong enough.
The app uses Angularjs and Bootstrap 3.
The input field is not part of a form.
where you catch that boolean just say to display the div next to input like
myDiv.visible = true;
Without knowing your exact Javascript, I can't really answer it directly.
I would do something like
function invalid() {
if (invalid = true) {
document.getElementById("alert").style.visibility = 'visible'
}
}
make sure the error message is set to hidden,
then have the checker function run on focus..
<input type="text" onfocus="invalid()">
https://jsfiddle.net/we67geke/1/
This comment by user Lex solved the problem.
You can manually set the visibility of the uib-tooltip using the
tooltip-is-open attribute. Simply use the same boolean you are using
to keep track of the invalid characters.
As you mentioned
The app uses Angularjs and Bootstrap 3.
I suggest that you should use Boostrap tooltip. Use $('#element').tooltip('show') and $('#element').tooltip('hide') with your flag to handle status of Tooltip.
I don't know how your codes work, my idea seems like:
HTML:
<input type=text (keypress)="eventHandler()"> // angular >= 2
<input type=text ng-keypress="eventHandler()"> // angular 1
Angular code:
eventHandler() {
if (isIllegal) {
$('#element').tooltip('show');
} else {
$('#element').tooltip('hide');
}
}
Something like that.
Bootstrap Tooltip: https://getbootstrap.com/docs/3.3/javascript/#tooltips

Categories

Resources