Best way to print a NSTableView - Swift 5 + cocoa

225 Views Asked by At

I am new in Swift cocoa programming and I am trying build a finance program. I am almost done but I am stuck with the following problem. I am trying to print a multipage NStableView from a storyboard with textlabel bfore and after. I can print the NSView without issue if the tableView is fit in one page. If more than one page, only the first page show up. I did not found how to expand the Tableview.

I have search through all the post without a valide solution.

I can print the NSTableView itself without the NSView and it will show all the pages. But of course, it wont print the accompagning textlabel, nor the TableheaderView.

I have manage to adapt an exemple that let me print the whole table with its header, but no textlabel. It rebuilt the table cell by cell for printing.

I have also found a more promissing exemple, were I can print all what I need with a stackView.

2 problems :

  1. The tableView print fine inside the stackView but it want to resize or cut the last column. I had to play with the frame size and other option with partial success.
  2. I have tried to print the TableHeaderView separatly in its stackView but that did not work well. So I draw in the storyboard a serie of label in an horizonal StackView that match the tableView header. Eveything look fine in the Storyboard but the program resize each label before printing. Could not find a solution for taht problem.

Any suggestion would be appreciate. Is SwiftUI easier to use? I would have to update my OS to 10.15...

1

There are 1 best solutions below

0
On

The solution that I have found for now is the build my printout in Stackview, but there must be a better solution. The TableView print fine inside the Stackview but the HeaderView don’t print. The solution I used is to rebuild an HeaderView with a series of labels and put them inside a horizontal StackView that I can print in the vertical Stackview before the table. The header is designed in the storyboard. Note that the printing parameters were not completely optimized, I am just starting with Xcode.the printout include a Title, the headerView, the TableView and a Label with the Inventory total. The table can be multipage. The content of the table is fictive]1

let printOpts: [NSPrintInfo.AttributeKey: Any] = [.headerAndFooter: true, .orientation : 1]
let printInfo = NSPrintInfo(dictionary: printOpts)

//printInfo.paperSize = NSMakeSize(595, 842)

printInfo.paperSize = NSMakeSize(612, 792)

printInfo.scalingFactor = 0.8
printInfo.orientation = .landscape

printInfo.leftMargin = 30
printInfo.rightMargin = 0
printInfo.topMargin = 40
printInfo.bottomMargin = 30


let titreLabel = NSTextField.init(labelWithString: monTitre)
let InValueText =  valeur_inv.stringValue  //  "Lorem ipsum dolor sit amet, consectetur adipisicing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua."
let InvValuesLabel = NSTextField.init(wrappingLabelWithString: "Valeur d'inventaire: " +  InValueText + " $")


let pageContentSize = NSSize(width: printInfo.paperSize.width - printInfo.leftMargin - printInfo.rightMargin,
height: printInfo.paperSize.height - printInfo.topMargin - printInfo.bottomMargin)
let initialFrameForPrinting = NSRect(origin: .zero, size: pageContentSize)

let stackView = NSStackView(frame: initialFrameForPrinting)
stackView.autoresizesSubviews = false
stackView.autoresizingMask = [.height]
stackView.orientation = .vertical
stackView.alignment = .left

stackView.addArrangedSubview(titreLabel)
stackView.spacing = 20.0
stackView.addArrangedSubview(header_stackView)  // an horizontal stackview with the header, build in the storyboard.
stackView.spacing = 0   // -20 does not work
stackView.addArrangedSubview(PrintTableView)
//PrintTableView.sizeLastColumnToFit()
stackView.spacing = 20
stackView.addArrangedSubview(InvValuesLabel)  // Inventory values at the bottom of the table

//stackView.addArrangedSubview(ValInvBoxView)

  // won't work earlier than when the table is embedded in a view hierarchy

 // MARK: Configure the print operation
 // Print 'naturally', starting in top-left (for LTR languages at least?) instead of centering the content like a picture.
 printInfo.isHorizontallyCentered = true
 printInfo.isVerticallyCentered = false

 // Using `.fit` would shrink the content if it was a single-line label, but actually behaves the same with our more complex layout.
 //printInfo.horizontalPagination = .clip
 printInfo.horizontalPagination = .fit
 printInfo.verticalPagination = .automatic
 printInfo.scalingFactor = 0.8

 let printOperation = NSPrintOperation(view: stackView, printInfo: printInfo)
// let printOperation = NSPrintOperation(view: myPrintView, printInfo: printInfo) // print the table header only

 printOperation.printPanel.options.insert(NSPrintPanel.Options.showsPaperSize)
 printOperation.printPanel.options.insert(NSPrintPanel.Options.showsOrientation)
//printOperation.showsPrintPanel = true
 printOperation.showsProgressPanel = true
 
 printOperation.run()
 printOperation.cleanUp()

self.dismiss(true) in the storyboard.