Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Disabled TextBox could't updated #688

Closed
jo49bimpf opened this issue Dec 7, 2018 · 20 comments
Closed

Disabled TextBox could't updated #688

jo49bimpf opened this issue Dec 7, 2018 · 20 comments

Comments

@jo49bimpf
Copy link

jo49bimpf commented Dec 7, 2018

Hello,

after updating from 3.2.4 to 3.3.2 the update of a disabled input textfield won't work any more.
This is the code:

<com:TTemplateColumn 
    SortExpression="Kategoriestufe2" 
    ID="Kategoriestufe2ht" 
    HeaderText="Kategoriestufe2" 
    HeaderStyle.CssClass="pflichtfeld_fa_header sort-arrow"  
    ItemTemplate="<%# $this->Parent->Data->Kategoriestufe2 %>" 
>
<prop:EditItemTemplate>
    <com:TTextBox 
        ID="Kategoriestufe2tx" 
        Columns="30" 
        style="Background-color:white;" 
        enabled = "false"
        MaxLength="200" 
        Text=<%# $this->Parent->Data->Kategoriestufe2 %> 
    />
</prop:EditItemTemplate>

If I set in the TTextBox "Kategorystufe2tx" enabled to true, it will work again.
What's happen or what do I have to change to get the old functionality?

Thanks and regards
Juergen

@ctrlaltca
Copy link
Member

What is actually updating the text field? Are you databinding the TDataGrid again?

@jo49bimpf
Copy link
Author

i set the new values via javascript. This works fine. I can see the new value in my browser.
Then I click update and a php-function "updateVersion" is executed. At the the end, $this->loaddata() is called. And in the loaddata() theres is a bind executed.

@jo49bimpf
Copy link
Author

jo49bimpf commented Dec 7, 2018

This is the command to save the new value to the db:

$version_save_rec->Kategoriestufe2 = trim($param->Item->Kategoriestufe2ht->Kategoriestufe2tx->Text);

and in an echo before, I see that in $param->Item->Kategoriestufe2ht->Kategoriestufe2tx->Text is the old value

@jo49bimpf
Copy link
Author

this is what I'm seeing in the browser:

grafik

And this the firefox-debugger showing:

grafik

@jo49bimpf
Copy link
Author

In the DOM, I see the correct value:

grafik

@ctrlaltca
Copy link
Member

Just a guess, but the main change between prado 3.2 and 3.3 was the use of jQuery instead of protoype. Since prado 3.3, jquery's serialize() is used to collect form inputs when sending ajax requests; serialize() is known not to collect disabled inputs (see https://stackoverflow.com/questions/4748655/how-do-i-make-serialize-take-into-account-those-disabled-input-elements), but a few workarounds exist:

  • use the readonly attribute instead of disabled (at least for text inputs)
  • enable all inputs, serialize(), and then disable them again
    I guess the first workaround is probably the easy and fast solution for you.

@jo49bimpf
Copy link
Author

I've tried readonly befor I wrote this issue. But it didn't work anyway.

So, I'll try the serialize()-workaround.

@ctrlaltca
Copy link
Member

Here's the line you may want to patch: https://github.com/pradosoft/prado/blob/prado-3.3/framework/Web/Javascripts/source/prado/activecontrols/ajax3.js#L301
If it works for you, I'll be glad to integrate the patch

@jo49bimpf
Copy link
Author

Hmm, in 3.3.2 this line is not changed:
grafik

the originla line is the outcommented one.

@ctrlaltca
Copy link
Member

You may want to change the code as follows:

if(this.options.PostInputs != false)
{
  var form = this.getForm();
  var disabled = form.find(':input:disabled').removeAttr('disabled');
  var params = jQuery('input, select, textarea').serialize() + '&' + jQuery.param(data);
  disabled.attr('disabled','disabled');
  return params;
} else {

Note: i did not test the code, it may contain typos

@jo49bimpf
Copy link
Author

there comes this error:
grafik

@ctrlaltca
Copy link
Member

mhh.. try jQuery(form).find(':input:disabled').removeAttr('disabled');

@jo49bimpf
Copy link
Author

yes. this works without typeerror.

@ctrlaltca
Copy link
Member

Nice, I'll get the fix and a testcase ready during the weekend, time permitting.

@jo49bimpf
Copy link
Author

for the fist tests, it looks fine. I'll do some further tests and come back to you end of next week.
Thanks alot for your help!!!!!!!!!! A+++

@jo49bimpf
Copy link
Author

I've nothing heared from my customer. So I think it's fine and works well.

@ctrlaltca
Copy link
Member

ctrlaltca commented Apr 12, 2019

Looking again at this bug, i don't think it's a good idea to change this behavior.
On a normal <form>, disabled inputs don't get posted, as per spec
Prado active controls try to mimic the behavior of normal controls but using ajax. Introducing this change would mean creating a (subtle) difference on how TTextBox works between a normal and an ajax request.
If you really want a control that works this way, here's a more correct way to do it:

  1. create a new class extending TTextBox and set it ReadOnly (so it will get posted by forms)
  2. reimplement TTextBox::loadPostData() so that it will update its value even when it's readonly:
- 		if (!$this->getReadOnly() && $this->getText() !== $value) {
+ 		if ($this->getText() !== $value) {
			$this->setText($value);
  1. use this class in place of TTextBox where needed.

@jo49bimpf
Copy link
Author

jo49bimpf commented Apr 16, 2019

ok, thanks for the information.
Would it be correct in this way (I've never done this before):

class TCategoryTextBox extends TTextbox
{
  public function loadPostData()
 {
		parent::loadPostData();
		
		if (!$this->getReadOnly() && $this->getText() !== $value) {
			if ($this->getText() !== $value) {
				$this->setText($value);
			}
		}
		
	}
}

@ctrlaltca
Copy link
Member

It's probably easier to just trick TTextbox this way:

<?php

class YCategoryTextBox extends TTextBox
{
	public function loadPostData($key, $values)
	{
		$this->setReadOnly(false);
		parent::loadPostData($key, $values);
		$this->setReadOnly(true);
	}
}

Save it somewhere in the application, eg. as protected/Common/YCategoryTextBox.php
Here's a quick example to ensure it works:

<com:TClientScript>
function makeid() {
  var text = "";
  var possible = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789";

  for (var i = 0; i < 10; i++)
    text += possible.charAt(Math.floor(Math.random() * possible.length));

  $('#<%= $this->txtOrig->ClientID %>').val(text);
  return false;
}
</com:TClientScript>
<com:Application.Common.YCategoryTextBox ID="txtOrig" ReadOnly="true" />
<button onclick="return makeid()">change text</button>
<com:TActiveButton ID="cmdSendText" Text="send text" OnCallback="cmdSendText" />
<com:TActiveLabel ID="labResult" />
	public function cmdSendText($sender, $param)
	{
		$this->labResult->Text=$this->txtOrig->Text;
	}

@jo49bimpf
Copy link
Author

Hello,

thanks for your support. Think, I've got it. First tests were successful.

Thanks and regards
Jürgen

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants