2012-06-04 70 views
1

有谁知道我会如何打印滚动复合材料的内容?SWT如何打印ScrolledComposite的内容?

无论何时我打印到GC上,它只会复制滚动组合的当前可查看区域。我想要的是能够复制滚动复合的全部内容。

例如,下面的代码会在一个小窗口内制作一个巨大的按钮。无论何时我打印下面的gc,它只会输出滚动复合材料的小可视区域。是否有可能在滚动的复合材料中打印所有内容?

Shell shell = new Shell(getDisplay()); 
shell.setLayout(new FillLayout()); 
shell.setSize(200, 200); 
shell.setLocation(20, 20); 


ScrolledComposite sc = new ScrolledComposite(shell, SWT.H_SCROLL| SWT.V_SCROLL); 
sc.setMinSize(availWidth, availHeight + 30); 

Button b = new Button(sc, SWT.PUSH); 
b.setText("Button"); 
b.setSize(availWidth, availHeight); 
sc.setContent(b); 

Image image = new Image(getDisplay(), availWidth, availHeight); 
GC imageGC = new GC(image); 
sc.print(imageGC); 

回答

1

Note >>>

见下文@CryptDemon意见。虽然该解决方案已知可在Windows 7和Eclipse 3.7.x版本上运行。


是的,这是可能的。你面临的问题是由于Windows画图事件产生的方式(我假定Windows操作系统,因为我只有那个!!),因为 滚动窗口

在任何特定时刻(根据您的代码),您的scrolled composite的可见尺寸为,比实际尺寸小。现在,当您在scrolled composite上拨打print()时,只会打印其中一部分(此时可用/可见)的一部分。就像这样:

Border is for clarity

解决方案是创建scrolled composite内固定Composite并调用打印上。

Code:

import org.eclipse.swt.SWT; 
import org.eclipse.swt.custom.ScrolledComposite; 
import org.eclipse.swt.events.SelectionAdapter; 
import org.eclipse.swt.events.SelectionEvent; 
import org.eclipse.swt.graphics.GC; 
import org.eclipse.swt.graphics.Image; 
import org.eclipse.swt.graphics.ImageData; 
import org.eclipse.swt.graphics.ImageLoader; 
import org.eclipse.swt.layout.FillLayout; 
import org.eclipse.swt.layout.GridLayout; 
import org.eclipse.swt.widgets.Button; 
import org.eclipse.swt.widgets.Composite; 
import org.eclipse.swt.widgets.Display; 
import org.eclipse.swt.widgets.Shell; 

public class Scrolled 
{ 
    public static void main(String[] args) 
    { 
     final Display display = new Display(); 

     Shell shell = new Shell(display); 
     shell.setLayout(new FillLayout()); 
     shell.setSize(200, 200); 
     shell.setLocation(20, 20); 

     final ScrolledComposite sc = new ScrolledComposite(shell, SWT.BORDER | SWT.V_SCROLL | SWT.H_SCROLL); 
     sc.setLayout(new GridLayout(1,true)); 

     final Composite innerComposite = new Composite(sc, SWT.NONE); 
     innerComposite.setSize(400, 400); 
     innerComposite.setLayout(new GridLayout(1, true)); 

     for(int i = 0; i < 10; i++) 
     { 
       Button b = new Button(innerComposite, SWT.PUSH); 
       b.setText("Text"); 
       b.addSelectionListener(new SelectionAdapter() { 
        public void widgetSelected(SelectionEvent e) 
        { 
         Image image = new Image(display, innerComposite.getBounds().width, innerComposite.getBounds().height); 
         ImageLoader loader = new ImageLoader(); 

         GC gc = new GC(image); 
         sc.print(gc); 
         gc.dispose(); 

         loader.data = new ImageData[]{image.getImageData()}; 
         loader.save("c:/temp/out.png", SWT.IMAGE_PNG); 
        } 
       }); 
     } 

     sc.setMinSize(innerComposite.computeSize(SWT.DEFAULT, SWT.DEFAULT)); 
     sc.setContent(innerComposite); 
     sc.setExpandHorizontal(true); 
     sc.setExpandVertical(true); 


     shell.open(); 
     while (!shell.isDisposed()) { 
       if (!display.readAndDispatch()) 
         display.sleep(); 
     } 
     display.dispose(); 
    } 
} 

