Создание пользовательского JButton в Java

голоса
86

Есть ли способ , чтобы создать JButtonс вашей собственной графической кнопкой , а не только с изображением внутри кнопок?

Если нет, то есть еще один способ создать собственный JButtonв Java?

Задан 05/08/2008 в 13:15
источник пользователем
На других языках...                            


5 ответов

голоса
85

Когда я был первым обучения Java мы должны были сделать Yahtzee , и я подумал , что было бы здорово , чтобы создать пользовательские компоненты Swing , и контейнеры , а не просто рисовать все на одном JPanel. Преимущество проходящих Swingкомпонентов, конечно, иметь возможность добавлять поддержку горячих клавиш и других функции доступности , которые вы не можете сделать , просто имея paint()метод печать красивой картинки. Это не может быть сделано лучший способ , однако, но это может быть хорошей отправной точкой для вас.

Редактирование 8/6 - Если бы не было видно из изображений, каждый Жребий кнопка , которую вы можете нажать. Это переместит его к DiceContainerниже. Глядя на исходный код , который вы можете увидеть , что каждая кнопка Жребий обращается динамически, на основе его стоимости.

альтернативный текст
альтернативный текст
альтернативный текст

Вот основные шаги:

  1. Создать класс, расширяющий JComponent
  2. Вызов родительского конструктора super()в своих конструкторах
  3. Убедитесь, что вы класс реализует MouseListener
  4. Поместите это в конструкторе:

    enableInputMethods(true);   
    addMouseListener(this);
    
  5. Перекрыть эти методы:

    public Dimension getPreferredSize()  
    public Dimension getMinimumSize()  
    public Dimension getMaximumSize()
    
  6. Перекрыть этот метод:

    public void paintComponent(Graphics g)
    

Объем пространства , вы должны работать с при составлении вашей кнопки определяются getPreferredSize(), предполагая , что getMinimumSize()и getMaximumSize()возвращает то же значение. Я не экспериментировал слишком много с этим , но, в зависимости от компоновки, которая используется для графического интерфейса пользователя ваша кнопка может выглядеть совершенно иначе.

И , наконец, исходный код . В случае , если я пропустил что - нибудь.

Ответил 05/08/2008 в 14:03
источник пользователем

голоса
32

Да, это возможно. Одним из главных плюсов для использования свинг является легкость, с которой абстрактные элементы управления могут быть созданы и манипулирует.

Вот быстрый и грязный способ расширить существующий класс JButton нарисовать круг справа от текста.

package test;

import java.awt.Color;
import java.awt.Container;
import java.awt.Dimension;
import java.awt.FlowLayout;
import java.awt.Graphics;

import javax.swing.JButton;
import javax.swing.JFrame;

public class MyButton extends JButton {

    private static final long serialVersionUID = 1L;

    private Color circleColor = Color.BLACK;

    public MyButton(String label) {
        super(label);
    }

    @Override
    protected void paintComponent(Graphics g) {
        super.paintComponent(g);

        Dimension originalSize = super.getPreferredSize();
        int gap = (int) (originalSize.height * 0.2);
        int x = originalSize.width + gap;
        int y = gap;
        int diameter = originalSize.height - (gap * 2);

        g.setColor(circleColor);
        g.fillOval(x, y, diameter, diameter);
    }

    @Override
    public Dimension getPreferredSize() {
        Dimension size = super.getPreferredSize();
        size.width += size.height;
        return size;
    }

    /*Test the button*/
    public static void main(String[] args) {
        MyButton button = new MyButton("Hello, World!");

        JFrame frame = new JFrame();
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.setSize(400, 400);

        Container contentPane = frame.getContentPane();
        contentPane.setLayout(new FlowLayout());
        contentPane.add(button);

        frame.setVisible(true);
    }

}

Обратите внимание , что с помощью переопределения paintComponent , что содержимое кнопки можно изменить, но что граница нарисованная paintBorder методом. GetPreferredSize метод также необходимо управлять, чтобы динамически поддерживать изменения в содержание. Уход должен быть принят при измерении метрик шрифта и размеров изображения.

Для создания элемента управления , который вы можете положиться, приведенный выше код не правильный подход. Размеры и цвет динамичны в свинге и зависят от внешнего вида используются. Даже по умолчанию Металл вид изменился по версии JRE. Было бы лучше реализовать AbstractButton и соответствовать рекомендациям , изложенным в Swing API. Хорошая отправная точка , чтобы посмотреть на javax.swing.LookAndFeel и javax.swing.UIManager классов.

http://docs.oracle.com/javase/8/docs/api/javax/swing/LookAndFeel.html

http://docs.oracle.com/javase/8/docs/api/javax/swing/UIManager.html

Понимание анатомии LookAndFeel полезно для написания элементов управления: Создание пользовательского внешнего вида и

Ответил 05/08/2008 в 13:53
источник пользователем

голоса
12

Вы всегда можете попробовать Synth выглядеть и чувствовать. Вы предоставляете файл XML, который действует как своего рода таблицу стилей, наряду с любыми изображениями, которые вы хотите использовать. Код может выглядеть следующим образом:

try {
    SynthLookAndFeel synth = new SynthLookAndFeel();
    Class aClass = MainFrame.class;
    InputStream stream = aClass.getResourceAsStream("\\default.xml");

    if (stream == null) {
        System.err.println("Missing configuration file");
        System.exit(-1);                
    }

    synth.load(stream, aClass);

    UIManager.setLookAndFeel(synth);
} catch (ParseException pe) {
    System.err.println("Bad configuration file");
    pe.printStackTrace();
    System.exit(-2);
} catch (UnsupportedLookAndFeelException ulfe) {
    System.err.println("Old JRE in use. Get a new one");
    System.exit(-3);
}

Оттуда, пойти дальше и добавить JButton, как обычно. Единственное изменение состоит в том, что вы используете метод SetName (строка), чтобы определить, что кнопка должна отобразить в файле XML.

Файл XML может выглядеть следующим образом:

<synth>
    <style id="button">
        <font name="DIALOG" size="12" style="BOLD"/>
        <state value="MOUSE_OVER">
            <imagePainter method="buttonBackground" path="dirt.png" sourceInsets="2 2 2 2"/>
            <insets top="2" botton="2" right="2" left="2"/>
        </state>
        <state value="ENABLED">
            <imagePainter method="buttonBackground" path="dirt.png" sourceInsets="2 2 2 2"/>
            <insets top="2" botton="2" right="2" left="2"/>
        </state>
    </style>
    <bind style="button" type="name" key="dirt"/>
</synth>

Связать элемент есть указывает, что для сопоставления (в данном примере, он будет применять этот стиль к любым кнопкам, чье имущество имя было установлено в «грязь»).

И несколько полезных ссылок:

http://javadesktop.org/articles/synth/

http://docs.oracle.com/javase/tutorial/uiswing/lookandfeel/synth.html

Ответил 05/08/2008 в 13:47
источник пользователем

голоса
8

Я, наверное, миллион миль в заблуждении прямой (но я только молодые: P). но не могли бы вы добавить рисунок на панель, а затем в MouseListener для графического объекта, так что, когда пользователь на графических ваши действия предварительно формуют.

Ответил 20/08/2008 в 16:48
источник пользователем

голоса
6

Я не сделал развития SWING, поскольку мои ранние классы CS, но если он не был построен в вас может просто наследовать javax.swing.AbstractButton и создать свой собственный. Должно быть довольно просто подключить что-то вместе с их существующей структурой.

Ответил 05/08/2008 в 13:30
источник пользователем

Cookies help us deliver our services. By using our services, you agree to our use of cookies. Learn more