Transform onChange when using register - react-hook-form

Is it possible to trasnform outgoing values with just register and v7 of react-hook-form?
I did this by overwriting the e I pass to onChange however it never becomes the value I set it. 325
const { onChange, ...registration } = props.form.register('foo');
const handleChange = e => {
const value = e.target.value;
const transformedValue = 325;
onChange({
type: e.type,
target: {
name: e.target.name,
type: e.target.type,
value: transformedValue
}
});
};
return <input {...registration} onChange={handleChange} />

The problem here is that no ref can be initialised by your call to register outside the <input /> element.
For the registration of a ref you can either add a custom register, this would give you the possibility to modify the current value of your <input /> element after a change via the setValue method (which is provided by useForm). Or another way would be to share your ref to your <input />.
However, I think that setValueAs should also work well in your case. This will run the provided function before returning your input value. Here is the relevant section from the docs.
<input {...register("foo", { setValueAs: value => `${value} 325` })} />

Related

.Net MVC and Kendo - conditionally bind div based on selected option

I am almost there!
I would like to show a specific div based on the selected value.
For example, if selected value = "Option1" is chosen, then show corresponding div.
I've tried the following in the data-bind:
data-bind="if"selectedValue() === 'Option1'"
I am successfully able to use data-bind="visible" selectedValue" to toggle, but both divs show. I would like to get at the object property itself.
Here's the code:
<select data-bind=", options: availableValues, optionsText: 'Name', value: selectedValue, optionsCaption: 'Select One'"></select>
<div data-bind="if:selectedFieldType() === 'Option1' ">
#Html.Partial("_Edit" + this.Model.Type)
</div>
<div data-bind="if:selectedFieldType() === 'Option2' ">
#Html.Partial("_Add" + this.Model.Type)
</div>
$(function () {
var testModel = {
availableValues: ko.observableArray(#Html.Json(Model.SelectedValueOptions)),
selectedValue: ko.observable(null))
};
testModel.value= ko.dependentObservable(function () {
if (this.selectedValue()) {
return this.selectedValue().Val;
}
}, testModel);
var tryGetValue = $.grep(testModel.availableSelectedValues(), function (item) {
return item.Val === '#Model.Value';
})[0] || null;
testModel.selectedValue(tryGetValue);
ko.applyBindings(testModel, $('#general-section')[0]);
});
Thanks to Artem's comment, I was able to fix it - I was referencing if:value()...and needed to reference the value referenced in the model as opposed to the name I used in the binding parameters (e.g. testModel.value - value was what I needed to reference (in my case that was xyzType as opposed to the generic term "value" that was used in the data-bind options.

kendo checkbox checked binding. Not able to bind to an array of checkboxes

I have an array of checkboxes and I would like to use it as an array, for example set single iitems in a group of options and retrieve the values of the group.
For a single checkbox I'm able to set it and get the click event, as an array I don't get anything.
HTML code :
<div class="k-group" id="chkbox-options">
<label>
Red
<input type="checkbox" id="chk1" value="Red" data-bind="checked: colors" />
Green
<input type="checkbox" id="chk2" value="Green" data-bind="checked: colors" />
Blue
<input type="checkbox" id="chk3" value="Blue" data-bind="checked: colors" />
</label>
</div>
Javascript code :
<script type="text/javascript">
var colordata = null;
$(document).ready(function () {
colordata = kendo.observable({
colors: ["Blue"]
});
kendo.bind($("chkbox-options"), colordata);
$("#dump-values").click(function () {
kendoConsole.log(colordata.colors.toString());
});
$("#chk1").click(function () {
kendoConsole.log("click chk1");
if (this.checked) {
kendoConsole.log("click chk1 true");
}
});
});
</script>
I can get the click event on a single checkbox, while I cannot set the values of the checkboxes in kendo.observable in the field var colordata.
I saw a similar example in the kendo documentation but I'm not able to make it work.
Thanks for your help
Marco
couple of points:
1. in kendo.bind # is missing for the div id chkbox-options
2. you need to read the changed colors inside the change event of the the observable object. The change happens after the click event so inside click event you always see the old data.
I have corrected your jsFiddle: http://jsfiddle.net/whizkid747/rPjjJ/4/
var colordata = null;
$(document).ready(function () {
colordata = kendo.observable({
colors: ["Blue"]
});
kendo.bind($("#chkbox-options"), colordata);
colordata.bind("change", function(e) {
var selectedColors = '';
$.each(colordata.colors, function(key, value){
selectedColors = selectedColors + " " + value;
});
if(colordata.colors.length == 0){
console.log('no colors selected');
}else{
console.log('selected colors:' + selectedColors);
}
});
});

How to let ng-model not update immediately?

