#1
  1. Plays with fire
    Devshed Beginner (1000 - 1499 posts)

    Join Date
    Aug 2003
    Location
    Barsoom
    Posts
    1,146
    Rep Power
    144

    Get only visible text, not overflow


    Hi--

    I'm trying to limit the amount of text a user can input into a field by what's visible. That is, I have a div that's styled with a font, size, height and width.

    When users enter text I'd like to prevent them from typing more than can fit. So far, I've got a text field that copies text to a styled div on the page as a preview.

    Is there a way to just capture the text that's visible and ignore anything that's considered overflow?

    Hope this makes sense...

    Thank you!
    “Be ashamed to die until you have won some victory for humanity.” -- Horace Mann

    "...all men are created equal." -- US Declaration of Independence
  2. #2
  3. Lazy Moderator
    Devshed Supreme Being (6500+ posts)

    Join Date
    Mar 2007
    Location
    Washington, USA
    Posts
    16,436
    Rep Power
    9645
    Put the text into another hidden div on the page, don't constrain its width, then check the width as they type. Remember that divs are naturally block-level so you'd have to inline/inline-block it, or use a span.

    Comments on this post

    • Frank Grimes agrees
    • s-p-n agrees : :O Clever!
  4. #3
  5. Plays with fire
    Devshed Beginner (1000 - 1499 posts)

    Join Date
    Aug 2003
    Location
    Barsoom
    Posts
    1,146
    Rep Power
    144
    Originally Posted by requinix
    Put the text into another hidden div on the page, don't constrain its width, then check the width as they type. Remember that divs are naturally block-level so you'd have to inline/inline-block it, or use a span.
    Interesting. I'll try this. I also need to check for text that's pasted, not just typed.

    Thank you!


    EDIT: This works great! What would you suggest for managing pasted text that's too long? Do I really need to write a function that deletes words until my max width is met?
    Last edited by Frank Grimes; August 31st, 2016 at 04:15 PM.
    “Be ashamed to die until you have won some victory for humanity.” -- Horace Mann

    "...all men are created equal." -- US Declaration of Independence
  6. #4
  7. Lazy Moderator
    Devshed Supreme Being (6500+ posts)

    Join Date
    Mar 2007
    Location
    Washington, USA
    Posts
    16,436
    Rep Power
    9645
    For pasting, fire your Javascript on the keyup event - rather than keypress, which is what I'd guess you're using now.

    For the user experience I would suggest not altering the text automatically but showing an error to the user that the text is too long. Then they are free to edit as they see fit until they meet the requirements. If you really want to take automatic action then yes, you basically have to keep removing words until it fits. You could try to be clever with a bit of math, like if the text is 125% of the width then you try cutting at 4/5th of the text, but it's not worth the added complexity.

    Removing words is as simple as a loop using
    Code:
    newvalue = oldvalue.replace(/\W+\w*$/, ""); // regex to remove the last word and stuff before it
    You should also do a sanity check that newvalue != oldvalue each time.

    If you're wondering about \w* instead of \w+, that's so text like "abc def " will replace to "abc def" then to "abc"; otherwise \W+\w+ would not match the first one and you'd trigger the sanity check.

    There's also the case of someone typing a single really long word, which would be removed entirely. In that case (newvalue == "", oldvalue != "") then you might want to start cutting letters instead of whole words - or decide that it's unlikely to be an issue and not do anything special.
  8. #5
  9. ~ bald headed old fart ~
    Devshed Newbie (0 - 499 posts)

    Join Date
    May 2005
    Location
    chertsey, a small town s.w. of london, england
    Posts
    356
    Rep Power
    132
    Hi there Frank Grimes,

    check out the attachment to see another possible solution.

    This example is based on a pre-selected character count.

    coothead
    Attached Files
    ~ the original bald headed old fart ~
  10. #6
  11. Plays with fire
    Devshed Beginner (1000 - 1499 posts)

    Join Date
    Aug 2003
    Location
    Barsoom
    Posts
    1,146
    Rep Power
    144
    @requinix -- Thanks again! I am using keyup, not keypress. After sleeping on this, I think what will work is displaying a warning to users that the text is too long and allow them to change it, just as you suggest. When they press SAVE, I'll do another check. If it's too long, I'll start truncating words until it isn't. I think after a couple times using this, they'll understand. I hope anyway, since they've ignored all my previous training and documentation.

    @Coothead -- Thank you! Unfortunately, I can't use a letter count since this isn't displayed with a monospaced font. M's are wider than I's, for example. The only way this will work for me is actual pixel width, which complicates everything.

    Thank you both!
    Last edited by Frank Grimes; September 1st, 2016 at 09:36 AM.
    “Be ashamed to die until you have won some victory for humanity.” -- Horace Mann

    "...all men are created equal." -- US Declaration of Independence
  12. #7
  13. Plays with fire
    Devshed Beginner (1000 - 1499 posts)

    Join Date
    Aug 2003
    Location
    Barsoom
    Posts
    1,146
    Rep Power
    144
    Originally Posted by requinix
    Removing words is as simple as a loop using
    Code:
    newvalue = oldvalue.replace(/\W+\w*$/, ""); // regex to remove the last word and stuff before it
    You should also do a sanity
    I had mixed results with this regex. It retained apostrophes and some other punctuation, which I also need to remove, so I went a different direction:

    Code:
    lastIndex = oldvalue.lastIndexOf(" ");
    newvalue = oldvalue.substring(0, lastIndex);
    Just separate by spaces. Not as elegant, but it works.
    “Be ashamed to die until you have won some victory for humanity.” -- Horace Mann

    "...all men are created equal." -- US Declaration of Independence

IMN logo majestic logo threadwatch logo seochat tools logo