10

I am new to ruby on rails and twitter bootstrap. Accept my apologize if my question sound dumb. I am using twitter bootstrap for my site design. I have been trying to use bootstrap to change my label to textbox using hyperlink button click.

<div class="control-group">
    <label for="name" class="control-label"><p class="text-info">Saghir<i class="icon-star"></i></p></label>
    <div class="controls">
        <a href="#">Edit</a>
    </div>

but I am unable to do so, should I use jquery to do so, or I can use bootstrap for that. Please point me to right direction. Thanks in advance

Edit Code is updated with hyperlink(it could be button too). it is like, when I click on "Edit" hyperlink my label should show content "Saghir" that can be used using placeholder attribute of bootstrap. I can submit form to update values to database.

Lain
  • 2,166
  • 4
  • 23
  • 47
Saghir A. Khatri
  • 3,429
  • 6
  • 45
  • 76
  • 2
    Bootstrap does not provide whatever it is that you're seeking. Use jQuery. If you want more help, you'll need to be a little clearer on what you want to do. For example, where is the code for the "hyperlink button" that would be clicked. And then what do you want the label text to be when it's clicked? – Chris Peters May 28 '13 at 12:52
  • i have update my question @ChrisPeters thanks for pointing me out. i am trying jquery now. Regards. – Saghir A. Khatri May 28 '13 at 12:59
  • @ChrisPeters I think what he's looking to do is to hide the `label` when a user clicks on the `edit` link and show a `text input` instead. .. – Amyth May 28 '13 at 13:02

5 Answers5

15

I think you need jQuery for it. Try this :

$('#edit').click(function() {
 var text = $('.text-info').text();
 var input = $('<input id="attribute" type="text" value="' + text + '" />')
 $('.text-info').text('').append(input);
 input.select();

 input.blur(function() {
   var text = $('#attribute').val();
   $('#attribute').parent().text(text);
   $('#attribute').remove();
 });
});
.control-label .text-info { display:inline-block; }
 
<label for="name" class="control-label"><p class="text-info">Saghir</p><i class="icon-star"></i></label>
<div class="controls">
   <a href="#" id="edit" class="btn">Edit</a>
</div>
<script src="//code.jquery.com/jquery-2.1.1.min.js"></script>

Update

If you want change label to input and text of label put into placeholder of input, try this for

$('#edit').click(function() {
 var text = $('.text-info').text();
 var input = $('<input type="text" placeholder="' + text + '" />')
 $('.text-info').text('').append(input);
});
.control-label .text-info { display:inline-block; }
<label for="name" class="control-label"><p class="text-info">Saghir</p><i class="icon-star"></i></label>
<div class="controls">
   <a href="#" id="edit" class="btn">Edit</a>
</div>
<script src="//code.jquery.com/jquery-2.1.1.min.js"></script>

jsfiddle jsfiddle 2

rails_id
  • 8,120
  • 4
  • 46
  • 84
13

As Chris said, Bootstrap does not provide this functionality as it is a front-end framework. you can use jQuery to achieve this. Though, you'll need to add some custom id's or classes to your elements to make sure you are only selecting the required elements. You can do something like the following:

HTML

<div class="control-group">
    <label for="name" class="control-label">
        <p class="text-info">Saghir<i class="icon-star"></i></p>
    </label>
    <input type="text" class="edit-input" />
    <div class="controls">
        <a class="edit" href="#">Edit</a>
    </div>
</div>

jQuery

$(document).ready(function() {
    $('a.edit').click(function () {
        var dad = $(this).parent().parent();
        dad.find('label').hide();
        dad.find('input[type="text"]').show().focus();
    });

    $('input[type=text]').focusout(function() {
        var dad = $(this).parent();
        $(this).hide();
        dad.find('label').show();
    });
});

CSS

.edit-input {
    display:none;
}

Here is a working JSFiddle for your reference.

Amyth
  • 32,527
  • 26
  • 93
  • 135
  • @anonymousxxx: According to the question OP wanted to change the label to an input box when the anchor link is clicked. That is what the above example does. – Amyth May 28 '13 at 13:37
3

Use a hidden input

<div class="control-group">
    <label for="name" class="control-label"><p class="text-info">Saghir<i class="icon-star"></i></p></label>
    <input type="text" class="input-medium" style="display:none;">
    <div class="controls">
        <a href="#" onclick="edit(this);">Edit</a>
    </div>
</div>

When user click on "Edit", grab the text from text-info (eg Saghir), hide the label, show the input and set the inputs placeholder-attribute.

