Substituir caracteres linha a linha em um JTextArea

Srs, boa noite,

Estou tentando fazer um código que leia linha sim, linha não de um arquivo texto conforme mostro abaixo e substituir caracteres por outro, dento de uma JTextArea.

A D A E7
Introdução
A
Um dia a areia branca
D
Seus pés irão tocar
E7
E vai molhar seus cabelos

Quero ler as notas em cima da letra da musica e trocar A ====> B , B =====> C# , C ===> D , D ====> E , E ==== F# , F ====> G, G=====>A , A# =====>C …, Quando quero trocar de tom uma musica, neste caso, quero tocar esta musica que esta em LA Maior para Si Maior.

Fiz um código com CASEs e IFs , só que o programa troca por exemplo o A =====>B, depois ele troca este B que eu já converti outra vez, ou seja, a cada passada de linha, o programa troca todas as cifras (texto) e o que eu quero é que ele troque linha a linha lida uma só vez, será que fui claro ? Vcs poderiam me dar uma ideia como fazer isso ??? Segue abaixo o código que fiz e que deu erro;

  // Cliquei no botão alterar
   if ((txttomatual.getText() .equals (txtnovotom.getText()))) {
           JOptionPane.showMessageDialog(null, "Tom atual e Novo tom, não podem ser iguais ");  
    }else{ 
      String tomAtual = txttomatual.getText();
      String tomNovo = txtnovotom.getText();
      String texto = txtarea.getText();        //pego o texto da jTextArea
      String[] linhas = texto.split("\n");
      for (int i = 0; i < linhas.length; i += 2) {    //leio linha a linha do texto, somente a linha das cifras
          System.out.println("cifra: " + linhas[i]);
           int indice=0;
           System.out.print(linhas[i]);               // i + 2 para acessar a próxima linha,  linha cifra
           while  ((indice < linhas[i].length())) {   // leio caracteres a caractertes
            char nota = linhas[i].charAt(indice);  // pego o caracter A.B,C,D,E.F.G, A#, C#,D# ,F# ...
            switch (tomAtual + tomNovo) {  // tenho 2 JTextFields, onde tenho o tom atual e o novo tom
              case "AB":             //Se a musica esta no tom de A e eu quero transporta-la para B
              if  (nota ==  'A') {        // se o caractere  lido for um A, eu substituo por B
                   txtarea.setText(txtarea.getText().replaceFirst("A", "B"));  
              }else if   (nota ==  'B') {      //Se o caractere lido for um B eu o substituo por C#  
                   txtarea.setText(txtarea.getText().replaceFirst("B", "C#"));
             }  
             if  (nota ==  'C') {  
                   txtarea.setText(txtarea.getText().replaceFirst("C", "D"));       
             }else if  (nota ==  'D') {  
                   txtarea.setText(txtarea.getText().replaceFirst("D", "E")); 
             } 
              if  (nota ==  'E') {  
                   txtarea.setText(txtarea.getText().replaceFirst("E", "F#"));     
              }else if  (nota ==  'F') {  
                   txtarea.setText(txtarea.getText().replaceFirst("F", "G")); 
              }    
                if  (nota ==  'G') {  
                   txtarea.setText(txtarea.getText().replaceFirst("G", "A"));         
             }
                           .
                           .
             break;
            default:
                JOptionPane.showMessageDialog(null, "Novo tom, so aceita A,B,C,D,E,F,G ou 
                                                                                  A#,C#,D#,E,F#,G#"); 
              
         }  // Fim Suitch  
             indice++;               // leio o próximo caractere na linha               
           }  // Fim while
     
      }  //Fim For

obrigado.

Armando

Cara, linha a linha é meio complicado, salvo se você tiver quebras explícitas (\n) ou similares.
O que ocorre é que o conteúdo da JTextArea é uma String única, independente de linhas ou não.
Caso você possua a indicação dos \n, então você precisa splitar a Stringona em várias Strings delimitadas pelo \n e, então, para cada linha, efetuar a substituição do que precisa.

1 curtida

Amigo, boa tarde,

Eu tenho este controle do (\n) conforme vc pode ver no código que fiz, o problema é que quando eu atualizo uma linha e escrevo de novo essa linha, o código escreve todo o texto e reescreve de novo.

Meu problema é quando eu escrevo a linha que modifiquei, eu, tentarei explicar de novo para ver se consigo ser compreendido.

Tenho um texto numa JtextArea (txtarea) em java , é a letra de uma musica e em cima da letra estão as notas(Cifras) A = LÁ B= SI D = RÉ E7 = MI 7, esta musica esta no tom de “LÁ Maior”

A D A E7
Introdução
A B
Um dia a areia branca
D
Seus pés irão tocar
E7
E vai molhar seus cabelos

  • Digamos que quero tocar essa musica que esta no tom de “Lá maior”, quero toca-la em “Sí Maior”. Logo, tenho que mudar todas as notas (cifras) em um tom, ou seja, o que é A = B o que é D=E o que é B=C# o que é E7= F#7 e assim por diante, isso é teoria musical.

  • O código que tentei fazer, conforme enviei, lê linha a linha, caractere por caractere, substitui a primeira linha (até aqui o programa funciona bem), mas ele modifica todas as linhas e não somente a que estou. Tentei usar a linha de baixo, mas o programa faz a mesma coisa, substitui todas as linhas, inclusive as linhas da letra da musica, onde tem A,B,C,D,E …

                   txtarea.setText(txtarea.getText().replaceFirst("A", "B"));  
    
  • Ou seja, ele deveria pegar uma linha, ler o caractere e substituir, a 2ª linha (onde temos a linha da letra , não me interessa, por isso pulo 2 linhas), leio a 3ª linha, pego o caractere, substituo e vou para a 5 linha …

  • Sei o erro que acontece no código, só não sei conserta-lo.

  • Seguinte; o programa lê a linha e substitui o caractere, de acordo com a linha abaixo;

    txtarea.setText(txtarea.getText().replaceFirst(“A”, “B”)); //substituo A por B (Lá por SI)

  • Só que o código substitui todo o texto que esta na JTextArea que contenha A por B e quando vou ler a linha seguinte (linha 3) o código volta a substituir a linha 1 e inclusive ele altera a letra da musica, caso tenha a letra (A, B,C,D,E,F).

  • Quando na verdade, eu quero que ele altere as notas da 1 linha, somente as notas, as notas da 3 linha, as notas da 5 linha …

  • Melhor falando, quero alterar cada nota que esta na linha onde tenho as notas, (linha sim , sim não) e substituir no texto que esta na JtextArea. Como eu altero somente um caractere por linha, salvo esta linha e faço o mesmo para a outra linha que contenha cifras.

  • Muito obrigado pela pronta ajuda , fico no aguardo de resolver este problema.

Obrigado.

Armando

  • Amigo, muito obrigado pela rapidez da sua ajuda, mas será que agora eu me fiz mais claro

Veja se assim funciona:

		String tomAtual = txttomatual.getText();
		String tomNovo = txtnovotom.getText();
		String texto = txtarea.getText(); // pego o texto da jTextArea
		String[] linhas = texto.split("\n");
		for (int i = 0; i < linhas.length; i += 2) { // leio linha a linha do texto, somente a linha das cifras
			System.out.println("cifra: " + linhas[i]);
			int indice = 0;
			System.out.print(linhas[i]); // i + 2 para acessar a próxima linha, linha cifra
			StringBuilder sb = new StringBuilder();
			
			while ((indice < linhas[i].length())) { // leio caracteres a caractertes
				char nota = linhas[i].charAt(indice); // pego o caracter A.B,C,D,E.F.G, A#, C#,D# ,F# ...
				switch (tomAtual + tomNovo) { // tenho 2 JTextFields, onde tenho o tom atual e o novo tom
				case "AB": // Se a musica esta no tom de A e eu quero transporta-la para B
					if (nota == 'A') { // se o caractere lido for um A, eu substituo por B
						sb.append("B");
					} else if (nota == 'B') { // Se o caractere lido for um B eu o substituo por C#
						sb.append("C#");
					} else if (nota == 'C') {
						sb.append("D");
					} else if (nota == 'D') {
						sb.append("E");
					} else if (nota == 'E') {
						sb.append("F#");
					} else if (nota == 'F') {
						sb.append("G");
					} else if (nota == 'G') {
						sb.append("A");
					} else {
						//caso seja espaço em branco ou outro qualquer
						sb.append(nota);
					}
					break;
				default:
					JOptionPane.showMessageDialog(null, "Novo tom, so aceita A,B,C,D,E,F,G ou A#,C#,D#,E,F#,G#");

				} // Fim Suitch
				indice++; // leio o próximo caractere na linha
			} // Fim while
			txtarea.setText(txtarea.getText().replace(linhas[i], sb.toString()));
		} // Fim For

Caro Amigo, boa noite,

Perfeito, era isso que eu queria e eu tinha que usar o “append(nota)” e no final do código txtarea.setText(txtarea.getText().replace(linhas[i], sb.toString()));

Cara, 10 ! muito bom, vc fez um cara feliz, gostaria muito de ter mais conhecimento sobre a linguagem Java, mas um dia eu chego lá.

Muito obrigado e que Deus o proteja e lhe ajude muito.

Vlw de + , brigado !!!

Armando.

1 curtida

O único meio de conhecer mais é estudando.