1

I am attempting to convert my string into title case which I'm able to do successfully. using this method:

title.toLowerCase().split(' ').map(function (s) {
        return s.charAt(0).toUpperCase() + s.substring(1);
    }).join(' ');

But this current logic applies well for one specific title schema. I am attempting to customize it to work better in different scenarios but when doing so none of them have an effect on the outcome of the title.

For starters as seen in the code snippet below, the word (case) is lower case and that should be capitalized too. It seems to not capitalize the first letter after parentheses.

I also attempt to have an outcome where Tv = TV replace the word and = &. I am approaching this using the .replace method

How can I adjust the code snippet below in order to add these conditions?

let title = "Adjusting the title (case and test) on tv"

titleCase = title.toLowerCase().split(' ').map(function (s) {
        return s.charAt(0).toUpperCase() + s.substring(1);
    }).join(' ');
    
titleCase.replace(/ and /ig, ' & ');

titleCase.replace("Tv", "TV")

console.log(titleCase)

My expected outcome is : Adjusting The Title (Case & Test) On TV

maimok
  • 333
  • 1
  • 3
  • 12
  • You can split on a regex rather than a simple string `' '` — `title.split(/\W/)` splits on all "non-word" characters, so will also split on parentheses and get the "case", however _split_ drops the pattern/characters you split on, so you'd need a way to preserve punctuation. – Stephen P Sep 03 '20 at 00:52
  • @maimok I think my answer found a good solution, let me know if it helps you. Happy to explain too. – tonitone120 Sep 03 '20 at 01:59
  • Does this answer your question? [JavaScript titleCase function without regex](https://stackoverflow.com/questions/33766968/javascript-titlecase-function-without-regex) – AncientSwordRage Nov 30 '21 at 17:28

5 Answers5

4

letterToCapitalize finds the first occurrence of [a-zA-Z0-9_] in each word you're trying to capitalize (the first suitable letter of).

In your code, you must remember that .replace(...) actually returns a brand new string. It does not modify the string in place (in JavaScript, primitive data-types, of which strings are one, are not modifiable). The problem was you weren't assigning this new string to a variable that you were logging out.

let title = "Adjusting the title (case and test) on tv"

let titleCase = title.toLowerCase().split(' ').map((s) => {
    let letterToCapitalize = s.match(/\w/)[0];
    return s.replace(letterToCapitalize, letterToCapitalize.toUpperCase())
    }).join(' ');
    
titleCase = titleCase.replace(/and/ig, '&').replace("Tv", "TV");

console.log(titleCase)
tonitone120
  • 1,920
  • 3
  • 8
  • 25
  • I got at error when using this because it couldn't handle a "word" with no letters such as "&". `Uncaught TypeError: s.match(...) is null` – Keyslinger Feb 08 '22 at 23:59
0

solution is:

let title = "Adjusting the title (case and test) on tv";
let titleCase;

titleCase = title.toLowerCase().split(' ').map(function (s) {
        return s.charAt(0).toUpperCase() + s.substring(1);
    }).join(' ').replace(/ and /ig, ' & ').replace(/Tv/ig, "TV");

console.log(titleCase);
Emy
  • 639
  • 4
  • 13
  • I appreciate your response, would you know why the word `case` after the first `(` does not capitalize? this is an issue that I am having with strings that have a `( )` in the title. – maimok Sep 03 '20 at 00:51
  • @maimok the "case" is still uncapitalized because the split is being done on a single space, which makes the token `"(case"` — `charAt(0)` on that is the open-parenthesis, not the letter `c` – Stephen P Sep 03 '20 at 00:53
  • @StephenP thank you, is there any alternatives you know if I can use in place of the `charAt(0)`? It seems to adjust the 0 to a 1, 2 etc.. makes the string illegible – maimok Sep 03 '20 at 00:56
  • @maimok The problem is that splitting only on space is just too simplistic (see my comment on your question). If you split on space then you must _search_ for the first "word character" in the split results array, not just blindly capitalize `charAt(0)`. Titlecase is actually fairly complicated as there are words you are _not supposed_ to capitalize for proper titlecase (the, a, is, in, etc) and there's the problem you found with "TV"... basically anything already in all-caps should not be lowercased. (and yes, the matter does _entirely_ have to do with parentheses, not with "synchronization") – Stephen P Sep 03 '20 at 01:05
0

With the below method, all you need to do is to specify the words that should be converted to symbols in the symbol object and the words that need to be all upper case in the allUpperCase array.

let title = "Adjusting the title (case and test) on tv";
let reg  = /\w+/g;

// convert all words to titleCase
title = title.replace(reg, (word) => {
  return word.charAt(0).toUpperCase() + word.slice(1);
});

// convert words that should be symbols
const symbols = {'and': '&'};
for(symbol of Object.keys(symbols)){
  let str = symbol;
  title = title.replace(new RegExp(str, 'ig'), symbols[symbol]);
}

// convert all words that need to be allUppercase
const allUpperCase = ['TV'];
allUpperCase.forEach(item => {
  title = title.replace(new RegExp(item, 'ig'), found => {
    return found.toUpperCase();
  });
});

console.log(title);
AMD
  • 163
  • 1
  • 10
0

the solution in 1 line using Regex

const str = 'Adjusting the title (case and test) on tv';
const titleCase = (str) => str.replace(/\b[a-z]/gi, (cahr) => cahr.toUpperCase()).replace(/Tv/gi, 'TV');
-1

this is the solution:

let title = "Adjusting the title (case and test) on tv";
let titleCase;

titleCase = title
    .toLowerCase()
    .split(" ")
    .map(function (s) {
        return s.charAt(0) == '(' ? '(' + s.charAt(1).toUpperCase() + s.substring(2) : s.charAt(0).toUpperCase() + s.substring(1);
    })
    .join(" ")
    .replace(/ and /gi, " & ")
    .replace(/Tv/gi, "TV");

console.log(titleCase);
Emy
  • 639
  • 4
  • 13