2010-12-10 31 views
41

g2 là phiên bản của lớp Graphics2D. Tôi muốn có thể vẽ văn bản nhiều dòng, nhưng điều đó đòi hỏi một ký tự dòng mới. Mã sau đây hiển thị trong một dòng.Sự cố với dòng mới trong Graphics2D.drawString

String newline = System.getProperty("line.separator"); 
g2.drawString("part1\r\n" + newline + "part2", x, y); 

Trả lời

69

Phương thức drawString không xử lý dòng mới.

Bạn sẽ phải chia chuỗi trên nhân vật mới-line bản thân và vẽ các đường từng người một với một dọc đúng offset:

void drawString(Graphics g, String text, int x, int y) { 
    for (String line : text.split("\n")) 
     g.drawString(line, x, y += g.getFontMetrics().getHeight()); 
} 

Đây là một ví dụ hoàn chỉnh để cung cấp cho bạn ý tưởng:

import java.awt.*; 

public class TestComponent extends JPanel { 

    private void drawString(Graphics g, String text, int x, int y) { 
     for (String line : text.split("\n")) 
      g.drawString(line, x, y += g.getFontMetrics().getHeight()); 
    } 

    public void paintComponent(Graphics g) { 
     super.paintComponent(g); 
     drawString(g, "hello\nworld", 20, 20); 
     g.setFont(g.getFont().deriveFont(20f)); 
     drawString(g, "part1\npart2", 120, 120); 
    } 

    public static void main(String s[]) { 
     JFrame f = new JFrame(); 
     f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 
     f.add(new TestComponent()); 
     f.setSize(220, 220); 
     f.setVisible(true); 
    } 
} 

mang đến cho các kết quả sau:

enter image description here

+6

+1 - câu trả lời đầy đủ –

+0

Vẽ tùy chỉnh được thực hiện bằng cách ghi đè phương thức paintComponent() và trước tiên bạn nên gọi super.paintComponent (g). – camickr

+0

Điểm tốt. Đã cập nhật. – aioobe

7

Tôi vừa tạo một phương thức để vẽ tự động chia tách văn bản dài bằng cách cho chiều rộng đường kẻ.

public static void drawStringMultiLine(Graphics2D g, String text, int lineWidth, int x, int y) { 
    FontMetrics m = g.getFontMetrics(); 
    if(m.stringWidth(text) < lineWidth) { 
     g.drawString(text, x, y); 
    } else { 
     String[] words = text.split(" "); 
     String currentLine = words[0]; 
     for(int i = 1; i < words.length; i++) { 
      if(m.stringWidth(currentLine+words[i]) < lineWidth) { 
       currentLine += " "+words[i]; 
      } else { 
       g.drawString(currentLine, x, y); 
       y += m.getHeight(); 
       currentLine = words[i]; 
      } 
     } 
     if(currentLine.trim().length() > 0) { 
      g.drawString(currentLine, x, y); 
     } 
    } 
} 
+0

Thans nó hoạt động tuyệt vời !! –

0

Dưới đây là một đoạn tôi đã sử dụng để vẽ văn bản trong một JPanel với sự mở rộng tab và nhiều dòng:

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

public class Scratch { 
    public static void main(String argv[]) { 
     JFrame frame = new JFrame("FrameDemo"); 

     frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 

     JPanel panel = new JPanel() { 
      @Override 
      public void paint(Graphics graphics) { 
       graphics.drawRect(100, 100, 1, 1); 
       String message = 
         "abc\tdef\n" + 
         "abcx\tdef\tghi\n" + 
         "xxxxxxxxdef\n" + 
         "xxxxxxxxxxxxxxxxghi\n"; 
       int x = 100; 
       int y = 100; 
       FontMetrics fontMetrics = graphics.getFontMetrics(); 
       Rectangle2D tabBounds = fontMetrics.getStringBounds(
         "xxxxxxxx", 
         graphics); 
       int tabWidth = (int)tabBounds.getWidth(); 
       String[] lines = message.split("\n"); 
       for (String line : lines) { 
        int xColumn = x; 
        String[] columns = line.split("\t"); 
        for (String column : columns) { 
         if (xColumn != x) { 
          // Align to tab stop. 
          xColumn += tabWidth - (xColumn-x) % tabWidth; 
         } 
         Rectangle2D columnBounds = fontMetrics.getStringBounds(
           column, 
           graphics); 
         graphics.drawString(
           column, 
           xColumn, 
           y + fontMetrics.getAscent()); 
         xColumn += columnBounds.getWidth(); 
        } 
        y += fontMetrics.getHeight(); 
       } 
      } 

      @Override 
      public Dimension getPreferredSize() { 
       return new Dimension(400, 200); 
      } 
     }; 
     frame.getContentPane().add(panel, BorderLayout.CENTER); 

     frame.pack(); 

     frame.setVisible(true); } 
} 

Nó thực sự có vẻ như Utilities.drawTabbedText() là đầy hứa hẹn, nhưng tôi không thể tìm ra những gì nó cần thiết làm đầu vào.