from 16x2 to 16x4 frequency analyzer

does anyone know how to convert this program to be used on a display 16x4
I would like to see the bars also on Line 3 and 4 of the display and not just on 1 and 2, does anyone know how to do?

#include <LiquidCrystal.h>

// The LCD is conected to pins 13,12,11,10,9,8

LiquidCrystal lcd(12, 11, 7, 6, 3, 2);

byte vumetro[8][8];

float vumetros[16];

// The analog pin 0 is used to read value.
int valor_analogico = 0; 
// The 6 & 7 pins are used for control the integrated.
int strobe = 4; 
int reset = 5; 
int valores_frecuencias[7]; 

void setup() {
  // Built the characters for bars.
  for (int j=0; j<=7; j++)  
  {
    for (int i=0; i<=7; i++)
    {
      if (i<=j)
      { vumetro[j][7-i] = B01110;}
//      { vumetro[j][7-i] = B01010;}  Uncomment this lines for getting other variants for bars.
//      { vumetro[j][7-i] = B11111;}      
      else
      { vumetro[j][7-i] = 0;}
    }
  }  
  for (int i=0; i<=7;i++)
  {
    lcd.createChar(i, vumetro[i]);
  }

  lcd.begin(16, 2);      
  for (int j=0; j<=7;j++)
  {
    lcd.setCursor(j, 0);
    lcd.write(j);
    lcd.setCursor(j, 1);
    lcd.write(7);    
    
  pinMode(valor_analogico, INPUT);
  pinMode(strobe, OUTPUT);
  pinMode(reset, OUTPUT);
  analogReference(DEFAULT);

  digitalWrite(reset, LOW);
  digitalWrite(strobe, HIGH);
    
  }  
 
}

void loop() {
  
  digitalWrite(reset, HIGH);
  digitalWrite(reset, LOW);

  // The read of integrated is done by multiplexing.
  for (int i = 0; i < 7; i++)
  {
    digitalWrite(strobe, LOW);
    delayMicroseconds(5); 
    valores_frecuencias[i] = analogRead(valor_analogico);
    digitalWrite(strobe, HIGH);
  }

// It's necesary to interpolate for calculating 16 bars having only 7 values read.
for (int k=0; k<=15; k++)
  {
  switch (k) 
  {
    case 0:
      vumetros[k]= valores_frecuencias[0]/64;
      break;
    
    case 1:
      vumetros[k]= (valores_frecuencias[0]/64 + valores_frecuencias[1]/64)/2;
      break;

    case 2:
      vumetros[k]= valores_frecuencias[1]/64;
      break;
   
    case 3:
      vumetros[k]= (valores_frecuencias[1]/64 + valores_frecuencias[2]/64)/2;
      break;
 
    case 4:
      vumetros[k]= valores_frecuencias[2]/64;
      break;
    
    case 5:
      vumetros[k]= (valores_frecuencias[1]/64 + valores_frecuencias[2]/64 + valores_frecuencias[3]/64)/3;
      break;
        
    case 6:
      vumetros[k]= (valores_frecuencias[2]/64 + valores_frecuencias[3]/64 + valores_frecuencias[4]/64)/3;
      break;

    case 7:
      vumetros[k]= random(2)+valores_frecuencias[3]/64;
      break;
      

    case 8:
      vumetros[k]= random(2)+valores_frecuencias[3]/64;
      break;

    case 9:
      vumetros[k]= (valores_frecuencias[2]/64 + valores_frecuencias[3]/64 + valores_frecuencias[4]/64)/3;
      break;

    case 10:
      vumetros[k]= (valores_frecuencias[3]/64 + valores_frecuencias[4]/64 + valores_frecuencias[5]/64)/3;
      break;

    case 11:
      vumetros[k]= valores_frecuencias[4]/64;
      break;

    case 12:
      vumetros[k]= (valores_frecuencias[4]/64 + valores_frecuencias[5]/64)/2;
      break;

    case 13:
      vumetros[k]= valores_frecuencias[5]/64;
      break;

    case 14:
      vumetros[k]= (valores_frecuencias[5]/64 + valores_frecuencias[6]/64)/2;
      break;

    case 15:
      vumetros[k]= valores_frecuencias[6]/64;
      break;
  }

  Dibuja_vumetro(k, vumetros[k]);
  delay(2);
  }
  
}

void Dibuja_vumetro(int posicion, int altura)
{
  if (altura>7)
  {
    lcd.setCursor(posicion, 1);
    lcd.write(7);
    lcd.setCursor(posicion, 0);
    lcd.write(altura-8);    
  }
  else
  {
    lcd.setCursor(posicion, 1);
    lcd.write(altura);
    lcd.setCursor(posicion, 0);
    lcd.write(32);    
  }
}

You should start out by changing lcd.begin(16, 2); to lcd.begin(16, 4);

Now, in a perfect world, you should be able to set the cursor with

lcd.setCursor(j, 2);

or

lcd.setCursor(j, 3);

for the appropriate line.

Unfortunately the LiquidCrystal library does not deal with 16x4 displays correctly so without some changes to your code or to the library your output is going to be offset by four spaces.

Here are some previous threads dealing with the problem.
LCD 16x4 setCursor is not working right - Interfacing - Arduino Forum September 19, 2009
LiquidCrystal 16x4 error - Bugs & Suggestions - Arduino Forum March 13, 2010
[solved] 16x4 LCD: Characters in row 3&4 are moved to the right - Displays - Arduino Forum June 06, 2011
Problem in LiquidCrystal lib (20x4) - Displays - Arduino Forum August 20, 2011
A 16 X 4 acting like 32 X 2 - Displays - Arduino Forum February 26, 2012
LiquidCrystal library error with PC1604 display - Displays - Arduino Forum September 28, 2013

There is a thread with a very simple fix. Look at reply #18
[solved] 16x4 LCD: Characters in row 3&4 are moved to the right - #19 by system - Displays - Arduino Forum June 17, 2012

Don

Thanks for the repaly
I have solved the problem of the offset on the third and fourth raw (it is a bug of the arduino liquid crystal library)

My big problem is to create the carachter for the basr and associate it with the height read by the algoritm

// Built the characters for bars.
  for (int j=0; j<=7; j++)  
  {
    for (int i=0; i<=7; i++)
    {
      if (i<=j)
      { vumetro[j][7-i] = B01110;}
//      { vumetro[j][7-i] = B01010;}  Uncomment this lines for getting other variants for bars.
//      { vumetro[j][7-i] = B11111;}      
      else
      { vumetro[j][7-i] = 0;}
    }
  }  
  for (int i=0; i<=7;i++)
  {
    lcd.createChar(i, vumetro[i]);
  }

I don't understand how i can convert it to create the characters also fo the third and fourth raw

It is ok also if i use 3 raw instead of 4

UP