Output:

enter image description here

+0

那么,似乎在Windows上工作就好,但它不适用于Linux系统。 GTK小部件仍然只是打印出可视区域。这太遗憾了。我的程序是跨平台的,所以我真的需要解决这个问题的方法。 – CryptDemon

+0

糟糕!无论如何,在您的问题中添加了“跨平台”标签。 – Favonius

0

SWT(GTK3似乎修复这个bug),然而,在我们的项目中,我们打算使用SWT(GTK2)保持,我们的解决方案是创建一个临时shell和重新控制临时shell

import org.eclipse.swt.SWT; 
import org.eclipse.swt.custom.ScrolledComposite; 
import org.eclipse.swt.events.SelectionAdapter; 
import org.eclipse.swt.events.SelectionEvent; 
import org.eclipse.swt.graphics.GC; 
import org.eclipse.swt.graphics.Image; 
import org.eclipse.swt.graphics.ImageData; 
import org.eclipse.swt.graphics.ImageLoader; 
import org.eclipse.swt.layout.FillLayout; 
import org.eclipse.swt.layout.GridLayout; 
import org.eclipse.swt.widgets.Button; 
import org.eclipse.swt.widgets.Composite; 
import org.eclipse.swt.widgets.Display; 
import org.eclipse.swt.widgets.Shell; 

public class Scrolled { 
    public static void main(String[] args) { 
     final Display display = new Display(); 

     Shell shell = new Shell(display); 
     shell.setLayout(new FillLayout()); 
     shell.setSize(200, 200); 
     shell.setLocation(20, 20); 

     final ScrolledComposite sc = new ScrolledComposite(shell, SWT.BORDER | SWT.V_SCROLL | SWT.H_SCROLL); 
     sc.setLayout(new GridLayout(1, true)); 

     final Composite innerComposite = new Composite(sc, SWT.NONE); 
     innerComposite.setSize(400, 400); 
     innerComposite.setLayout(new GridLayout(1, true)); 

     for (int i = 0; i < 10; i++) { 
      Button b = new Button(innerComposite, SWT.PUSH); 
      b.setText("Text"); 
      b.addSelectionListener(new SelectionAdapter() { 
       public void widgetSelected(SelectionEvent e) { 
        Image image = new Image(display, innerComposite.getBounds().width, 
          innerComposite.getBounds().height); 
        ImageLoader loader = new ImageLoader(); 

        GC gc = new GC(image); 

        // Create a temp shell and reparent it+ 
        Shell newShell = new Shell(shell); 
        newShell.setLayout(new FillLayout()); 
        Composite oldParent = sc.getParent(); 
        oldParent.setRedraw(false); 
        sc.setParent(newShell); 
        newShell.open(); 
        sc.print(gc); 
        sc.setParent(oldParent); 
        oldParent.setRedraw(true); 

        gc.dispose(); 
        newShell.dispose(); 

        loader.data = new ImageData[] { image.getImageData() }; 
        loader.save("./out.png", SWT.IMAGE_PNG); 
       } 
      }); 
     } 

     sc.setMinSize(innerComposite.computeSize(SWT.DEFAULT, SWT.DEFAULT)); 
     sc.setContent(innerComposite); 
     sc.setExpandHorizontal(true); 
     sc.setExpandVertical(true); 

     shell.open(); 
     while (!shell.isDisposed()) { 
      if (!display.readAndDispatch()) 
       display.sleep(); 
     } 
     display.dispose(); 
    } 
}