How can I use Ractive's on-tap attribute with Slim templates? - slim-lang

In my Slim template, I have:
th class=="sortable {{ sortColumn === 'name' ? 'sorted' : '' }}" on-tap=="sort:name" Name
This renders:
<th class="sortable sorted">Name</th>
The sort method is not being called when the item is clicked.
Should the on-tap attribute work in this case or does it need a different syntax? I have tried Slim's splat attribute:
th class=="sortable {{ sortColumn === 'name' ? 'sorted' : '' }}" *({:on-tap => ["sort:name"]})
but Slim complains when it hits on-tap.
Any help is appreciated.

EDITED: sorry, I misunderstood first time around. Based on this:
The sort method is not being called when the item is clicked.
I suspect you're mixing up method calls versus events.
If you want to call a method on the ractive instance, the syntax is:
on-tap='sort("name")'
And would be handled via:
new Ractive({
sort: function(name){
}
});
If you want to raise an event, you would use the syntax you have:
on-tap='sort:name'
And handle it via:
new Ractive({
oninit: function(){
this.on('sort', function(event, name){
});
}
});
See http://jsfiddle.net/yccknhh5/.

Related

Bootstrap select2 placeholder in laravel 5.3

I'm using select2 for my laravel project:
https://select2.github.io/examples.html
And I populate my select menus like this:
{{ Form::select('category_id', ['' => ''] + $categories, null, ['id' => 'category_id', 'class' => 'select2']) }}
And my js:
$(".select2").select2({
placeholder: "Select a category"
});
But this doesn't work, the placeholder doesn't show. Any advice?
Can you include your generated html code?. I think the problem is your selector $(".select2"). The js code inside the select2 function looks ok for me. Try putting the id of the select inside the jQuery function.
So for example if your generated html code is
<select id="my_super_selector">
<option val="1">1</option>
...
</select>
You should use $('#my_super_selector'). Try it and let me know!
Cheers!

CakePHP controller to build and send Form as HTML to Jquery UI Dialog Box

