Grails - Multiple forms/Passing remote checkbox selections - grails

I have a basic structure as such:
<g:form>
actionSubmit
</g:form>
<g:form>
actionSubmit
</g:form>
<g:each in personList - variable=person>
<tr>
<td><g:checkBox name="personList" value="${person.id}" checked="${false}"/></td>
<td>
<g:form>
actionSubmit
</g:form>
</td>
</tr>
</g:each>
Each of these forms relies on the personList checkbox array as a variable. The prior edition of my code wrapped the entire div in a form, which worked but caused problems when I added the third form in the table.
How can I pass the selected checkboxes? I have checkbox that selects all of the boxes - I just need to assign a variable/hiddenField with that array of selected boxes.
Thanks!
Edit
The issue with having a single form is that I have a column in each row has the ability to add elements to a one to many relationship. If I could pass the person.id with the corresponding action submit (so if I hit the actionSubmit on row 2, I want to pass person.id of row 2), then this is a piece of cake.
However, whenever I tried to tie the person ID, I end up with an array of ALL person IDs. So I figured the only way around this is to have separate forms.
<td>
<div id="reportsToResultsDiv2_${person.id}" class="reportsToResultsDiv2_${person.id}">
<g:select id="reportsTo" name="reportsTo.id" from="${rtResults}" optionKey="id" value="" />
<g:actionSubmit action="addReportsTo" value="Add" params="[c_id:'${person.id}']"/>
</div>
</td>

I don't think checkbox supports both value and checked in that way.
Perhaps this is what you want?
<g:each in="${personList}" var="person>
<g:form controller="person" action="doSomething">
<g:hidden name="personId" value="${person.id}"/>
<g:checkBox name="superFly" checked="${person.superFly}"/>
</g:form>
</g:each>

Would a single form and several g:actionSubmit buttons work for you?
Generates a submit button that maps to a specific action, which lets you have multiple submit buttons in a single form. - http://grails.org/doc/latest/ref/Tags/actionSubmit.html
<g:form controller="book">
<g:checkBox name="personList" value="${person.id}"/>
<tr><td>
<g:actionSubmit action="action1" value="firstButton"/>
</td></tr>
<tr><td>
<g:actionSubmit action="action2" value="secondButton"/>
</td></tr>
</g:form>

Related

Pass one of many objects from view to controller

In an ASP.Net Core web app, I'm passing a List<Parameter> to a view via ViewBag.Parameters. The view also has a SelectParameterViewModel that consists of one property only, an int ParameterId. The objects are then displayed in a table like so (I skipped straight to tbody as the view works fine from a cosmetic perspective):
#model WebApp.Models.ReportViewModels.SelectParameterViewModel
[...]
<tbody>
#foreach (var item in ViewBag.Parameters)
{
<tr>
<td class="col-xs-1">
<form asp-controller="Report" asp-action="Launch">
<div asp-validation-summary="ModelOnly" class="text-danger"></div>
<input asp-for="#Model.ParameterId" type="hidden" value="#item.Id" />
<input type="submit" class="btn btn-primary btn-sm" value="Select" />
</form>
</td>
<td class="col-xs-8">#item.Description</td>
<td class="col-xs-3">
<a asp-action="Edit" asp-route-id="#item.Id">Edit</a> |
<a asp-action="Details" asp-route-id="#item.Id">Details</a> |
<a asp-action="Delete" asp-route-id="#item.Id">Delete</a>
</td>
</tr>
}
</tbody>
I would like the user to click on the button of the chosen table-row and submit either that row's Parameter (preferred) or the Parameter's Id, like I tried to do in this case. I would then do the same with the <a> tags on the third column. The point is that I don't want the user to simply type /Report/Launch/id and run the report, as each user would have its own sets of parameters and should not be allowed to use any of the others', and the ViewBag only contains the list of its Parameter. I can change the view model and/or the receiving controller's argument depending on the solution, both would work. I tried a few versions of the above html, but none would work, while the above returns ParameterId with value 0.
I couldn't find a similar scenario in other SO questions. There were some solutions that involved JavaScript and, correct me if I'm wrong, but that would still show the ParameterId value in the webpage source. While that would be sort-of-ok in this specific case, I have other cases where I definitely would not want that to happen.
What would be an elegant solution to achieve this? Thank you!

Group of Radio Buttons with None selected in MVC

