Uploaded image for project: 'JDK'
  1. JDK
  2. JDK-4301195

Text with font Arial 11pt is sometimes put too narrow

    Details

    • Subcomponent:
      2d
    • CPU:
      x86
    • OS:
      solaris_2.5

      Description

      Text with font Arial 11pt is sometimes put too narrow, in the worst case the let
      ters are printet one upon the other. In some other cases the distance between tw
      o letters is too big. This problem occurs particularly together with printing. (
      BugID 4271596, 4280944, 4253334).

      Here's an example src:


      import java.awt.*;
      import java.awt.event.*;
      import java.awt.font.*;
      import java.io.*;
      import java.util.*;
      import java.sql.*;

      import java.awt.print.*;
      import javax.swing.plaf.basic.*;

      import javax.swing.*;
      import javax.swing.text.*;
      import javax.swing.event.*;
      import javax.swing.border.*;
      import javax.swing.text.rtf.*;
      import javax.swing.undo.*;

      public class TextExample3 extends JFrame implements Printable
      {

        protected String fontFamily = "Arial";
        protected int fontSize = 11;

        protected JTextPane textPane;
        protected StyleContext styleContext;
        protected DefaultStyledDocument doc;
        protected StyledEditorKit kit;
        protected JFileChooser fileChooser;
        protected JToolBar toolBar;

        protected JComboBox cbFonts;
        protected JComboBox cbSizes;
        protected JToggleButton boldButton;
        protected JToggleButton italicButton;

        protected String fontName = "";

        protected String[] fontNames;
        protected String[] fontSizes;

        protected boolean update;

        protected int startPos = -1;
        protected int finishPos = -1;

        public TextExample3() {
          super("Text Example");
          setSize(600, 400);
          
          textPane = new JTextPane();
          kit = new StyledEditorKit();
          textPane.setEditorKit(kit);
          styleContext = new StyleContext();
          doc = new DefaultStyledDocument(styleContext);
          textPane.setDocument(doc);

          JScrollPane ps = new JScrollPane(textPane);
          getContentPane().add(ps, BorderLayout.CENTER);

          JMenuBar menuBar = new JMenuBar();
          
          // ************** file menu ***************************
          JMenu mFile = new JMenu("File");
          
          // menu item new
          Action actionNew = new AbstractAction("New") {
            public void actionPerformed(ActionEvent e) {
              doc = new DefaultStyledDocument(styleContext);
              textPane.setDocument(doc);
              showAttributes(0);
            }
          };
          JMenuItem item = mFile.add(actionNew);
          
          // add menu item print
          Action actionPrint = new AbstractAction("Print") {
            public void actionPerformed(ActionEvent e) {
              Thread runner = new Thread() {
                public void run() {
                  printData();
                }
              };
              runner.start();
            }
          };
          item = mFile.add(actionPrint);

          mFile.addSeparator();

          // add menu item exit
          Action actionExit = new AbstractAction("Exit") {
            public void actionPerformed(ActionEvent e) {
              System.exit(0);
            }
          };

          item = mFile.add(actionExit);

          menuBar.add(mFile);
          setJMenuBar(menuBar);

          // ************** tool bar for font adjustment ***************************
          toolBar = new JToolBar();
          
          GraphicsEnvironment ge = GraphicsEnvironment.
            getLocalGraphicsEnvironment();
          fontNames = ge.getAvailableFontFamilyNames();

          //toolBar.addSeparator();
          cbFonts = new JComboBox(fontNames);
          cbFonts.setMaximumSize(cbFonts.getPreferredSize());
          cbFonts.setEditable(true);

          ActionListener lst = new ActionListener() {
            public void actionPerformed(ActionEvent e) {
              fontName = cbFonts.getSelectedItem().toString();
              MutableAttributeSet attr = new SimpleAttributeSet();
              StyleConstants.setFontFamily(attr, fontName);
              setAttributeSet(attr);
              textPane.grabFocus();
            }
          };
          cbFonts.addActionListener(lst);
          toolBar.add(cbFonts);

          toolBar.addSeparator();
          
          fontSizes = new String[] {"8", "9", "10", "11", "12", "14",
            "16", "18", "20", "22", "24", "26", "28", "36", "48", "72"};
          cbSizes = new JComboBox(fontSizes);
          cbSizes.setMaximumSize(cbSizes.getPreferredSize());
          cbSizes.setEditable(true);

          lst = new ActionListener() {
            public void actionPerformed(ActionEvent e) {
              int newFontSize = 0;
              try {
                newFontSize = Integer.parseInt(cbSizes.
                  getSelectedItem().toString());
              }
              catch (NumberFormatException ex) { return; }

              fontSize = newFontSize;
              MutableAttributeSet attr = new SimpleAttributeSet();
              StyleConstants.setFontSize(attr, fontSize);
              setAttributeSet(attr);
              textPane.grabFocus();
            }
          };
          cbSizes.addActionListener(lst);
          toolBar.add(cbSizes);

          toolBar.addSeparator();

          boldButton = new JToggleButton("bold");
          lst = new ActionListener() {
            public void actionPerformed(ActionEvent e) {
              MutableAttributeSet attr = new SimpleAttributeSet();
              StyleConstants.setBold(attr, boldButton.isSelected());
              setAttributeSet(attr);
              textPane.grabFocus();
            }
          };
          boldButton.addActionListener(lst);
          toolBar.add(boldButton);

          toolBar.addSeparator();

          italicButton = new JToggleButton("italic");
          lst = new ActionListener() {
            public void actionPerformed(ActionEvent e) {
              MutableAttributeSet attr = new SimpleAttributeSet();
              StyleConstants.setBold(attr, italicButton.isSelected());
              setAttributeSet(attr);
              textPane.grabFocus();
            }
          };
          italicButton.addActionListener(lst);
          toolBar.add(italicButton);
          getContentPane().add(toolBar, BorderLayout.NORTH);
              
          WindowListener wndCloser = new WindowAdapter() {
            public void windowClosing(WindowEvent e) {
              System.exit(0);
            }
          };
          addWindowListener(wndCloser);

          CaretListener caretLst = new CaretListener() {
            public void caretUpdate(CaretEvent e) {
              showAttributes(e.getDot());
            }
          };
          textPane.addCaretListener(caretLst);

          FocusListener focusLst = new FocusListener() {
            public void focusGained(FocusEvent e) {
              if (startPos>=0 && finishPos>=0)
                if (textPane.getCaretPosition()==startPos) {
                  textPane.setCaretPosition(finishPos);
                  textPane.moveCaretPosition(startPos);
                }
                else
                  textPane.select(startPos, finishPos);
            }

            public void focusLost(FocusEvent e) {
              startPos = textPane.getSelectionStart();
              finishPos = textPane.getSelectionEnd();
            }
          };
          textPane.addFocusListener(focusLst);

          showAttributes(0);
          setVisible(true);
        }

        private void setTextStyle() {

            Style style = doc.getLogicalStyle(0);
            StyleConstants.setFontFamily(style,fontFamily);
            StyleConstants.setFontSize(style,fontSize);
           
            doc.addStyle(style.getName(),style);
          
        }
        
        protected void setAttributeSet(AttributeSet attr) {
          setAttributeSet(attr, false);
        }

        protected void setAttributeSet(AttributeSet attr,
         boolean setParagraphAttributes)
        {
          if (update)
            return;
          int xStart = textPane.getSelectionStart();
          int xFinish = textPane.getSelectionEnd();
          if (!textPane.hasFocus()) {
            xStart = startPos;
            xFinish = finishPos;
          }
          if (setParagraphAttributes)
            doc.setParagraphAttributes(xStart,
            xFinish - xStart, attr, false);
          else if (xStart != xFinish)
            doc.setCharacterAttributes(xStart,
              xFinish - xStart, attr, false);
          else {
            MutableAttributeSet inputAttributes =
              kit.getInputAttributes();
            inputAttributes.addAttributes(attr);
          }
        }

        protected void showAttributes(int p) {
          update = true;
          AttributeSet a = doc.getCharacterElement(p).
            getAttributes();
          String name = StyleConstants.getFontFamily(a);
          if (!fontName.equals(name)) {
            fontName = name;
            cbFonts.setSelectedItem(name);
          }
          int size = StyleConstants.getFontSize(a);
          if (fontSize != size) {
            fontSize = size;
            cbSizes.setSelectedItem(Integer.toString(fontSize));
          }
          boolean bold = StyleConstants.isBold(a);
          if (bold != boldButton.isSelected())
            boldButton.setSelected(bold);
          boolean italic = StyleConstants.isItalic(a);
          if (italic != italicButton.isSelected())
            italicButton.setSelected(italic);
         update = false;
        }
        
            
        public void printData() {
          getJMenuBar().repaint();
          try {
            PrinterJob prnJob = PrinterJob.getPrinterJob();
            prnJob.setPrintable(this);
            if (!prnJob.printDialog())
              return;
            setCursor( Cursor.getPredefinedCursor(
              Cursor.WAIT_CURSOR));
            prnJob.print();
            setCursor( Cursor.getPredefinedCursor(
              Cursor.DEFAULT_CURSOR));
            JOptionPane.showMessageDialog(this,
              "Printing completed successfully", "Info",
              JOptionPane.INFORMATION_MESSAGE);
          }
          catch (PrinterException e) {
            e.printStackTrace();
            System.err.println("Print error: "+e.toString());
          }
        }

        public int print(Graphics pg, PageFormat pageFormat,
         int pageIndex) throws PrinterException {
          
          if(pageIndex != 0) return NO_SUCH_PAGE;

            // change RenderingHints to get better print result
          Graphics2D g2 = (Graphics2D)pg;
          RenderingHints qualityHints =
          new RenderingHints(RenderingHints.KEY_RENDERING,
          RenderingHints.VALUE_RENDER_QUALITY);
          qualityHints.put(RenderingHints.KEY_TEXT_ANTIALIASING,
          RenderingHints.VALUE_TEXT_ANTIALIAS_ON);
          qualityHints.put(RenderingHints.KEY_COLOR_RENDERING,
          RenderingHints.VALUE_COLOR_RENDER_QUALITY);
          qualityHints.put(RenderingHints.KEY_FRACTIONALMETRICS,
          RenderingHints.VALUE_FRACTIONALMETRICS_ON);
          qualityHints.put(RenderingHints.KEY_DITHERING,
          RenderingHints.VALUE_DITHER_DISABLE);
          qualityHints.put(RenderingHints.KEY_RENDERING,
          RenderingHints.VALUE_RENDER_QUALITY);
          g2.setRenderingHints(qualityHints);
          
          g2.translate((int)pageFormat.getImageableX(),
            (int)pageFormat.getImageableY());
          int wPage = (int)pageFormat.getImageableWidth();
          int hPage = (int)pageFormat.getImageableHeight();
          g2.setClip(0, 0, wPage, hPage);

          // this code doesn't change the print result ??

          // disable double buffering of JTextPane
          textPane.setDoubleBuffered(false);
          // paint text on the pinter graphics context
          textPane.paintAll(g2);
          textPane.setDoubleBuffered(true);

          // check RenderingHint
          RenderingHints rhints = g2.getRenderingHints();
          System.out.println("------ the RenderingHints of the printing graphics context -------");
          System.out.println(rhints.toString());
          System.out.println("------------------------------------------------------------------");
          
          FontRenderContext frc = g2.getFontRenderContext();
          System.out.println("------ the FontRenderContext of the printing graphics context -------");
          System.out.println("isAntiAliased = " +frc.isAntiAliased());
          System.out.println("usesFractionalMetrics = " +frc.usesFractionalMetrics());
          //System.out.println("------ the device configuration -------");
          //System.out.println("Device = " + g2.getDeviceConfiguration().getDevice().getIDstring());
          System.out.println("------------------------------------------------------------------");
          return PAGE_EXISTS;
        }

        public static void main(String argv[]) {
          new TextExample3();
        }
      // end of class TextExample
      }

      To reproduce select Font Arial Point 11 and type any text
      Compare to Arial 12 point.

      Customer is developing on win NT with jdk 1.2.2-w.

        Attachments

          Issue Links

            Activity

              People

              • Assignee:
                prr Philip Race
                Reporter:
                pmaier Peter Maier (Inactive)
              • Votes:
                0 Vote for this issue
                Watchers:
                0 Start watching this issue

                Dates

                • Created:
                  Updated:
                  Resolved:
                  Imported:
                  Indexed: