Элегантный способ реализации в Java Swing?

1

У меня часто возникает проблема, что метод или свойство Swing требует, чтобы объект был реализован. Например, чтобы нарисовать JPanel, мне может понадобиться знать, насколько высок определенный шрифт, но эта информация недоступна до тех пор, пока панель не будет реализована, поэтому до этого я получу нулевой указатель. Хуже того, не всегда ясно (по крайней мере для меня), какие методы требуют реализации объекта, а какие нет.

Очевидно, я могу сделать что-то глупое:

  1. рисовать фиктивный текст, чтобы добиться реализации
  2. получить метрики шрифта
  3. стирать фиктивный текст
  4. рассчитать и нарисовать реальный текст

Кажется невероятным, что нужно сделать это. Есть ли более элегантный способ принудительного осуществления, чтобы я мог получить надежный доступ к метрикам шрифтов?

Типичный пример кода:

void draw( Point2D center ){

    String sLabel = owner.getLabel();
    NodeData.DATA_TYPE eType = owner.data_type;

    int iSymbolWidth = 10;

    // build text
    if( sLabel == null ) sLabel = "";
    Font font = new Font( "TimesRoman", Font.PLAIN, 12 );
    text_node.setTextPaint( Color.DARK_GRAY );
    text_node.setText( sLabel );
    text_node.setFont( font );
    Panel_Main panel = owner.application.getDisplayPanel();
    java.awt.FontMetrics fm = panel.canvas.getGraphics().getFontMetrics(); // <--- ERROR HERE
    int iText_AdvanceWidth = ( int ) ( fm.stringWidth( sLabel ) * 1.2 ) + LABEL_MARGIN * 2;
    int iText_Height = fm.getHeight();
            .... etc

Часть проблемы заключается в том, что объект, на котором я рисую, принадлежит Piccolo, библиотеке рисования графа, поэтому библиотеке принадлежит paintComponent, а не мне. При роспинге через исходный код Piccolo мне кажется, что мне нужно переопределить один из своих внутренних методов: paint (PPaintContext paintContext), который в основном должен быть эквивалентен переопределению paintComponent.

  • 0
    Спасибо! Вот один совет ... Ваш шрифт определен как 12 точек (см. Третий аргумент в конструкторе Font). Есть 72 точки на дюйм.
  • 2
    Выборочная окраска должна быть сделана в методе paintComponent() . Этот метод будет когда-либо вызываться только для реализованных компонентов.
Показать ещё 2 комментария
Теги:
swing
rendering
font-size

1 ответ

3
Лучший ответ

Как обсуждалось здесь, каждый компонент Swing имеет делегат UI, который вычисляет правильный предпочтительный размер для компонента, учитывая выбранный пользователем Look & Feel. В результате самым элегантным решением является позволить менеджеру компоновки использовать предпочтительный размер компонентов. Невыполнение этого часто приводит к его патологическому поведению. Как показано здесь и здесь, вы можете validate() контейнер-контейнер, чтобы получить желаемую геометрию перед setVisible(), но это означает, что может быть оправдан другой подход. В качестве конкретного примера этот пример BoxLayout лучше сделать с помощью GroupLayout, проиллюстрированный здесь и здесь.

Как правило, вам нужно только изучить FontMetrics, чтобы рассчитать предпочтительный размер ваших собственных компонентов, как показано здесь.

  • 0
    Как должно быть очевидно из моего примера кода, я делаю произвольную отрисовку, поэтому я предполагаю, что это приводит к необходимости переопределить paintComponent.
  • 0
    В этом контексте вы можете использовать TextLayout , как здесь, так и здесь .

Ещё вопросы

Сообщество Overcoder
Наверх
Меню