function edit(element) {
    var parent=$(element).parent().parent();
    var placeholder=$(parent).find('.text-info').text();
    //hide label
    $(parent).find('label').hide();
    //show input, set placeholder
    var input=$(parent).find('input[type="text"]');
    $(input).show();
    $(input).attr('placeholder', placeholder);
}

working fiddle : http://jsfiddle.net/TKW74/

davidkonrad
  • 83,997
  • 17
  • 205
  • 265
  • @anonymousxxx, thank you :-) Of course, Saghir A. Khatri needs to implement a feature that enables the user to go back to "label-mode", and/or hide the link after the input has been made visible, but that should be easy. – davidkonrad May 28 '13 at 18:51
3

I know its a old question, But just added Update option to Saghirs answer ,

http://jsfiddle.net/integerz/k3p4vhnb/

    function edit(element) {
        var parent = $(element).parent().parent();
        var placeholder = $(parent).find('.text-info').text();
        //hide label
        $(parent).find('label').hide();
       //show input, set placeholder
        var input = $(parent).find('input[type="text"]');
        var edit = $(parent).find('.controls-edit');
        var update = $(parent).find('.controls-update');
        $(input).show();
        $(edit).hide();
        $(update).show();
        //$(input).attr('placeholder', placeholder);
    }

    function update(element) {
        var parent = $(element).parent().parent();
        var placeholder = $(parent).find('.text-info').text();
        //hide label
        $(parent).find('label').show();
        //show input, set placeholder
        var input = $(parent).find('input[type="text"]');
        var edit = $(parent).find('.controls-edit');
        var update = $(parent).find('.controls-update');
        $(input).hide();
        $(edit).show();
        $(update).hide();
    //$(input).attr('placeholder', placeholder);
    $(parent).find('label').text($(input).val());
}

This will enable the user to get back to the normal mode. Also the Ajax call for update can be triggered on update function.

Saghir A. Khatri
  • 3,429
  • 6
  • 45
  • 76
VIP
  • 89
  • 6
2

I fiddled a litte more with Amyth's answer. This one just lets you click the text to edit it. You just need to add a class to any text element to enable the functionality. Enter key updates the text. Click outside the input to abort.

HTML:

<span class="edit-on-click">Click to edit</span>

JS:

$(document).ready(function() {
  $('.edit-on-click').click(function() {
    var $text = $(this),
      $input = $('<input type="text" />')

    $text.hide()
      .after($input);

    $input.val($text.html()).show().focus()
      .keypress(function(e) {
        var key = e.which
        if (key == 13) // enter key
        {
          $input.hide();
          $text.html($input.val())
            .show();
          return false;
        }
      })
      .focusout(function() {
        $input.hide();
        $text.show();
      })
  });
});

JSFiddle

Update (implementing AJAX to update db value):

Here's how I ended up using it in practice: this uses data attributes on the original element for id, model, and field to update in an ajax request. (This is from a Django app using Bootstrap, so some lines might be obsolete for you depending on your setup.)

HTML:

<span onclick="editOnClick(this)" 
      data-id="123" 
      data-model="myapp.MyModel" 
      data-field="my_field">Click to edit</span>

JS:

function editOnClick(el) {
    var $text = $(el),
            $input = $('<input type="text" />');

    $text.hide()
            .after($input);

    $input.val($.trim($text.html())).show()
            .tooltip({title:"press ENTER to save<br>click outside to cancel", container:"body", trigger:'focus', html:true})
            .focus()
            .keypress(function(e) {
                var key = e.which;
                if (key == 13) // enter key
                {
                    $.ajax({
                        type: "POST",
                        data: {
                            value:$input.val(),
                            obj_id:$text.attr('data-id'),
                            obj_model:$text.attr('data-model'),
                            obj_field:$text.attr('data-field'),
                            csrfmiddlewaretoken:'{{ csrf_token }}'
                        },
                        url: "{% url 'edit_on_click' %}",
                        cache: false,
                        dataType: "html",
                        success: function(html, textStatus) {
                            $input.hide();
                            $text.html(html)
                                    .show();
                        },
                        error: function (XMLHttpRequest, textStatus, errorThrown) {
                            alert('Error: ' + XMLHttpRequest.responseText)
                        }
                    });

                    return false;
                }
            })
            .focusout(function() {
                $input.hide();
                $text.show();
            })
}
Felix Böhme
  • 508
  • 5
  • 12
  • This is awesome. Thanks. Do you think you can expand on how I would dynamically set the when editing the text? Right now it just makes an input field, but I need to have the ID from the original output of the text so I can do a post update. I loop through and output a series of tags in PHP and can include the ID in the span that gets clicked on. Make sense? – Jeff Solomon Nov 15 '16 at 22:00