Опубликован: 04.12.2009 | Доступ: свободный | Студентов: 8416 / 657 | Оценка: 4.30 / 3.87 | Длительность: 27:27:00
Лекция 12:

Компонентное программирование

< Лекция 11 || Лекция 12: 1234

12.3. Пример создания компонента в NetBeans – панель с заголовком

Задание новых свойств и событий

увеличить изображение
Рис. 12.3. Задание новых свойств и событий

В качестве простейшего примера визуального компонента создаем панель, у которой имеется заголовок ( title ). Унаследуем наш компонент от класса javax.swing.JPanel – для этого в импорте запишем

import javax.swing.*;

а в качестве родительского класса вместо Object напишем JPanel.

С помощью рефакторинга заменим имя myBean на JTitledPanel, в узле полей Fields (а не в Bean Patterns!) поле sampleProperty на title, а константу PROP_SAMPLE_PROPERTY уберем, написав в явном виде имя свойства "title" в методе firePropertyChange.

После чего в области Bean Patterns правой клавишей мыши вызовем всплывающее меню, и там вызовем пункт Rename… ("Переименовать") для свойства sampleProperty – заменим имя на title. Это приведет к тому, что методы getSampleProperty и setSampleProperty будут переименованы в getTitle и setTitle.

Обязательно следует присвоить начальное значение полю title – в заготовке, полученной из Bean Pattern, это не делается. Мы установим

private String title="Заголовок";

Для показа заголовка необходимо импортировать классы java.awt.Graphics, java.awt.geom.Rectangle2D и переопределить в JTitledPanel.java метод paint:

public void paint(Graphics g){
    super.paint(g);
    FontMetrics fontMetrics=g.getFontMetrics();
    Rectangle2D rect = fontMetrics.getStringBounds(title, g);
    g.drawString(title,(int)Math.round((this.getWidth()-rect.getWidth())/2),
                 10);
    }

Для того, чтобы можно было пользоваться классами Graphics, FontMetrics и Rectangle2D, нам следует добавить импорт

import java.awt.*;
import java.awt.geom.Rectangle2D;

Отметим, что можно было бы не вводить переменные fontMetrics и rect, а сразу писать в методе drawString соответствующие функции в следующем виде:

g.drawString(title,
      (int)Math.round( ( this.getWidth() -
      g.getFontMetrics().getStringBounds(title,g).getWidth()
      )/2 ),
      10);

Но от этого текст программы стал бы гораздо менее читаемым. Даже несмотря на попытки отформатировать текст так, чтобы было хоть что-то понятно.

Еще одно необходимое изменение – добавление repaint() в операторе setTitle. Если этого не сделать, после изменения свойства компонент не перерисуется с вновь установленным заголовком.

В результате получим следующий код компонента:

/*
 * JTitledPanel.java
 *
 * Created on 30 Октябрь 2006 г., 23:16
 */

package java_gui_example;

import java.beans.*;
import java.io.Serializable;
import javax.swing.*; //добавлено вручную
import java.awt.*; //добавлено вручную
import java.awt.geom.Rectangle2D; //добавлено вручную

/**
 * @author В.Монахов
 */
public class JTitledPanel extends JPanel implements Serializable {

   private String title="Заголовок"; //добавлено вручную
   
   private PropertyChangeSupport propertySupport;
   
   public JTitledPanel() {
       super();
       propertySupport = new PropertyChangeSupport(this);
   }
   
   public String getTitle() {
       return title;
   }
   
   public void setTitle(String value) {
       String oldValue = title;
       title = value;
       propertySupport.firePropertyChange("title", oldValue, title);
       repaint(); //добавлено вручную
   }
   
   public void addPropertyChangeListener(PropertyChangeListener listener) {
       propertySupport.addPropertyChangeListener(listener);
   }
   
   public void removePropertyChangeListener(PropertyChangeListener listener){
       propertySupport.removePropertyChangeListener(listener);
   }
   
   public void paint(Graphics g){ //метод добавлен вручную
     super.paint(g);
     FontMetrics fontMetrics=g.getFontMetrics();
     Rectangle2D rect = fontMetrics.getStringBounds(title, g);
     g.drawString(title,(int)Math.round((this.getWidth() -
                                              rect.getWidth())/2), 10);
   }
}

Для того, чтобы добавить наш компонент в палитру, следует открыть файл JTitledPanel.java в окне редактора исходного кода, и в меню Tools выбрать пункт Add to Palette. После чего в появившемся диалоге выбрать палитру, на которую будет добавлен компонент.

Выбор палитры, на которую будет добавлен компонент

Рис. 12.4. Выбор палитры, на которую будет добавлен компонент

Желательно выбрать Beans (чтобы не путать наши компоненты со стандартными) и нажать OK. Теперь компонент можно использовать наравне с другими.

Использование созданного компонента

Рис. 12.5. Использование созданного компонента

Теперь мы можем менять текст заголовка как в редакторе свойств на этапе визуального проектирования, так и программно во время работы приложения. Мы также можем рисовать по нашей панели, и заголовок при этом будет виден, как и отрисовываемые примитивы. Например, мы можем вывести по нажатию на какую-нибудь кнопку строку "Тест":

Graphics g=jTitledPanel1.getGraphics();
FontMetrics fontMetrics=g.getFontMetrics();
Rectangle2D rect = fontMetrics.getStringBounds("Тест", g);
g.drawString("Тест",10,30 );

Если мы будем усовершенствовать код нашего компонента, нет необходимости каждый раз удалять его из палитры компонентов и заново устанавливать – достаточно после внесения изменений заново скомпилировать проект ( Build main project – F11 ).

< Лекция 11 || Лекция 12: 1234
Полетаев Дмитрий
Полетаев Дмитрий
Не очень понятно про оболочечные Данные,ячейки памяти могут наверно размер менять,какое это значение те же операции только ячейки больше,по скорости тоже самое
Максим Старостин
Максим Старостин

Код с перемещением фигур не стирает старую фигуру, а просто рисует новую в новом месте. Точку, круг.