react-select CreatableSelect dont allow numbers - react-select

How can I not allow a user to type numbers on my CreatableSelect component?
<CreatableSelect
onKeyDown={handleNumberInput}
components={animatedComponents}
isSearchable={true}
isMulti
options={selectTags}
onChange={newTagsSelectedfunction}
/>
I'm trying to do it with onKeyDown but wonder if it could accept a pattern property

I found a solution by accessing the key property of the event
const handleNumberInput = (e) => {
if (Number.isInteger(Number(e.key))) {
e.preventDefault();
}
};

Related

Trying to block user from typing numbers on an antd Input without having to use state (or useState)

I'm using antd Form and have some Inputs in it. I wish to know if antd has something that can validate the users input and determine if what he typed are letters or numbers. I want the input to only allow the user to type (show) in the input only alphabets but not numbers.
Form.Item has a property called rules where you can establish a pattern using RegExp, but this is not what I want, because the user can still type numbers and they will be shown on the UI. Pattern property only pops a message like "field does not accept numbers" and I assume that when I submit the data it will take what the user typed regardless of the failed rule/pattern.
I have been able to do what I'm asking by having to create a state with an object with all my values, removing the name property from the Form.Item and adding it to the Input, along with an onChange and value property but this requires more "wiring'. If you have worked with antd Form, there is an onFinish property that collects all the data so you don't have to create a separate state.When removing the name property from Form.Item, antd won't be able to collect the data of the form anymore thus rendering it useless. I wish to know if antd has something that can help me achieve what I typed in the beginning.
Following code does what I want, but uses state.
My Form.Item
<Form.Item
// name="nombre"
label="Nombre(s)"
rules={[
{ required: false, message: "REQUIRED_ERROR_MESSAGE" },
{
pattern: new RegExp(/^[a-záéíóúüñçA-Z]*$/i),
message: "field does not accept numbers",
},
]}
>
<Input
onChange={handleWordInput}
value={altaFormValues.nombre}
name="nombre"
/>
</Form.Item>
My Input handler function:
const handleWordInput = (e) => {
console.log("e", e.target.value);
const re = /^[a-záéíóúüñçA-Z\s]*$/;
const { name, value } = e.target;
if (value === "" || re.test(value)) {
setAltaFormValues((prevState) => {
return { ...prevState, [name]: value };
});
}
};

loadOptions getting called for same string which was searched earlier and cacheOptions is enabled

I am trying to use AsyncSelect from react-select library.
I have enabled cacheOptions option.
Using below mentioned steps I am seeing an issue with loadOptions
Search for a string test
List of options gets displayed
Clear the input field
Enter same string again test
Immediately displays same list of options
loadOptions fires an API with search input tes
Clear the input field
Enter same string again test
Immediately displays same list of options
loadOptions fires API with search input te.
I am not sure why loadOptions getting fired in this scenario if I am entering the same search string.
Here is the AsyncSelect
<AsyncSelect
classNamePrefix="select-item"
onChange={ onOptionSelect }
getOptionValue={ item => item.id }
placeholder="Search by Item"
formatOptionLabel={ company => <CompanyWithIcon Item={ Item } /> }
loadOptions={ loadOptions }
styles={ customStyles }
isSearchable
cacheOptions
isClearable
/>
Here is the loadOptions function
const loadOptions = inputValue => searchItem(inputValue);
Can anybody please help?
I think it is happening because you are not using a callback or a promise for loadOptions. The loadOptions should return a promise.
Reference doc -> https://react-select.com/props#async-props says:
loadOptions:
Function that returns a promise, which is the set of options to be used once the promise resolves.
It should be like below:
const loadOptions = (inputValue, callback) => {
setTimeout(() => {
callback(searchItem(inputValue));
}, 1000);
};

show block toolbar programmatically gutenberg