I am using cakePHP and Jquery UI for a small project.
I have an 'Add Item' link on my index.ctp of Item.
I want to show a jQuery UI dialog with the forum in for adding an Item when the 'Add Item' link is clicked.
So that I can make use of cakePHP's awesome FormHelper I want the controller's add() method to return the html the FormHelper creates if($this->request->is('ajax')) but this is giving me Internal Server Errors (when I Inspect Element in Chrome).
I know this isn't very MVC but my reasoning is that I want my app to work if the user has Js enabled or not, therefore the 'Add Item' link shows the add.ctp View if they don't have jQuery but if they do I've got preventDefault() in my jQuery script.
The jQuery click handler then sets up the dialog box's properties (jQueryUI Dialog Box) and then makes an ajax request to add() for the form.
I copied and pasted the FormHelper code I used on add.ctp but instead of echoing, added each line to $htmlString. I then called echo $htmlString; exit(); but here I get the 500 Internal Server Error.
If I comment out all the FormHelper lines in the add() function everything works ($htmlString is just "") so there is something going wrong here.
As I said I know this isn't very MVC-y but I can't think of another way to do it. Could I potentially get add.ctp returned rather than the copy and pasted code? That would keep the MVC model right and also if $this->layout = 'ajax' then I will only get the exact add.ctp file code right?
Thanks for your time and help in advance.
Edit - Added jQuery ajax request and cakephp Controller add() function
Jquery ajax request:
$('.add_project').click(function(event) {
//Kill default
event.preventDefault();
$.ajax({
url : $(this).attr('href'),
type : 'post',
data : 'ajax=1',
dataType: 'html',
success: function(response) {
alert(response);
//Check jquery loaded
if(jQuery.ui) {
//Fill dialog with form
$("#dialog").html(response).show();
//Show dialog
$("#dialog").dialog("open");
}
}
});
});
CakePHP Controller code:
public function add()
{
//If this has been requested with ajax then give the form that we create on add.ctp
if($this->request->is('ajax'))
{
App::import('Helper', 'Form');
$this->loadModel('Project');
$html = '';
$html += $this->Form->create('Project');
$html += $this->Form->input('name');
$html += $this->Form->input('colour', array(
'options' => array('blue' => 'Blue', 'green' => 'Green', 'red' => 'Red', 'orange' => 'Orange', 'yellow' => 'Yellow')
));
$html += $this->Form->end('Create Project');
echo html;
exit();
}
I'm pretty positive it's nothing to do with the ajax request it's more of a problem in cakephp that it doesn't like to use the FormHelper in the controller. I know this is bad MVC practice but I can't think of another way to do this dynamically (as in the fact that cakephp builds the html tags based on the Model).
Thanks again.
The 500 Internal Server error you are receiving is because you are using a Helper within a Controller.
However! you can pass a view back through your ajax request.
Create the method in your controller. Create the view with the form helper
ajaxForm.ctp
$this->Form->create('Project');
$this->Form->input('name');
$this->Form->input('colour', array(
'options' => array('blue' => 'Blue', 'green' => 'Green', 'red' => 'Red', 'orange' => 'Orange', 'yellow' => 'Yellow')
));
$this->Form->end('Create Project');
controller
public function ajaxForm(){
if($this->request->is('ajax')){
$this->layout = 'ajax'; // to avoid returning your full layout
$this->render('ajaxForm');
}
}
Separate your html and frontend code from the php backend code your add function can be empty if you aren't passing any data to the view and you won't need to check for ajax if the add function is not being called by non ajax requests. It will be dedicated to your ajax request in your view.
//controller file
App::import('Helper', 'Form');
public function add()
{
}
//App/Views/Projects/add.ctp file
echo $this->Form->create('Project');
echo $this->Form->input('name');
echo $this->Form->input('colour', array(
'options' => array('blue' => 'Blue', 'green' => 'Green', 'red' => 'Red', 'orange' => 'Orange', 'yellow' => 'Yellow')
));
echo $this->Form->end('Create Project');

How to prevent JqueryUI from suppressing http calls in an accordion element header

I'm using the following code in a rails partial to place a call to a controller action upon expansion of an accordion element header:
<a> <%= link_to candidate[:title], :controller => :books, :controller=> :confirm_details, :remote => :true, :candidate => candidate %></a>
<div id=<%= candidate[:asin].to_s %>>
</div>
This partial takes a collection of candidates and creates an accordion widget with an anchor as the accordion section header, each such header's href pointing to the books controller action get_details. It also generates a div which has a unique ID for the candidate as it's id attribute.
The get_details action is set up to grab the appropriate div based on that id number and populate its html with data pulled from the controller action.
The problem is that clicking on the anchor tag should both expand the accordion and place a call to the controller, however no http request is being generated. Is Jquery's default behavior to suppress calls from such elements? Should I be using a different tactic? My original thought is that this is the best approach as it lets me use rails' conventional ajax functionality 100%.
Thanks in advance.
What you could do is delegate the click event on those anchors to the accordion element and do whatever you need to place the call to the controller. This handler will be executed along with the default click handler of the accordion:
$( "#accordion" )
.accordion()
.on('click', 'h3 > a', function() {
console.log(this.href);
});​
DEMO

ASP.Net MVC ActionLink

I'm trying to create an ActionLink in one of my views that sends the selected value of a dropdown list to a new action. So far I have this, I just need to find a way to populate the ID on the end of my ActionLink.
<%= Html.DropDownList("StatusDropDown") %>
<%= Html.ActionLink("Apply","Index",new {Controller="Tasks", Action="Index", id="DROPDOWN LIST SECLECTED VALUE"}) %>
Obviously this link would need to be updated whenever the selected index of the drop down is changed. Is this something I need to do in javascript or is there a better way of managing this from within ASP.Net MVC?
Thanks
If you don't want to use form submission (i.e., want the parameter passed as part of the url instead of a form parameter), you'll need to build the url client-side with javascript.
<%= Html.DropDownList("StatusDropDown") %>
<a id="applyLink" href="#">Apply</a>
<script type="text/javascript">
function setHref( elem, val )
{
if (val) {
$(elem).attr( "href", "/Tasks/" + val );
$("#applyLink").unbind("click");
}
else {
$(elem).attr( "href", "#" );
$("#applyLink").click( function() { alert( "No value chosen" ); } );
}
}
$(function() {
var dropdown = $("#StatusDropDown");
dropdown.change( function() {
setHref( this, $(this).val() );
});
setHref( dropdown, null );
});
</script>
A link goes to another page, it is in effect a redirect. The only way to update where that link goes to with reference to the drop down list is with javascript.
It sounds like you want a kind of submit action. In that case you should use a form and a submit button, creating the appropriate handlers in your controller. Remember you can just do a redirect in your controller based upon the submitted value of the form. So something like this:
<form method="post" action="/MyForm">
<input type="select" name="mySelect">
<option value="1">First Option</option>
<option value="2">Second Option</option>
</input>
</form>
And in your controller:
public ActionResult MyForm(int mySelect)
{
return Redirect(String.Format("myurl?id={0}", mySelect));
// Note the above is only preferable if you're going to an external link
// Otherwise you should use the below:
return RedirectToAction("myAction", new { id = mySelect });
}
Obviously in this simplified example, the MyForm proxy to your desired action is redundant, but it illustrates the idea so you can apply it to your specific situation.

link_to method and click event in Rails

How do I create a link of this type:
<a href="#" onclick="document.getElementById('search').value=this.value">
using method link_to in Rails?
I couldn't figure it out from Rails docs.
You can use link_to_function (removed in Rails 4.1):
link_to_function 'My link with obtrusive JavaScript', 'alert("Oh no!")'
Or, if you absolutely need to use link_to:
link_to 'Another link with obtrusive JavaScript', '#',
:onclick => 'alert("Please no!")'
However, putting JavaScript right into your generated HTML is obtrusive, and is bad practice.
Instead, your Rails code should simply be something like this:
link_to 'Link with unobtrusive JavaScript',
'/actual/url/in/case/javascript/is/broken',
:id => 'my-link'
And assuming you're using the Prototype JS framework, JS like this in your application.js:
$('my-link').observe('click', function (event) {
alert('Hooray!');
event.stop(); // Prevent link from following through to its given href
});
Or if you're using jQuery:
$('#my-link').click(function (event) {
alert('Hooray!');
event.preventDefault(); // Prevent link from following its href
});
By using this third technique, you guarantee that the link will follow through to some other page—not just fail silently—if JavaScript is unavailable for the user. Remember, JS could be unavailable because the user has a poor internet connection (e.g., mobile device, public wifi), the user or user's sysadmin disabled it, or an unexpected JS error occurred (i.e., developer error).
To follow up on Ron's answer if using JQuery and putting it in application.js or the head section you need to wrap it in a ready() section...
$(document).ready(function() {
$('#my-link').click(function(event){
alert('Hooray!');
event.preventDefault(); // Prevent link from following its href
});
});
just use
=link_to "link", "javascript:function()"
another solution is catching onClick event and for aggregate data to js function you can
.hmtl.erb
<%= link_to "Action", 'javascript:;', class: 'my-class', data: { 'array' => %w(foo bar) } %>
.js
// handle my-class click
$('a.my-class').on('click', function () {
var link = $(this);
var array = link.data('array');
});

Resources