Reputation: 13417
Im using jquery-tokeninput, but a fork of it which allows the User
to add new custom tokens (Tag
) for each Resource
.
Example here (Scroll down to the tag box and type a few letters. you can type ones that dont exist): http://www.tomsguide.fr/solutions/nouveau_sujet.htm
The current return value from the fork I'm using is this (new value in quotes):
16,42,'Subway',37,'McDonald\'s',734
I'm having extreme difficulty trying to handle this in Rails. This sums it up perfectly.
This is what I have so far, and its not working, probably for a lot of reasons I'm not seeing, but the main reason is that I need to create new Tag instances but not save them, that way I can somehow pass them back into the token input, and save the new Tags along with the new Resource when they submit the form. When you use Tag.new though, it doesnt create an ID.
attr_accessor :tokens_list
# CUSTOM TOKENS
def tag_tokens=(tokens)
self.tokens_list = tokens.split(",")
if new_custom_tokens?
self.tokens_list.each do |token|
tokens_list << token if token.include? "'"
end
end
self.tag_ids = self.tokens_list
end
def new_custom_tokens?
self.tokens_list.each do |token|
return true if token.include? "'"
end
false
end
def create
@title = "Submit Resource"
@resource = Resource.new(params[:resource])
assign_to_global_user?
# CUSTOM TOKENS
if @resource.new_custom_tokens?
custom_token_time_restriction
# Create Tag.new
end
if @resource.valid?
@resource.save
flash[:notice] = "Your link has been successfully submitted."
redirect_to root_url
else
render :action => :new
end
end
def assign_to_global_user?
if user_signed_in?
@resource.user_id = current_user.id
else
@resource.user_id = User.find_by_username("Global_User").id
end
end
private
# CUSTOM TOKENS
def custom_token_time_restriction
limit = 7 # days
if (@resource.user_id != User.global_user_id) and (Time.now - limit.days > User.find(@resource.user_id).created_at)
# TODO: Check if they are anonymous or their account is newer than 7 days
else
flash[:notice] = "You be Logged in to add new tags, and your account must be older than #{limit} days."
render :action => :new
end
end
<div class="field">
<%= f.label :tags %>
<%= f.text_field :tag_tokens, "data-pre" => @resource.tags.to_json(:only => [:id, :name]), :class => :tagbox %>
</div>
Upvotes: 0
Views: 696
Reputation: 479
I had the same problem. This is what I have done:
This is the function where I return tokens of search in json format.
tags = TagMaster.where("name LIKE ?", "%#{params[:q]}%").limit(10)
if tags == []
list << {"id" => "0","name"=>new_tag.rstrip}
else
tags.each { |tag| list << {"id" => tag.id.to_s, "name" => tag.name }}
end
respond_to do |format|
format.json { render :json => list.to_json, :layout => false }
end
Now this will allow show you whatever you type in auto complete dropdown and on clicked it will show as a token.
Now you can't add any more custom tokens because any token that is not in database will return id 0 so only one custom token is allowed at this point of time.
For that problem I did following.
var k = jQuery.noConflict();
k("#project_tags").tokenInput("tag_list", {
hintText: "Enter Tags for your Project",
noResultsText: "No Such Tags",
searchingText: "Looking for your Tags",
preventDuplicates: true,
theme: "facebook",
onAdd: function (item) {
if (item.id == '0') {
k.ajax({
url: '/add_project_tag',
data: { name: item.name },
success:function(data) {
k("#project_tags").tokenInput("add", {id: data, name: item.name});
k("#project_tags").tokenInput("remove", {id: '0' });
}
});
}
}
});
As you can see here i call add_project_tag where I store that custom tag into database and it returns id of that inserted tag. So now you simply add the same token with it's id and remove token with 0.
So now there won't be any token with 0 and you can add as many new token as you want.
Hope this helps. Throw your questions if any more complications.
Upvotes: 1