I'm new to MVC - I'm creating a simple survey application with a Survey Model and Controller and multiple Views in which users fill out their answers.
In my views I have a table of radio buttons, where each row is a group and the user has to select one radio button in each row. When the page loads, I want none of the radio buttons to be checked, forcing them to make a selection (throwing an error if they do not).
The problem is that the last radio button in each row is being selected somehow by default. I even specifically set one of the other buttons to checked to see what would happen, but when it loads it's still the last one that is checked. I have no idea why that is happening, how to change it, or even then what would be the best way to validate a selection is made in each group when the user tries to move on.
My Survey Model contains these STRING properties: mddbccu, mddtfuu, mddbccub, mddtfuub. There is nothing in my model except the properties.
This is an example of one of the rows of radio buttons in a view:
<tr>
<td>#Html.DisplayNameFor(Function(model) model.mddtfuu)</td>
<td>
<div><input name="mddtfuu" id="mddtfuu0" value="Never" checked="" type="radio"></div>
</td>
<td>
<div><input name="mddtfuu" id="mddtfuu1" value="Rarely" checked="" type="radio"></div>
</td>
<td>
<div><input name="mddtfuu" id="mddtfuu2" value="Sometimes" checked="" type="radio"></div>
</td>
<td>
<div><input name="mddtfuu" id="mddtfuu3" value="Usually" checked="" type="radio"></div>
</td>
<td>
<div><input name="mddtfuu" id="mddtfuu4" value="Always" checked="" type="radio"></div>
</td>
</tr>
Remove "checked" property from each radio button.
Thats it. Simple.......
i.e:
<input name="mddtfuu" id="mddtfuu0" value="Never" type="radio">

Struts 2 select tag - Using the tag (with the same list) multiple times on a page does not work

I need to be able to use the same drop down list multiple times on a page. The first time i use the 'list' on the select tag, it works fine. The same list does not populate the second select tag i use it on. Here are the details.
In the action class, i populate the ArrayList containing values i need to populate the select tag.
setNames(new SomeDAO().getNames());
In the JSP
<s:select list="names"
id="nameList"
listKey="nameId"
listValue="userName"
/>
This select list populates just fine. If I use the following select tag on the same page (using the same list), it fails to print.
<s:select list="names"
id="rName"
listKey="nameId"
listValue="userName" />
If i replace the 'list' above with #{'test':'test'} (hardcoded list), the tag shows up fine. Looks like the property i set in the Action is getting cleared after the first use. Is that whats happening or am i doing something wrong? I get an 'IllegalStateException: Response already committed' error
Edit 1:
setNames() is used in the action method that deals with the JSP page. It is a simple getter function.
In the JSP, here is what i have.
<tr>
<td align="left" class="td-plain">Add New:</td>
<td class="td-plain">
<s:select list="names"
id="addNameID"
name="addUserNameID"
listKey="reinsId"
listValue="reinsName"
headerKey=""
headerValue="--User Name--"
/>
</td>
<td class="td-plain"><input id="addTreatyNumber" type="text" /></td>
<td class="td-plain"><input id="addReinsPercentage" type="text" /></td>
<td class="td-plain"><input id="addFlatDollarRetentionAmt" type="text" /></td>
<td class="td-plain">
<%if(finance){ %>
<input type="button" class="greyButton" value="Add" onclick="addReinsInfo()"/>
<%}else{ %>
None
<%} %>
</td>
</tr>
and then later down on that page, i have
<tr id='<s:property value="caseGroupId"/>:<s:property value="treatyId"/>'>
<td class="td-plain"><input type='checkbox' id='<s:property value="caseGroupId"/>:<s:property value="treatyId"/>'/></td>
<td class="td-plain">
<s:select list="names"
id="rName"
name="dName"
listKey="reinsId"
listValue="reinsName"
headerKey=""
headerValue="--User Name--"
/>
</td>
<td class="td-plain_"><s:textfield id="tNumber" value="%{treatyNumber}"/></td>
<td class="td-plain_"><s:textfield id="tPercentage" value="%{reinspercentage}"/></td>
<td class="td-plain_"><s:textfield id="rAmount" value="%{flatDollarRetentionAmt}"/></td>
<td class="td-plain"><input type="button" value="Delete" class="greyButton"/></td>
</tr>
If I change the 'list' in the second tag to
list="#{'Test':'Test'}"
the tag shows up fine. Please let me know if i can provide any further info.
Edit 2: I was able to get this to work by setting the drop down list values to the session.
As asked by #Dave and #Quaternion, post the relevant Java/JSP code.
But until then... I've noted that you are not using name attribute in Struts Selects;
while you can refer multiple times from different tags to the same source (the list attribute), to populate the Select from the same list of objects, you should instead specify a different name for each one, to define which variable (sent back to the Action) contains the selected value of which Select;
this may not be the answer to the current question but it will show up to you soon.

How to implement this validation in a Knockout-based form?

