From 67dd1a2a9ffa5a927596c58cfa41ff7e0a4cfa6f Mon Sep 17 00:00:00 2001 From: xzk <1423665680@qq> Date: Sat, 30 Nov 2024 19:22:45 +0800 Subject: [PATCH] v3 --- src/Main.java | 102 +++++------ src/model/DataManager.java | 37 ++-- src/model/Goods.java | 52 +++++- src/view/GoodsManagementView.java | 278 ++++++++++++++++++++++++++++++ 4 files changed, 396 insertions(+), 73 deletions(-) create mode 100644 src/view/GoodsManagementView.java diff --git a/src/Main.java b/src/Main.java index d66eeb0..0cbd5e5 100644 --- a/src/Main.java +++ b/src/Main.java @@ -1,4 +1,3 @@ -package src; import javafx.application.Application; import javafx.application.Platform; @@ -7,100 +6,97 @@ import javafx.scene.Scene; import javafx.scene.control.*; import javafx.scene.layout.*; import javafx.stage.Stage; -import view.InboundView; -import view.InventoryView; -import view.OutboundView; +import view.*; public class Main extends Application { - + private BorderPane contentArea; - + @Override public void start(Stage primaryStage) { try { // 创建主布局 BorderPane mainLayout = new BorderPane(); - + // 创建菜单栏 MenuBar menuBar = createMenuBar(); mainLayout.setTop(menuBar); - + // 创建左侧导航栏 VBox leftPanel = createLeftPanel(); mainLayout.setLeft(leftPanel); - + // 创建内容区域 contentArea = new BorderPane(); contentArea.setStyle("-fx-background-color: #f4f4f4;"); contentArea.setPadding(new Insets(10)); - + // 设置默认欢迎页面 showWelcomePage(); - + mainLayout.setCenter(contentArea); - + // 创建状态栏 HBox statusBar = createStatusBar(); mainLayout.setBottom(statusBar); - + // 设置场景 Scene scene = new Scene(mainLayout, 1200, 800); primaryStage.setScene(scene); primaryStage.setTitle("仓库管理系统"); primaryStage.show(); - + } catch (Exception e) { e.printStackTrace(); } } - + private VBox createLeftPanel() { VBox leftPanel = new VBox(10); leftPanel.setPadding(new Insets(10)); leftPanel.setStyle("-fx-background-color: #e8e8e8;"); leftPanel.setPrefWidth(200); - + // 创建搜索框 TextField searchField = new TextField(); searchField.setPromptText("搜索..."); - + // 创建导航树 TreeView navigationTree = createNavigationTree(); - + // 添加到左侧面板 leftPanel.getChildren().addAll(searchField, navigationTree); VBox.setVgrow(navigationTree, Priority.ALWAYS); - + return leftPanel; } - + private void showWelcomePage() { VBox welcomeBox = new VBox(20); welcomeBox.setAlignment(javafx.geometry.Pos.CENTER); - + Label welcomeLabel = new Label("欢迎使用仓库管理系统"); welcomeLabel.setStyle("-fx-font-size: 24px; -fx-font-weight: bold;"); - + Label infoLabel = new Label("请从左侧菜单选择要使用的功能"); infoLabel.setStyle("-fx-font-size: 14px;"); - + welcomeBox.getChildren().addAll(welcomeLabel, infoLabel); contentArea.setCenter(welcomeBox); } - + private HBox createStatusBar() { HBox statusBar = new HBox(10); statusBar.setPadding(new Insets(5)); statusBar.setStyle("-fx-background-color: #e8e8e8;"); - + Label statusLabel = new Label("就绪"); Label userLabel = new Label("当前用户:管理员"); Label timeLabel = new Label(getCurrentTime()); - Region spacer = new Region(); HBox.setHgrow(spacer, Priority.ALWAYS); - + statusBar.getChildren().addAll(statusLabel, spacer, userLabel, timeLabel); // 动态更新时间 Thread timeThread = new Thread(() -> { @@ -122,72 +118,75 @@ public class Main extends Application { } private MenuBar createMenuBar() { MenuBar menuBar = new MenuBar(); - + // 系统菜单 Menu systemMenu = new Menu("系统"); MenuItem settingsItem = new MenuItem("系统设置"); MenuItem exitItem = new MenuItem("退出"); systemMenu.getItems().addAll(settingsItem, exitItem); - + // 库存管理菜单 Menu inventoryMenu = new Menu("库存管理"); MenuItem inboundItem = new MenuItem("入库管理"); MenuItem outboundItem = new MenuItem("出库管理"); MenuItem queryItem = new MenuItem("库存查询"); inventoryMenu.getItems().addAll(inboundItem, outboundItem, queryItem); - + // 货物管理菜单 Menu goodsMenu = new Menu("货物管理"); MenuItem goodsInfoItem = new MenuItem("货物信息"); MenuItem categoryItem = new MenuItem("分类管理"); goodsMenu.getItems().addAll(goodsInfoItem, categoryItem); - + // 报表菜单 Menu reportMenu = new Menu("报表统计"); MenuItem inventoryReportItem = new MenuItem("库存报表"); MenuItem logItem = new MenuItem("操作日志"); reportMenu.getItems().addAll(inventoryReportItem, logItem); - + // 为入库管理菜单项添加事件处理 inboundItem.setOnAction(e -> showInboundView()); // 为出库管理菜单项添加事件处理。 outboundItem.setOnAction(e -> showOutboundView()); + // 为货物信息菜单项添加事件处理 + goodsInfoItem.setOnAction(e -> showGoodsManagementView()); + menuBar.getMenus().addAll(systemMenu, inventoryMenu, goodsMenu, reportMenu); return menuBar; } - + private TreeView createNavigationTree() { TreeItem root = new TreeItem<>("功能导航"); root.setExpanded(true); - + // 库存管理 TreeItem inventory = new TreeItem<>("库存管理"); inventory.getChildren().addAll( - new TreeItem<>("入库管理"), - new TreeItem<>("出库管理"), - new TreeItem<>("库存查询") + new TreeItem<>("入库管理"), + new TreeItem<>("出库管理"), + new TreeItem<>("库存查询") ); - + // 货物管理 TreeItem goods = new TreeItem<>("货物管理"); goods.getChildren().addAll( - new TreeItem<>("货物信息"), - new TreeItem<>("分类管理") + new TreeItem<>("货物信息"), + new TreeItem<>("分类管理") ); - + // 报表统计 TreeItem report = new TreeItem<>("报表统计"); report.getChildren().addAll( - new TreeItem<>("库存报表"), - new TreeItem<>("操作日志") + new TreeItem<>("库存报表"), + new TreeItem<>("操作日志") ); - + root.getChildren().addAll(inventory, goods, report); - + TreeView tree = new TreeView<>(root); - + // 为导航树添加事件处理 tree.setOnMouseClicked(event -> { TreeItem item = tree.getSelectionModel().getSelectedItem(); @@ -202,6 +201,9 @@ public class Main extends Application { case "出库管理": showOutboundView(); break; + case "货物信息": + showGoodsManagementView(); + break; default: // 其他菜单项的处理逻辑 break; @@ -211,7 +213,7 @@ public class Main extends Application { return tree; } - + private void showInboundView() { InboundView inboundView = new InboundView(); contentArea.setCenter(inboundView); @@ -224,7 +226,11 @@ public class Main extends Application { InventoryView inventoryView = new InventoryView(); contentArea.setCenter(inventoryView); } + private void showGoodsManagementView() { + GoodsManagementView goodsManagementView = new GoodsManagementView(); + contentArea.setCenter(goodsManagementView); + } public static void main(String[] args) { launch(args); } -} \ No newline at end of file +} diff --git a/src/model/DataManager.java b/src/model/DataManager.java index 89480d6..6bcf6fc 100644 --- a/src/model/DataManager.java +++ b/src/model/DataManager.java @@ -10,40 +10,40 @@ public class DataManager { private Map goodsMap; private List suppliers; private Map inventory; - + private DataManager() { goodsMap = new HashMap<>(); suppliers = new ArrayList<>(); inventory = new HashMap<>(); initializeData(); } - + public static DataManager getInstance() { if (instance == null) { instance = new DataManager(); } return instance; } - + private void initializeData() { // 电子产品类 addGoodsWithStock("G001", "苹果手机", "iPhone 15", "台", 6999.00, "电子产品", 50); addGoodsWithStock("G002", "联想笔记本", "ThinkPad T14", "台", 5999.00, "电子产品", 30); addGoodsWithStock("G003", "华为平板", "MatePad Pro", "台", 3999.00, "电子产品", 40); addGoodsWithStock("G004", "戴尔显示器", "27寸 4K", "台", 2399.00, "电子产品", 25); - + // 办公家具类 addGoodsWithStock("G005", "办公桌", "1.4米", "张", 799.00, "办公家具", 100); addGoodsWithStock("G006", "办公椅", "人体工学", "把", 599.00, "办公家具", 150); addGoodsWithStock("G007", "文件柜", "三层", "个", 459.00, "办公家具", 80); addGoodsWithStock("G008", "会议桌", "2.4米", "张", 1599.00, "办公家具", 20); - + // 办公用品类 addGoodsWithStock("G009", "打印纸", "A4 70g", "箱", 89.00, "办公用品", 200); addGoodsWithStock("G010", "签字笔", "0.5mm黑色", "盒", 15.00, "办公用品", 500); addGoodsWithStock("G011", "订书机", "标准型", "个", 35.00, "办公用品", 300); addGoodsWithStock("G012", "文件夹", "A4蓝色", "个", 8.00, "办公用品", 1000); - + // 添加供应商 suppliers.add("苹果官方旗舰店"); suppliers.add("联想专卖店"); @@ -56,14 +56,15 @@ public class DataManager { suppliers.add("家具城"); suppliers.add("办公用品直营店"); } - - private void addGoodsWithStock(String id, String name, String specification, - String unit, double price, String category, int initialStock) { - Goods goods = new Goods(id, name, specification, unit, price, category); + + + private void addGoodsWithStock(String id, String name, String specification, + String unit, double price, String category, int initialStock) { + Goods goods = new Goods(id, name, specification, unit, price, category, initialStock, ""); goodsMap.put(id, goods); inventory.put(id, initialStock); } - + public void addGoods(Goods goods) { goodsMap.put(goods.getId(), goods); if (!inventory.containsKey(goods.getId())) { @@ -82,28 +83,28 @@ public class DataManager { return reports; } - + public Goods getGoods(String id) { return goodsMap.get(id); } - + public List getAllGoods() { return new ArrayList<>(goodsMap.values()); } - + public List getSuppliers() { return new ArrayList<>(suppliers); } - + public int getStock(String goodsId) { return inventory.getOrDefault(goodsId, 0); } - + public void updateStock(String goodsId, int quantity) { inventory.put(goodsId, inventory.getOrDefault(goodsId, 0) + quantity); } - + public Map getAllStock() { return new HashMap<>(inventory); } -} \ No newline at end of file +} diff --git a/src/model/Goods.java b/src/model/Goods.java index 0ed7cbe..9de85d2 100644 --- a/src/model/Goods.java +++ b/src/model/Goods.java @@ -1,5 +1,7 @@ package model; +import java.time.LocalDateTime; + public class Goods { private String id; private String name; @@ -7,7 +9,12 @@ public class Goods { private String unit; private double price; private String category; - + private int quantity; + private String remark; + private LocalDateTime inboundTime; + private String operator; + private String supplier; + public Goods(String id, String name, String specification, String unit, double price, String category) { this.id = id; this.name = name; @@ -15,11 +22,36 @@ public class Goods { this.unit = unit; this.price = price; this.category = category; + this.quantity = 0; + this.remark = ""; + this.inboundTime = null; + this.operator = ""; + this.supplier = ""; } - public Goods(String id, String goodsName, int quantity, String remark) { + public Goods(String id, String name, String specification, String unit, double price, String category, int quantity, String remark) { + this.id = id; + this.name = name; + this.specification = specification; + this.unit = unit; + this.price = price; + this.category = category; + this.quantity = quantity; + this.remark = remark; + this.inboundTime = null; + this.operator = ""; + this.supplier = ""; } + public Goods(String id, String goodsName, int quantity, String remark) { + this.id = id; + this.name = goodsName; + this.quantity = quantity; + this.remark = remark; + this.inboundTime = null; + this.operator = ""; + this.supplier = ""; + } // Getters and Setters public String getId() { return id; } @@ -34,8 +66,14 @@ public class Goods { public void setPrice(double price) { this.price = price; } public String getCategory() { return category; } public void setCategory(String category) { this.category = category; } - - public int getQuantity() { - return 0; - } -} \ No newline at end of file + public int getQuantity() { return quantity; } + public void setQuantity(int quantity) { this.quantity = quantity; } + public String getRemark() { return remark; } + public void setRemark(String remark) { this.remark = remark; } + public LocalDateTime getInboundTime() { return inboundTime; } + public void setInboundTime(LocalDateTime inboundTime) { this.inboundTime = inboundTime; } + public String getOperator() { return operator; } + public void setOperator(String operator) { this.operator = operator; } + public String getSupplier() { return supplier; } + public void setSupplier(String supplier) { this.supplier = supplier; } +} diff --git a/src/view/GoodsManagementView.java b/src/view/GoodsManagementView.java new file mode 100644 index 0000000..b4e79d5 --- /dev/null +++ b/src/view/GoodsManagementView.java @@ -0,0 +1,278 @@ +package view; + +import javafx.collections.FXCollections; +import javafx.geometry.Insets; +import javafx.geometry.Pos; +import javafx.scene.control.*; +import javafx.scene.layout.*; +import javafx.scene.control.cell.PropertyValueFactory; +import model.DataManager; +import model.Goods; +import model.InventoryManager; + +import java.time.LocalDateTime; +import java.time.format.DateTimeFormatter; +import java.util.List; + +public class GoodsManagementView extends BorderPane { + + private TextField idField; + private TextField nameField; + private TextField specificationField; + private TextField unitField; + private TextField priceField; + private TextField categoryField; + private TextField quantityField; + private TableView tableView; + + public GoodsManagementView() { + initializeUI(); + } + + private void initializeUI() { + // 顶部操作区域 + VBox topArea = createTopArea(); + setTop(topArea); + + // 中间表格区域 + tableView = createTableView(); + setCenter(tableView); + + // 加载现有货物数据 + loadGoodsData(); + + // 添加双击事件以填充文本字段 + tableView.setOnMouseClicked(event -> { + if (event.getClickCount() == 2) { + Goods selectedGoods = tableView.getSelectionModel().getSelectedItem(); + if (selectedGoods != null) { + fillFields(selectedGoods); + } + } + }); + } + + private VBox createTopArea() { + VBox topArea = new VBox(10); + topArea.setPadding(new Insets(10)); + + // 基本信息 + GridPane basicInfo = new GridPane(); + basicInfo.setHgap(10); + basicInfo.setVgap(10); + + Label idLabel = new Label("货物ID:"); + idField = new TextField(); + idField.setPromptText("请输入货物ID"); + idField.setEditable(false); // ID 不可编辑 + + Label nameLabel = new Label("货物名称:"); + nameField = new TextField(); + nameField.setPromptText("请输入货物名称"); + + Label specificationLabel = new Label("规格:"); + specificationField = new TextField(); + specificationField.setPromptText("请输入规格"); + + Label unitLabel = new Label("单位:"); + unitField = new TextField(); + unitField.setPromptText("请输入单位"); + + Label priceLabel = new Label("价格:"); + priceField = new TextField(); + priceField.setPromptText("请输入价格"); + + Label categoryLabel = new Label("类别:"); + categoryField = new TextField(); + categoryField.setPromptText("请输入类别"); + + basicInfo.addRow(0, idLabel, idField, nameLabel, nameField); + basicInfo.addRow(1, specificationLabel, specificationField, unitLabel, unitField); + basicInfo.addRow(2, priceLabel, priceField, categoryLabel, categoryField); + + // 库存信息 + GridPane stockInfo = new GridPane(); + stockInfo.setHgap(10); + stockInfo.setVgap(10); + + Label quantityLabel = new Label("数量:"); + quantityField = new TextField(); + quantityField.setPromptText("请输入数量"); + + stockInfo.addRow(0, quantityLabel, quantityField); + + // 设置列宽 + ColumnConstraints column1 = new ColumnConstraints(); + column1.setMinWidth(80); + ColumnConstraints column2 = new ColumnConstraints(); + column2.setMinWidth(200); + ColumnConstraints column3 = new ColumnConstraints(); + column3.setMinWidth(80); + ColumnConstraints column4 = new ColumnConstraints(); + column4.setMinWidth(200); + + basicInfo.getColumnConstraints().addAll(column1, column2, column3, column4); + stockInfo.getColumnConstraints().addAll(column1, column2); + + // 操作按钮 + HBox buttonBox = new HBox(10); + buttonBox.setAlignment(Pos.CENTER_RIGHT); + buttonBox.setPadding(new Insets(10, 0, 0, 0)); + + Button saveButton = new Button("修改"); + saveButton.setOnAction(e -> handleSave()); + + Button clearButton = new Button("清空"); + clearButton.setOnAction(e -> handleClear()); + + buttonBox.getChildren().addAll(saveButton, clearButton); + + topArea.getChildren().addAll(basicInfo, stockInfo, buttonBox); + return topArea; + } + + private TableView createTableView() { + TableView table = new TableView<>(); + + TableColumn idCol = new TableColumn<>("货物ID"); + idCol.setCellValueFactory(new PropertyValueFactory<>("id")); + + TableColumn nameCol = new TableColumn<>("货物名称"); + nameCol.setCellValueFactory(new PropertyValueFactory<>("name")); + + TableColumn specificationCol = new TableColumn<>("规格"); + specificationCol.setCellValueFactory(new PropertyValueFactory<>("specification")); + + TableColumn unitCol = new TableColumn<>("单位"); + unitCol.setCellValueFactory(new PropertyValueFactory<>("unit")); + + TableColumn priceCol = new TableColumn<>("价格"); + priceCol.setCellValueFactory(new PropertyValueFactory<>("price")); + + TableColumn categoryCol = new TableColumn<>("类别"); + categoryCol.setCellValueFactory(new PropertyValueFactory<>("category")); + + TableColumn quantityCol = new TableColumn<>("数量"); + quantityCol.setCellValueFactory(new PropertyValueFactory<>("quantity")); + + // 新增的列 + TableColumn inboundTimeCol = new TableColumn<>("入库时间"); + inboundTimeCol.setCellValueFactory(new PropertyValueFactory<>("inboundTime")); + + TableColumn operatorCol = new TableColumn<>("入库操作员"); + operatorCol.setCellValueFactory(new PropertyValueFactory<>("operator")); + + TableColumn supplierCol = new TableColumn<>("供应商"); + supplierCol.setCellValueFactory(new PropertyValueFactory<>("supplier")); + + TableColumn remarkCol = new TableColumn<>("备注"); + remarkCol.setCellValueFactory(new PropertyValueFactory<>("remark")); + + table.getColumns().addAll(idCol, nameCol, specificationCol, unitCol, priceCol, categoryCol, quantityCol, + inboundTimeCol, operatorCol, supplierCol, remarkCol); + + return table; + } + + private void loadGoodsData() { + List goodsList = DataManager.getInstance().getAllGoods(); + tableView.setItems(FXCollections.observableArrayList(goodsList)); + } + + private void handleSave() { + try { + String id = idField.getText().trim(); + String name = nameField.getText().trim(); + String specification = specificationField.getText().trim(); + String unit = unitField.getText().trim(); + String priceText = priceField.getText().trim(); + String category = categoryField.getText().trim(); + String quantityText = quantityField.getText().trim(); + + // 输入验证 + if (id.isEmpty() || name.isEmpty() || specification.isEmpty() || unit.isEmpty() || + priceText.isEmpty() || category.isEmpty() || quantityText.isEmpty()) { + showAlert("错误", "请填写完整的货物信息!"); + return; + } + + double price; + int quantity; + try { + price = Double.parseDouble(priceText); + if (price <= 0) { + showAlert("错误", "价格必须大于0!"); + return; + } + } catch (NumberFormatException e) { + showAlert("错误", "请输入有效的价格!"); + return; + } + + try { + quantity = Integer.parseInt(quantityText); + if (quantity <= 0) { + showAlert("错误", "数量必须大于0!"); + return; + } + } catch (NumberFormatException e) { + showAlert("错误", "请输入有效的数量!"); + return; + } + + // 查找货物对象 + Goods existingGoods = DataManager.getInstance().getGoods(id); + if (existingGoods == null) { + showAlert("错误", "货物ID不存在!"); + return; + } + + // 更新货物对象 + existingGoods.setName(name); + existingGoods.setSpecification(specification); + existingGoods.setUnit(unit); + existingGoods.setPrice(price); + existingGoods.setCategory(category); + existingGoods.setQuantity(quantity); + + // 更新表格 + tableView.refresh(); + + // 清空输入 + handleClear(); + + showAlert("成功", "货物信息已更新!"); + + } catch (Exception e) { + showAlert("错误", "保存失败:" + e.getMessage()); + } + } + + private void handleClear() { + idField.clear(); + nameField.clear(); + specificationField.clear(); + unitField.clear(); + priceField.clear(); + categoryField.clear(); + quantityField.clear(); + } + + private void fillFields(Goods goods) { + idField.setText(goods.getId()); + nameField.setText(goods.getName()); + specificationField.setText(goods.getSpecification()); + unitField.setText(goods.getUnit()); + priceField.setText(String.valueOf(goods.getPrice())); + categoryField.setText(goods.getCategory()); + quantityField.setText(String.valueOf(goods.getQuantity())); + } + + private void showAlert(String title, String content) { + Alert alert = new Alert(Alert.AlertType.INFORMATION); + alert.setTitle(title); + alert.setHeaderText(null); + alert.setContentText(content); + alert.showAndWait(); + } +}