ورود

View Full Version : مبتدی: استفاده از JList و JButton در برنامه



Sina.iRoid
یک شنبه 27 مهر 1393, 20:15 عصر
سلام دوستان. ممنون میشم اگر راهنماییم کنید.

ابتدا کدهای من و ببینید:

کلاس MultipleListFrame:

import java.awt.FlowLayout;


import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JList;
import javax.swing.JScrollPane;
import javax.swing.ListSelectionModel;




@SuppressWarnings("serial")
public class MultipleListFrame extends JFrame{

protected JList<String> colorList;
protected JList<String> copyList;
protected JButton copyBtn;

protected String[] colorsName = {"Blue", "Red", "Black", "Yellow", "White", "Green"};

//Constructor
public MultipleListFrame() {
super("Multiple List Selection");
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
setLayout(new FlowLayout());

colorList = new JList<>(colorsName);
colorList.setVisibleRowCount(3);
colorList.setSelectionMode(ListSelectionModel.MULT IPLE_INTERVAL_SELECTION);
add(new JScrollPane(colorList));

copyBtn = new JButton("Copy >>");
add(copyBtn);

copyList = new JList<>();
copyList.setVisibleRowCount(3);
copyList.setFixedCellWidth(100);
copyList.setFixedCellHeight(15);
copyList.setSelectionMode(ListSelectionModel.SINGL E_SELECTION);
add(new JScrollPane(copyList));

ButtonHandler ob = new ButtonHandler(this);
copyBtn.addActionListener(ob);

setSize(400, 400);
setVisible(true);
}
}


کلاس ButtonHandler:


import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;


public class ButtonHandler implements ActionListener{

private MultipleListFrame ob;

//Constructor
public ButtonHandler(MultipleListFrame ob) {
this.ob = ob;
}

@Override
public void actionPerformed(ActionEvent e) {
ob.copyList.setListData((String[]) ob.colorList.getSelectedValues());
}
}


و کلاس اصلی:


public class DriverClass {

public static void main(String[] args) {

new MultipleListFrame();
}
}


دوستان این برنامه کرش می کنه اما نمی دونم چرا. درضمن در کلاس ButtonHandler وقتی که از متد getSelectedValues() استفاده میکنم، یه خط سیاه روی این کتد میکشه و در ضمن پیغام میده که باید حتما به String کست کنیم. من دلیل کست کردن و اون خط سیاه و نمی دونم. به نظرم مشکل کرش برنامه هم از همینجاست.
ممنون میشم اگر راهنماییم کنید:لبخندساده:

محمد فدوی
یک شنبه 27 مهر 1393, 21:12 عصر
کدت رو اجرا نکردم ولی در یه نگاه دو تا ایراد توش هست:
۱. colorList و copyList توی کلاس فریمت بصورت protected تعریف شدن و از کلاس ButtonHandler قابل دسترسی نیستن. باید بصورت public تعریفشون کنی یا راه استاندارد تر اینه که متدهای getCopyList و getColorList رو اضافه کنی که copyList و colorList رو برگردونن.
۲. متد JList::getSelectedValues دیگه منسوخ شدست و به همین دلیل هم این خط رو میکشه. در چنین مواردی Javadoc رو بخون خودش یه متد جایگزین بت معرفی میکنه. الان به جای این متد باید از getSelectedValuesList استفاده کنی که یه List رو بت تحویل میده...

پیشنهادم اینه که لقمه رو دور سرت نچرخونی و کلاس ButtonHandler رو بی دلیل اضافه نکنی. میتونی کلاس فریمت رو تغییر بدی تا واسط ActionListener رو هم پیاده سازی کنه:


public class MultipleListFrame extends JFrame implements ActionListener {
...
@Override
public void actionPerformed(ActionEvent e) {
...
}
}


کدت اجرا کن اگه بازم ایرادی داشت بگو...

Sina.iRoid
یک شنبه 27 مهر 1393, 21:47 عصر
ممنون از راهنماییتون.
در مورد public, protected, private من اینطور راجع بش می دونم:

public که همه جا میشه ازش استفاده کرد.
protected و فقط میشه داخل همون پکیجی که هست استفاده کرد.
private هم فقط داخل همون کلاسی که تعریف شده.

من همه این کلاس ها رو داخل یک پکیج تعریف کردم. برای همین protected تعریف کردم.

و در مورد تعریف کلاس
ButtonHandler هم باید بگم که چون من می خوام سعی کنم که برنامه هایی و که می نویسم و، مفاهیم شی گرایی و کاملا رعایت کنم. احساس می کنم که به این کلاس نیاز هست. اما خودم مطمئن نیستم!؟
ممنون از شما.

محمد فدوی
دوشنبه 28 مهر 1393, 00:57 صبح
بله اگه توی یه Package باشن مشکلی پیش نمیاد.
در مورد ButtonHandler هم شما چون توی خود کلاس ButtonHandler به یه MultipleListFrame نیاز پیدا میکنی، این توی طراحیتون ایجاد دور میکنه (شما توی MultipleListFrame به یه ButtonHandler نیاز داری و بالعکس!) این اتفاق زیاد توی برنامه‌نویسی شیءگرا میفته. نمیتونم استناد کنم به جایی ولی نظر شخصیم اینه که این باعث کاهش ساخت‌یافتگی هردو کلاس میشه. در هر صورت برای Event Handling توی جاوا من چهارتا رویکرد تابحال دیدم:
۱. یه کلاس Handler جداگونه نوشته بشه (کاری که شما کردی)
۲. یه کلاس Handler در کنار یا داخل کلاس JFrame نوشته بشه:


public class MultipleListFrame extends JFrame {
private class ButtonHandler extends ActionListener {
...
}
...
}


۳. خود کلاس JFrame بیاد و Handling رو انجام بده (مثل چیزی که من پیشنهاد دادم)
۴. از کلاس‌های بی‌نام استفاده بشه (که توی Java8 بخشی از این روش با Lambdaها انجام میشه)


public class MultipleListFrame extends JFrame {
public MultipleListFrame() {
...
// Java 8:
copyBtn.addActionListener(e -> {
// Event Handling...
});

// Java 7:
copyBtn.addActionListener(new ActionListener() {
public @Override void actionPerformed(ActionEvent e) {
// Event Handling...
}
});
...
}
}


من خودم همیشه از ترکیب ۳ و ۴ استفاده میکنم و فکرم میکنم سلیقه‌ای باشه.