2017-02-04 14 views
-1

Я пытаюсь создать пользовательский JLabel с эффектом набросков это мой код:Текст JLabel вне границ

package test; 

import java.awt.BasicStroke; 
import java.awt.BorderLayout; 
import java.awt.Color; 
import java.awt.Font; 
import java.awt.Graphics; 
import java.awt.Graphics2D; 
import java.awt.RenderingHints; 
import java.awt.Shape; 
import java.awt.Stroke; 
import java.awt.font.GlyphVector; 
import java.awt.geom.Rectangle2D; 

import javax.swing.JFrame; 
import javax.swing.JLabel; 
import javax.swing.JPanel; 
import javax.swing.SwingUtilities; 

public class OutlineLabel extends JLabel { 

    private Color outlineColor = Color.BLACK; 
    private Color fillColor = Color.WHITE; 


    public OutlineLabel() { 
     super(); 

    } 
    public void setThin(int thin){ 
     //this.thin=thin; 
    } 
    public OutlineLabel(String text,Color inline,Color outline) { 
     super(text); 
     outlineColor=outline; 
     fillColor=inline; 
    } 

    @Override 
    public void paintComponent(Graphics g) { 
     String text = getText(); 

     BasicStroke outlineStroke = new BasicStroke(1.5f); 

     if (g instanceof Graphics2D) { 
      Graphics2D g2 = (Graphics2D) g; 

      // remember original settings 
      Color originalColor = g2.getColor(); 
      Stroke originalStroke = g2.getStroke(); 
      RenderingHints originalHints = g2.getRenderingHints(); 


      // create a glyph vector from your text 
      GlyphVector glyphVector=g.getFont().layoutGlyphVector(g2.getFontRenderContext(),text.toCharArray(),0,text.length(),Font.LAYOUT_LEFT_TO_RIGHT); 

      // get the shape object 
      Shape textShape = glyphVector.getOutline(); 

      // activate effects 
      g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, 
        RenderingHints.VALUE_ANTIALIAS_ON); 
      g2.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, 
        RenderingHints.VALUE_TEXT_ANTIALIAS_ON); 
      g2.setRenderingHint(RenderingHints.KEY_RENDERING, 
        RenderingHints.VALUE_RENDER_QUALITY); 

      //g.translate(getX(), getY()+160); 
      g2.setColor(outlineColor); 
      g2.setStroke(outlineStroke); 
      g2.draw(textShape); // draw outline 

      g2.setColor(fillColor); 
      g2.fill(textShape); // fill the shape 

      // reset to original settings after painting 
      g2.setColor(originalColor); 
      g2.setStroke(originalStroke); 
      g2.setRenderingHints(originalHints); 
     } 
    } 

    public static void main(String[] args) { 
     JFrame w = new JFrame(); 
     w.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 
     Font myFont = new Font("Arial", Font.BOLD,146); 
     OutlineLabel label = new OutlineLabel("TEST",Color.red,Color.yellow); 
     label.setFont(myFont); 
     JPanel p=new JPanel(); 
     p.add(label); 
     w.setContentPane(p); 
     w.pack(); 
     w.setVisible(true); 
    } 
} 

Проблема заключается в том, что текст обращается за пределы компонентов .. . Я хотел бы понять, почему и как это исправить, вы можете убедиться, что удалить комментарий от:

g.translate(getX(), getY()+160); 

текст хорошо нарисованный, но это не приемлемо, поскольку метка должна быть использована в более сложная компоновка и несколько раз, я не могу переводить каждый раз, когда координация на основе labe l, мне нужно более общее решение.

Может кто-нибудь мне помочь?

+1

Override 'getPreferredSize().' – trashgod

+0

Переопределение getPreferredSize не имеет никакого значения ... – navy1978

+0

Я не вижу вашей реализации. Почему бы не добавить «Границу» в прилагаемый «Контейнер»? – trashgod

ответ

0

Хорошо, я нашел решение для этого. Если кто-то есть та же проблема: я не знаю, почему, но называя:

Shape textShape = glyphVector.getOutline(); 

TextShape автоматически переводится из высоты самой формы. Так что это выходит за пределы. Если вы хотите вернуть его в центр компонента (Vertical Alignment), вам понадобится AffineTransform. В примере, я разместил, прежде чем достаточно, чтобы заменить эту строку:

g.translate(getX(), getY()+160); 

с ними:

int heightComponent=getHeight(); 
int heightShape=(int)textShape.getBounds().getHeight(); 
final AffineTransform transform = AffineTransform.getTranslateInstance(
        0,heightShape+((int)heightComponent/2-heightShape/2)); 
textShape=transform.createTransformedShape(textShape); 

нотабене Комментарии к моему первому сообщению совершенно неправильны. Вы можете расширять Label, никаких проблем вообще ... и вам не нужно переопределять getPreferredSize, достаточно установить предпочтительный размер извне класса.