CSS input styling antics

Dear Lazyweb,

How do I style an INPUT element so that its contents behave like a DIV, wrapping text and expanding height to fit?

I have a page that has an "edit' mode where I've got a bunch of populated form elements, and in non-edit mode, those are styled to just look like normal text. It looks a little like the following. I want the thing on the left to look like the thing on the right when the box is un-checked.

Existing:

Edit

Desired:

Edit

A. All work and no play makes Jack a dull boy.

C. All work and no play makes Jack a dull boy.

D. All work and no play makes Jack a dull boy.

33

I realize I could accomplish this by having a separate DIV that shadows the content of the INPUT elements and selectively exposing one or the other, but that's more of a hassle. This feels like it should be achievable with CSS.

Previously, previously, previously, previously.

Tags: , , ,

33 Responses:

  1. Via Mastodon

    is contenteditable on a regular div not an option here?

    • Kludge Guru says:
      Via Mastodon

      seconded, do the opposite of what you describe - make divs contenteditable, get innerHTML or innerText (or textContent? I always forget the difference between the two)

      Edit: or maybe just a textarea?

    • jwz says:
      Via Mastodon

      They also have to actually work as form submission fields, for saving the edits, and I don't think contenteditable allows that, so we're just back to shadowed elements again.

      • doable thisway says:
        United States

        https://glasshost.tech/using-html5-how-do-i-use-contenteditable-fields-in-a-form-submission/

        It's doable without frameworks but with regular old js.

        • jwz says:
          1
          United States

          Again, you did not read the assignment. I am not looking for a JS solution.

          • doable thisway says:
            2
            United States

            Not possible without javascript.  Possible without shadowing an input field (or introducing other placeholder elements).  The answer I linked is not the answer you referred to.

            Sometimes "no" is the actual answer, even if it's not the one you wanted.  I apologize for trying to be helpful.  I promise it won't happen again.  

            • jwz says:
              3
              United States

              The question was "can I do this with CSS" and "no" is as perfectly acceptable answer to that.

              "Here are a bunch of hacks to do this with JS" is not an answer to that question, and given that I already said "I know how to do this with JS and that is not the question that I am asking", that answer is obviously and explicitly unwelcome.

      • Via Mastodon

        Ah, yeah. :/

  2. Colinaut says:
    United States

    I know my way around CSS quite well and as far as I know this is not possible without some sort of javascript hack as you mention. Multiline is what textarea is for. In fact, the HTML spec specifies that it is for a single line. And it's not like a td or other element that you can add `display` css to make it behave different. form elements have their own rules. They behave more like built-in to the spec web components.

    • jwz says:
      United States

      Even switching the input elements to textarea doesn't do it because textarea has a fixed height and does not size with its content.

      • Colinaut says:
        United States

        Ah yeah lack autoresize is an issue for textarea. It's definitely a weirdness that there is not an easy css only way to handle it. CSS Tricks has a couple articles, which I assume you stumbled on, talking about how to handle it with js/css hacks or using a div with contenteditable. The latter is a cheeky hack but I'm not sure how well it will play with basic form submission, so I guess depends on your needs.

      • dusoft says:
        Denmark

        We might get the auto-sizing in a couple of months/years:
        https://github.com/whatwg/html/issues/6807

        Chrome already has experimental support, so hopefully it will be months.

  3. Curioso says:
    Via Mastodon

    <Input> is for one line of plain text only, with no wrapping.

    If you need multiline and line wrapping too, you should use <textarea>.

    If plain text is not enough, there is contenteditable; but usually is a pain to manage, so if you can't avoid this requirement, you better use one of the many libraries for editing rich text.

    • jwz says:
      3
      Via Mastodon

      As you can see from my example, textarea also doesn't work, as it does not auto-size height like div does.

      "Include half a megabyte of some bullshit framework" is about the most useless of all possible suggestions.

      • Curioso says:
        1
        Via Mastodon

        Sorry, missed that point. You may find this helpful: https://css-tricks.com/the-cleanest-trick-for-autogrowing-textareas/

        Why are you so hostile to using libraries? It is what everybody has been doing for rich text editing since rich text editing on the web became a thing. Reinventing the wheel never was a good engineering practice.

        • jwz says:
          11
          Via Mastodon

          Why am I so hostile to libraries? Because I'm not the kind of person who buys a new car because the "check engine" light came on.

          But please, lecture me on good engineering practices. I'm sure you have a lot to teach me.

          • Ivan says:
            2
            Croatia

            I totally agree with you. But the article he linked has a clever CSS only solution, did you take a look?

            • extra88 says:
              1
              United States

              It's not CSS-only, it needs `oninput="this.parentNode.dataset.replicatedValue = this.value"` on the <textarea> to work.

              • jwz says:
                5
                United States

                It's also ridiculously complicated, and probably fragile. If you're already going down the JS rathole, just using textarea.scrollHeight is much more straightforward and comprehensible.

                But, again, JS solutions misunderstood the assignment.

                I am apparently catnip for people who can't help but responding, "This isn't what you asked, but". Very much the 'more of a comment than a question" crowd.

          • 2
            Via Mastodon

            I wanted to make a resizeable panel - I could have used a multi-megabyte "bullshit framework" (after spending several days learning how to use it) or I could write 30 simple lines of JavaScript. I chose the latter. (I'm curious if there's a way of doing this with pure CSS; but I can live with this amount of pure JS)

            There's an example of autogrowing a textarea here, using a bit of JS (I have not tested it): https://developer.mozilla.org/en-US/docs/Web/API/HTMLTextAreaElement

        • 2
          Via Mastodon

          Libraries are a good way to get there fast. Writing for own is a good way to learn. I'm with @jwz here 🙂

          From experience, these effortless solutions can also start being a pita when you're no longer developing and are forced to upgrade, while my "reinvented wheels" tend to remain rock solid for many years. It's always a trade-off that also depend on your goals.

        • some rando says:
          1
          United States

          Retired engineers have the luxury of being stubborn about doing things their way, which naturally is the Good and Correct way. Common practice is, in fact, often fundamentally Bad and Incorrect, and sometimes they're the only people with the perspective to say so!

          Either way, scolding them about it is extremely silly.

          • jwz says:
            2
            United States

            I already blocked this dumbass on Mastodon after they tripled down, so no need to keep flogging them here where they won't see it.

        • phuzz says:
          2
          United Kingdom

          Why are you so hostile to using libraries?

          Some people are weird and old fashioned and don't think that a webpage should be multiple megabytes of javascript with about 50kB of actual content (and I am one of them).

  4. Frooble says:
    United States

    I've used this paradigm for years and years, but I've only done it by swapping out elements.

  5. jzw says:
    Via Mastodon

    seconding textarea if at all possible. Getting input to behave that way is probably doable with enough js and css. Expanding to fit is just a little inline js to change the size to match the input: https://stackoverflow.com/a/48460773

  6. Via Mastodon

    pretty sure there's no way to do it w/ css alone
    100% sure that, if it is possible, it would only work robustly after a world of pain. "one more victory like this and we're ruined" scenario

  7. Georg says:
    Bulgaria

    What I typically do in situations like this is use an <input id="foo"> element with no text. The text goes into a <label for="foo"> node. The input can be made to appear and disappear e.g. using the display= attribute in all the usual ways. No JS required.

  8. atotic says:
    6
    Via Mastodon

    impossible today, will be a one liner two years from now. csswg is working on this. form-sizing: normal; will do this for text area, shipping in chrome canary.
    https://x.com/yisibl/status/1704879401710846429?s=46&t=3SiBUO1_R4dAVRODdL9QuQ

    • jwz says:
      Via Mastodon

      Nice! What will that do for input type=text? "Be like div" is the obvious correct answer but I wouldn't want to assume.

      • atotic says:
        Via Mastodon

        I did not participate, my guess is they did not consider input=text. It's a weird edge case, like a text area where CR is not allowed.

  9. James Young says:
    Via Mastodon

    if you're still interested in an auto-resizing textarea, this article (and replies) from @simon might be useful: https://fedi.simonwillison.net/@simon/111156224107211174

  • Previously