Metoda zmieniająca język menu w projekcie Java Swing MVC

0

Witam. Od jakiegoś czasu próbuję w swoim programie w Swingu dodać funkcję tłumaczenia menu na różne języki. Miałem zamiar zrobić to tak. Plik tekstowy będzie po lewej zawierał zadeklarowaną w klasie "View" nazwę JComponentu a po prawej oddzielone myślnikiem jego tłumaczenie. W kontrolerze znajduje się metoda, która zamienia to na HashMapę, która z kolei jest przechowywana w klasie model. Teraz ręcznie, albo za pomocą jakiejś pętli robię listę JComponentów, które miałyby być przetłumaczone, Potem robię podwójną pętlę: dla każdego komponentu, dla każdego argumentu z hashMapy, jeśli ich nazwy są takie same, to ustawiam etykietę JComponentu na wartość z HashMapy. No i tutaj mam problem, bo niby mogę sobie odnaleźć nazwy zmiennych za pomocą

 Class<View> c = View.class;
 Field[] fields = c.getDeclaredFields();

ale chyba nie mogę wywołać w żaden sposób obiektu z takiej tablicy np. przez fields[i].getCośTam, żeby potem za pomocą "setText" ustawić mu inną etykietę. Może wszystko robię źle i od początku trzeba to było jakoś inaczej, no ale byłbym wdzięczny za podpowiedzi do tego i może przy okazji, do reszty kodu, co mógłbym poprawić. Dzisiaj próbowałem jakoś to zrobić poprzez listę metod użytych w klasie View, no ale też utknąłem w jednym miejscu. Załączam plik tekstowy, z którego robię HashMapę i cztery klasy nad którymi pracuję, ale jakby miał to być problem, to ta metoda, o której pisałem jest w klasie Controller i nazywa się "changeLanguage"

import java.io.IOException;

public class App {
	 
	 public static void main(String[] args) throws IOException, NoSuchMethodException, SecurityException {
		 
	  Model m = new Model();
	  View v = new View("Cipher_Studio");
	  Controller c = new Controller(m, v);
	  c.initController();
	  c.makeLangMenuMap();	  
	  c.changeLanguage();

	  c.makeADictionaryMap(m.getDictionariesPath());
	 }
	}

public class Controller {

	private Model model;
	private View view;

	public Controller(Model m, View v) {
		model = m;
		view = v;
	}

	public Controller() {
		// TODO Auto-generated constructor stub
	}

	public void initController() {
		view.getjGetFile().addActionListener(e -> loadFiles());
		view.getmOpenTextFile().addActionListener(e -> loadFiles());
		view.getjExecute().addActionListener(e -> execute());
		view.getjDirectDict().addActionListener(e -> makeADictionaryMap());
		view.getmLoadDictionaries().addActionListener(e -> makeADictionaryMap());
		view.getmSaveFile().addActionListener(e -> saveFiles());
		view.getmMenuLangFile().addActionListener(e -> makeLangMenuMap());
		view.getmExit().addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				view.getFrame().dispose();
			}
		});
	}

	public void makeLangMenuMap()  { //making hashMap from txt file that translating JComponents labels 

		JFileChooser jGet = new JFileChooser();
		File file = new File(Model.basicPath);
		jGet.setCurrentDirectory(file);
		HashMap <String,String> map = new HashMap<>();

		if (jGet.showOpenDialog(null) == JFileChooser.APPROVE_OPTION) 
		{
			file = jGet.getSelectedFile();
			try {
				Scanner scanner = new Scanner(file);
				while (scanner.hasNextLine()) {
					String line = scanner.nextLine();
					String parts[] = line.split("-", 2);
					map.put(parts[0], parts[1]);
				}
			} catch (FileNotFoundException e1) {
				// TODO Auto-generated catch block
				e1.printStackTrace();
			}
		}
		model.setCurrLangMenu(map);
//		 map.entrySet().forEach(entry->{
//			    System.out.println(entry.getKey() + " " + entry.getValue());  
//			 });
		}
		


	private void saveFiles() {
		JFileChooser jGet = new JFileChooser();
		File file = new File(model.getSavePath());

		jGet.setCurrentDirectory(file);
		jGet.setDialogTitle("Save results:");
		jGet.setName(view.getEnterTheNumField().getText());
		jGet.setApproveButtonText("Save");
		String s = model.getIsCipheredTxt() + model.getIsCaesarTxt() + "_key_value:_"
				+ model.getCypherValueForFileName() + "_" + model.getInputTextName(); // setting suggested file name
		jGet.setSelectedFile((new File(s)));

		if (jGet.showOpenDialog(null) == JFileChooser.APPROVE_OPTION) 
		{
			file = jGet.getSelectedFile();
			try {
				PrintWriter pw = new PrintWriter(file);
				Scanner scanner = new Scanner(view.getDecryptedTxt().getText());
				while (scanner.hasNext()) {
					pw.println(scanner.nextLine());
				}
				pw.close();
			} catch (FileNotFoundException e1) {
				// TODO Auto-generated catch block
				e1.printStackTrace();
			}
		}
	}

	private void loadFiles() {
		JFileChooser jGet = new JFileChooser();
		File file = new File(model.getFilePath());
		jGet.setCurrentDirectory(file);

		if (jGet.showOpenDialog(null) == JFileChooser.APPROVE_OPTION) // jeśli wybierzemy juz jakis plik
		{
			view.getJTextInput().setText(null);
			view.getDecryptedTxt().setText(null);

			file = jGet.getSelectedFile();
			model.setInputTextName(file.getName());
			try {
				Scanner scanner = new Scanner(file);
				while (scanner.hasNext()) {
					view.getJTextInput().append(scanner.nextLine() + "\n");
				}
			} catch (FileNotFoundException e1) {
				// TODO Auto-generated catch block
				e1.printStackTrace();
			}
		}
	}

	private void execute() { //depends on radio buttons settings it decrypt or encrypt text for Ceasar or Vigenere cipher

		view.getDecryptedTxt().setText(null);
		String input = view.getJTextInput().getText();
		String output = "";

		if (view.getJrCipher().isSelected()) {
			String sCipher = view.getEnterTheNumField().getText();

			if (view.getJrCeasar().isSelected()) {
				try {
					int sCipherNum = Integer.parseInt(sCipher);
					CaesarCipher caesar = new CaesarCipher(sCipherNum);
					output = caesar.encrypt(input);
				} catch (Exception e) {
					JOptionPane.showMessageDialog(null, "Enter the number between 0 and 26");
					// TODO: handle exception
				}
			} else

			{
				int[] array = new int[sCipher.length()];

				for (int i = 0; i < sCipher.length(); i++) {
					char curChar = sCipher.charAt(i);
					if (model.alphabet.indexOf(curChar) == -1) {
						JOptionPane.showMessageDialog(null,
								"Only latin letters allowed");
						Arrays.fill(array, 0);
						break;
					} else {
						array[i] = model.alphabet.indexOf(curChar);
					}

				}
				VigenereCipher vc = new VigenereCipher(array);
				output = vc.encrypt(input);
			}
		}

		else {
			if (view.getJrCeasar().isSelected()) {
				CaesarCracker cc = new CaesarCracker();
				output = cc.decrypt(input);
			} else {
				VigenereBreaker vb = new VigenereBreaker();
				output = vb.breakForAllLanguages(input, model.getListOfDictionaries());
			}
		}
		model.setCypherValueForFileName(view.getEnterTheNumField().getText());
		if (view.getJrCipher().isSelected()) {
			model.setCiphered(true);
			model.setIsCipheredTxt("Encrypt_");
		} else {
			model.setCiphered(false);
			model.setIsCipheredTxt("Decrypt_");
		}
		if (view.getJrCeasar().isSelected()) {
			model.setIsCaesarTxt("Caesar_Cipher_");
		} else {
			model.setIsCaesarTxt("Vigenere_Cipher_");
		}
		view.getDecryptedTxt().append(output);
	}

	private void makeADictionaryMap() {
		VigenereBreaker vb = new VigenereBreaker();

		JFileChooser chooser = new JFileChooser();
		File file = new File(model.getDictionariesPath());
		chooser.setCurrentDirectory(file);
		chooser.setMultiSelectionEnabled(true);
		chooser.showOpenDialog(null);
		model.setDictionaries(chooser.getSelectedFiles());
		model.setListOfDictionaries(vb.makeDictionaryMap(model.getDictionaries()));
	}

	public void makeADictionaryMap(String dictionaryAdress) {
		VigenereBreaker vb = new VigenereBreaker();

		File[] fileList = new File(dictionaryAdress).listFiles();

		model.setDictionaries(fileList);
		model.setListOfDictionaries(vb.makeDictionaryMap(model.getDictionaries()));
	}
	
	public void changeLanguage() throws NoSuchMethodException, SecurityException, IllegalAccessException, IllegalArgumentException, InvocationTargetException 
	{
		Class<View> c = View.class; 
		Method methods[] = c.getMethods();//tablica wszystkim metod z kontrolera
		for(String s: model.getCurrLangMenu().keySet()) 
		{
			s = s.replaceAll(" ", "");		//umknęło mi wcześniej, żeby wywalić spacje 
			for(Method m: methods) 
			{
				if(m.getName().contains("get"+s.toString())) //zeby ustawić właściwy getter dla componentu, ktorego etykietę chciałbym zmienić
						{	
					//no i tutaj wydaje mi się powinienem jakoś dostać się do JComponentu i za pomocą "setName"
					//ustawić mu etykietę zgodną z tłumaczeniem zawartym w pliku tekstowym
						}
			
		}
		}
		// Here i want to compare "fields[]" with hashmap langMenu and set label name
		// for each visible JComponent in menu according
		// with hashMap worth
	}	
}

import static javax.swing.GroupLayout.Alignment.BASELINE;
import static javax.swing.GroupLayout.Alignment.CENTER;
import static javax.swing.GroupLayout.Alignment.LEADING;

import java.util.ArrayList;
import java.util.Collections;
import java.util.HashMap;

import javax.swing.ButtonGroup;
import javax.swing.GroupLayout;
import javax.swing.JButton;
import javax.swing.JComponent;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JMenu;
import javax.swing.JMenuBar;
import javax.swing.JMenuItem;
import javax.swing.JRadioButton;
import javax.swing.JScrollPane;
import javax.swing.JTextArea;
import javax.swing.JTextField;

public class View {
	
	private JFrame frame;
	private JTextArea JTextInput, decryptedTxt;
	private JTextField enterTheNumField ;		
	private JLabel jSource, jOperation, jCypher, lEnterTheNum;
	private JButton jGetFile, jExecute, jDirectDict;
	private JRadioButton jrCipher, jrBreak, jrCeasar, jrVigenere;
	private ButtonGroup jrChooseOperation, jrChooseCipher;
	private JMenuBar menuBar;
	private JMenu menuFile, menuEdit;
	private JMenuItem mOpenTextFile, mLoadDictionaries, mSaveFile, mExit, mMenuLangFile;	
	private ArrayList <Object> JElements;

	
	
	
	public View (String title) 
	{
	 	frame = new JFrame();
	 	frame.setSize(600,600);
	 	frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    	frame.setLocationRelativeTo(null);		 	
		frame.setTitle("Cipher_Vigenere_v:0.5");			
		frame.setLayout(null);	
		
		menuBar = new JMenuBar();
		menuFile = new JMenu("File");
		menuEdit = new JMenu("Edit");
		mOpenTextFile = new JMenuItem("Get text");
		mLoadDictionaries = new JMenuItem("Get dictionaries");
		mSaveFile = new JMenuItem("Save");
		mExit = new JMenuItem("Close");	
		mMenuLangFile = new JMenuItem("Load language menu file");
		frame.setJMenuBar(menuBar);
		
		menuBar.add(menuFile);
		menuBar.add(menuEdit);
		menuFile.add(mOpenTextFile);
		menuFile.add(mLoadDictionaries);
		menuFile.add(mSaveFile);
		menuFile.addSeparator();
		menuFile.add(mExit);	
		menuEdit.add(mMenuLangFile);
		
        GroupLayout layout = new GroupLayout(frame.getContentPane());
        frame.getContentPane().setLayout(layout);
        layout.setAutoCreateGaps(true);
        layout.setAutoCreateContainerGaps(true);		
		
		jSource = new JLabel("Source:");
		jOperation = new JLabel("Operation:");
		jCypher = new JLabel("Choose cipher:");
		lEnterTheNum = new JLabel("Enther the cipher:");
		enterTheNumField = new JTextField(10);
		enterTheNumField.setMaximumSize(enterTheNumField.getPreferredSize());
		
		jrChooseOperation = new ButtonGroup();
		jrCipher = new JRadioButton("Cipher", true);
		jrChooseOperation.add(jrCipher);
		jrBreak = new JRadioButton("Decipher", false);
		jrChooseOperation.add(jrBreak);

		jrChooseCipher = new ButtonGroup();		
		jrCeasar = new JRadioButton("Caesar", true);
		jrChooseCipher.add(jrCeasar);
		jrVigenere = new JRadioButton("Vigenere", false);
		jrChooseCipher.add(jrVigenere);
		
		jGetFile = new JButton("text");
		jExecute = new JButton("execute");
		jDirectDict = new JButton("dictionaries");
		JTextInput = new JTextArea();
		decryptedTxt = new JTextArea();
		


		JScrollPane scrollPane = new JScrollPane(JTextInput);
		JScrollPane spDecrypted = new JScrollPane(decryptedTxt);
		
        layout.setHorizontalGroup(layout.createParallelGroup(LEADING) 
        		
            			.addComponent(scrollPane)
            			.addComponent(spDecrypted)
            			.addGroup(layout.createParallelGroup(LEADING)
            					.addGroup(layout.createSequentialGroup()
            							.addGroup(layout.createParallelGroup(LEADING)
            									.addComponent(jSource)
            									.addComponent(jGetFile)
            									.addComponent(jDirectDict)
            									)	
            					.addGroup(layout.createParallelGroup(CENTER)
            							.addComponent(jOperation)
            							.addGroup(layout.createSequentialGroup()
            									.addComponent(jrCipher)	        									
            									.addComponent(jrBreak) 
            									)           								         							
            							)   							
            					.addGroup(layout.createParallelGroup(CENTER)            							
            							.addGroup(layout.createSequentialGroup()
            									.addComponent(jrCeasar)
            									.addComponent(jrVigenere)
            									)
            							.addComponent(lEnterTheNum)
            							.addComponent(jCypher))
            					.addGroup(layout.createParallelGroup(LEADING)
            							.addComponent(enterTheNumField)           							
            							.addComponent(jExecute)
            							)
            					))
            );
            

     
            layout.setVerticalGroup(layout.createSequentialGroup()
                    .addGroup(layout.createParallelGroup(LEADING)
                            .addGroup(layout.createSequentialGroup()
                                .addGroup(layout.createParallelGroup(CENTER)
                                    .addComponent(jSource)
                                    .addComponent(jOperation)
                                    .addComponent(jCypher)
                                		)
                                .addGroup(layout.createParallelGroup(BASELINE)
                                    .addComponent(jGetFile)
                                    .addComponent(jrCipher)
                            		.addComponent(jrBreak)
                            		.addComponent(jrCeasar)
                            		.addComponent(jrVigenere)
                                		))
                    					)
                    .addGroup(layout.createParallelGroup(BASELINE)
                            .addComponent(jDirectDict)
                            .addComponent(lEnterTheNum)
                            .addComponent(enterTheNumField)
                    		)

                    .addComponent(scrollPane)
                    .addComponent(jExecute)
                    .addComponent(spDecrypted)            

            );		
  	      frame.setVisible(true);
		
		
	}

	public JMenuItem getmMenuLangFile() {
		return mMenuLangFile;
	}

	public void setmMenuLangFile(JMenuItem mMenuLangFile) {
		this.mMenuLangFile = mMenuLangFile;
	}

	public ArrayList<Object> getJElements() {
		return JElements;
	}

	public void setJElements(ArrayList<Object> jElements) {
		JElements = jElements;
	}

	public JFrame getFrame() {
		return frame;
	}

	public void setFrame(JFrame frame) {
		this.frame = frame;
	}

	public JTextArea getJTextInput() {
		return JTextInput;
	}

	public void setJTextInput(JTextArea jTextInput) {
		JTextInput = jTextInput;
	}

	public JTextArea getDecryptedTxt() {
		return decryptedTxt;
	}

	public void setDecryptedTxt(JTextArea decryptedTxt) {
		this.decryptedTxt = decryptedTxt;
	}

	public JTextField getEnterTheNumField() {
		return enterTheNumField;
	}

	public void setEnterTheNumField(JTextField enterTheNumField) {
		this.enterTheNumField = enterTheNumField;
	}

	public JLabel getjSource() {
		return jSource;
	}

	public void setjSource(JLabel jSource) {
		this.jSource = jSource;
	}

	public JLabel getjOperation() {
		return jOperation;
	}

	public void setjOperation(JLabel jOperation) {
		this.jOperation = jOperation;
	}

	public JLabel getjCypher() {
		return jCypher;
	}

	public void setjCypher(JLabel jCypher) {
		this.jCypher = jCypher;
	}

	public JLabel getlEnterTheNum() {
		return lEnterTheNum;
	}

	public void setlEnterTheNum(JLabel lEnterTheNum) {
		this.lEnterTheNum = lEnterTheNum;
	}

	public JButton getjGetFile() {
		return jGetFile;
	}

	public void setjGetFile(JButton jGetFile) {
		this.jGetFile = jGetFile;
	}

	public JButton getjExecute() {
		return jExecute;
	}

	public void setjExecute(JButton jExecute) {
		this.jExecute = jExecute;
	}

	public JButton getjDirectDict() {
		return jDirectDict;
	}

	public void setjDirectDict(JButton jDirectDict) {
		this.jDirectDict = jDirectDict;
	}

	public JRadioButton getJrCipher() {
		return jrCipher;
	}

	public void setJrCipher(JRadioButton jrCipher) {
		this.jrCipher = jrCipher;
	}

	public JRadioButton getJrBreak() {
		return jrBreak;
	}

	public void setJrBreak(JRadioButton jrBreak) {
		this.jrBreak = jrBreak;
	}

	public JRadioButton getJrCeasar() {
		return jrCeasar;
	}

	public void setJrCeasar(JRadioButton jrCeasar) {
		this.jrCeasar = jrCeasar;
	}

	public JRadioButton getJrVigenere() {
		return jrVigenere;
	}

	public void setJrVigenere(JRadioButton jrVigenere) {
		this.jrVigenere = jrVigenere;
	}

	public ButtonGroup getJrChooseOperation() {
		return jrChooseOperation;
	}

	public void setJrChooseOperation(ButtonGroup jrChooseOperation) {
		this.jrChooseOperation = jrChooseOperation;
	}

	public ButtonGroup getJrChooseCipher() {
		return jrChooseCipher;
	}

	public void setJrChooseCipher(ButtonGroup jrChooseCipher) {
		this.jrChooseCipher = jrChooseCipher;
	}

	public JMenuBar getMenuBar() {
		return menuBar;
	}

	public void setMenuBar(JMenuBar menuBar) {
		this.menuBar = menuBar;
	}

	public JMenu getMenuFile() {
		return menuFile;
	}

	public void setMenuFile(JMenu menuFile) {
		this.menuFile = menuFile;
	}

	public JMenuItem getmOpenTextFile() {
		return mOpenTextFile;
	}

	public void setmOpenTextFile(JMenuItem mOpenTextFile) {
		this.mOpenTextFile = mOpenTextFile;
	}

	public JMenuItem getmLoadDictionaries() {
		return mLoadDictionaries;
	}

	public void setmLoadDictionaries(JMenuItem mLoadDictionaries) {
		this.mLoadDictionaries = mLoadDictionaries;
	}

