4

Hello I am trying to mimic the character counter on twitter. So when you type or paste the limit decreases. But the service I am writing this for will also have a url shortener so I want to offset it by the amount of characters the final URL will be. The Shortening takes place on the publishing end not when you enter the URL.

I have pretty much everything working but when I click off the element the offset does not exist anymore and the character count is set back to what it would be if the links were their full length. I believe this is because I am using the .change() Method rather than .bind("input paste") but input paste was not applying an offset.

/* Character Count for Posts */                
function checkPostForURL(post){
    var matches = [],
        urlexp = new RegExp("(^|[ \t\r\n])((http|https):(([A-Za-z0-9$_.+!*(),;/?:@&~=-])|%[A-Fa-f0-9]{2}){2,}(#([a-zA-Z0-9][a-zA-Z0-9$_.+!*(),;/?:@&~=%-]*))?([A-Za-z0-9$_+!*();/?:~-]))","g"),
        $linkShort = $('#linkstoshort'),
        matchIdx = 0;

    if ( post !== undefined ){
        if ( urlexp.test(post) ){
               var offset = 0;
               $('.shortenlinks').show();
               matches = post.match(urlexp);

               $linkShort.html('');

                for(; matchIdx < matches.length; matchIdx++) {
                    var match = matches[matchIdx],
                        matchOffset = match.length - 23;

                    offset += matchOffset;

                    $linkShort.append('<li>'+match+'</li>');
                }

                return offset;
        }
    }
 }

$(function(){
    var $postMsg = $('#post-msg'),
        message = $postMsg.text(),
        twstartchars = 140 - message.length,
        fbstartchars = 420 - message.length,
        $fbCount = $("#fb-char"),
        $twCount = $("#tw-char"),
        setRemainingChars = function (evt) {
            var a = $postMsg.val().length,
                post = $postMsg.val();        

            var offset = checkPostForURL(post);
            if ( offset ){
                a = a - offset;
            }

            $fbCount.text((420-a));
            $twCount.text((140-a));
            if ( a > 120 ){
                    $fbCount.css('color','red');
                    if ( a > 380 ){
                            $fbCount.css('color','red');
                    }
            }else{
                    $fbCount.css('color','#333');
                    $twCount.css('color','#333');
            }
        };

    $fbCount.text(fbstartchars);
    $twCount.text(twstartchars);

    $postMsg.on('keypress change', setRemainingChars);
});

UPDATE: I made a JS fiddle to better demonstrate what I am trying to do http://jsfiddle.net/FUADn/384/

BillPull
  • 8,335
  • 15
  • 54
  • 93
  • This is awesome. However, I am not sure where the number 21 comes from. I am assuming this is just how Twitter shortens the url. I went to twitter.com and i think that 21 needs to be a 23. There seems to be a 2 character discrepancy with your code and my twitter.com test. Awesome snippet otherwise :) – chrisallick Mar 30 '14 at 22:41
  • 1
    yea this was 3 years ago since then theyve needed to add more characters to that shortened URL which was a real pain in the ass to account for when making this. Definitely makes me realize how much better I am at JS now ill update the answer with a few modifications – BillPull Apr 01 '14 at 02:05
  • haha, it's not that bad. I am about to send a site live that basically uses your code with a slight modification and wrapped into a jquery plugin so i can just get the computed value. good snippet! – chrisallick Apr 02 '14 at 01:46

1 Answers1

0

Have you tried binding a .keyup() event on the input instead of a change event? This should technically work and keep the binding after you use the moust etc.

Jamie
  • 970
  • 1
  • 10
  • 29
  • I tried keyup with the same results. Could you provide a code example or modify the jsfiddle above. – BillPull Nov 29 '11 at 20:19
  • http://jsfiddle.net/FUADn/2/ - this seems to work fine for me when I move out of the box – Jamie Nov 29 '11 at 20:55