I am trying to display autocomplete results for a list of managers. I have the following code:
Application.js
function log(message) {
$( "<div/>" ).text( message ).prependTo("#log");
}
$("#managers").autocomplete({
source : function(request, response) {
$.ajax({
url : "/managerlist",
dataType : "json",
data : {
style : "full",
maxRows : 12,
term : request.term
},
success : function(data) {
var results = [];
$.each(data, function(i, item) {
var itemToAdd = {
value : item,
label : item
};
results.push(itemToAdd);
});
return response(results);
}
});
}
});
Project controller
def manager_list
list=Project.all.map{|i|i.manager_user_id}
arr= [].concat(list.sort{|a,b| a[0]<=>b[0]}).to_json
render :json =>arr
end
Routes.rb
match '/managerlist' => 'projects#manager_user_id'
_form.html.erb
<p>
<%= f.label :manager_user_id %><br />
<input id="managers" />
</p>
The following code is fine, I don't recieve no errors in firebug. However when I try to enter a managers name for example James Johnson the name won't appear. I have also tried putting the whole function in the _form.html.erb and wrapped it in tags this didn't work. Is there any idea why this is happening
So I've managed to fix my error, which was because of the ordering of Jquery core and Jquery ui.
I've got the managers to be listed. In the image below.
From the image it can be seen that when I type 'Arm' it brings the entire list of managers, when it should display 'Deshawn Armstrong'. I understand that this is most probably to do with my project controller below
Project controller
def manager_list
list=Project.all.map{|i|i.manager_user_id}
arr= [].concat(list.sort{|a,b| a[0]<=>b[0]}).to_json
render :json =>arr
end
Check the response in the Firebug console and make sure the string is in proper json format for the autocomplete.
It appears that you are just returning an array. The dataType setting in .ajax doesn't convert to json; it's just expecting that format back. If you are not sending json back from your url : "/managerlist", this may be the problem.
Actually, provided your ajax function is working correctly, you could just:
return response(JSON.stringify({ results: results }));
jsfiddle example of JSON.stringify: http://jsfiddle.net/xKaqL/
Based on your new information, you need to add a minLength option to your autocomplete.
$("#managers").autocomplete({
minLength: 2, // 2 or whatever you want
// rest of your code
Related
I appreciate that there may be many answers out there but if there are i cant quite interpret them to suit my needs..I am looking to update a records attribute in my model using ajax.
In my case the attribute selected: true
In my scenario i am clicking on an element and looking to update that elements record in the model
<ul class="components">
<% #component.each do |c| %>
<li id="<%= c.component_name %>" data-id="<%= c.id %>" data-remote="true"><%= c.component_name %></li>
<% end %>
</ul>
jQuery
$('#Literacy, #Numeracy').on('click', function(){
var component_name = $(this).text();
var component_id = $(this).data('id');
data_send = { id: component_id }
$.ajax({
method: 'put',
url: '/components/selected_component',
data: data_send,
success: function(data) {
console.log(data)
}
});
});
Controller
def selected_component
#component = Component.find(params[:id])
#component.update_attributes(selected: true)
end
Maybe im looking at this incorrectly but how can i get the id via the click event (stored as component_id) into my selected_component method
Im missing a few bits here but struggling with what today
At the moment I am getting an error
Missing template components/selected_component
but i dont want to render that page after successful update, I just want to stay on the same page
EDIT
to solve my issue i just had to add this to my format.js
{ render nothing: true }
A missing template error corresponds to not having a view that knows what to do when it gets a JavaScript request.
In your views/components/, just make an selected_components.js.erb file and that should clear the error you're getting.
I have a profile page where I render all of the user's lists using a partial:
users/show.html.erb
<%= render #lists %>
For each list I show how many wishes are associated:
lists/_list.html.erb
<p class="muted" id="wishes_count"><%= pluralize(list.wishes.count, "wish") %></p>
I'm using drag and drop to allow the user to move wishes from one list to another using jQuery sortable.
Right now, I'm using the following code:
wishes.js.erb
$(document).ready(function(){
$('.user_list_wishes').sortable({
connectWith: ".user_list_wishes",
items: ".user_list_wish",
placeholder: "sortable_placeholder",
update: function(e, ui)
{
if (this === ui.item.parent()[0])
{
item_id = ui.item.data('item-id');
list_id = $(this).data('list-id');
position = ui.item.index();
$.ajax({
type: 'POST',
url: $(this).data('update-url'),
dataType: 'json',
data: { id: item_id, wish: { row_order_position: position, list_id: list_id } }
}),
$("#wishes_count").html('<%= pluralize(list.wishes.count, "wish") %>')
}
}
})
})
This line of code:
$("#wishes_count").html('<%= pluralize(list.wishes.count, "wish") %>')
makes my application throw a NoMethodError undefined method 'wishes' for nil:NilClass
I believe it has something to do with how I render lists and reference them individually in my javascript?
Any suggestions on how to solve this problem is much appreciated!
You must handle the scenario where list is null using the following condition:
$("#wishes_count").html('<%= pluralize(list ? list.wishes.count : 0, "wish") %>')
I think the problem could be in your render call - according to the documentation:
If you have an instance of a model to render into a partial, you can use a shorthand syntax:
<%= render #customer %>
Assuming that the #customer instance variable contains an instance of the Customer model, this will use _customer.html.erb to render it and will pass the local variable customer into the partial which will refer to the #customer instance variable in the parent view.
So check that this is the case - do you have a partial called _lists.html.erb and a parent variable called list?
In one of my forms, I have an element called event_id which value I select from a dropdown box. Once I select event_id, I want to use Ajax to call the controller, and return panel_event_id as a ruby variable that I can use in the rest of the form. Here's what I'm doing:
In routes.rb, I have the following:
match 'panel_event_id', :to => "panels#event_id"
I have the following javascript function (not sure about the syntax):
<script type="text/javascript">
$('select').change(set_session_event_id);
function set_session_event_id()
{
var event_id = document.getElementById("event_id");
var event_id_value = event_id.value;
$.post('panel_event_id', { set_event_id: event_id_value });
}
</script>
What do I put in my panel_controler.rb, in the following method:
def panel_event_id
end
and how do I act on it back in my view?
You could render a json in your controller :
def panel_event_id
...
render :json => panel_event.as_json(:only => [ :id ])
end
After that, you could handle the success event of the post method. See the doc here : http://guides.rubyonrails.org/layouts_and_rendering.html and here http://api.jquery.com/jQuery.post/ and here http://api.rubyonrails.org/classes/ActiveModel/Serializers/JSON.html#method-i-as_json.
we are just started with Sigma Grid ,and it is awesome in its functionality when we compared to other Grids.
But i encountered some problem with Sigma Grid ,or may be with javascript.
I dont know whether the problem is with Grid or with my code.
I have a table with 3 fields namely MailID,MailName,MailData.
MailID is int ,MailName and MailData contains HTML content and it save as string in database.
When i load the Grid,i have some problems.
Problem 1 :
As i said above the Maildata contain html content,the following image is just a example with <*b> ,u can see that the HTML is automatically rendering on the grid itself ,i need the exact string.
please check the following image.
Problem 2 :
as u can see i have links on the grid,for edit,send,delete but on one filed its damaged.[check the image below ]
the code i used to render links is following .
{id: 'mailid' , header: "Action", width :120 , resizable : false, sortable : false , printable : false ,
renderer : function(value ,record,columnObj,grid,colNo,rowNo){
var no= record[columnObj.fieldIndex];
var cod = (record['maildata']);
return 'Edit | Delete';
Problem 3 :
The third value of MailData is 5 and it is integer ,when i alert the value its shows it correctly.
check the following image.
But when i alert the second value of maildata it giving error ,the second value of MailData is "hai newuser" ,it showing the following error on firebug.
missing ) after argument list
alert(hai newuser)
check the image below.
But when i alert 9th value of MailData it run correctly ,the content is <b>poy</b> ,this one is also save as string,but the grid automatically BOLD [which i dnt like].Check the image below.
also there are some others the 7the value contain ;".: etc ,also /b ,when i alert the data it showing the following error,
unexpected end of XML source
alert(<b>jjfdslkdjflsdnfsldfnf
dsOptions and ColOptions are following .
var dsOption= {
fields :[
{name : 'mailid' },
{name : 'mailname',type:"text" },
{name : 'maildata',type:"text" }
],
recordType : 'object',
}
function my_renderer(value ,record,columnObj,grid,colNo,rowNo)
{
var no= record[columnObj.fieldIndex];
return "<img src=\"./images/flag_" + no.toLowerCase() + ".gif\">";
}
function showalert(no)
{
$(document).ready(function()
{
$.post("http://localhost/power/index.php/power/give",{ name: no}, function(data)
{
//alert("Data Loaded: " + data);
$("#editor").show("fast");
$( '#txtar' ).ckeditor();
$('#txtar' ).val( data.maildata );
//$("#editor").html(data);
},"json"
);
});
}
var colsOption = [
{id: 'mailid' , header: "Mail ID" , width :60},
{id: 'mailname' , header: "Mail Name" , width :160 ,type:"text"},
{id: 'maildata' , header: "Mail Data" , width :190,type:"text" },
{header: "Group" , width :70,
editor : { type :"select" ,options : {'php':'php','asp':'asp'}
,defaultText : 'php' } },
{id: 'mailid' , header: "Action", width :120 , resizable : false, sortable : false , printable : false ,
renderer : function(value ,record,columnObj,grid,colNo,rowNo){
var no= record[columnObj.fieldIndex];
var cod = (record['maildata']);
return 'Edit | Delete';
} }
];
I am littlebit new in Javascript and Sigmagrid,i think that i am doing something worst with codes,pls help me to success.
Thank you.
Note : i posted the same Question on Sigma Grid Forum too,i think that it is not a problem.
Problem 2
The string cod contains a >
Problem 3
The string hai newuser needs to be contained in " or ' or it is considered a variable name
Basically you have to decide -- are you going to validate the html or not. If you don't validate the HTML then html errors in the data will show as errors on your page. You could also HTML escape the html so you will see the HTML codes -- this is probably the best plan.
Other sites use (like this one) use markdown -- this is easier to validate -- then they generate the actual HTML before display.
In addition you are having problems with the alert. Alert displays strings not HTML so you will see what you are seeing -- different results than expected depending on the HTML.
I would take a step back and ask yourself -- what is the type of the data, how am I going to display it. How am I going to validate that if it is HTML it is valid.
There are the problems you need to address -- your examples all stem from this problem.
Trying to figure out how to do this, using Sanderson begincollectionitems method, and would like to use autocomplete with a field in each row.
I think I see how to add a row with an autocomplete, just not sure the approach for existing rows rendered with guid.
Each row has an of field that the user can optionally point to a record in another table. Each autocomplete would need to work on the html element idfield_guid.
I'm imagining using jquery to enumerate the elements and add the autocomplete to each one with the target being the unique of field for that row. Another thought is a regex that maybe let you enumerate the fields and add autocomplete for each in a loop where the unique field id is handled automatically.
Does that sound reasonable or can you suggest the right way? Also is there a reasonable limit to how many autocomplete on a page? Thanks for any suggestions!
Edit, here's what I have after the help. data-jsonurl is apparently not being picked up by jquery as it is doing the html request to the url of the main page.
$(document).ready(function () {
var options = {
source: function(request, response) {
$.getJSON($(this).data("jsonurl"), request, function (return_data) {
response(return_data.itemList);
});
},
minLength: 2
};
$('.ac').autocomplete(options);
});
<%= Html.TextBoxFor(
x => x.AssetId,
new {
#class = "ac",
data_jsonurl = Url.Action("AssetSerialSearch", "WoTran", new { q = Model.AssetId })
})
%>
And the emitted html look okay to me:
<input class="ac" data-jsonurl="/WoTran/AssetSerialSearch?q=2657" id="WoTransViewModel_f32dedbb-c75d-4029-a49b-253845df8541__AssetId" name="WoTransViewModel[f32dedbb-c75d-4029-a49b-253845df8541].AssetId" type="text" value="2657" />
The controller is not a factor yet, in firebug I get a request like this:
http://localhost:58182/WoReceipt/Details/undefined?term=266&_=1312892089948
What seems to be happening is that the $(this) is not returning the html element but instead the jquery autocomplete widget object. If I drill into the properties in firebug under the 'element' I eventually do see the data-jsonurl but it is not a property of $(this). Here is console.log($this):
You could use the jQuery UI Autocomplete plugin. Simply apply some know class to all fields that require an autocomplete functionality as well as an additional HTML5 data-url attribute to indicate the foreign key:
<%= Html.TextBoxFor(
x => x.Name,
new {
#class = "ac",
data_url = Url.Action("autocomplete", new { fk = Model.FK })
})
%>
and then attach the plugin:
var options = {
source: function(request, response) {
$.getJSON($(this).data('url'), request, function(return_data) {
response(return_data.suggestions);
});
},
minLength: 2
});
$('.ac').autocomplete(options);
and finally we could have a controller action taking two arguments (term and fk) which will return a JSON array of suggestions for the given term and foreign key.
public ActionResult AutoComplete(string term, string fk)
{
// TODO: based on the search term and the foreign key generate an array of suggestions
var suggestions = new[]
{
new { label = "suggestion 1", value = "suggestion 1" },
new { label = "suggestion 2", value = "suggestion 2" },
new { label = "suggestion 3", value = "suggestion 3" },
};
return Json(suggestions, JsonRequestBehavior.AllowGet);
}
You should also attach the autocomplete plugin for newly added rows.