age calculator swing by java
طريقة إنشاء برنامج لحساب الأعمار
في هذا الدرس ستتعلم طريقة إنشاء برنامج لحساب الأعمار ( Age Calculator ) باستخدام إطار الـ Swing.
مميزات البرنامج
- يمكن إستخدام هذا البرنامج لحساب عمر الشخص الحي أو المدة التي عاشها الشخص المتوفي.
- لحساب عمر الشخص الحي, ضع فقط تاريخ ميلاده.
- لحساب المدة التي عاشها الشخص المتوفي, ضع تاريخ ميلاده و تاريخ وفاته.
import java.awt.Color;import java.awt.Font;import java.awt.event.ActionEvent;import java.awt.event.ActionListener;import java.awt.event.ItemEvent;import java.awt.event.ItemListener;import java.time.LocalDate;import java.time.Period;import javax.swing.JButton;import javax.swing.JCheckBox;import javax.swing.JComboBox;import javax.swing.JFrame;import javax.swing.JLabel;import javax.swing.SwingUtilities;import javax.swing.UIManager;import javax.swing.UIManager.LookAndFeelInfo;// و بالتالي أصبح إنشاء كائن منه يمثل إنشاء نافذة JFrame يرث من الكلاس Main هنا جعلنا الكلاسpublic class Main extends JFrame {// هنا قمنا بتعريف الأشياء التي سيتم وضعها في النافذةJLabel birthDate, deathDate, result;JCheckBox deathDateState;JComboBox dayOfBirth, monthOfBirth, yearOfBirth, dayOfDeath, monthOfDeath, yearOfDeath;JButton calculateAge;// سنستخدم هذه المتغيرات لتخزين التواريخ التي إختارها المستخدم من النافذة بشكل مؤقتint d1, d2, m1, m2, y1, y2;// لتخزين تاريخ وفاته endDate لتخزين تاريخ ميلاد الشخص, و الكائن startDate سنستخدم الكائنLocalDate startDate, endDate;// سنستخدم هذه المتغيرات لعرض الفارق النهائي بين تاريخ الميلاد و التاريخ الحالي أو تاريخ الوفاةlong daysCounter, monthsCounter, yearsCounter;// لتحديد نوع خط و حجم العناوين التي سنضيفها في النافذة font سنستخدم الكائنFont font = new Font("Arial", Font.BOLD, 18);// فقط createAndShowGUI() سيقوم الكونستركتور بإستدعاء الدالة ColorPicker عند إنشاء كائن من الكلاسpublic Main() {createAndShowGUI();}// هنا نضع كود إنشاء النافذة و محتوياتهاprivate void createAndShowGUI() {// لجعل النافذة محتوى االنافذة يظهر بشكل أجمل Nimbus إلى الـ UIManager هنا قمنا بتغيير الـtry {for (LookAndFeelInfo info : UIManager.getInstalledLookAndFeels()) {if ("Nimbus".equals(info.getName())) {UIManager.setLookAndFeel(info.getClassName());break;}}}catch (Exception e) { }// هنا وضعنا أسماء الأشهر التي تظهر في قائمة الأشهرString[] months = {"Jan", "Feb", "Mar", "Apr", "May", "Jun","Jul", "Aug", "Sep", "Oct", "Nov", "Dec"};// هنا وضعنا أرقام الأشهر الأولية التي سنضعها في قائمة الأرقامInteger[] days = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10,11, 12, 13, 14, 15, 16, 17, 18, 19, 20,21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31};// currentYear هنا قمنا بتخزين رقم السنة الحالية في المتغيرint currentYear = LocalDate.now().getYear();// هنا قمنا بإنشاء مصفوفة, عدد عناصرها يساوي عدد السنة الحاليةInteger[] years = new Integer[currentYear];// هنا قمنا بتخزين أرقام السنين من 1 إلى عدد السنين الحاليةfor (int i = 0; i < years.length; i++)years[i] = i + 1;// هنا قمنا بإنشاء جميع الأشياء التي سنضيفها فيا النافذةbirthDate = new JLabel("Birth Date");deathDate = new JLabel("Death Date");deathDateState = new JCheckBox();dayOfBirth = new JComboBox(days);monthOfBirth = new JComboBox(months);yearOfBirth = new JComboBox(years);dayOfDeath = new JComboBox(days);monthOfDeath = new JComboBox(months);yearOfDeath = new JComboBox(years);calculateAge = new JButton("Calculate Age");result = new JLabel("", JLabel.CENTER);// هنا قمنا بتحديد حجم و مكان كل شيء سيتم إضافته في النافذةbirthDate.setBounds(175, 40, 200, 30);dayOfBirth.setBounds(120, 80, 50, 30);monthOfBirth.setBounds(173, 80, 70, 30);yearOfBirth.setBounds(246, 80, 70, 30);deathDateState.setBounds(158, 140, 20, 30);deathDate.setBounds(183, 140, 200, 30);dayOfDeath.setBounds(120, 180, 50, 30);monthOfDeath.setBounds(173, 180, 70, 30);yearOfDeath.setBounds(246, 180, 70, 30);calculateAge.setBounds(118, 250, 200, 60);result.setBounds(0, 345, 440, 30);// هنا قمنا بتحديد حجم و نوع خط العناوين الموجودة في النافذةbirthDate.setFont(font);deathDate.setFont(font);calculateAge.setFont(font);result.setFont(new Font("Arial", Font.BOLD, 17));// هنا قمنا بتحديد السنة الإفتراضية المختارة من قوائم السنينyearOfBirth.setSelectedItem(2000);yearOfDeath.setSelectedItem(2000);// هنا جعلنا خيار تحديد الوفاة و القوائم الموجودة ضمنه غير مفعلة إفتراضياًdeathDate.setEnabled(false);dayOfDeath.setEnabled(false);monthOfDeath.setEnabled(false);yearOfDeath.setEnabled(false);// هنا قمنا بإضافة جميع الأشياء التي قمنا بإنشائها في النافذةadd(birthDate);add(deathDate);add(dayOfBirth);add(monthOfBirth);add(yearOfBirth);add(deathDateState);add(dayOfDeath);add(monthOfDeath);add(yearOfDeath);add(calculateAge);add(result);// Check Box هنا قمنا بتحديد ما يحدث عندما يقوم المستخدم بوضع علامة صح أو إزالتها من الـdeathDateState.addItemListener(new ItemListener() {@Overridepublic void itemStateChanged(ItemEvent e) {// عند وضع علامة الصح سيتم تفعيل خيار تحديد تاريخ الوفاةif (deathDateState.isSelected()) {deathDate.setEnabled(true);dayOfDeath.setEnabled(true);monthOfDeath.setEnabled(true);yearOfDeath.setEnabled(true);}// عند إزالة علامة الصح سيتم تفعيل خيار تحديد تاريخ الوفاةelse {deathDate.setEnabled(false);dayOfDeath.setEnabled(false);monthOfDeath.setEnabled(false);yearOfDeath.setEnabled(false);}}});// هنا قمنا بتحديد ما يحدث عندما يقوم المستخدم بتغيير الشهر من قائمة الأشهر في تاريخ الميلادmonthOfBirth.addItemListener(new ItemListener() {@Overridepublic void itemStateChanged(ItemEvent e) {// سيتم تخزين إسم الشهر المختار من قائمة الأشهر و على أساسه سيتم توليد عدد الأيام الموجودة في الشهرString month = monthOfBirth.getSelectedItem().toString();if( month.equals("Jan") || month.equals("Mar") || month.equals("May")|| month.equals("Jul") || month.equals("Aug") || month.equals("Oct") || month.equals("Dec") )for( int i = 1; i <= 31; i++ )dayOfBirth.addItem(i);else if( month.equals("Feb") )for( int i = 1; i <= 28; i++ )dayOfBirth.addItem(i);elsefor( int i = 1; i <= 30; i++ )dayOfBirth.addItem(i);}});// هنا قمنا بتحديد ما يحدث عندما يقوم المستخدم بتغيير الشهر من قائمة الأشهر في تاريخ الميلادmonthOfDeath.addItemListener(new ItemListener() {@Overridepublic void itemStateChanged(ItemEvent e) {// سيتم تخزين إسم الشهر المختار من قائمة الأشهر و على أساسه سيتم توليد عدد الأيام الموجودة في الشهرString month = monthOfDeath.getSelectedItem().toString();if( month.equals("Jan") || month.equals("Mar") || month.equals("May")|| month.equals("Jul") || month.equals("Aug") || month.equals("Oct") || month.equals("Dec") )for( int i = 1; i <= 31; i++ )dayOfDeath.addItem(i);else if( month.equals("Feb") )for( int i = 1; i <= 28; i++ )dayOfDeath.addItem(i);elsefor( int i = 1; i <= 30; i++ )dayOfDeath.addItem(i);}});// هنا قمنا بتحديد ما يحدث عند النقر على زر إظهار العمرcalculateAge.addActionListener(new ActionListener() {@Overridepublic void actionPerformed(ActionEvent e) {// سنستخدم هذا المتغير لتخزين نص النتيجة التي ستظهرString text = "";// هنا قمنا بتخزين تاريخ الميلاد الذي إختاره المستخدم في المتغيرات التاليةy1 = yearOfBirth.getSelectedIndex() + 1;m1 = monthOfBirth.getSelectedIndex() + 1;d1 = dayOfBirth.getSelectedIndex() + 1;// إذا كان خيار تحديد الميلاد مفعل, سيتم تخزين التاريخ المحدد في المتغيرات التاليةif (deathDateState.isSelected()) {y2 = yearOfDeath.getSelectedIndex() + 1;m2 = monthOfDeath.getSelectedIndex() + 1;d2 = dayOfDeath.getSelectedIndex() + 1;}// إذا كان خيار تحديد الميلاد غير مفعل, سيتم تخزين التاريخ الحالي في المتغيرات التاليةelse {y2 = LocalDate.now().getYear();m2 = LocalDate.now().getMonthValue();d2 = LocalDate.now().getDayOfMonth();}// endDate و التاريخ الثاني في الكائن startDate هنا قمنا بوضع تاريخ الميلاد الذي حدده المستخدم في الكائنstartDate = LocalDate.of(y1, m1, d1);endDate = LocalDate.of(y2, m2, d2);// هنا قمنا بتخزين الفارق بين التواريخ في المتغيرات التاليةyearsCounter = Period.between(startDate, endDate).getYears();monthsCounter = Period.between(startDate, endDate).getMonths();daysCounter = Period.between(startDate, endDate).getDays();// هنا قلنا إذا كان التاريخين متواسيين سيتم إظهار التنبيه التاليif (yearsCounter == 0 && monthsCounter == 0 && daysCounter == 0) {result.setForeground(Color.red);result.setText("Cannot compare same date!");}// هنا قلنا أنه إذا كانت التواريخ المحددة هي منطقياً صحيحة سيتم إظهار العمرelse if (!Period.between(startDate, endDate).isNegative()){if (yearsCounter == 1)text += yearsCounter + " year ";else if (yearsCounter > 1)text += yearsCounter + " years ";if (monthsCounter == 1){if (yearsCounter > 0 && daysCounter > 0)text += ", " + monthsCounter + " month ";else if (yearsCounter > 0 && daysCounter == 0)text += "and " + monthsCounter + " month ";elsetext += monthsCounter + " month ";}if (monthsCounter > 1){if (yearsCounter > 0 && daysCounter > 0)text += ", " + monthsCounter + " months ";else if (yearsCounter > 0 && daysCounter == 0)text += "and " + monthsCounter + " months ";elsetext += monthsCounter + " months ";}if (daysCounter == 1){if (yearsCounter == 0 && monthsCounter == 0)text += daysCounter + " day";elsetext += "and " + daysCounter + " day";}if (daysCounter > 1){if (yearsCounter == 0 && monthsCounter == 0)text += daysCounter + " days";elsetext += "and " + daysCounter + " days";}result.setForeground(Color.black);result.setText(text);}// هنا قلنا أنه إذا كانت التواريخ المحددة هي منطقياً غير مقبولة سيتم إظهار التنبيه التاليelse{result.setForeground(Color.red);result.setText("Logic order of Dates is wrong!");}}});// هنا قمنا بتحديد بعض خصائص النافذة و جعلناها مرئيةsetDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);setSize(436, 446);setTitle("Age Calculator");setLocationRelativeTo(null);setResizable(false);setLayout(null);setVisible(true);}public static void main(String[] args) {SwingUtilities.invokeLater(new Runnable() {@Overridepublic void run() {// التي ستنشئ النافذة createAndShowGUI() و بالتالي سيتم إستدعاء الدالة Main هنا قمنا بإنشاء كائن من الكلاسnew Main();}});}}