0

I've got a table with a load of auto complete boxes in it which look like so...

<richui:autoComplete style="width:500px" name="objSelect[${newRow-1}].id" value= "" action="${createLinkTo('dir': 'object/searchAJAX')}" forceSelection = "true" maxResultsDisplayed="20" minQueryLength ="3" onItemSelect="updateHiddenInput(id,${newRow-1})" />

I've got it to call a function called updateHiddenInput when a user selects a value passing in the id selected as well as the row the autocomplete is on (this function then updates a hidden field in the same row, using the values passed in, with the ID). The function looks like so: -

function updateHiddenInput(id, num){
    var objID = "objectID[" + num + "].id";
    $(document.getElementById(objID)).val(id);
}

Everything works until I add a new row within my table, this pushes everything down one row and stops the autocomplete from updating the right rows hidden field (as its still referencing the old row).

Currently I have another piece of code that goes through and renames all the fields when a new row is inserted, but I have no idea how to update the autocomplete so that it passes through the right row number, anyone know how I can alter this?

The only other alternative I could think of would be to just pass through the object itself as well as the ID I can then locate the hidden based off the object, but I can't work out how to do this, any suggestions gratefully received! :S

I've tried changing onItemSelect="updateHiddenInput(id,${newRow-1})" to onItemSelect="updateHiddenInput(id,this)"

Theoretically so I can just pass through the autocomplete object and from there just traverse the page to find the hidden field I want to update. However when I then attempt to use that object in my function, for example with something like: -

var mynumber = $(myobject).closest('td').find('input').val();

I always get an "undefined" returned when I try to alert back the value...

If I just put in an alert(myobject) in the function it returns AutoComplete instance0 autoLook[0].id but if I've inserted new lines the id value doesn't change (i.e the objects id is now autoLook[3].id but it still shows [0], which I think could be part of the problem but I've got now idea how I can update this value...

I notice when looking in firebug at the html there is a /script linked to the autocomplete which could be the problem as this doesn't get updated when new lines are added and I can see multiple references to the old/original id value (see below) so maybe the passing through of this isn't passing the current objects values through...?

<script type="text/javascript">
var autoCompleteDataSource = new YAHOO.util.XHRDataSource("/Framework/object/searchAJAX");
autoCompleteDataSource.responseType = YAHOO.util.XHRDataSource.TYPE_XML;
autoCompleteDataSource.responseSchema = {
resultNode : "result",
fields : [
{ key: "name" },
{ key: "id" }
]
};
;
autoComplete = new YAHOO.widget.AutoComplete('autoLook[0].id','ad186a42e45d14d5cde8281514f877e42', autoCompleteDataSource);
autoComplete.queryDelay = 0;
autoComplete.prehighlightClassName = 'yui-ac-prehighlight';
autoComplete.useShadow = false;
autoComplete.minQueryLength = 3;
autoComplete.typeAhead = false;
autoComplete.forceSelection = true;
autoComplete.maxResultsDisplayed = 20;
autoComplete.shadow = false;
var itemSelectHandler = function(sType, args) {
var autoCompleteInstance = args[0];
var selectedItem = args[1];
var data = args[2];
var id = data[1];
updateHiddenInput(id,this) };
autoComplete.itemSelectEvent.subscribe(itemSelectHandler);
</script>

My thanks so far to user1690588 for all his help thus far! :)

On further digging I'm convinced that my issues is down to the line autoComplete = new YAHOO.widget.AutoComplete('autoLook[0].id','a5b57b386a2d1c283068b796834050186', autoCompleteDataSource); specifically the part where its inputting autoLook[].id and if I could change this I'd then be ok, but this line is auto generated and I've got no idea how to update it, anyone have any similar experience?

