Search code examples
google-sheetsformattingspreadsheetnumber-formattingconditional-formatting

Is there a way to have google sheets read imperial height as a number?


I'm making a sheet with details about a bunch of fictional characters, and one column I want to have is their height. I would also really like to use Conditional Formatting with a Color Scale to color-code the tallest and shortest characters, and everything in between. Unfortunately, I live in the US, and am used to height expressed in feet and inches (e.g. 5'10''), which Google Sheets of course does not recognize as a number. Is there any way to remedy this, besides writing everything in terms of just inches (e.g. 60), such that I could apply conditional formatting directly to the column?

I've tried different formats (e.g. 5'10), and I considered having a hidden column with just the inch value and have conditional formatting work off of that row (doesn't work with Color Scale as far as I can tell, since you can't input a custom formula). One thought I had is somehow formatting things as an improper fraction with a denominator of 12, but hiding the denominator? But I have no idea how that would work. I've Googled as best I can, but I haven't found anything (everything's just about changing row height, which makes sense in hindsight).


Solution

  • I understand that you have two goals in mind. First of all, you should decide which unit length to use for managing heights. I have chosen inches, but you could work with feet if you need. This will simplify the scenario and will allow you to work easily with the data, but you could always create a function that translates inches to the foot/inches combo in order to show the data to a third party. This is the example table that I will use:

    Initial situation

    And this is my code, I will explain it at the bottom:

    function main() {
      var sheet = SpreadsheetApp.getActiveSheet();
      var data = sheet.getDataRange().getValues();
    
      data = sortTable(data);
      sheet.getDataRange().setValues(data);
    
      for (var i = 1; i < data.length; i++) {
        data[i][2] = gradient(data.length, i);
      }
    
      for (var i = 1; i < data.length; i++) {
        sheet.getRange(i, 2).setBackground("#" + data[i][2][0] + data[i][2][1] +
          data[i][2][2]);
      }
    }
    
    function sortTable(data) {
      data.sort(function(a, b) {
        return b[1] - a[1];
      })
    
      return data;
    }
    
    function gradient(arraySize, position) {
      var relativePosition = position / arraySize;
      var topColor = [parseInt("00", 16), parseInt("7A", 16), parseInt("33",
        16)]; // Green
      var bottomColor = [parseInt("FF", 16), parseInt("FF", 16), parseInt("FF",
        16)]; // White
      var positionColor = [0, 0, 0];
    
      for (var i = 0; i < 3; i++) {
        positionColor[i] = Math.floor(topColor[i] * (1 - relativePosition) +
          bottomColor[i] * relativePosition).toString(16);
      }
    
      return positionColor;
    }
    

    First of all you have to read the data with a combination of getValues()/setValues(), and once you do that you can sort the table based on height so you can create the gradient later. Please notice how I separated the sorting function for better clarity.

    After that you need the gradient color for setBackground(). To do so I developed a simple linear gradient function that calculates the RGB code from the top to the bottom. In my example the gradient fades from green to white, but you can change it. I also separated the gradient script into its own function. At this point you already have the sorted table and its gradient colors, so you only have to use setValues() and you are done. Feel free to leave any comment if you have doubts about this approach. This would be the final result:

    Final situation

    UPDATE

    Based in your comments I get that you need an imperial height format. For that case, you could use =INT(B2)&"' "&TRIM(TEXT(ROUND(MOD(B2,1)*12*16,0)/16,"# ??/??")&"""") (assuming that B2 contains the height). This approach will use Sheets Formulas to calculate the remainder part of the height, and its expression as an irreducible fraction. This is the final result:

    Extra question