简体   繁体   中英

Replace text of multiple nodes at once

I am trying to build an online version of my resume and I would like the names of the months in my work experience to shrink based on the size of the screen, eg have it go from January 2011 - January 2012 to Jan 2011 - Jan 2012.

Here is a sample of my HTML

<section id="work">
  <div id="job1">
    <ul> 
      <li>September 2013 - Present</li>
      <li>Job Title</li>
      <li>Employer Name</li>
      <li>Location</li>
    </ul>               
    <ul>
      <li>job duties</li>
      <li>job duties</li>
    </ul> 
  </div>    
  <div id="job2">
    <ul> 
      <li>January 2012 - September 2013</li>
      <li>Job Title</li>
      <li>Employer Name</li>
      <li>Location</li>
    </ul>             
    <ul>
      <li>job duties</li>
      <li>job duties</li>
    </ul> 
  </div>
</section>

I initially did this by shortening each text node one-by-one, like so:

function shrinkMonths(idName) {
        var dates = $(idName).find("ul:first-child li:first-child");
        var words = dates.text().split(" ");
        words[0] = words[0].substr(0,3);
        if (idName !== "#job1") {
            words[3] = words[3].substr(0,3);    
        }
        return words.join(" ");
    }

$("#job1").find("ul:first-child li:first-child").text(shrinkMonths("#job1"));
$("#job2").find("ul:first-child li:first-child").text(shrinkMonths("#job2"));

You can see this at http://codepen.io/polly_nomial/pen/nghJx

I would like to do this all at once so I selected all of my dates at once, and this created a string of all my dates but the year of last date was concatenated with the first month of the next date (September, 2013, -, PresentJanuary, 2012, -, September, 2013NextMonth). So I was able to split the text appropriately and shorten the months, but when I try to return the text, it gives back the entire string to each node instead of individually.

function shrinkMonths(list) {
  var words = list.split(" ");
  var temp1 = null;
  var temp2 = null;

  for(var i = 0; (4*i+3)+i < words.length; i++) {
    if(i === 0) {
      temp1 = words[4*i+3].slice(0,7);
      temp2 = words[4*i+3].slice(7);
      words.splice(4*i+3,1,temp1,temp2);
    }
    else {
      temp1 = words[(4*i+3) + i].slice(0,4);
      temp2 = words[(4*i+3) + i].slice(4);
      words.splice((4*i+3) + i,1,temp1,temp2);
    }
  }

  words[0] = words[0].slice(0,3);

  var k = 1;
  while(5*k+2 < words.length) {
    words[5*k - 1] = words[5*k - 1].slice(0,3);
    words[5*k + 2] = words[5*k + 2].slice(0,3);
    k++;
  }  

  return words.join(" ");
}

var change = shrinkMonths($(".work").find("div ul:first-child li:first-child").text());

$(".work").find("div ul:first-child li:first-child").text(change);

You can see this here http://codepen.io/polly_nomial/pen/Jorgn

So how do I select all the text nodes at once, change them, and then return each text node individually?

CSS only idea. What if instead of plain month name September you use something like this:

<span class="month" data-full="September" data-short="Sep"></span>

Then using media queries you can do this:

.month:after {
    content: attr(data-full);
}
@media (max-width: 600px) {
    .month:after {
        content: attr(data-short);
    }
}

Here we go. No Javascript involved. 7 lines of code. IE9+ (media queries), IE8+ ( :after ).

Demo: http://jsfiddle.net/ryAb3/

You want to iterate across the dates, not jam all their data together and then split it out:

    dates.each(function() {
       var date = $(this);
       var text = date.text();
       ...
       date.text(changedText);
    });

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM