Titlekeys support implemented in Preferences and Setting classes
This commit is contained in:
parent
a5004a9a31
commit
bc2764b123
6 changed files with 235 additions and 18 deletions
|
@ -1,6 +1,5 @@
|
||||||
package konogonka;
|
package konogonka;
|
||||||
|
|
||||||
import java.util.HashMap;
|
|
||||||
import java.util.prefs.Preferences;
|
import java.util.prefs.Preferences;
|
||||||
|
|
||||||
public class AppPreferences {
|
public class AppPreferences {
|
||||||
|
@ -8,8 +7,12 @@ public class AppPreferences {
|
||||||
public static AppPreferences getInstance() { return INSTANCE; }
|
public static AppPreferences getInstance() { return INSTANCE; }
|
||||||
|
|
||||||
private Preferences preferences;
|
private Preferences preferences;
|
||||||
|
private int titleKeysCount;
|
||||||
|
|
||||||
private AppPreferences(){ preferences = Preferences.userRoot().node("konogonka"); }
|
private AppPreferences(){
|
||||||
|
preferences = Preferences.userRoot().node("konogonka");
|
||||||
|
titleKeysCount = getTitleKeysCount();
|
||||||
|
}
|
||||||
|
|
||||||
public void setAll(
|
public void setAll(
|
||||||
String xciHeaderKey,
|
String xciHeaderKey,
|
||||||
|
@ -98,11 +101,25 @@ public class AppPreferences {
|
||||||
public String getSystemKey(int number){ return preferences.get("key_area_key_system_0"+number, "");}
|
public String getSystemKey(int number){ return preferences.get("key_area_key_system_0"+number, "");}
|
||||||
public void setSystemKey(int number, String key){ preferences.put("key_area_key_system_0"+number, key); }
|
public void setSystemKey(int number, String key){ preferences.put("key_area_key_system_0"+number, key); }
|
||||||
|
|
||||||
public int getTitleKeysCount(){ return preferences.getInt("title_keys_count", 0);}
|
|
||||||
public void setTitleKeysCount(int number){ preferences.putInt("title_keys_count", number);}
|
|
||||||
|
|
||||||
public String[] getTitleKey(int number){
|
|
||||||
return preferences.get(Integer.toString(number), "0 = 0").split(" = ", 2);
|
public int getTitleKeysCount(){
|
||||||
|
return preferences.getInt("title_keys_count", 0);
|
||||||
}
|
}
|
||||||
public void setTitleKey(int number, String name, String value){ preferences.put(Integer.toString(number), name+" = "+value); }
|
// Since we don't want to store title keys that are no longer in use, we have to (try to) remove them.
|
||||||
|
// This part of code works as a charm. Don't touch.
|
||||||
|
public void setTitleKeysCount(int number){
|
||||||
|
if (this.titleKeysCount > number){
|
||||||
|
for (int i = number; i < this.titleKeysCount; i++) {
|
||||||
|
preferences.remove("title_key_"+i);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
preferences.putInt("title_keys_count", number);
|
||||||
|
this.titleKeysCount = number;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String[] getTitleKeyPair(int number){
|
||||||
|
return preferences.get("title_key_"+number, "0 = 0").split(" = ", 2);
|
||||||
|
}
|
||||||
|
public void setTitleKey(int number, String pair){ preferences.put("title_key_"+number, pair); }
|
||||||
}
|
}
|
||||||
|
|
|
@ -82,6 +82,11 @@ public class NCAController implements TabController {
|
||||||
keysMap.put("key_area_key_system_0"+i, AppPreferences.getInstance().getSystemKey(i));
|
keysMap.put("key_area_key_system_0"+i, AppPreferences.getInstance().getSystemKey(i));
|
||||||
// TODO: Add titlekeys
|
// TODO: Add titlekeys
|
||||||
}
|
}
|
||||||
|
for (int i = 0; i < AppPreferences.getInstance().getTitleKeysCount(); i++){
|
||||||
|
String[] pair = AppPreferences.getInstance().getTitleKeyPair(i);
|
||||||
|
if ( ! pair[0].equals("0") && ! pair[1].equals("0"))
|
||||||
|
keysMap.put(pair[0], pair[1]);
|
||||||
|
}
|
||||||
|
|
||||||
AnalyzerNCA analyzerNCA = new AnalyzerNCA(file, keysMap);
|
AnalyzerNCA analyzerNCA = new AnalyzerNCA(file, keysMap);
|
||||||
analyzerNCA.setOnSucceeded(e->{
|
analyzerNCA.setOnSucceeded(e->{
|
||||||
|
|
113
src/main/java/konogonka/Settings/ListSelectorController.java
Normal file
113
src/main/java/konogonka/Settings/ListSelectorController.java
Normal file
|
@ -0,0 +1,113 @@
|
||||||
|
package konogonka.Settings;
|
||||||
|
|
||||||
|
import javafx.collections.FXCollections;
|
||||||
|
import javafx.collections.ObservableList;
|
||||||
|
import javafx.fxml.FXML;
|
||||||
|
import javafx.fxml.Initializable;
|
||||||
|
import javafx.scene.control.ListView;
|
||||||
|
import javafx.scene.control.TextField;
|
||||||
|
import javafx.scene.control.TextFormatter;
|
||||||
|
import javafx.scene.input.KeyEvent;
|
||||||
|
import konogonka.ServiceWindow;
|
||||||
|
|
||||||
|
import java.net.URL;
|
||||||
|
import java.util.Arrays;
|
||||||
|
import java.util.HashMap;
|
||||||
|
import java.util.ResourceBundle;
|
||||||
|
|
||||||
|
public class ListSelectorController implements Initializable {
|
||||||
|
@FXML
|
||||||
|
private ListView<String> listView;
|
||||||
|
@FXML
|
||||||
|
private TextField newRecordName, newRecordValue;
|
||||||
|
private ObservableList<String> observableList;
|
||||||
|
|
||||||
|
private int mandatoryValueLength;
|
||||||
|
private String predictionPattern;
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void initialize(URL url, ResourceBundle resourceBundle) {
|
||||||
|
observableList = FXCollections.observableArrayList();
|
||||||
|
listView.setItems(observableList);
|
||||||
|
|
||||||
|
newRecordValue.setTextFormatter(new TextFormatter<Object>(change -> {
|
||||||
|
if (change.getControlNewText().matches("^[a-fA-F0-9]+$") || change.getControlNewText().isEmpty())
|
||||||
|
return change;
|
||||||
|
return null;
|
||||||
|
}));
|
||||||
|
}
|
||||||
|
public void initSelector(int length, String predictionPattern){
|
||||||
|
this.mandatoryValueLength = length;
|
||||||
|
|
||||||
|
if (predictionPattern == null){ // If we need no validation, restrict only spaces/tabs adding
|
||||||
|
newRecordName.setTextFormatter(new TextFormatter<Object>(change -> {
|
||||||
|
if (change.getControlNewText().contains(" ") || change.getControlNewText().contains("\t"))
|
||||||
|
return null;
|
||||||
|
return change;
|
||||||
|
}));
|
||||||
|
}
|
||||||
|
else { // Otherwise use pattern as name of key + 2 dec numbers
|
||||||
|
this.predictionPattern = predictionPattern;
|
||||||
|
|
||||||
|
newRecordName.setText(predictionPattern);
|
||||||
|
newRecordName.setTextFormatter(new TextFormatter<Object>(change -> {
|
||||||
|
if (change.getControlNewText().matches("^"+predictionPattern+"[0-9]{0,2}$"))
|
||||||
|
return change;
|
||||||
|
return null;
|
||||||
|
}));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* Must be run on start
|
||||||
|
* Set list content
|
||||||
|
*/
|
||||||
|
void setList(HashMap<String, String> stringPairsArray){
|
||||||
|
if (stringPairsArray != null && ! stringPairsArray.isEmpty())
|
||||||
|
for (String name: stringPairsArray.keySet())
|
||||||
|
validateAndAdd(name+" = "+stringPairsArray.get(name));
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* Return list content
|
||||||
|
* */
|
||||||
|
String[] getList(){
|
||||||
|
return Arrays.copyOf(observableList.toArray(), observableList.toArray().length, String[].class);
|
||||||
|
}
|
||||||
|
|
||||||
|
@FXML
|
||||||
|
private void listKeyPressed(KeyEvent event){
|
||||||
|
if (event.getCode().toString().equals("DELETE"))
|
||||||
|
removeRecord();
|
||||||
|
}
|
||||||
|
|
||||||
|
@FXML
|
||||||
|
private void removeRecord(){ observableList.remove(listView.getSelectionModel().getSelectedItem()); }
|
||||||
|
|
||||||
|
@FXML
|
||||||
|
private void addNewRecord(){
|
||||||
|
if (newRecordValue.getText().length() == mandatoryValueLength && ! newRecordName.getText().isEmpty()) {
|
||||||
|
if (predictionPattern == null) {
|
||||||
|
validateAndAdd(newRecordName.getText() + " = " + newRecordValue.getText());
|
||||||
|
newRecordName.clear();
|
||||||
|
newRecordValue.clear();
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
if (newRecordName.getText().matches("^"+predictionPattern+"[0-9]{2}$")){
|
||||||
|
validateAndAdd(newRecordName.getText() + " = " + newRecordValue.getText());
|
||||||
|
newRecordName.setText(predictionPattern);
|
||||||
|
newRecordValue.clear();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
ServiceWindow.getErrorNotification("Error", "Value name should be: '"+predictionPattern+"XX' where XX are two decimal numbers.");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
ServiceWindow.getErrorNotification("Error", "One of the fields empty or value leigh is incorrect.");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void validateAndAdd(String addingItem){
|
||||||
|
if (!observableList.contains(addingItem)) {
|
||||||
|
observableList.add(addingItem);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -5,7 +5,6 @@ import javafx.fxml.Initializable;
|
||||||
import javafx.scene.control.Button;
|
import javafx.scene.control.Button;
|
||||||
import javafx.scene.control.TextField;
|
import javafx.scene.control.TextField;
|
||||||
import javafx.scene.control.TextFormatter;
|
import javafx.scene.control.TextFormatter;
|
||||||
import javafx.scene.layout.VBox;
|
|
||||||
import javafx.stage.FileChooser;
|
import javafx.stage.FileChooser;
|
||||||
import javafx.stage.Stage;
|
import javafx.stage.Stage;
|
||||||
import konogonka.AppPreferences;
|
import konogonka.AppPreferences;
|
||||||
|
@ -19,8 +18,10 @@ import java.util.ResourceBundle;
|
||||||
public class SettingsController implements Initializable {
|
public class SettingsController implements Initializable {
|
||||||
@FXML
|
@FXML
|
||||||
private Button okBtn, cancelBtn, importKeysBtn, importTitleKeysBtn;
|
private Button okBtn, cancelBtn, importKeysBtn, importTitleKeysBtn;
|
||||||
|
|
||||||
@FXML
|
@FXML
|
||||||
private VBox titleKeysVbox;
|
ListSelectorController ListSelectorTitleKeysController;
|
||||||
|
|
||||||
@FXML
|
@FXML
|
||||||
private TextField
|
private TextField
|
||||||
xciHdrKeyTF,
|
xciHdrKeyTF,
|
||||||
|
@ -52,6 +53,17 @@ public class SettingsController implements Initializable {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void initialize(URL url, ResourceBundle resourceBundle) {
|
public void initialize(URL url, ResourceBundle resourceBundle) {
|
||||||
|
ListSelectorTitleKeysController.initSelector(32, null); // 32 required
|
||||||
|
|
||||||
|
HashMap<String, String> preparedPairsMapInit = new HashMap<>();
|
||||||
|
for (int i = 0; i < AppPreferences.getInstance().getTitleKeysCount(); i++){
|
||||||
|
preparedPairsMapInit.put(
|
||||||
|
AppPreferences.getInstance().getTitleKeyPair(i)[0],
|
||||||
|
AppPreferences.getInstance().getTitleKeyPair(i)[1]
|
||||||
|
);
|
||||||
|
}
|
||||||
|
ListSelectorTitleKeysController.setList(preparedPairsMapInit);
|
||||||
|
|
||||||
xciHdrKeyTF.setText(AppPreferences.getInstance().getXciHeaderKey());
|
xciHdrKeyTF.setText(AppPreferences.getInstance().getXciHeaderKey());
|
||||||
hdrKeyTF.setText(AppPreferences.getInstance().getHeaderKey());
|
hdrKeyTF.setText(AppPreferences.getInstance().getHeaderKey());
|
||||||
keyApp0TF.setText(AppPreferences.getInstance().getApplicationKey(0));
|
keyApp0TF.setText(AppPreferences.getInstance().getApplicationKey(0));
|
||||||
|
@ -157,12 +169,37 @@ public class SettingsController implements Initializable {
|
||||||
catch (IOException ioe){
|
catch (IOException ioe){
|
||||||
ioe.printStackTrace();
|
ioe.printStackTrace();
|
||||||
}
|
}
|
||||||
/*
|
|
||||||
for (String key: fileMap.keySet()){
|
|
||||||
System.out.print(key+ " - ");
|
|
||||||
System.out.println(fileMap.get(key));
|
|
||||||
}
|
}
|
||||||
//*/
|
});
|
||||||
|
|
||||||
|
importTitleKeysBtn.setOnAction(e->{
|
||||||
|
FileChooser fileChooser = new FileChooser();
|
||||||
|
fileChooser.setTitle("title.keys");
|
||||||
|
fileChooser.setInitialDirectory(new File(System.getProperty("user.home")));
|
||||||
|
fileChooser.getExtensionFilters().add(new FileChooser.ExtensionFilter("title.keys", "title.keys"));
|
||||||
|
|
||||||
|
File prodKeysFile = fileChooser.showOpenDialog(importKeysBtn.getScene().getWindow());
|
||||||
|
|
||||||
|
if (prodKeysFile != null && prodKeysFile.exists()) {
|
||||||
|
try {
|
||||||
|
BufferedReader br = new BufferedReader(
|
||||||
|
new FileReader(prodKeysFile)
|
||||||
|
);
|
||||||
|
|
||||||
|
String fileLine;
|
||||||
|
String[] keyValue;
|
||||||
|
HashMap<String, String> preparedPairsMap = new HashMap<>();
|
||||||
|
while ((fileLine = br.readLine()) != null){
|
||||||
|
keyValue = fileLine.trim().split("\\s+?=\\s+?", 2);
|
||||||
|
if (keyValue.length == 2 && keyValue[0].length() == 32 && keyValue[1].length() == 32){
|
||||||
|
preparedPairsMap.put(keyValue[0], keyValue[1]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
ListSelectorTitleKeysController.setList(preparedPairsMap);
|
||||||
|
}
|
||||||
|
catch (IOException ioe){
|
||||||
|
ioe.printStackTrace();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -201,15 +238,20 @@ public class SettingsController implements Initializable {
|
||||||
keySys6TF.getText(),
|
keySys6TF.getText(),
|
||||||
keySys7TF.getText()
|
keySys7TF.getText()
|
||||||
);
|
);
|
||||||
|
String[] titleKeysSet = ListSelectorTitleKeysController.getList();
|
||||||
|
if (titleKeysSet != null){
|
||||||
|
AppPreferences.getInstance().setTitleKeysCount(titleKeysSet.length);
|
||||||
|
for (int i = 0; i < titleKeysSet.length; i++)
|
||||||
|
AppPreferences.getInstance().setTitleKey(i, titleKeysSet[i]);
|
||||||
|
}
|
||||||
thisStage.close();
|
thisStage.close();
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
private void setTextValidation(TextField tf){
|
private void setTextValidation(TextField tf){
|
||||||
tf.setTextFormatter(new TextFormatter<Object>(change -> {
|
tf.setTextFormatter(new TextFormatter<Object>(change -> {
|
||||||
if (change.getControlNewText().contains(" ") | change.getControlNewText().contains("\t"))
|
if (change.getControlNewText().contains(" ") || change.getControlNewText().contains("\t"))
|
||||||
return null;
|
return null;
|
||||||
else
|
|
||||||
return change;
|
return change;
|
||||||
}));
|
}));
|
||||||
}
|
}
|
||||||
|
|
40
src/main/resources/FXML/Settings/ListSelectorLayout.fxml
Normal file
40
src/main/resources/FXML/Settings/ListSelectorLayout.fxml
Normal file
|
@ -0,0 +1,40 @@
|
||||||
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
|
|
||||||
|
<?import javafx.scene.control.Button?>
|
||||||
|
<?import javafx.scene.control.Label?>
|
||||||
|
<?import javafx.scene.control.ListView?>
|
||||||
|
<?import javafx.scene.control.TextField?>
|
||||||
|
<?import javafx.scene.layout.HBox?>
|
||||||
|
<?import javafx.scene.layout.VBox?>
|
||||||
|
<?import javafx.scene.shape.SVGPath?>
|
||||||
|
|
||||||
|
<VBox spacing="5.0" VBox.vgrow="ALWAYS" xmlns="http://javafx.com/javafx/8.0.171" xmlns:fx="http://javafx.com/fxml/1" fx:controller="konogonka.Settings.ListSelectorController">
|
||||||
|
<children>
|
||||||
|
<HBox alignment="CENTER_LEFT" spacing="5.0" VBox.vgrow="ALWAYS">
|
||||||
|
<children>
|
||||||
|
<ListView fx:id="listView" onKeyPressed="#listKeyPressed" prefWidth="200.0" HBox.hgrow="ALWAYS" />
|
||||||
|
<VBox spacing="5.0">
|
||||||
|
<children>
|
||||||
|
<Button mnemonicParsing="false" onAction="#removeRecord">
|
||||||
|
<graphic>
|
||||||
|
<SVGPath content="M19,6.41L17.59,5L12,10.59L6.41,5L5,6.41L10.59,12L5,17.59L6.41,19L12,13.41L17.59,19L19,17.59L13.41,12L19,6.41Z" fill="#cc0101" />
|
||||||
|
</graphic>
|
||||||
|
</Button>
|
||||||
|
</children>
|
||||||
|
</VBox>
|
||||||
|
</children>
|
||||||
|
</HBox>
|
||||||
|
<HBox spacing="5.0" VBox.vgrow="NEVER">
|
||||||
|
<children>
|
||||||
|
<TextField fx:id="newRecordName" HBox.hgrow="ALWAYS" />
|
||||||
|
<Label text="=" />
|
||||||
|
<TextField fx:id="newRecordValue" HBox.hgrow="ALWAYS" />
|
||||||
|
<Button mnemonicParsing="false" onAction="#addNewRecord">
|
||||||
|
<graphic>
|
||||||
|
<SVGPath content="M19,13H13V19H11V13H5V11H11V5H13V11H19V13Z" fill="#007f08" />
|
||||||
|
</graphic>
|
||||||
|
</Button>
|
||||||
|
</children>
|
||||||
|
</HBox>
|
||||||
|
</children>
|
||||||
|
</VBox>
|
|
@ -224,7 +224,7 @@
|
||||||
<SVGPath content="M1,12H10.76L8.26,9.5L9.67,8.08L14.59,13L9.67,17.92L8.26,16.5L10.76,14H1V12M19,3C20.11,3 21,3.9 21,5V19A2,2 0 0,1 19,21H5C3.89,21 3,20.1 3,19V16H5V19H19V7H5V10H3V5A2,2 0 0,1 5,3H19Z" />
|
<SVGPath content="M1,12H10.76L8.26,9.5L9.67,8.08L14.59,13L9.67,17.92L8.26,16.5L10.76,14H1V12M19,3C20.11,3 21,3.9 21,5V19A2,2 0 0,1 19,21H5C3.89,21 3,20.1 3,19V16H5V19H19V7H5V10H3V5A2,2 0 0,1 5,3H19Z" />
|
||||||
</graphic>
|
</graphic>
|
||||||
</Button>
|
</Button>
|
||||||
<VBox fx:id="titleKeysVbox" spacing="5.0" />
|
<fx:include fx:id="ListSelectorTitleKeys" source="ListSelectorLayout.fxml" />
|
||||||
</children>
|
</children>
|
||||||
</VBox>
|
</VBox>
|
||||||
</content>
|
</content>
|
||||||
|
|
Loading…
Reference in a new issue