diff --git a/src/main/java/module-info.java b/src/main/java/module-info.java index c525a65..eedc2c7 100644 --- a/src/main/java/module-info.java +++ b/src/main/java/module-info.java @@ -1,29 +1,32 @@ module org.to.telegramfinalproject { requires javafx.controls; requires javafx.fxml; + requires javafx.graphics; // بهتره اضافه باشه + requires javafx.media; requires javafx.web; + requires org.json; + requires java.sql; + requires java.desktop; + + // لایبرری‌های جانبی — اگر واقعاً در مسیر ماژول هستند requires org.controlsfx.controls; requires com.dlsc.formsfx; requires net.synedra.validatorfx; requires org.kordamp.ikonli.javafx; requires org.kordamp.bootstrapfx.core; requires eu.hansolo.tilesfx; - requires org.json; - requires java.sql; - requires java.desktop; - requires spark.core; - requires javax.servlet.api; requires mp3agic; - requires jdk.internal.le; - requires javafx.media; + requires spark.core; // فقط اگر واقعاً استفاده می‌کنی + requires javax.servlet.api; // فقط اگر واقعاً استفاده می‌کنی - // FXML کنترلرها در این پکیج‌اند: + // کنترلرها/کلاس‌هایی که FXML به آن‌ها دسترسی بازتابی دارد opens org.to.telegramfinalproject.UI to javafx.fxml; - // اگر FXML از کلاس‌های Client هم استفاده می‌کند: opens org.to.telegramfinalproject.Client to javafx.fxml; + opens org.to.telegramfinalproject.Models to javafx.fxml; // اگر مدل‌ها داخل FXML مصرف می‌شوند - // فقط اگر لازم است از بیرون به این API‌ها کامپایل شود: + // اگر پکیج‌هایی را می‌خواهی خارج از ماژول در دسترس قرار دهی + exports org.to.telegramfinalproject.UI; exports org.to.telegramfinalproject.Client; - // ⚠️ عمداً NOT exporting/opens ریشه‌ی پکیج، چون کلاس ندارد. + exports org.to.telegramfinalproject.Models; } diff --git a/src/main/java/org/to/telegramfinalproject/UI/AddMembersController.java b/src/main/java/org/to/telegramfinalproject/UI/AddMembersController.java index 4e62c3a..9d8d61a 100644 --- a/src/main/java/org/to/telegramfinalproject/UI/AddMembersController.java +++ b/src/main/java/org/to/telegramfinalproject/UI/AddMembersController.java @@ -206,11 +206,9 @@ public class AddMembersController { private Image loadAvatar(String path) { try { - // 1) اگر ریسورس داخلی باشد var in = getClass().getResourceAsStream(path); if (in != null) return new Image(in); - // 2) اگر URL کامل یا file URI return new Image(path, true); } catch (Exception e) { return new Image( @@ -233,7 +231,6 @@ public class AddMembersController { List ids = selectedContacts.stream().map(Contact::getId).toList(); - // تلاش برای batch JSONObject batchReq = new JSONObject() .put("action", "add_members_to_group") .put("group_id", groupInternalId.toString()) @@ -248,11 +245,10 @@ public class AddMembersController { return; } - // fallback: تک‌به‌تک boolean allOk = true; for (String uid : ids) { JSONObject single = new JSONObject() - .put("action", "add_member_to_group") + .put("action", "add_members_to_group") .put("group_id", groupInternalId.toString()) .put("user_id", uid); JSONObject r = ActionHandler.sendWithResponse(single); diff --git a/src/main/java/org/to/telegramfinalproject/UI/ManageGroupController.java b/src/main/java/org/to/telegramfinalproject/UI/ManageGroupController.java index 78490c4..82195b0 100644 --- a/src/main/java/org/to/telegramfinalproject/UI/ManageGroupController.java +++ b/src/main/java/org/to/telegramfinalproject/UI/ManageGroupController.java @@ -14,6 +14,8 @@ import org.to.telegramfinalproject.Client.ActionHandler; import java.io.File; import java.io.IOException; +import java.nio.file.Path; +import java.nio.file.Paths; import java.util.Objects; import java.util.UUID; @@ -116,13 +118,27 @@ public class ManageGroupController { groupIdField.setText(originalGroupId); if (!originalImageUrl.isBlank()) { - groupImage.setImage(new Image(originalImageUrl, true)); + String uri = resolveLocalUri(originalImageUrl); + if (uri != null) { + groupImage.setImage(new Image(uri, true)); + } } + adminCount.setText(String.valueOf(countRole(data, "admin") + 1)); memberCount.setText(String.valueOf(countRole(data, "member") + Integer.parseInt(adminCount.getText()))); } + private String resolveLocalUri(String raw) { + if (raw == null || raw.isBlank()) return null; + if (raw.startsWith("file:/") || raw.startsWith("http")) return raw; + + Path base = Paths.get(System.getProperty("user.dir"), "uploads"); + Path resolved = base.resolve(raw.startsWith("/") ? raw.substring(1) : raw) + .normalize(); + return resolved.toUri().toString(); // file:///C:/.../uploads/avatars/2025-09-05/... + } + private int countRole(JSONObject groupData, String role) { var arr = groupData.optJSONArray("members"); if (arr == null) return 0; diff --git a/uploads/avatars/2025-09-08/a01fa00f-00cc-4222-9e75-4f44fe0d6d26.jpg b/uploads/avatars/2025-09-08/a01fa00f-00cc-4222-9e75-4f44fe0d6d26.jpg new file mode 100644 index 0000000..5a37195 Binary files /dev/null and b/uploads/avatars/2025-09-08/a01fa00f-00cc-4222-9e75-4f44fe0d6d26.jpg differ