MorkPork
  • 844
  • 3
  • 20
  • 41
  • How you are adding new row in the table? – MKB Nov 18 '13 at 17:07
  • I add it via an AJAX call which just goes off and generates the html and psots it. After this is done it then runs through and renames all the elements in the table. – MorkPork Nov 18 '13 at 17:12
  • I've figured out I can change `onItemSelect="updateHiddenInput(id,${newRow-1})"` to `onItemSelect="updateHiddenInput(id,\$(this))"` which then enables me to pass `$(this)` to the function (if I `alert($(this))` I get `object Object` back). But I now can't work out how to get from that to working out the line that $(this) is on...! Alertnig $(this).id does nothing... :/ – MorkPork Nov 18 '13 at 17:14
  • Sorry that muddies the water slightly, its just a variable that tells it which row its on. that code is from the fragment that I insert when making the AJAX post (it tells it which row to end up) it just ends up as a number identifying the row its on... – MorkPork Nov 18 '13 at 17:22
  • I'm not sure that adding in the `\$(this)` is actually passing through the object at all as no matter what I try I can't get any information from it (can you send empty objects..?) – MorkPork Nov 18 '13 at 17:29
  • Try only `this` instead off `\$(this)` – MKB Nov 18 '13 at 17:32
  • curses, it appears that renaming the object doesn't change the details passed through with the `this`, even though the item has had its name/id updated :( Back to square one, unless there is some way I can use the `this` to find the actual object on the page and determine which line its on in the table...? – MorkPork Nov 19 '13 at 09:14
  • let us [continue this discussion in chat](http://chat.stackoverflow.com/rooms/41463/discussion-between-user1690588-and-morkpork) – MKB Nov 19 '13 at 09:19

1 Answers1

1

I have not much idea about your gsp page but I tried it on my side:

My gsp:

<!DOCTYPE html>
<html>
<head>
<resource:autoComplete skin="default"/>
<script src="//ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js"></script>
<script type="text/javascript">
    var counter = ${list.size()};

    function asd() {
        jQuery.ajax({
            url: " ${createLink(controller: 'oauthCallBack', action: 'testAuto')}",
            data: "idx=" + counter++,
            success: function (data) {
                jQuery("#tableId").append("<tr><td>" + data + "</td></tr>");
            }
        });
    }

    function updateHiddenInput(id, tg) {
        jQuery(tg).val(id);
    }
</script>
</head>

<body>
<g:form>
<table id="tableId">
    <g:each in="${list}" var="vr" status="idx">
        <tr>
            <td>
                <richui:autoComplete name="name" id="uniqueId${idx}" action="${createLinkTo('dir': 'oauthCallBack/test')}" onItemSelect="updateHiddenInput(id, someId${idx})"/>
                <g:hiddenField name="someName" id="someId${idx}" value=""/>
            </td>
        </tr>
    </g:each>
</table>
</g:form>
<button onclick="asd()">Add</button>
</body>
</html>

My action:

def testAuto() {
    render template: 'addNew', model: [idx: params.idx]
}

My template(addNew):

<richui:autoComplete name="name" id="uniqueId${idx}" action="${createLinkTo('dir': 'oauthCallBack/test')}"
                 onItemSelect="updateHiddenInput(id, someId${idx})"/>
<g:hiddenField name="someName" id="someId${idx}" value=""/>

Try this..,.



EDIT.....................................................................................

I supposed that you have successfully updated all the input field names. Then you can edit hidden field like:

View:

<tr class="dummyClass">
    <td>
        <richui:autoComplete name="name[${idx}]" id="uniqueId[${idx}]" action="${createLinkTo('dir': 'oauthCallBack/test')}" onItemSelect="updateHiddenInput(id, this)"/>
        <g:hiddenField name="someName[${idx}]" id="someId[${idx}]" value=""/>
    </td>
</tr>

jQuery:

function updateHiddenInput(id, tg) {
    jQuery(tg._elTextbox).closest("tr.dummyClass").find("input[type=hidden]").val(id);
}


EDIT.....................................................................................

Why you need to change the 'id'? Changing name is sufficient to send values in order. And you can update the hidden field without id as above edit.

If you still need to change the id then you can change it by cloning the tr and then use regex. See this answer for full working example.

Community
  • 1
  • 1
MKB
  • 7,587
  • 9
  • 45
  • 71
  • Thanks for the suggestion, but the problem I have is once I insert another row into the table I rename all the inputs in order (so 1 becomes 2, 2 becomes 3 etc) and this way will always reference the original `someId${idx}` and start updating the wrong field. I was hoping to somehow pass the autocomplete object into the function so I could then dynamically work out where it was on the page and find the hiddenfield relative to it, but passing in the object doesn't appear to work :S – MorkPork Nov 20 '13 at 08:59
  • Why are you renaming the inputs? I am also added row in the table and it is working fine, no need to change the name of the inputs. – MKB Nov 20 '13 at 11:18
  • Your example adds the row to the end, whereas I also have given the user the ability in mine to add rows in the middle of a table, or to drag rows up and down to reset their place (the table represents a sequence of 'events' as part of a test. When I save those values back to the database I need to know what order they are in so that they are saved and recalled in the right order and the way I did that at the time was using the objects ID to determine the order of the events. – MorkPork Nov 20 '13 at 13:20
  • What I need to do is go back and modify my code so that the rename/order of things only happens once when the user hits save. To do that though I need to also go back and alter how I add rows in (so that each new row gets a unique ID tying the auto complete and the hidden field together etc). – MorkPork Nov 20 '13 at 13:21
  • Can you post your hidden field tag? – MKB Nov 20 '13 at 17:18
  • Have you successfully renamed all the input fields? – MKB Nov 20 '13 at 17:59
  • Renaming the hidden fields (and even the autocomplete fields) was working fine, it was the fact that the autocomplete field, while the id was renamed, wasn't changing the id it was using/storing during the autocomplete script (that is generated automatically by grails, see the last chunk of code I pasted in my original post above). I'll definitely give your suggested solution a bash tomorrow and see if that works though, cheers! :) – MorkPork Nov 20 '13 at 21:49
  • 1
    Why you need to change the 'id'? Changing name is sufficient to send values in order. And you can update the hidden field without id see my edited answer(`jQuery(tg._elTextbox).closest("tr.dummyClass").find("input[type=hidden]").val(id);`). – MKB Nov 21 '13 at 05:03
  • Ah... On save I was sifting through the params in the save controller and was picking things up from there to save. I had assumed that it was the ID value that I was using to get this on not the name, I'll have to check but if its name then I can hopefully use this and jobs a goodun! :) I'll let you know once I get a chance to try it, thanks! – MorkPork Nov 21 '13 at 10:12
  • After making the relatively simple change of not renaming the IDs, just the names, the problem is solved!! I can't believe it was that simple! If you want to make that an answer I will gladly mark it as the answer! :) – MorkPork Nov 21 '13 at 13:46