代码之家  ›  专栏  ›  技术社区  ›  Hakanai

有没有一个好方法可以在Swing应用程序中保存打印机设置?

  •  13
  • Hakanai  · 技术社区  · 15 年前

    我们正在使用新的Java打印API,它使用 PrinterJob.printDialog(attributes) 向用户显示对话框。

    想保存用户的设置以便下次使用,我想这样做:

    PrintRequestAttributeSet attributes = loadAttributesFromPreferences();
    if (printJob.printDialog(attributes)) {
        // print, and then...
    
        saveAttributesToPreferences(attributes);
    }
    

    然而,通过这样做,我发现有时(我还没有弄清楚如何)属性会在内部得到一些错误的数据,然后当您打印时,会得到一个空白的白色页面。然后代码将中毒设置保存到首选项中,所有后续打印运行也会得到中毒设置。此外,由于新对话框似乎不使用旧设置,因此整个练习点(使新运行的设置与用户为上一次运行选择的设置相同)都将失败。

    所以我想知道有没有合适的方法。当然,Sun并不打算用户每次启动应用程序时都必须选择打印机、页面大小、方向和边距设置。

    编辑 要显示存储方法的实现,请执行以下操作:

    private PrintRequestAttributeSet loadAttributesFromPreferences()
    {
        PrintRequestAttributeSet attributes = null;
    
        byte[] marshaledAttributes = preferences.getByteArray(PRINT_REQUEST_ATTRIBUTES_KEY, null);
        if (marshaledAttributes != null)
        {
            try
            {
                @SuppressWarnings({"IOResourceOpenedButNotSafelyClosed"})
                ObjectInput objectInput = new ObjectInputStream(new ByteArrayInputStream(marshaledAttributes));
    
                attributes = (PrintRequestAttributeSet) objectInput.readObject();
            }
            catch (IOException e)
            {
                // Can occur due to invalid object data e.g. InvalidClassException, StreamCorruptedException
                Logger.getLogger(getClass()).warn("Error trying to read print attributes from preferences", e);
            }
            catch (ClassNotFoundException e)
            {
                Logger.getLogger(getClass()).warn("Class not found trying to read print attributes from preferences", e);
            }
        }
    
        if (attributes == null)
        {
            attributes = new HashPrintRequestAttributeSet();
        }
    
        return attributes;
    }
    
    private void saveAttributesToPreferences(PrintRequestAttributeSet attributes)
    {
        ByteArrayOutputStream storage = new ByteArrayOutputStream();
        try
        {
            ObjectOutput objectOutput = new ObjectOutputStream(storage);
            try
            {
                objectOutput.writeObject(attributes);
            }
            finally
            {
                objectOutput.close(); // side-effect of flushing the underlying stream
            }
        }
        catch (IOException e)
        {
            throw new IllegalStateException("I/O error writing to a stream going to a byte array", e);
        }
    
        preferences.putByteArray(PRINT_REQUEST_ATTRIBUTES_KEY, storage.toByteArray());
    }
    

    编辑: 好吧,似乎它不记得打印机的原因是它根本不在PrintRequestAttributeSet中。事实上,页边距和页面大小都会被记住,至少在设置被随机污染之前是这样。但用户选择的打印机不在此处:

    [0] = {java.util.HashMap$Entry@9494} class javax.print.attribute.standard.Media -> na-letter
    [1] = {java.util.HashMap$Entry@9501} class javax.print.attribute.standard.Copies -> 1
    [2] = {java.util.HashMap$Entry@9510} class javax.print.attribute.standard.MediaPrintableArea -> (10.0,10.0)->(195.9,259.4)mm
    [3] = {java.util.HashMap$Entry@9519} class javax.print.attribute.standard.OrientationRequested -> portrait
    
    1 回复  |  直到 15 年前
        1
  •  1
  •   Gilbert Le Blanc    14 年前

    看来你要找的是 PrintServiceAttributeSet ,而不是 PrintRequestAttributeSet .

    看看 PrintServiceAttribute 接口,并查看所需的元素是否已作为类实现。如果不是,你可以实现你自己的 PrintServiceAttribute 类。