	public JMenuItem getmSaveFile() {
		return mSaveFile;
	}

	public void setmSaveFile(JMenuItem mSaveFile) {
		this.mSaveFile = mSaveFile;
	}

	public JMenuItem getmExit() {
		return mExit;
	}

	public void setmExit(JMenuItem mExit) {
		this.mExit = mExit;
	}

}
package viginereBreakerPackage3;

import java.io.File;
import java.util.HashMap;
import java.util.HashSet;

public class Model {
	
	private HashMap <String, HashSet<String>> listOfDictionaries;
	private HashMap<String, String> currLangMenu;
	private File[] dictionaries;
	static final String basicPath = (new java.io.File(".").getAbsolutePath()).substring(0,new java.io.File(".").getAbsolutePath().length()-2);//not sure 
	//is this should to be declared as a static final
	private String dictionariesPath, filePath, savePath, inputTextName, cypherValueForFileName, isCipheredTxt, isCaesarTxt;
	private boolean isCiphered, isRightCipher;
	static final String alphabet = "abcdefghijklmnopqrstuvqxwz";	
	

	public HashMap<String, HashSet<String>> getListOfDictionaries() {
		return listOfDictionaries;
	}

	public void setListOfDictionaries(HashMap<String, HashSet<String>> listOfDictionaries) {
		this.listOfDictionaries = listOfDictionaries;
	}

	public File[] getDictionaries() {
		return dictionaries;
	}

	public void setDictionaries(File[] dictionaries) {
		this.dictionaries = dictionaries;
	}

	public String getDictionariesPath() {
		dictionariesPath = (new StringBuilder(basicPath)).append("/dictionaries").toString();
		return dictionariesPath;
	}

	public void setDictionariesPath(String dictionariesPath) {
		this.dictionariesPath = dictionariesPath;
	}

	public String getFilePath() {
		filePath = (new StringBuilder(basicPath)).append("/messages").toString();
		return filePath;
	}

	public void setFilePath(String filePath) {
		this.filePath = filePath;
	}

	public String getSavePath() {
		savePath = (new StringBuilder(basicPath)).append("/workspace").toString();
		//savePath = (new StringBuilder(basicPath)).append("/messages").toString();
		return savePath;
	}

	public void setSavePath(String savePath) {
		this.savePath = savePath;
	}

	public String getInputTextName() {
		return inputTextName;
	}

	public void setInputTextName(String inputTextName) {
		this.inputTextName = inputTextName;
	}

	public String getCypherValueForFileName() {
		return cypherValueForFileName;
	}

	public void setCypherValueForFileName(String cypherValueForFileName) {
		this.cypherValueForFileName = cypherValueForFileName;
	}


	public boolean isCiphered() {
		return isCiphered;
	}

	public void setCiphered(boolean isCiphered) {
		this.isCiphered = isCiphered;
	}

	public String getIsCipheredTxt() {
		return isCipheredTxt;
	}

	public void setIsCipheredTxt(String isCipheredTxt) {
		this.isCipheredTxt = isCipheredTxt;
	}

	public String getIsCaesarTxt() {
		return isCaesarTxt;
	}

	public void setIsCaesarTxt(String isCaesarTxt) {
		this.isCaesarTxt = isCaesarTxt;
	}

	public boolean isRightCipher() {
		return isRightCipher;
	}

	public void setRightCipher(boolean isRightCipher) {
		this.isRightCipher = isRightCipher;
	}

	public HashMap<String, String> getCurrLangMenu() {
		return currLangMenu;
	}

	public void setCurrLangMenu(HashMap<String, String> currLangMenu) {
		this.currLangMenu = currLangMenu;
	}	
}
0

Dobrze kombinujesz, ale wymyślasz koło od nowa. Java udostępnia mechanizm zarządzania wersjami językowymi aplikacji za pomocą plików properties Properties - pliki tekstowe.

Sama realizacja jest opisana na przykład tutaj https://netbeans.org/kb/docs/java/gui-automatic-i18n.html

1 użytkowników online, w tym zalogowanych: 0, gości: 1