Code:
<input type="text" ng-modal="name" />
{{name}}
When I input something into the input, the following {{name}} will change immediately. Is it able to configure it only update the name after I input all characters and leave the input?
This is about recent additions to AngularJS, to serve as future answer.
Angular newer versions (now in 1.3 beta), AngularJS natively supports this option, using ngModelOptions, like
ng-model-options="{ updateOn: 'default blur', debounce: { default: 500, blur: 0 } }"
NgModelOptions docs
Example:
<input type="text" name="username"
ng-model="user.name"
ng-model-options="{updateOn: 'default blur', debounce: {default: 500, blur: 0} }" />
Update
As many have mentioned Angular now has built-in support for this using the ng-model-options directive. See more here.
<input type="text" ng-model="name" ng-model-options="{updateOn: 'blur'}" />
Old answer below:
There's no built-in option for ng-model to change that behaviour, but you can write a custom directive doing it. #Gloopy wrote a directive like that for another question. You can look at the fiddle here.
The directive unregisters from the input and keydown events which trigger the update after each keystroke.
<input type="text" ng-model="name" ng-model-onblur />
Update:
Updated fiddle to use latest stable AngularJS (1.2.16 as of writing), instead of directly referencing the master version at github.
Also added an explicit priority so that the directive is run after ng-model to ensure event listeners are changed correctly.
A better option is to use the ng-model-options:
<input type="text" ng-model="name" ng-model-options="{updateOn: 'blur'}" />
Working directive code(ng-1.2RC3):
use:
ng-model-onblur
.directive('ngModelOnblur', function () {
return {
restrict: 'A',
require: 'ngModel',
priority: 1,
link: function (scope, element, attrs, ngModelCtrl) {
if (attrs.type === 'radio' || attrs.type === 'checkbox') { return; }
var update = function () {
scope.$apply(function () {
ngModelCtrl.$setViewValue(element.val().trim());
ngModelCtrl.$render();
});
};
element.off('input').off('keydown').off('change').on('focus', function () {
scope.$apply(function () {
ngModelCtrl.$setPristine();
});
}).on('blur', update).on('keydown', function (e) {
if (e.keyCode === 13) {
update();
}
});
}
};
})

Ember.TextArea set input through handlebars helper

I got a Ember.Handlerbars.JSON helper, which formats a given value to an indented JSON string.
I'd like to set the content (value) of a textarea like this:
{{#view Ember.TextArea}}
{{JSON someValue}}
{{/view}}
This does not work, since what I should set the textareas' "value" attribute instead.
However, this also doe not work
{{view Ember.TextArea valueBinding="JSON someValue"}}
You could solve this by using a computed property, see http://jsfiddle.net/pangratz666/3A33H/:
Handlebars:
<script type="text/x-handlebars" >
{{#with App.jsonController}}
{{view Ember.TextArea valueBinding="formatted" rows="10" }}
{{/with}}
</script>​
JavaScript:
App = Ember.Application.create({
formatJSON: function(obj) {
return JSON.stringify(obj, null, '\t');
}
});
App.jsonController = Ember.Object.create({
content: {
abc: 123,
foo: 'hello'
},
formatted: function() {
var obj = this.get('content');
return App.formatJSON(obj);
}.property('content')
});​
Update to your comments:
In the fiddle in the comment ( http://jsfiddle.net/4QNur/ ) your are declaring {{view Ember.TextArea valueBinding="JSON App.someComplexValue"}}: this does not work since valueBinding takes a path as argument and not an expression, like JSON App.someComplexValue. If you want to bind to a transformed value, just create a computed property and bind to this. That's the Ember way of doing such stuff...
In your original question you have the following code:
{{#view Ember.TextArea}}
{{JSON someValue}}
{{/view}}
This does not work in this case, since the value for the Ember.TextArea can only be set via a value respectively valueBinding:
{{view Ember.TextArea valueBinding="App.controller.transformedComplexValue" }}

Jquery ui - Autocomplete - Change Label of Field while keeping the same post value

im working on this jquery data entry form in which i need a specific field to be autocompleted with data from mysql
i got everything working, autocomplete retrieves data from the sql through php matching is great in english/latin and utf8 characters
the values get retrieved from the sql as "'number' => 'name'"
right now the autocomplete has 3 values in the output, value, label and id.
as id and value it uses the 'name'
and the label is the 'number' of my sql string (which is posted to the next page when the form is submited)
so everyting works ok, my 'number' is posted correctly, there is a minor annoyance tho
when i select something from the autocomplete list, the field is populated with the 'number'
is there any way to fill it with the 'name'?
ie: search for 'name', get dropdown with 'names', click and get the 'name' in the field, and when i submit i get the 'number' posted?
any help would be greatly appreciated.
if you need to take a look at my code, it's posted on a previous question: Jquery ui - Autocomplete - UTF8 charset
thanx in advance :)
The usual way to do this is:
Use a hidden input to hold the value you'd like to POST, then autocomplete a separate field.
Populate the hidden input on select
Populate the visible, autocompleted input with the label property of the item that was selected.
So, for example:
HTML:
<input type="hidden" name="name" />
<input type="text" id="name_auto" />
JavaScript:
$(function () {
var cache = {},
lastXhr;
$( ".name" ).autocomplete({
minLength: 1,
source: function( request, response ) {
var term = request.term;
if ( term in cache ) {
response( cache[ term ] );
return;
}
lastXhr = $.getJSON( "search.php", request, function( data, status, xhr ) {
cache[ term ] = data;
if ( xhr === lastXhr ) {
response( data );
}
});
},
select: function (event, ui) {
event.preventDefault();
this.value = ui.item.label;
},
change: function (event, ui) {
if (ui.item) {
$("input[name='name']").val(ui.item.value);
} else {
$("input[name='name']").val('');
}
}
});
});
You can use the result (handler) from u'r autocomplete
where the variable data such as arrays and you can return two data at once
Expl:
in javascript
$().ready(function()
{
var url = "<?=base_url()?>index.php/master/agen";
var width_val = 308;
$("#name_auto").autocomplete(url,
{
width: width_val,
selectFirst: false,
});
$("name_auto").result(function(event, data, format)
{
$("#name_auto").val(data[0]);
$("#id").val(data[1]);
});
});
in HTML :
<input type="hidden" name="number" id="id" />
<input type="text" id="name_auto" name="name" />
in PHP :
foreach ($source->result() as $row)
{
echo "$row->nama|$row->id\n";
}
note : here I use PHP CodeIgniter in its

Resources