I am creating a block with InnerBlocks component.
If no content added to the InnerBlocks (and even with content in fact) it is very difficult to popup the block toolbar
I would like to add an iconbutton on top corner that will show the block floating toolbar
How can I tell the .block-editor-block-contextual-toolbar to show?
I don't see any method of the .wp-block in the inspector that would do that and the documentation of Block Controls: Block Toolbar and Settings Sidebar https://developer.wordpress.org/block-editor/how-to-guides/block-tutorial/block-controls-toolbar-and-sidebar/ is quite basic
Many thanks
You can use useSelect() to determine if there are any blocks present in the InnerBlocks component:
import { useSelect } from '#wordpress/data';
const hasInnerBlocks = useSelect((select) => (
select('core/block-editor').getBlock(clientId).innerBlocks.length > 0
), [clientId]);
Then you can use hasInnerBlocks to conditionally render whatever you'd like within the edit function:
{ !!hasInnerBlocks && (
<BlockControls group="block">
<ToolbarGroup
// Toolbar group settings here
/>
</BlockControls>
) }
Try to use same code structure among the edit and save methods. The RIchText need to be waraped inside div.
<div>
<RichText.Content
className={ `sticky-note-${ props.attributes.alignment }` }
style={ {
fontSize: props.attributes.fontSize,backgroundColor: props.attributes.color,
} }
tagName="p"
value={ props.attributes.content }/>
</div>
Example
I created this example to illustrate your situation.
import { InnerBlocks, BlockControls } from '#wordpress/block-editor';
// ...
edit: () => {
const blockProps = {
// your own props
};
return (
<div { ...blockProps }>
<BlockControls>
// your controls
</BlockControls>
<InnerBlocks />
</div>
);
}
Problem
For the BlockControls to decide whether or not it should appear, it needs to get some context from its parent which your own props don't have.
Solution:
Use the block props instead for the parent of BlockControls.
Steps:
Import useBlockProps from #wordpress/block-editor:
import { InnerBlocks, BlockControls, useBlockProps } from '#wordpress/block-editor';
Pass your own props as an argument to useBlockProps():
const blockProps = useBlockProps({
// your own props
});
Result
import { InnerBlocks, BlockControls, useBlockProps } from '#wordpress/block-editor';
// ...
edit: () => {
const blockProps = useBlockProps({
// your own props
});
return (
<div { ...blockProps }>
<BlockControls>
// your controls
</BlockControls>
<InnerBlocks />
</div>
);
}
Links
I hope that helped.
My answer is based on Wordpress's official Block Editor Handbook:
https://developer.wordpress.org/block-editor/how-to-guides/block-tutorial/block-controls-toolbar-and-sidebar/#block-toolbar
https://developer.wordpress.org/block-editor/how-to-guides/block-tutorial/nested-blocks-inner-blocks/
https://developer.wordpress.org/block-editor/reference-guides/block-api/block-edit-save/#block-wrapper-props

Fluent/Fabric - Is it possible to clear the input of the NormalPeoplePicker programmatically?

Is it possible to clear the input text (e.g. "qweqweqweqwe" in the example below) of the (Fluent/Fabric) NormalPeoplePicker programmatically?
I have tried accessing the input element (via the onBlur event) and attempted to change it's value and innerHtml but that doesn't work. Also, that doesn't seem to be a good way of doing it.
https://developer.microsoft.com/en-us/fluentui#/controls/web/peoplepicker
NormalPeoplePicker Component keep input value inside state and its not possible to change it directly:
const picker = React.useRef(null)
...
<NormalPeoplePicker
...
onBlur={() => {
if(picker.current) {
picker.current.input.current.value = ""; // Uncaught TypeError: Cannot set property value of #<Autofill> which has only a getter
}
}}
/>
From Official Documentation inside implementation section there is useful method updateValue which allows to change the input value.
const picker = React.useRef(null)
...
<NormalPeoplePicker
...
onBlur={() => {
if(picker.current) {
picker.current.input.current._updateValue("");
}
}}
/>
Codepen working example ln: 104.
Note:
This is a temporary solution, test every use case before production.
let orgSelected: ITag[] = [];
orgSelected.push({key:0 name:''});
const [selectedOrg,setselectedOrg] = useState(orgSelected);
On TagPicker Property just assign the statevalue like this.
selectedItems={selectedOrg}
This way the tagpicker property will always be selected with an empty item.

Vue-Native checkbox change value

I want to be able to change the value of a checkbox by clicking on it. recentContacts are loading just fine, and specifying initial checked values in the computed function works well. The :on-press seems to change the value but does not reflect in the UI.
Please Help
Template
<nb-list>
<nb-list-item v-for="contact in recentContacts" v-bind:key="contact.uid">
<nb-checkbox :on-press="() => contact.checked =! contact.checked" :checked="contact.checked"></nb-checkbox>
<nb-text>{{contact.firstName}} {{contact.lastName}}</nb-text>
</nb-list-item>
</nb-list>
Code
export default {
computed: {
recentContacts() {
return store.state.admin.userData.recentContacts.map(rc => {
rc.checked = false;
return rc;
});
}
},
}
EDIT:
I am guessing because VUEX is imutable. I've got this to work by having recentContacts inside of the data attribute instead of computed just not how I want to do things.