I started to work on an ASP.NET MVC4 solution with the SPA template (Single Page Application).
The starting template manage some todo lists with a kind of post-it design.
I slightly modified the template this way:
no more post-it design for dislaying elements
but a table to list all elements + delete + edit button on each element
at the end of the table: an add button
I have now the ability to edit one element in a form tag like this:
<form data-bind="with: currentTodoList, validate: true">
<h1>Edition</h1>
<table>
<tr>
<td>ID</td>
<td><b data-bind="text: todoListId"></b></td>
</tr>
<tr>
<td>User ID:</td>
<td><input class="required" data-bind="value: userId" /></td>
</tr>
<tr>
<td>Title:</td>
<td><input class="required" data-bind="value: title" /></td>
</tr>
<tr>
<td>Category:</td>
<td><input data-bind="value: category" /></td>
</tr>
</table>
<p>
<button data-bind="click: $parent.saveTodoList">Save</button>
<button data-bind="visible: todoListId, click: $parent.deleteTodoList">Delete</button>
<button data-bind="click: $parent.showGrid">Cancel</button>
</p>
</form>
As you can see above, I set the validate data-binding on the form tag and I have some input element with the class required.
When I test this implementation it doesn't work as expected. Example:
If I clear (empty) the userId field (which is required) I have a red validation message (picture 1). OK.
If I fill this userId field again, the red validation messaged disappeared. OK.
Then if I clear (empty) the title field (which is also required) I have the red validation message next to the userId field (picture 2). NOK.
The inverse is also true: userId <--> title. Any idea where is the problem?
Here is a link to download my test VS2012 solution to reproduce the problem.
Ok, so I played with your markup a little, with slight modification to the view model (not using a list, but editing a single entry).
Take a look at this jsfiddle - http://jsfiddle.net/Zxjrb/1/
I have added a span for validation message for ID and User ID, skipped the span for Title and Category.
<span data-bind='visible: todoListId.hasError, text: todoListId.validationMessage'> </span>
You can see the messages coming up, when Id or UserId field being empty, and that not happening for the title/category fields.

Access individual elements in a list

I have a list of, let's say, persons. Every person has a field that is "friend", that could be "yes" or "no". Their "friendship" status is presented in a column in the list:
<g:if test="${person.friend.status=='no' }">
<td><g:textField name="status" value="${person.friend.status}" readonly="readonly" style="width:60px;border:0px; background:transparent;color:black"/></td>
<td style="width:20px">
<g:actionSubmitImage action="acceptFriend" value="aceptar" src="${resource(dir: 'images', file: '/skin/tick_16.png')}" style="width:5px;height:8px;"/>
</td>
<td>
<g:actionSubmitImage action="refuseFriend" value="aceptar" src="${resource(dir: 'images', file: '/skin/wrong_16.png')}" style="width:5px;height:8px;"/>
</td>
</g:if>
As you can see, when the friend status is "no", two buttons are presented, one to say "that person is my friend" and another one to say "this person is not my friend". My question is:
When i click on the image that says "this person is my friend", I call the action "acceptFriend". But, how to access to the indivivual person instance, to change his status to "yes", and persist in the database? I think it may be with the "params" variable, but how to store it in the params to be accessed in the Controller?
Thank you!
I believe, you cannot use the g:actionSubmitImage like this, because in the tag's documentation is written:
You cannot use multiple actionSubmitImage tags within the same form and have it work in Internet Explorer 6 or 7 unless you add some custom JavaScript. See this page for a bit more information and a workaround.
The correct solution would be to have a form per friend in list and then you can easily pass the ID of the domain class.
The actionSubmitImage creates a submit button in some form.
Create the form for each person in the list you're iterating.
In that form, add a hidden field named "id" with a value="${person.id}", and in acceptFriend action read it from params.id.
<img src="${resource(dir: 'images', file: '/skin/wrong_16.png')}" style="width:5px;height:8px;" />
This is not tested code, just to give you the idea.
By request of Tom Metz, i post the snippet with both g:actionSubmitImage tags working:
<form>
<g:hiddenField name="contrato" value="${factura.id}"/>
<td> <g:link title="${message(code :'contratosVer.tooltip')}" controller="campaign" action="show" id="${factura.id}" style="width:160px"> <g:img dir="images" file="/skin/eye_16.png"/></g:link> </td>
<td><g:textField name="campaign" value="${factura.nombre}" readonly="readonly" style="width:120px;border:0px; background:transparent;color:black"/></td>
<td><g:textField name="total" value="${factura.presupuestosPendientes.total}" readonly="readonly" style="width:40px;border:0px; background:transparent;color:black"/></td>
<g:if test="${factura.estado=='Espera'}">
<td><g:textField name="estado" value="${factura.estado}" readonly="readonly" style="width:60px;border:0px; background:transparent;color:black"/></td>
<td style="width:20px">
<g:actionSubmitImage action="aceptarCamp" value="aceptar" src="${resource(dir: 'images', file: '/skin/tick_16.png')}" style="width:5px;height:8px;"/>
</td>
<td>
<g:actionSubmitImage action="rechazarCamp" value="aceptar" src="${resource(dir: 'images', file: '/skin/wrong_16.png')}" style="width:5px;height:8px;"/>
</td>
</g:if>
<g:else>
<td><g:textField name="estado" value="${factura.estado}" readonly="readonly" style="width:65px;border:0px; background:transparent;color:black"/></td>
<td></td><td></td>
</g:else>
<g:set var="desc" value="${result.toString()}" />
<g:if test="${desc.size() > 120}"><g:set var="desc" value="${desc[0..120] + '...'}" /></g:if>
</form>
Sorry for the delay, mate, but I was away from work for three days.

Resources