7

.container {
  /* 
     Container's width can be dynamically resized. 
     I put width = 300px in the example to demonstrate a case 
     where container's width couldn't hold second msg 
  */
  width: 300px;
  display: flex;
  flex-direction: column;
  align-items: flex-start;
  padding: 1em;
  background-color: blue;
}

.parent{
  display:flex;
  flex-direction:row;
  flex-wrap:nowrap;
  padding:1em;
  background-color:red;
  box-sizing:border-box;
  margin-bottom: 1em;
}
.name{
  background-color:mistyrose;
  width: 70px;
  padding: 1em;
}
.msg{
  background-color:powderblue;
  max-width: 30vw;
  padding:.5em;
  word-wrap:break-word;
}
<div class='container'>
 <div class="parent">
    <div class="name">
      David
    </div>
    <div class="msg">
    How are you? How are you? How are you? How are you? How are you? How are you? How are you? How are you? How are you? How are you? How are you? How are you? How are you? 

    </div>
  </div>
  <div class="parent">
    <div class="name">
      Hannah
    </div>
    <div class="msg">
    somethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomething

    </div>
  </div>
</div>

Ideally , I want each msg to have max-width of 30vw, but at the same time respect parent's width. The first row behaves correctly, but the second row doesn't. If parent's width is resized to some value smaller than 30vw, the second msg will overflow.

I want something like max-width = min(30vw, parent's width)

NOTE: Container's width can be dynamically resized. I put width = 300px in the example to demonstrate a case where container cannot hold the second msg which somehow has width = it's max-width = 30vw.

You can also see the example at http://jsfiddle.net/vbj10x4k/231/

Phuc Nguyen
  • 73
  • 1
  • 5

3 Answers3

4

Simply set max-width:100% to .parent so this one respect the width of .container then rely on flex and your element will shrink by default. Also don't forget min-width:0 on the element itself to enable the element to shrink.

.container {
  width: 300px;
  display: flex;
  flex-direction: column;
  align-items: flex-start;
  padding: 1em;
  background-color: blue;
}

.parent{
  display:flex;
  flex-direction:row;
  flex-wrap:nowrap;
  padding:1em;
  background-color:red;
  box-sizing:border-box;
  margin-bottom: 1em;
  max-width:100%; /*Added this */
}
.name{
  background-color:mistyrose;
  width: 70px;
  padding: 1em;
}
.msg{
  background-color:powderblue;
  max-width:30vw;
  min-width:0; /*addedd this*/
  padding:.5em;
  word-wrap:break-word;
}
<div class='container'>
 <div class="parent">
    <div class="name">
      David
    </div>
    <div class="msg">
    How are you? How are you? How are you? How are you? How are you? How are you? How are you? How are you? How are you? How are you? How are you? How are you? How are you? 

    </div>
  </div>
  <div class="parent">
    <div class="name">
      Hannah
    </div>
    <div class="msg">
    somethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomethingsomething

    </div>
  </div>
</div>
Temani Afif
  • 245,468
  • 26
  • 309
  • 415
  • I updated the post to add note. I mean the container's width can be dynamically resized. So ideally I don't want to set fixed value to children's max-width :D – Phuc Nguyen Jun 15 '18 at 09:30
  • @PhucNguyen but at least did you understand why the issu ? ... remove the max-width and you will see how the first one and second behave – Temani Afif Jun 15 '18 at 09:37
  • no I don't understand. both `msg`s have the same class. first msg also has `max-width = 30vw`, but it still fits in the container, while the second one doesn't fit – Phuc Nguyen Jun 15 '18 at 09:41
  • @PhucNguyen but remove the max-width and see what is happeing ... you will see that the first one is already fitting and the second one is overflowing TOO much ... so max-width simply reduced this second overflow – Temani Afif Jun 15 '18 at 09:44
  • Perfect solution! Work on all browsers. I should have saved myself 1 day if I asked earlier. – Phuc Nguyen Jun 15 '18 at 10:14
1

If you do not need to support IE11 or safari, a simple solution would be to switch your word-wrap:break-word; with word-wrap: anywhere (working example)

If you need to support safari (but still not IE11), then instead replace word-wrap:break-word; with word-break: break-word. Note that word-break: break-word is deprecated in favour of word-wrap: anywhere.

I would also recommend switching word-wrap for its more commonly used alias: overflow-wrap. It will be more effective when used in a search term.

Also see: Difference between overflow-wrap and word-break?

Max Hay
  • 230
  • 2
  • 11
0

Just add :

word-break: break-all;

in .msg