Skip to content

Commit 883fa21

Browse files
committed
master: v1.0.0 finished
1 parent 9102988 commit 883fa21

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

73 files changed

+4022
-0
lines changed

pom.xml

Lines changed: 45 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,45 @@
1+
<?xml version="1.0" encoding="UTF-8"?>
2+
<project xmlns="http://maven.apache.org/POM/4.0.0"
3+
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
4+
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
5+
<modelVersion>4.0.0</modelVersion>
6+
7+
<groupId>org.example</groupId>
8+
<artifactId>workshop2</artifactId>
9+
<version>1.0-SNAPSHOT</version>
10+
11+
<properties>
12+
<maven.compiler.source>19</maven.compiler.source>
13+
<maven.compiler.target>19</maven.compiler.target>
14+
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
15+
</properties>
16+
17+
<dependencies>
18+
<dependency>
19+
<groupId>org.openjfx</groupId>
20+
<artifactId>javafx-controls</artifactId>
21+
<version>19.0.2.1</version>
22+
</dependency>
23+
<dependency>
24+
<groupId>org.openjfx</groupId>
25+
<artifactId>javafx-fxml</artifactId>
26+
<version>19.0.2.1</version>
27+
</dependency>
28+
<dependency>
29+
<groupId>org.openjfx</groupId>
30+
<artifactId>javafx-media</artifactId>
31+
<version>19.0.2.1</version>
32+
</dependency>
33+
<dependency>
34+
<groupId>commons-codec</groupId>
35+
<artifactId>commons-codec</artifactId>
36+
<version>1.15</version>
37+
</dependency>
38+
<dependency>
39+
<groupId>javax.activation</groupId>
40+
<artifactId>activation</artifactId>
41+
<version>1.1.1</version>
42+
</dependency>
43+
</dependencies>
44+
45+
</project>
Lines changed: 108 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,108 @@
1+
package com.alimajidi.aa.controller;
2+
3+
import com.alimajidi.aa.model.User;
4+
import com.alimajidi.aa.view.App;
5+
import javafx.beans.property.SimpleIntegerProperty;
6+
import javafx.beans.property.SimpleStringProperty;
7+
import javafx.scene.control.TableColumn;
8+
import javafx.scene.control.TableRow;
9+
import javafx.scene.control.TableView;
10+
11+
import java.util.concurrent.atomic.AtomicInteger;
12+
13+
import static com.alimajidi.aa.view.MultiLanguage.*;
14+
15+
public class LeaderBoardMenuController {
16+
private final TableView<User> tableView = new TableView<>();
17+
private final TableColumn<User, String> userColumn = new TableColumn<>();
18+
private final TableColumn<User, Integer> difficultyColumn = new TableColumn<>();
19+
private final TableColumn<User, Integer> scoreColumn = new TableColumn<>();
20+
private final TableColumn<User, Integer> timeColumn = new TableColumn<>();
21+
22+
{
23+
tableView.setId("leaderBoardTableView");
24+
tableView.getColumns().add(userColumn);
25+
userColumn.textProperty().bind(App.createBiding(USERNAME));
26+
userColumn.setId("userColumn");
27+
userColumn.setResizable(false);
28+
29+
tableView.getColumns().add(difficultyColumn);
30+
difficultyColumn.textProperty().bind(App.createBiding(DIFFICULTY));
31+
difficultyColumn.setId("difficultyColumn");
32+
difficultyColumn.setResizable(false);
33+
34+
tableView.getColumns().add(scoreColumn);
35+
scoreColumn.textProperty().bind(App.createBiding(SCORE));
36+
scoreColumn.setId("scoreColumn");
37+
scoreColumn.setResizable(false);
38+
39+
tableView.getColumns().add(timeColumn);
40+
timeColumn.textProperty().bind(App.createBiding(TIME));
41+
timeColumn.setId("timeColumn");
42+
timeColumn.setResizable(false);
43+
44+
tableView.setSortPolicy(param -> false);
45+
}
46+
47+
private void setRowsId() {
48+
tableView.refresh();
49+
AtomicInteger atomicInteger = new AtomicInteger(1);
50+
tableView.setRowFactory(param -> {
51+
TableRow<User> row = new TableRow<>();
52+
row.setId("tableViewRow" + atomicInteger.getAndIncrement());
53+
return row;
54+
});
55+
}
56+
57+
public void showTableView(int difficulty) {
58+
tableView.getItems().clear();
59+
setRowsId();
60+
userColumn.setCellValueFactory(
61+
param -> new SimpleStringProperty(param.getValue().getUsername()));
62+
63+
difficultyColumn.setCellValueFactory(
64+
param -> new SimpleIntegerProperty(difficulty).asObject());
65+
66+
scoreColumn.setCellValueFactory(
67+
param -> new SimpleIntegerProperty(param.getValue().getHighScoreByDifficulty(difficulty)).asObject());
68+
69+
timeColumn.setCellValueFactory(
70+
param -> new SimpleIntegerProperty(param.getValue().getBestTimeByDifficulty(difficulty)).asObject());
71+
72+
73+
tableView.getItems().addAll(User.getUsers().stream().sorted((o1, o2) -> {
74+
if (o1.getHighScoreByDifficulty(difficulty) < o2.getHighScoreByDifficulty(difficulty)) return 1;
75+
else if (o1.getHighScoreByDifficulty(difficulty).equals(o2.getHighScoreByDifficulty(difficulty)))
76+
return Integer.compare(o1.getBestTimeByDifficulty(difficulty), o2.getBestTimeByDifficulty(difficulty));
77+
return -1;
78+
}).limit(10).toList());
79+
}
80+
81+
public void showTableView() {
82+
tableView.getItems().clear();
83+
setRowsId();
84+
userColumn.setCellValueFactory(
85+
param -> new SimpleStringProperty(param.getValue().getUsername()));
86+
87+
difficultyColumn.setCellValueFactory(
88+
param -> new SimpleIntegerProperty(param.getValue().getHighScoreDifficulty()).asObject());
89+
90+
scoreColumn.setCellValueFactory(
91+
param -> new SimpleIntegerProperty(param.getValue().getHighScore()).asObject());
92+
93+
timeColumn.setCellValueFactory(
94+
param -> new SimpleIntegerProperty(param.getValue().getHighScoreTime()).asObject());
95+
96+
97+
tableView.getItems().addAll(User.getUsers().stream().sorted((o1, o2) -> {
98+
if (o1.getHighScore() < o2.getHighScore()) return 1;
99+
else if (o1.getHighScore().equals(o2.getHighScore()))
100+
return Integer.compare(o1.getHighScoreTime(), o2.getHighScoreTime());
101+
return -1;
102+
}).limit(10).toList());
103+
}
104+
105+
public TableView<User> getTableView() {
106+
return tableView;
107+
}
108+
}
Lines changed: 106 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,106 @@
1+
package com.alimajidi.aa.controller;
2+
3+
import com.alimajidi.aa.model.User;
4+
import com.alimajidi.aa.view.App;
5+
import javafx.scene.control.Label;
6+
import org.apache.commons.codec.digest.DigestUtils;
7+
8+
import java.io.*;
9+
import java.util.ArrayList;
10+
import java.util.Objects;
11+
12+
import static com.alimajidi.aa.view.MultiLanguage.*;
13+
14+
public class LoginMenuController {
15+
16+
public static String generatePasswordHash(String password) {
17+
return new DigestUtils("SHA3-256").digestAsHex(password);
18+
}
19+
20+
public static void fetchDatabase() {
21+
String path = Objects.requireNonNull(
22+
User.class.getResource("/data/database.bin")).toExternalForm().substring(6);
23+
if (new File(path).length() == 0) return;
24+
ArrayList<User> users = new ArrayList<>();
25+
try (FileInputStream fileInputStream = new FileInputStream(path);
26+
ObjectInputStream in = new ObjectInputStream(fileInputStream)) {
27+
while (true) {
28+
Object userObject;
29+
try {
30+
userObject = in.readObject();
31+
} catch (Exception e) {
32+
break;
33+
}
34+
if (userObject instanceof User user) users.add(user);
35+
}
36+
User.setUsers(users);
37+
} catch (Exception e) {
38+
System.out.println("fetch failed: " + e.getMessage());
39+
}
40+
}
41+
42+
public static void updateDatabase() {
43+
String path = Objects.requireNonNull(
44+
User.class.getResource("/data/database.bin")).toExternalForm().substring(6);
45+
try (FileOutputStream fileOutputStream = new FileOutputStream(path, false);
46+
ObjectOutputStream out = new ObjectOutputStream(fileOutputStream)) {
47+
for (User user : User.getUsers()) out.writeObject(user);
48+
} catch (Exception e) {
49+
e.printStackTrace();
50+
}
51+
}
52+
53+
public static void addUser(String username, String password, boolean persian, boolean darkMode) {
54+
User user = new User(username, generatePasswordHash(password));
55+
User.getUsers().add(user);
56+
}
57+
58+
public static void removeUser(User user) {
59+
User.getUsers().remove(user);
60+
}
61+
62+
public static User getUserByUsername(String username) {
63+
return User.getUsers().stream().filter(user -> user.getUsername().equals(username)).findFirst().orElse(null);
64+
}
65+
66+
public static boolean isUsernameExists(String username) {
67+
return User.getUsers().stream().anyMatch(user -> user.getUsername().equals(username));
68+
}
69+
70+
public static boolean checkPassword(String username, String password) {
71+
return getUserByUsername(username).getPasswordHash().equals(generatePasswordHash(password));
72+
}
73+
74+
public static void login(Label label, String username, String password) {
75+
if (!isUsernameExists(username) || !checkPassword(username, password))
76+
label.textProperty().bind(App.createBiding(USER_PASS_INCORRECT));
77+
else {
78+
label.textProperty().bind(App.createBiding(LOGIN_SUCCESS));
79+
User userByUsername = getUserByUsername(username);
80+
App.getMediaPlayer().setVolume(userByUsername.getVolume());
81+
MainMenuController.setCurrentUser(userByUsername);
82+
setUserPreference();
83+
LoginMenuController.updateDatabase();
84+
}
85+
}
86+
87+
public static void setUserPreference() {
88+
App.setPersian(MainMenuController.getCurrentUser().isPersian());
89+
App.setDarkMode(MainMenuController.getCurrentUser().isDarkMode());
90+
}
91+
92+
public static void register(Label label, String username, String password) {
93+
if (isUsernameExists(username) || username.equals(""))
94+
label.textProperty().bind(App.createBiding(USER_UNAVAILABLE));
95+
else {
96+
label.textProperty().bind(App.createBiding(REGISTER_SUCCESS));
97+
addUser(username, password, App.isPersian(), App.isDarkMode());
98+
MainMenuController.setCurrentUser(getUserByUsername(username));
99+
LoginMenuController.updateDatabase();
100+
}
101+
}
102+
103+
public static void guest() {
104+
MainMenuController.setCurrentUser(User.getGuestUser());
105+
}
106+
}
Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
package com.alimajidi.aa.controller;
2+
3+
import com.alimajidi.aa.model.User;
4+
5+
public class MainMenuController {
6+
private static User currentUser;
7+
8+
public static User getCurrentUser() {
9+
return currentUser;
10+
}
11+
12+
public static void setCurrentUser(User currentUser) {
13+
MainMenuController.currentUser = currentUser;
14+
}
15+
}
Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
package com.alimajidi.aa.controller;
2+
3+
import com.alimajidi.aa.model.User;
4+
import com.alimajidi.aa.view.App;
5+
import javafx.scene.control.Label;
6+
7+
import static com.alimajidi.aa.view.MultiLanguage.*;
8+
9+
public class ProfileMenuController {
10+
11+
public static void logout() {
12+
MainMenuController.setCurrentUser(null);
13+
LoginMenuController.updateDatabase();
14+
}
15+
16+
public static void deleteAcc() {
17+
LoginMenuController.removeUser(MainMenuController.getCurrentUser());
18+
MainMenuController.setCurrentUser(null);
19+
LoginMenuController.updateDatabase();
20+
}
21+
22+
public static void changeUserPass(String username, String password, Label responseLabel) {
23+
if (MainMenuController.getCurrentUser().equals(User.getGuestUser()))
24+
responseLabel.textProperty().bind(App.createBiding(GUEST_CHANGE_USER_PASS));
25+
else {
26+
if (LoginMenuController.isUsernameExists(username)
27+
&& !username.equals(MainMenuController.getCurrentUser().getUsername()))
28+
responseLabel.textProperty().bind(App.createBiding(USER_UNAVAILABLE));
29+
else {
30+
MainMenuController.getCurrentUser().setUsername(username);
31+
MainMenuController.getCurrentUser().setPasswordHash(LoginMenuController.generatePasswordHash(password));
32+
responseLabel.textProperty().bind(App.createBiding(CHANGE_USER_PASS_SUCCESS));
33+
}
34+
}
35+
LoginMenuController.updateDatabase();
36+
}
37+
}

0 commit comments

Comments
 (0)