diff --git a/src/main/java/BsK/client/ui/component/CheckUpPage/CheckUpPage.java b/src/main/java/BsK/client/ui/component/CheckUpPage/CheckUpPage.java index 4150b1c..d8f96bf 100644 --- a/src/main/java/BsK/client/ui/component/CheckUpPage/CheckUpPage.java +++ b/src/main/java/BsK/client/ui/component/CheckUpPage/CheckUpPage.java @@ -164,7 +164,7 @@ public class CheckUpPage extends JPanel { private JTextField checkupIdField, customerLastNameField, customerFirstNameField,customerAddressField, customerPhoneField, customerIdField, customerCccdDdcnField; private JTextArea suggestionField, diagnosisField, conclusionField; // Changed symptomsField to suggestionField private JTextPane notesField; - private JComboBox doctorComboBox, statusComboBox, genderComboBox, provinceComboBox, districtComboBox, wardComboBox, checkupTypeComboBox, templateComboBox; + private JComboBox doctorComboBox, statusComboBox, genderComboBox, provinceComboBox, districtComboBox, wardComboBox, checkupTypeComboBox, templateComboBox, orientationComboBox; // Added orientationComboBox private JSpinner customerWeightSpinner, customerHeightSpinner, patientHeartRateSpinner, bloodPressureSystolicSpinner, bloodPressureDiastolicSpinner; private JDatePickerImpl datePicker, dobPicker, recheckupDatePicker; private String[][] medicinePrescription = new String[0][0]; // Initialize to empty @@ -931,7 +931,23 @@ public class CheckUpPage extends JPanel { // Add "Thêm mẫu" button next to template combobox + // Add orientation dropdown gbcTemplate.gridx = 2; gbcTemplate.weightx = 0.0; + JLabel orientationLabel = new JLabel("Hướng in:"); + orientationLabel.setFont(labelFont); + templatePanel.add(orientationLabel, gbcTemplate); + + gbcTemplate.gridx = 3; + orientationComboBox = new JComboBox<>(new String[]{"ngang", "dọc"}); + orientationComboBox.setFont(fieldFont); + orientationComboBox.setPreferredSize(new Dimension(80, 25)); + orientationComboBox.addActionListener(e -> { + printType = (String) orientationComboBox.getSelectedItem(); + }); + templatePanel.add(orientationComboBox, gbcTemplate); + + // Add template button + gbcTemplate.gridx = 4; gbcTemplate.weightx = 0.0; JButton addTemplateButton = new JButton("Thêm mẫu"); addTemplateButton.setFont(fieldFont); addTemplateButton.setBackground(new Color(63, 81, 181)); @@ -1544,6 +1560,24 @@ public class CheckUpPage extends JPanel { return button; } + /** + * Helper method to get the currently selected patient from the queue + * @return The currently selected Patient object, or null if none selected + */ + private Patient getCurrentSelectedPatient() { + if (selectedCheckupId == null) { + return null; + } + + // Find the patient in the queue by checkupId + for (Patient patient : patientQueue) { + if (patient != null && selectedCheckupId.equals(patient.getCheckupId())) { + return patient; + } + } + return null; + } + private void handleActionPanelClick(String name) { switch (name) { case "service": @@ -1611,6 +1645,10 @@ public class CheckUpPage extends JPanel { } // Step 2: Attempt to create the report object BEFORE saving anything. + // Get current patient's Google Drive URL for QR code + Patient currentPatient = getCurrentSelectedPatient(); + String currentPatientDriveUrl = (currentPatient != null) ? currentPatient.getDriveUrl() : ""; + UltrasoundResult ultrasoundResultPrint = new UltrasoundResult( checkupIdField.getText(), customerLastNameField.getText() + " " + customerFirstNameField.getText(), @@ -1624,12 +1662,13 @@ public class CheckUpPage extends JPanel { suggestionField.getText(), recheckupDatePicker.getJFormattedTextField().getText(), selectedImagesForPrint, - printType, + (String) orientationComboBox.getSelectedItem(), // Use selected orientation templateTitle, customerHeightSpinner.getValue().toString(), customerWeightSpinner.getValue().toString(), patientHeartRateSpinner.getValue().toString(), - bloodPressureSystolicSpinner.getValue() + "/" + bloodPressureDiastolicSpinner.getValue() + bloodPressureSystolicSpinner.getValue() + "/" + bloodPressureDiastolicSpinner.getValue(), + currentPatientDriveUrl // Google Drive URL for QR code ); JasperPrint jasperPrintToPrint; @@ -1652,12 +1691,12 @@ public class CheckUpPage extends JPanel { handleSave(); afterSaveActions(statusToSavePrint, "Đã lưu. Đang gửi lệnh in..."); - // Step 4: Finally, print using the pre-made object. + // Step 4: Finally, show print dialog with the pre-made object. try { - JasperPrintManager.printReport(jasperPrintToPrint, false); + JasperPrintManager.printReport(jasperPrintToPrint, true); // true = show print dialog } catch (JRException e) { - log.error("Error printing report directly", e); - JOptionPane.showMessageDialog(this, "Không thể in trực tiếp: " + e.getMessage(), "Lỗi In", JOptionPane.ERROR_MESSAGE); + log.error("Error showing print dialog", e); + JOptionPane.showMessageDialog(this, "Không thể hiển thị hộp thoại in: " + e.getMessage(), "Lỗi In", JOptionPane.ERROR_MESSAGE); } break; case "loupe": // This case now handles "Lưu & Xem" @@ -1676,6 +1715,10 @@ public class CheckUpPage extends JPanel { } // Step 2: Attempt to create the report object BEFORE saving anything. + // Get current patient's Google Drive URL for QR code + Patient viewPatient = getCurrentSelectedPatient(); + String viewPatientDriveUrl = (viewPatient != null) ? viewPatient.getDriveUrl() : ""; + UltrasoundResult ultrasoundResultView = new UltrasoundResult( checkupIdField.getText(), customerLastNameField.getText() + " " + customerFirstNameField.getText(), @@ -1689,12 +1732,13 @@ public class CheckUpPage extends JPanel { suggestionField.getText(), recheckupDatePicker.getJFormattedTextField().getText(), selectedImagesForPrint, - printType, + (String) orientationComboBox.getSelectedItem(), // Use selected orientation templateTitle, customerHeightSpinner.getValue().toString(), customerWeightSpinner.getValue().toString(), patientHeartRateSpinner.getValue().toString(), - bloodPressureSystolicSpinner.getValue() + "/" + bloodPressureDiastolicSpinner.getValue() + bloodPressureSystolicSpinner.getValue() + "/" + bloodPressureDiastolicSpinner.getValue(), + viewPatientDriveUrl // Google Drive URL for QR code ); JasperPrint jasperPrintToView; @@ -4243,6 +4287,8 @@ public class CheckUpPage extends JPanel { String selectedTemplateName = (String) templateComboBox.getSelectedItem(); if (selectedTemplateName == null || allTemplates == null || selectedTemplateName.equals("Không sử dụng mẫu")) { + // Reset orientation to landscape when no template is selected + orientationComboBox.setSelectedItem("ngang"); return; } @@ -4266,6 +4312,7 @@ public class CheckUpPage extends JPanel { // Set template print setting photoNum = Integer.parseInt(template.getPhotoNum()); printType = template.getPrintType(); + orientationComboBox.setSelectedItem(template.getPrintType()); // Update orientation dropdown templateName = template.getTemplateName(); templateTitle = template.getTemplateTitle(); templateGender = template.getTemplateGender(); diff --git a/src/main/java/BsK/client/ui/component/CheckUpPage/PrintDialog/UltrasoundResult.java b/src/main/java/BsK/client/ui/component/CheckUpPage/PrintDialog/UltrasoundResult.java index c0b6bbb..5664185 100644 --- a/src/main/java/BsK/client/ui/component/CheckUpPage/PrintDialog/UltrasoundResult.java +++ b/src/main/java/BsK/client/ui/component/CheckUpPage/PrintDialog/UltrasoundResult.java @@ -77,6 +77,7 @@ public class UltrasoundResult { private final List selectedImages; private final String printType; // "ngang" or "dọc" private final String templateTitle; + private final String driveUrl; // Google Drive URL for QR code // Vitals data private final String customerHeight; @@ -91,7 +92,7 @@ public class UltrasoundResult { String rtfContent, String conclusion, String suggestion, String recheckupDate, List selectedImages, String printType, String templateTitle, String customerHeight, - String customerWeight, String heartRate, String bloodPressure) { + String customerWeight, String heartRate, String bloodPressure, String driveUrl) { // Defensive null checks to prevent JasperReports from crashing on null parameters this.checkupId = checkupId != null ? checkupId : ""; @@ -112,6 +113,7 @@ public class UltrasoundResult { this.customerWeight = customerWeight != null ? customerWeight : ""; this.heartRate = heartRate != null ? heartRate : ""; this.bloodPressure = bloodPressure != null ? bloodPressure : ""; + this.driveUrl = driveUrl != null ? driveUrl : ""; // Google Drive URL } public void showDirectJasperViewer() { @@ -186,6 +188,9 @@ public class UltrasoundResult { } } + // Google Drive URL for QR code generation + parameters.put("driveURL", this.driveUrl); + // Load and compile the report JasperDesign jasperDesign = JRXmlLoader.load(inputStream); JasperReport jasperReport = JasperCompileManager.compileReport(jasperDesign); diff --git a/src/main/java/BsK/client/ui/component/CheckUpPage/PrintDialog/print_forms/ultrasoundresult.jrxml b/src/main/java/BsK/client/ui/component/CheckUpPage/PrintDialog/print_forms/ultrasoundresult.jrxml index 3cf54a2..7b6556e 100644 --- a/src/main/java/BsK/client/ui/component/CheckUpPage/PrintDialog/print_forms/ultrasoundresult.jrxml +++ b/src/main/java/BsK/client/ui/component/CheckUpPage/PrintDialog/print_forms/ultrasoundresult.jrxml @@ -44,6 +44,7 @@ + @@ -55,13 +56,13 @@ <element kind="image" uuid="fd80ab38-4cae-409b-84b9-356220d2b1e5" x="0" y="-5" width="70" height="64"> <expression><![CDATA[$P{logoImage}]]></expression> </element> - <element kind="textField" uuid="eb56d4c8-2a0d-45fa-89a2-ad6528f9a99b" x="70" y="0" width="267" height="20" fontName="Times New Roman" fontSize="14.0" bold="true"> + <element kind="textField" uuid="eb56d4c8-2a0d-45fa-89a2-ad6528f9a99b" x="70" y="0" width="233" height="20" fontName="Times New Roman" fontSize="14.0" bold="true"> <expression><![CDATA[$P{clinicName}]]></expression> </element> <element kind="staticText" uuid="2677daaf-d0fb-40ad-afaa-513efa16055c" x="70" y="20" width="150" height="15" fontName="Times New Roman" fontSize="10.0" bold="true" hTextAlign="Left"> <text><![CDATA[Địa chỉ: ]]></text> </element> - <element kind="textField" uuid="796d9ffd-6d2e-4ae3-bdfb-b08183d7d9c0" x="106" y="20" width="231" height="15" fontName="Times New Roman" fontSize="10.0"> + <element kind="textField" uuid="796d9ffd-6d2e-4ae3-bdfb-b08183d7d9c0" x="106" y="20" width="193" height="15" fontName="Times New Roman" fontSize="10.0"> <expression><![CDATA[$P{clinicAddress}]]></expression> </element> <element kind="staticText" uuid="1a1405ee-b3e4-4e98-ac08-6818bc29e902" x="70" y="36" width="150" height="15" fontName="Times New Roman" fontSize="10.0" bold="true" hTextAlign="Left"> @@ -134,17 +135,22 @@ <text><![CDATA[Huyết áp:]]></text> </element> <element kind="textField" uuid="3e1069a6-daea-45c2-b21f-935b49baba45" x="50" y="150" width="50" height="16" fontName="Times New Roman" fontSize="10.0"> - <expression><![CDATA[$P{checkupHeight} +" cm"]]></expression> + <expression><![CDATA[$P{checkupWeight} +" cm"]]></expression> </element> <element kind="textField" uuid="fb080012-3196-4535-bcd2-e87274c66fa5" x="150" y="150" width="50" height="16" fontName="Times New Roman" fontSize="10.0"> <expression><![CDATA[$P{checkupWeight} + " kg"]]></expression> </element> <element kind="textField" uuid="e4185ffe-8712-41e3-a9ff-2be6569dff15" x="243" y="150" width="47" height="16" fontName="Times New Roman" fontSize="10.0"> - <expression><![CDATA[$P{checkupHeartBeat} + " bpm"]]></expression> + <expression><![CDATA[$P{checkupHeartBeat} + " l/p"]]></expression> </element> <element kind="textField" uuid="6b0b21be-2ca3-4594-bbe9-34868e13eb1e" x="335" y="150" width="63" height="16" fontName="Times New Roman" fontSize="10.0"> <expression><![CDATA[$P{checkupBloodPressure} +" mmHg"]]></expression> </element> + <element kind="component" uuid="e8842007-3343-4399-a101-76a302d0755d" x="354" y="8" width="41" height="38"> + <component kind="barcode4j:QRCode"> + <codeExpression><![CDATA[$P{driveURL}]]></codeExpression> + </component> + </element> </element> <element kind="frame" uuid="a72ffc70-007e-43af-a566-b34e6e07b312" x="400" y="0" width="400" height="540"> <element kind="staticText" uuid="246a04b0-2565-4987-b7f3-dd369703035c" x="0" y="340" width="100" height="30" forecolor="#FF0905" fontName="Times New Roman" fontSize="15.0" bold="true"> @@ -168,14 +174,11 @@ <element kind="textField" uuid="e90ad772-4425-482d-9e75-f2bc66b9084d" x="0" y="358" width="400" height="70" fontName="Times New Roman" fontSize="10.0"> <expression><![CDATA[$P{checkupConclusion}]]></expression> </element> - <element kind="component" uuid="cb28d811-1328-45dc-9461-cfbb88b7eeae" x="-63" y="13" width="60" height="40"> + <element kind="component" uuid="cb28d811-1328-45dc-9461-cfbb88b7eeae" x="-97" y="9" width="50" height="39"> <component kind="barcode4j:Code128"> <codeExpression><![CDATA[$P{barcodeNumber}]]></codeExpression> </component> </element> - <element kind="staticText" uuid="6a7d5f66-d7cc-481f-9fff-8ece0789b3b4" x="-63" y="2" width="61" height="17" fontName="Times New Roman" fontSize="10.0" bold="false" hTextAlign="Center"> - <text><![CDATA[Mã khám bệnh]]></text> - </element> <element kind="textField" uuid="d63165c2-19e2-43ad-8a3f-004e00bffdfe" x="0" y="450" width="230" height="55" fontName="Times New Roman" fontSize="10.0"> <expression><![CDATA[$P{checkupSuggestion}]]></expression> </element> @@ -266,6 +269,10 @@ <expression><![CDATA[$P{image1}]]></expression> </element> </element> + <element kind="staticText" uuid="8f35aa72-22a4-45f0-a35e-8e35e832404e" x="-55" y="46" width="55" height="14" fontName="Times New Roman" fontSize="8.0" bold="false" hTextAlign="Center"> + <printWhenExpression><![CDATA[$P{driveURL} != null && !$P{driveURL}.trim().isEmpty()]]></printWhenExpression> + <text><![CDATA[Xem KQ online]]></text> + </element> </element> </band> </detail> diff --git a/src/main/java/BsK/common/entity/Patient.java b/src/main/java/BsK/common/entity/Patient.java index 32c915f..18ef7c3 100644 --- a/src/main/java/BsK/common/entity/Patient.java +++ b/src/main/java/BsK/common/entity/Patient.java @@ -29,7 +29,7 @@ public class Patient { private String cccdDdcn; private String heartBeat; private String bloodPressure; - + private String driveUrl; public Patient(String[][] array) { this.checkupId = array[0][0]; @@ -54,12 +54,13 @@ public class Patient { this.cccdDdcn = array[0][19]; this.heartBeat = array[0][20]; this.bloodPressure = array[0][21]; + this.driveUrl = array[0][22]; } // New constructor for a single patient data row public Patient(String[] data) { - if (data.length < 22) { - throw new IllegalArgumentException("Patient data array must contain at least 22 elements to include a conclusion."); + if (data.length < 23) { + throw new IllegalArgumentException("Patient data array must contain at least 23 elements to include a conclusion."); } this.checkupId = data[0]; this.checkupDate = data[1]; @@ -83,5 +84,6 @@ public class Patient { this.cccdDdcn = data[19]; this.heartBeat = data[20]; this.bloodPressure = data[21]; + this.driveUrl = data[22]; } } diff --git a/src/main/java/BsK/server/network/handler/ServerHandler.java b/src/main/java/BsK/server/network/handler/ServerHandler.java index 2771b03..b85704b 100644 --- a/src/main/java/BsK/server/network/handler/ServerHandler.java +++ b/src/main/java/BsK/server/network/handler/ServerHandler.java @@ -111,7 +111,8 @@ public class ServerHandler extends SimpleChannelInboundHandler<TextWebSocketFram ResultSet rs = statement.executeQuery( "select a.checkup_id, a.checkup_date, c.customer_last_name, c.customer_first_name,\n" + "d.doctor_first_name, d.doctor_last_name, a.suggestion, a.diagnosis, a.notes, a.status, a.customer_id, \n" + - "c.customer_number, c.customer_address, a.customer_weight, a.customer_height, c.customer_gender, c.customer_dob, a.checkup_type, a.conclusion, a.reCheckupDate, c.cccd_ddcn, a.heart_beat, a.blood_pressure\n" + + "c.customer_number, c.customer_address, a.customer_weight, a.customer_height, c.customer_gender, c.customer_dob,\n" + + "a.checkup_type, a.conclusion, a.reCheckupDate, c.cccd_ddcn, a.heart_beat, a.blood_pressure, c.drive_url\n" + "from checkup as a\n" + "join customer as c on a.customer_id = c.customer_id\n" + "join Doctor D on a.doctor_id = D.doctor_id\n" + @@ -152,11 +153,16 @@ public class ServerHandler extends SimpleChannelInboundHandler<TextWebSocketFram String cccdDdcn = rs.getString("cccd_ddcn"); String heartBeat = rs.getString("heart_beat"); String bloodPressure = rs.getString("blood_pressure"); + String driveUrl = rs.getString("drive_url"); + if (driveUrl == null) { + driveUrl = ""; + } String result = String.join("|", checkupId, checkupDate, customerLastName, customerFirstName, doctorLastName + " " + doctorFirstName, suggestion, diagnosis, notes, status, customerId, customerNumber, customerAddress, customerWeight, customerHeight, - customerGender, customerDob, checkupType, conclusion, reCheckupDate, cccdDdcn, heartBeat, bloodPressure + customerGender, customerDob, checkupType, conclusion, reCheckupDate, cccdDdcn, heartBeat, bloodPressure, + driveUrl ); resultList.add(result); @@ -181,7 +187,7 @@ public class ServerHandler extends SimpleChannelInboundHandler<TextWebSocketFram ResultSet rs = statement.executeQuery( "select a.checkup_id, a.checkup_date, c.customer_last_name, c.customer_first_name,\n" + "d.doctor_first_name, d.doctor_last_name, a.suggestion, a.diagnosis, a.notes, a.status, a.customer_id, \n" + - "c.customer_number, c.customer_address, a.customer_weight, a.customer_height, c.customer_gender, c.customer_dob, a.checkup_type, a.conclusion, a.reCheckupDate, c.cccd_ddcn, a.heart_beat, a.blood_pressure\n" + + "c.customer_number, c.customer_address, a.customer_weight, a.customer_height, c.customer_gender, c.customer_dob, a.checkup_type, a.conclusion, a.reCheckupDate, c.cccd_ddcn, a.heart_beat, a.blood_pressure, c.drive_url\n" + "from checkup as a\n" + "join customer as c on a.customer_id = c.customer_id\n" + "join Doctor D on a.doctor_id = D.doctor_id\n" + @@ -226,11 +232,16 @@ public class ServerHandler extends SimpleChannelInboundHandler<TextWebSocketFram String cccdDdcn = rs.getString("cccd_ddcn"); String heartBeat = rs.getString("heart_beat"); String bloodPressure = rs.getString("blood_pressure"); + String driveUrl = rs.getString("drive_url"); + if (driveUrl == null) { + driveUrl = ""; + } String result = String.join("|", checkupId, checkupDate, customerLastName, customerFirstName, doctorLastName + " " + doctorFirstName, suggestion, diagnosis, notes, status, customerId, customerNumber, customerAddress, customerWeight, customerHeight, - customerGender, customerDob, checkupType, conclusion, reCheckupDate, cccdDdcn, heartBeat, bloodPressure + customerGender, customerDob, checkupType, conclusion, reCheckupDate, cccdDdcn, heartBeat, bloodPressure, + driveUrl ); resultList.add(result); diff --git a/src/main/resources/database/BSK.db b/src/main/resources/database/BSK.db index 66eff4a..4f08c2d 100644 Binary files a/src/main/resources/database/BSK.db and b/src/main/resources/database/BSK.db differ