Backend printing bundle system changes

git-svn-id: svn+ssh://svn.gna.org/svn/gnustep/libs/gui/trunk@19705 72102866-910b-0410-8b05-ffd578937521
This commit is contained in:
Chad Hardin 2004-07-10 10:19:34 +00:00
parent ca71d7e075
commit 989ae0cdd8
36 changed files with 3424 additions and 1256 deletions

View file

@ -1,3 +1,57 @@
2004-07-09 Chad Hardin <cehardin@mac.com>
* Source/GNUmakefile:
* Headers/AppKit/NSPageLayout.h:
* Source/NSPageLayout.m:
* Headers/AppKit/NSPrintInfo.h:
* Source/NSPrintInfo.m:
* Headers/AppKit/NSPrintOperation.h:
* Source/NSPrintOperation.m:
* Headers/AppKit/NSPrintPanel.h:
* Source/NSPrintPanel.m:
* Headers/AppKit/NSPrinter.h:
* Source/NSPrinter.m:
Modifications for the backend printing bundle system.
* Headers/Additions/GNUstepGUI/GSEPSPrintOperation.h: added.
* Source/GSEPSPrintOperation.m: added.
* Headers/Additions/GNUstepGUI/GSPDFPrintOperation.h: added.
* Source/GSPDFPrintOperation.m: added.
* Headers/Additions/GNUstepGUI/GSPrintOperation.h: added.
* Source/GSPrintOperation.m: added.
* Headers/Additions/GNUstepGUI/GSPrinting.h: added.
* Source/GSPrinting.m: added.
Split off the various PrintOperation classes. This makes is clear that
the printing backend bundles subclass GSPrintOperation, not NSPrintOperation.
Also, GSPDFPrintOperation will probably become large when implemented, this
clarifies the class structure and prevent NSPrintOperation.m from become
overly large and confusing. The GSPrinting class is helper for loading the
proper printer backend bundle.
* GNUMakefile: includes the Printing directory.
* Printing: Added the printing bundles home directory.
* Printing/GNUmakefile: added.
* Printing/GSLPR: Added the first printing bundle.
* Printing/GSLPR/GNUmakefile: added.
* Printing/GSLPR/GNUmakefile.postamble: added.
* Printing/GSLPR/GNUmakefile.preamble: added.
* Printing/GSLPR/GSLPRPageLayout.h: added.
* Printing/GSLPR/GSLPRPageLayout.m: added.
* Printing/GSLPR/GSLPRPrincipalClass.h: added.
* Printing/GSLPR/GSLPRPrincipalClass.m: added.
* Printing/GSLPR/GSLPRPrintInfo.h: added.
* Printing/GSLPR/GSLPRPrintInfo.m: added.
* Printing/GSLPR/GSLPRPrintOperation.h: added.
* Printing/GSLPR/GSLPRPrintOperation.m: added.
* Printing/GSLPR/GSLPRPrintPanel.h: added.
* Printing/GSLPR/GSLPRPrintPanel.m: added.
* Printing/GSLPR/GSLPRPrintPrinter.h: added.
* Printing/GSLPR/GSLPRPrintPrinter.m: added.
Here it is, the first backend printing bundle, version one. The are very
little code changes from the original source, bugs that may have been
present there would have been carried over here. However, this is just the
first round. This bundle uses GNUstep's original PageLayout and PrintPanel
GORM panels, it does not have its own. Hence, it is very simple. The plan
is for the future GSCUPS bundle to also use GNUstep's GORM panels, not for
each bundle to have their own panels.
2004-07-09 Fred Kiefer <FredKiefer@gmx.de>
* Source/NSPanel.m:

View file

@ -56,7 +56,8 @@ PrinterTypes \
TextConverters \
ColorPickers \
KeyBindings \
Resources
Resources \
Printing
ifeq ($(doc), yes)
SUBPROJECTS += Documentation

View file

@ -0,0 +1,59 @@
/** <title>GSEPSPrintOperation</title>
<abstract>Controls generation of EPS print output.</abstract>
Copyright (C) 1996,2004 Free Software Foundation, Inc.
Author: Scott Christley <scottc@net-community.com>
Date: 1996
Author: Fred Kiefer <FredKiefer@gmx.de>
Date: November 2000
Updated to new specification
Author: Adam Fedor <fedor@gnu.org>
Date: Oct 2001
Modified for Printing Backend Support
Author: Chad Hardin <cehardin@mac.com>
Date: June 2004
This file is part of the GNUstep GUI Library.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; see the file COPYING.LIB.
If not, write to the Free Software Foundation,
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
#ifndef _GNUstep_H_GSEPSPrintOperation
#define _GNUstep_H_GSEPSPrintOperation
#include <Foundation/NSObject.h>
#include <Foundation/NSGeometry.h>
#include "AppKit/NSPrintOperation.h"
@class NSString;
@class NSView;
@class NSPrintInfo;
// subclass for EPS output
@interface GSEPSPrintOperation: NSPrintOperation
{
}
- (id) initWithView:(NSView *)aView
insideRect:(NSRect)rect
toPath:(NSString *)path
printInfo:(NSPrintInfo *)aPrintInfo;
@end
#endif // _GNUstep_H_GSEPSPrintOperation

View file

@ -0,0 +1,61 @@
/** <title>GSPDFPrintOperation</title>
<abstract>Controls generation of PDF print output.</abstract>
Copyright (C) 1996,2004 Free Software Foundation, Inc.
Author: Scott Christley <scottc@net-community.com>
Date: 1996
Author: Fred Kiefer <FredKiefer@gmx.de>
Date: November 2000
Updated to new specification
Author: Adam Fedor <fedor@gnu.org>
Date: Oct 2001
Modified for Printing Backend Support
Author: Chad Hardin <cehardin@mac.com>
Date: June 2004
This file is part of the GNUstep GUI Library.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; see the file COPYING.LIB.
If not, write to the Free Software Foundation,
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
#ifndef _GNUstep_H_GSPDFPrintOperation
#define _GNUstep_H_GSPDFPrintOperation
#include <Foundation/NSObject.h>
#include <Foundation/NSGeometry.h>
#include "AppKit/NSPrintOperation.h"
@class NSString;
@class NSView;
@class NSPrintInfo;
// subclass for PDF output
@interface GSPDFPrintOperation: NSPrintOperation
{
}
- (id) initWithView:(NSView *)aView
insideRect:(NSRect)rect
toPath:(NSString *)path
printInfo:(NSPrintInfo *)aPrintInfo;
@end
#endif // _GNUstep_H_GSPDFPrintOperation

View file

@ -0,0 +1,59 @@
/** <title>GSPrintOperation</title>
<abstract>Controls generation of print jobs. Backends determine the
file format and how to send the data to the printer.</abstract>
Copyright (C) 1996,2004 Free Software Foundation, Inc.
Author: Scott Christley <scottc@net-community.com>
Date: 1996
Author: Fred Kiefer <FredKiefer@gmx.de>
Date: November 2000
Updated to new specification
Author: Adam Fedor <fedor@gnu.org>
Date: Oct 2001
Modified for Printing Backend Support
Author: Chad Hardin <cehardin@mac.com>
Date: June 2004
This file is part of the GNUstep GUI Library.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; see the file COPYING.LIB.
If not, write to the Free Software Foundation,
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
#ifndef _GNUstep_H_GSPrintOperation
#define _GNUstep_H_GSPrintOperation
#include "AppKit/NSPrintOperation.h"
@class NSView;
@class NSPrintInfo;
@interface GSPrintOperation: NSPrintOperation
{
}
- (id) initWithView:(NSView *)aView
printInfo:(NSPrintInfo *)aPrintInfo;
- (BOOL) _deliverSpooledResult;
@end
#endif // _GNUstep_H_GSPrintOperation

View file

@ -0,0 +1,63 @@
/** <title>GSPrinting</title>
<abstract>Loads the proper bundle for the printing backend and
contains the class GSPrintingPrincipleClass, which is subclassed
by printing backend bundles.</abstract>
Copyright (C) 2004 Free Software Foundation, Inc.
Author: Chad Elliott Hardin <cehardin@mac.com>
Date: June 2004
This file is part of the GNUstep GUI Library.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; see the file COPYING.LIB.
If not, write to the Free Software Foundation,
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
#ifndef _GNUstep_H_GSPrinting
#define _GNUstep_H_GSPrinting
#include <Foundation/NSBundle.h>
@interface GSPrinting : NSObject
{
}
+(NSBundle*) printingBundle;
@end
@interface GSPrintingPrincipalClass : NSObject
{
}
+(Class) pageLayoutClass;
+(Class) printInfoClass;
+(Class) printOperationClass;
+(Class) printPanelClass;
+(Class) printerClass;
+(Class) gsPrintOperationClass;
@end
#endif // _GNUstep_H_GSPrinting

View file

@ -2,12 +2,15 @@
<abstract>Stores information used in printing.</abstract>
Copyright (C) 1996,1997 Free Software Foundation, Inc.
Copyright (C) 1996,1997,2004 Free Software Foundation, Inc.
Author: Simon Frankau <sgf@frankau.demon.co.uk>
Date: July 1997
Author: Adam Fedor <fedor@gnu.org>
Date: Oct 2001
Modified for Printing Backend Support
Author: Chad Hardin <cehardin@mac.com>
Date: June 2004
This file is part of the GNUstep GUI Library.
@ -124,6 +127,17 @@ typedef enum _NSPrintingPaginationMode {
@end
//
// Used by printing backend bundles
//
@interface NSPrintInfo (Private)
+(NSPrinter*) _resolvePrinterName: (NSString*) printerName;
@end
//
// Printing Information Dictionary Keys
//

View file

@ -2,7 +2,7 @@
<abstract>Controls generation of EPS, PDF or PS print jobs.</abstract>
Copyright (C) 1996 Free Software Foundation, Inc.
Copyright (C) 1996,2001,2004 Free Software Foundation, Inc.
Author: Scott Christley <scottc@net-community.com>
Date: 1996
@ -11,6 +11,9 @@
Updated to new specification
Author: Adam Fedor <fedor@gnu.org>
Date: Oct 2001
Modified for Printing Backend Support
Author: Chad Hardin <cehardin@mac.com>
Date: June 2004
This file is part of the GNUstep GUI Library.
@ -66,7 +69,7 @@ typedef enum _NSPrintingPageOrder {
NSView *_accessoryView;
NSPrintingPageOrder _pageOrder;
BOOL _showPanels;
BOOL _pathSet;
//BOOL _pathSet; removed, just test _path for nil
int _currentPage;
}
@ -178,4 +181,22 @@ typedef enum _NSPrintingPageOrder {
@end
//
// Private method used by the NSPrintOperation subclasses
// such as GSEPSPrintOperation, GSPDFPrintOperation. This
// also includes GSPrintOperation, which is used in the printing
// backend system. Printing bundles subclass GSPrintOperation
// and use that to interface with the native printing system.
//
@interface NSPrintOperation (Private)
- (id) initWithView:(NSView *)aView
insideRect:(NSRect)rect
toData:(NSMutableData *)data
printInfo:(NSPrintInfo *)aPrintInfo;
@end
#endif // _GNUstep_H_NSPrintOperation

View file

@ -3,10 +3,13 @@
Standard panel to query users for info on a print job
Copyright (C) 1996 Free Software Foundation, Inc.
Copyright (C) 1996,2004 Free Software Foundation, Inc.
Author: Scott Christley <scottc@net-community.com>
Date: 1996
Modified for Printing Backend Support
Author: Chad Hardin <cehardin@mac.com>
Date: June 2004
This file is part of the GNUstep GUI Library.
@ -55,7 +58,10 @@ enum {
NSPPOptionsButton = 33,
NSPPPaperFeedButton = 34,
NSPPLayoutButton = 35,
NSPPResolutionButton = 36,
//The following are not actually in the OpenStep spec.
//However, It is prudent to keep them here, I am just
//making you aware of this fact.
NSPPResolutionButton = 36,
NSPPOptionOKButton = 40
};
@ -66,7 +72,7 @@ enum {
id _accessoryView;
id _savePath;
int _picked;
NSRange _pages;
NSRange _pages; //this may also be removed
}
//
@ -107,4 +113,17 @@ enum {
@end
//
// Methods used by printing backend bundles that subclass NSPrintPanel
//
@interface NSPrintPanel (Private)
/* Private method used by NSPrintOperation */
- (void) _setStatusStringValue: (NSString *)string;
/*Private method for saving a print job as a file*/
- (BOOL) _getSavePath;
@end
#endif // _GNUstep_H_NSPrintPanel

View file

@ -3,10 +3,13 @@
Class representing a printer's or printer model's capabilities.
Copyright (C) 1996, 1997 Free Software Foundation, Inc.
Copyright (C) 1996, 1997,2004 Free Software Foundation, Inc.
Authors: Simon Frankau <sgf@frankau.demon.co.uk>
Date: June 1997
Modified for Printing Backend Support
Author: Chad Hardin <cehardin@mac.com>
Date: June 2004
This file is part of the GNUstep GUI Library.
@ -47,7 +50,24 @@ typedef enum _NSPrinterTableStatus {
{
NSString *_printerHost, *_printerName, *_printerNote, *_printerType;
int _cacheAcceptsBinary, _cacheOutputOrder;
BOOL _isRealPrinter;
//The way openstep handled NSPrinter was odd, it had a concept of "real"
//printers and
//not real printers. Printers that were not real were simply parsed PPDs,
//whether the printer was actually available or not was irrevelatn. This is
//is where the all the -types and +types methods come from. Apple's
//adoption of CUPS forced them to change this behavior, now, their types
//methods only search for the types of printers that are actually avaiable,
//it has nothing to do with the PPDs that happen to be avaiable on the file
//system. I think this is also the behavior we should adopt. Not simply
//because it is what Apple does but because it facilitates a generic printing
//backend system, especially one that will likely be using CUPS itself.
//This is why the following ivar is removed and the behavior of this class
//and the GSLPR Bundle has been changed. Doing this has also allowed me
//to put a lot of generic code in ths class that would have otherwise had
//to have been handles by each bundle. See +printerWithType: in NSPrinter.m
//BOOL _isRealPrinter;
NSMutableDictionary *_PPD;
NSMutableDictionary *_PPDOptionTranslation;
NSMutableDictionary *_PPDArgumentTranslation;
@ -112,4 +132,29 @@ typedef enum _NSPrinterTableStatus {
@end
//
// Private methods that will be usefull for the
// printing backend bundles that subclass NSPrinter
//
@interface NSPrinter (Private)
//
// Initialisation method used by backend bundles
//
-(id) initWithName:(NSString *)name
withType:(NSString *)type
withHost:(NSString *)host
withNote:(NSString *)note;
-(id) addValue:(NSString *)value
andValueTranslation:(NSString *)valueTranslation
andOptionTranslation:(NSString *)optionTranslation
forKey:(NSString *)key;
-(id) addString: (NSString*) string
forKey: (NSString*) key
inTable: (NSMutableDictionary*) table;
@end
#endif // _GNUstep_H_NSPrinter

39
Printing/GNUmakefile Normal file
View file

@ -0,0 +1,39 @@
#
# Makefile for the GNUstep Printing Backend Bundles
#
# Copyright (C) 2004 Free Software Foundation, Inc.
#
# Author: Chad Hardin <cehardin@mac.com
# Date: June 2004
#
# This file is part of the GNUstep GUI Library.
#
# This library is free software; you can redistribute it and/or
# modify it under the terms of the GNU Library General Public
# License as published by the Free Software Foundation; either
# version 2 of the License, or (at your option) any later version.
#
# This library is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
# Library General Public License for more details.
#
# If you are interested in a warranty or support for this source code,
# contact Scott Christley at scottc@net-community.com
#
# You should have received a copy of the GNU Library General Public
# License along with this library; see the file COPYING.LIB.
# If not, write to the Free Software Foundation,
# 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
include $(GNUSTEP_MAKEFILES)/common.make
#
# The list of subproject directories
#
SUBPROJECTS = \
GSLPR
include $(GNUSTEP_MAKEFILES)/aggregate.make

120
Printing/GSLPR/GNUmakefile Normal file
View file

@ -0,0 +1,120 @@
#
# GSLPR Printing Backend Bundle makefile for GNUstep GUI Library
#
# Copyright (C) 2004 Free Software Foundation, Inc.
#
# Author: Chad Hardin <cehardin@mac.com
#
# Date: June 2004
#
# This file is part of the GNUstep GUI Library.
#
# This library is free software; you can redistribute it and/or
# modify it under the terms of the GNU Library General Public
# License as published by the Free Software Foundation; either
# version 2 of the License, or (at your option) any later version.
#
# This library is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
# Library General Public License for more details.
#
# You should have received a copy of the GNU Library General Public
# License along with this library; see the file COPYING.LIB.
# If not, write to the Free Software Foundation,
# 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
GNUSTEP_LOCAL_ADDITIONAL_MAKEFILES=../../gui.make
include $(GNUSTEP_MAKEFILES)/common.make
include ../../config.make
include ../../Version
BUNDLE_NAME=GSLPR
BUNDLE_INSTALL_DIR= $(GNUSTEP_BUNDLES)/GSPrinting
GSLPR_PRINCIPAL_CLASS=GSLPRPrincipalClass
ifeq ($(GNUSTEP_TARGET_OS),mingw32)
GSLPR_BUNDLE_LIBS += -lgnustep-gui $(FND_LIBS) $(OBJC_LIBS)
endif
ifeq ($(GNUSTEP_TARGET_OS),cygwin)
GSLPR_BUNDLE_LIBS += -lgnustep-gui $(FND_LIBS) $(OBJC_LIBS)
endif
#
# Libraries
#
#GSLPR_LIBRARIES_DEPEND_UPON +=
#
# Resource files
#
#GSLPR_RESOURCE_FILES =
#
# Header files
#
GSLPR_HEADERS= \
GSLPRPrincipalClass.m \
GSLPRPageLayout.m \
GSLPRPrintInfo.m \
GSLPRPrintOperation \
GSLPRPrintPanel.m \
GSLPRPrinter.m
#
# Class files
#
GSLPR_OBJC_FILES= \
GSLPRPrincipalClass.m \
GSLPRPageLayout.m \
GSLPRPrintInfo.m \
GSLPRPrintOperation.m \
GSLPRPrintPanel.m \
GSLPRPrinter.m
#
# C files
#
#GSLPR_C_FILES =
#
# Languages
#
#GSLPR_LANGUAGES= \
# English
#
# Localized Resource Files
#
#GSLPR_LOCALIZED_RESOURCE_FILES= \
# GSLPRPrintPanel.gorm \
# GSLPRPageLayout.gorm
#
# Makefiles
#
-include GNUmakefile.preamble
#include $(GNUSTEP_MAKEFILES)/aggregate.make
include $(GNUSTEP_MAKEFILES)/bundle.make
-include GNUmakefile.postamble

View file

@ -0,0 +1,40 @@
#
# GNUmakefile.postamble
#
# Things to do before compiling
# before-all::
# Things to do after compiling
# after-all::
# Things to do before installing
# before-install::
# Things to do after installing
# after-install::
# Things to do before uninstalling
# before-uninstall::
# Things to do after uninstalling
# after-uninstall::
# Things to do before cleaning
# before-clean::
# Things to do after cleaning
# after-clean::
# Things to do before distcleaning
# before-distclean::
# Things to do after distcleaning
# after-distclean::
# Things to do before checking
# before-check::
# Things to do after checking
# after-check::

View file

@ -0,0 +1,41 @@
# Additional flags to pass to the preprocessor
ADDITIONAL_CPPFLAGS +=
# Additional flags to pass to the Objective-C compiler
ADDITIONAL_OBJCFLAGS +=
# Additional flags to pass to the C compiler
ADDITIONAL_CFLAGS +=
# Additional include directories the compiler should search
ADDITIONAL_INCLUDE_DIRS += -I../../Headers/Additions -I../../Headers -I../../Source
# Additional LDFLAGS to pass to the linker
ADDITIONAL_LDFLAGS +=
# Additional library directories the linker should search
ADDITIONAL_LIB_DIRS += -L../../Source/$(GNUSTEP_OBJ_DIR)
# Additional libraries
# GNUstepWeb
ADDITIONAL_GSW_LIBS +=
# GUI apps
ADDITIONAL_GUI_LIBS +=
# Libraries
ADDITIONAL_LIBRARY_LIBS +=
# ObjC stuff
ADDITIONAL_OBJC_LIBS +=
#-lgnustep-gui $(SYSTEM_LIBS)
# Tools
ADDITIONAL_TOOL_LIBS +=
# WebObjects
ADDITIONAL_WO_LIBS +=
#
# Flags dealing with installing and uninstalling
#
#GNUSTEP_INSTALLATION_DIR=$(GNUSTEP_SYSTEM_ROOT)
# Additional directories to be created during installation
#ADDITIONAL_INSTALL_DIRS +=

View file

@ -0,0 +1,47 @@
/** <title>GSLPRPageLayout</title>
<abstract>Standard panel for querying user about page layout.</abstract>
Copyright (C) 2001,2004 Free Software Foundation, Inc.
Written By: Adam Fedor <fedor@gnu.org>
Date: Oct 2001
Modified for Printing Backend Support
Author: Chad Hardin <cehardin@mac.com>
Date: June 2004
This file is part of the GNUstep GUI Library.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; see the file COPYING.LIB.
If not, write to the Free Software Foundation,
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
#ifndef _GNUstep_H_GSLPRPageLayout
#define _GNUstep_H_GSLPRPageLayout
#include <AppKit/NSPageLayout.h>
@class NSPrintInfo;
@class NSView;
@interface GSLPRPageLayout: NSPageLayout
{
}
@end
#endif // _GNUstep_H_NSPageLayout

View file

@ -0,0 +1,72 @@
/** <title>GSLPRPageLayout</title>
<abstract></abstract>
Copyright (C) 2004 Free Software Foundation, Inc.
Author: Chad Hardin <cehardin@mac.com>
Date: June 2004
This file is part of the GNUstep GUI Library.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; see the file COPYING.LIB.
If not, write to the Free Software Foundation,
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
#include <Foundation/NSDebug.h>
//#include <AppKit/NSApplication.h>
//#include <AppKit/NSFont.h>
//#include <AppKit/NSTextField.h>
//#include <AppKit/NSImage.h>
//#include <AppKit/NSImageView.h>
//#include <AppKit/NSBox.h>
//#include <AppKit/NSButton.h>
//#include <AppKit/NSComboBox.h>
//#include <AppKit/NSPopUpButton.h>
//#include <AppKit/NSMatrix.h>
//#include <AppKit/NSNibLoading.h>
//#include <AppKit/NSForm.h>
//#include <AppKit/NSFormCell.h>
//#include <AppKit/NSPrintInfo.h>
//#include <AppKit/NSPageLayout.h>
//#include <AppKit/NSPrinter.h>
//#include "GSGuiPrivate.h"
#include "GSLPRPageLayout.h"
//#include "GNUstepGUI/GSPrinting.h"
@implementation GSLPRPageLayout
//
// Class methods
//
+ (void)initialize
{
NSDebugMLLog(@"GSPrinting", @"");
if (self == [GSLPRPageLayout class])
{
// Initial version
[self setVersion:1];
}
}
+ (id) allocWithZone: (NSZone*)zone
{
NSDebugMLLog(@"GSPrinting", @"");
return NSAllocateObject(self, 0, zone);
}
@end

View file

@ -0,0 +1,37 @@
/*
Project: GSLPR
Copyright (C) 2004 Free Software Foundation
Author: Chad Hardin <cehardin@mac.com>
Created: 2004-06-12 19:40:40 +0000 by Chad Hardin
This application is free software; you can redistribute it and/or
modify it under the terms of the GNU General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This application is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111 USA.
*/
#ifndef _GSLPRPRINCIPALCLASS_H_
#define _GSLPRPRINCIPALCLASS_H_
#include <GNUstepGUI/GSPrinting.h>
@interface GSLPRPrincipalClass : GSPrintingPrincipalClass
{
}
@end
#endif // _GSLPRPRINCIPALCLASS_H_

View file

@ -0,0 +1,79 @@
/*
Project: GSLPR
Copyright (C) 2004 Free Software Foundation
Author: Chad Hardin <cehardin@mac.com>
Created: 2004-06-12 19:40:40 +0000 by Chad Hardin
This application is free software; you can redistribute it and/or
modify it under the terms of the GNU General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This application is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111 USA.
*/
#include <Foundation/NSDebug.h>
#include "GSLPRPrincipalClass.h"
#include "GSLPRPageLayout.h"
#include "GSLPRPrintInfo.h"
#include "GSLPRPrintOperation.h"
#include "GSLPRPrintPanel.h"
#include "GSLPRPrinter.h"
@implementation GSLPRPrincipalClass
//
// Class methods
//
+(Class) pageLayoutClass
{
NSDebugMLLog(@"GSPrinting", @"");
return [GSLPRPageLayout class];
}
+(Class) printInfoClass
{
NSDebugMLLog(@"GSPrinting", @"");
return [GSLPRPrintInfo class];
}
+(Class) printOperationClass
{
NSDebugMLLog(@"GSPrinting", @"");
return [GSLPRPrintOperation class];
}
+(Class) printPanelClass
{
NSDebugMLLog(@"GSPrinting", @"");
return [GSLPRPrintPanel class];
}
+(Class) printerClass
{
NSDebugMLLog(@"GSPrinting", @"");
return [GSLPRPrinter class];
}
+(Class) gsPrintOperationClass
{
NSDebugMLLog(@"GSPrinting", @"");
return [GSLPRPrintOperation class];
}
@end

View file

@ -0,0 +1,48 @@
/** <title>NSPrintInfo</title>
<abstract>Stores information used in printing.</abstract>
Copyright (C) 1996,1997,2004 Free Software Foundation, Inc.
Author: Simon Frankau <sgf@frankau.demon.co.uk>
Date: July 1997
Author: Adam Fedor <fedor@gnu.org>
Date: Oct 2001
Modified for Printing Backend Support
Author: Chad Hardin <cehardin@mac.com>
Date: June 2004
This file is part of the GNUstep GUI Library.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; see the file COPYING.LIB.
If not, write to the Free Software Foundation,
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
#ifndef _GNUstep_H_GSLPRPrintInfo
#define _GNUstep_H_GSLPRPrintInfo
#include <Foundation/NSCoder.h>
#include <AppKit/NSPrintInfo.h>
@interface GSLPRPrintInfo: NSPrintInfo
{
}
@end
#endif // _GNUstep_H_GSLPRPrintInfo

View file

@ -0,0 +1,164 @@
/*
GSLPRPrintInfo.m
Stores information used in printing
Copyright (C) 1996,1997,2004 Free Software Foundation, Inc.
Author: Simon Frankau <sgf@frankau.demon.co.uk>
Date: July 1997
Modified for Printing Backend Support
Author: Chad Hardin <cehardin@mac.com>
Date: June 2004
This file is part of the GNUstep GUI Library.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; see the file COPYING.LIB.
If not, write to the Free Software Foundation,
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
#include <Foundation/NSArray.h>
#include <Foundation/NSBundle.h>
#include <Foundation/NSDebug.h>
#include <Foundation/NSDictionary.h>
#include <Foundation/NSException.h>
#include <Foundation/NSEnumerator.h>
#include <Foundation/NSUserDefaults.h>
#include <Foundation/NSValue.h>
#include <AppKit/NSPrinter.h>
#include "GSLPRPrintInfo.h"
#include "GSLPRPrinter.h"
@implementation GSLPRPrintInfo
//
// Class methods
//
+ (void)initialize
{
NSDebugMLLog(@"GSPrinting", @"");
if (self == [GSLPRPrintInfo class])
{
// Initial version
[self setVersion:1];
}
}
+ (id) allocWithZone: (NSZone*)zone
{
NSDebugMLLog(@"GSPrinting", @"");
return NSAllocateObject(self, 0, zone);
}
+(NSPrinter*) defaultPrinter
{
NSUserDefaults *defaults;
NSString *name;
NSDebugMLLog(@"GSPrinting", @"");
defaults = [NSUserDefaults standardUserDefaults];
name = [defaults objectForKey: @"GSLPRDefaultPrinter"];
if( name == nil )
{
name = [[GSLPRPrinter printerNames] objectAtIndex: 0];
}
else
{
if( [GSLPRPrinter printerWithName: name] == nil )
{
name = [[GSLPRPrinter printerNames] objectAtIndex: 0];
}
}
return [GSLPRPrinter printerWithName: name];
}
+ (void)setDefaultPrinter:(NSPrinter *)printer
{
NSUserDefaults *defaults;
NSMutableDictionary *globalDomain;
NSDebugMLLog(@"GSPrinting", @"");
defaults = [NSUserDefaults standardUserDefaults];
globalDomain = (NSMutableDictionary*)[defaults persistentDomainForName: NSGlobalDomain];
if( globalDomain )
{
globalDomain = [globalDomain mutableCopy];
[globalDomain setObject: [printer name]
forKey: @"GSLPRDefaultPrinter"];
[defaults setPersistentDomain: globalDomain
forName: NSGlobalDomain];
}
else
{
NSDebugMLLog(@"GSPrinting", @"(GSLPR) Could not save default printer named %@ to NSUserDefaults GSLPRDefaultPrinter in NSGlobalDomain.", [printer name]);
}
}
-(id) initWithDictionary:(NSDictionary *)aDict
{
NSPrinter *printer;
NSString *pageSize;
NSSize size;
NSMutableDictionary *dict;
NSDebugMLLog(@"GPrinting", @"");
self = [super initWithDictionary: nil];
printer = [GSLPRPrintInfo defaultPrinter];
[self setPrinter: printer];
/* Set up other defaults from the printer object */
pageSize = [printer stringForKey: @"DefaultPageSize"
inTable: @"PPD"];
/* FIXME: Need to check for AutoSelect and probably a million other things... */
if (pageSize == nil)
pageSize = @"A4";
[self setPaperName: pageSize];
/* Set default margins. FIXME: Probably should check ImageableArea */
[self setRightMargin: 36];
[self setLeftMargin: 36];
[self setTopMargin: 72];
[self setBottomMargin: 72];
return self;
}
@end

View file

@ -0,0 +1,53 @@
/** <title>NSPrintOperation</title>
<abstract>Controls generation of EPS, PDF or PS print jobs.</abstract>
Copyright (C) 1996,2004 Free Software Foundation, Inc.
Author: Scott Christley <scottc@net-community.com>
Date: 1996
Author: Fred Kiefer <FredKiefer@gmx.de>
Date: November 2000
Updated to new specification
Author: Adam Fedor <fedor@gnu.org>
Date: Oct 2001
Modified for Printing Backend Support
Author: Chad Hardin <cehardin@mac.com>
Date: June 2004
This file is part of the GNUstep GUI Library.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; see the file COPYING.LIB.
If not, write to the Free Software Foundation,
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
#ifndef _GNUstep_H_GSLPRPrintOperation
#define _GNUstep_H_GSLPRPrintOperation
#include <GNUstepGUI/GSPrintOperation.h>
//GSPrintOperation is subclasses of GSPrintOperation, NOT NSPrintOperation.
//NSPrintOperation does a lot of work that is pretty generic.
//GSPrintOperation contains the method that does the actual
//spooling. A future Win32 printing printing bundle
//will likely have to implement much more
@interface GSLPRPrintOperation : GSPrintOperation
{
}
@end
#endif // _GNUstep_H_GSLPRPrintOperation

View file

@ -0,0 +1,168 @@
/*
GLPRSPrintOperation.m
Controls operations generating EPS, PDF or PS print jobs.
Copyright (C) 1996 Free Software Foundation, Inc.
Author: Scott Christley <scottc@net-community.com>
Date: 1996
Author: Fred Kiefer <FredKiefer@gmx.de>
Date: November 2000
Started implementation.
Modified for Printing Backend Support
Author: Chad Hardin
Date: June 2004
This file is part of the GNUstep GUI Library.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; see the file COPYING.LIB.
If not, write to the Free Software Foundation,
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
#include <math.h>
#include <config.h>
#include <Foundation/NSString.h>
#include <Foundation/NSDebug.h>
#include <Foundation/NSData.h>
#include <Foundation/NSFileManager.h>
#include <Foundation/NSException.h>
#include <Foundation/NSPathUtilities.h>
#include <Foundation/NSTask.h>
#include <Foundation/NSThread.h>
#include <Foundation/NSUserDefaults.h>
#include <Foundation/NSValue.h>
#include <AppKit/AppKitExceptions.h>
#include <AppKit/NSAffineTransform.h>
#include <AppKit/NSApplication.h>
#include <AppKit/NSGraphicsContext.h>
#include <AppKit/NSView.h>
#include <AppKit/NSPrinter.h>
#include <AppKit/NSPrintPanel.h>
#include <AppKit/NSPrintInfo.h>
#include <AppKit/NSPrintOperation.h>
#include <AppKit/NSWorkspace.h>
#include <AppKit/PSOperators.h>
#include "GSLPRPrintOperation.h"
#define NSNUMBER(a) [NSNumber numberWithInt: (a)]
#define NSFNUMBER(a) [NSNumber numberWithFloat: (a)]
//A subclass of GSPrintOperation, NOT NSPrintOperation.
@implementation GSLPRPrintOperation
//
// Class methods
//
+ (id) allocWithZone: (NSZone*)zone
{
NSDebugMLLog(@"GSPrinting", @"");
return NSAllocateObject(self, 0, zone);
}
- (id)initWithView:(NSView *)aView
printInfo:(NSPrintInfo *)aPrintInfo
{
self = [super initWithView: aView
printInfo: aPrintInfo];
_path = [NSTemporaryDirectory() stringByAppendingPathComponent: @"GSLPRPrintJob-"];
_path = [_path stringByAppendingString:
[[NSProcessInfo processInfo] globallyUniqueString]];
_path = [_path stringByAppendingPathExtension: @"ps"];
RETAIN( _path );
return self;
}
- (BOOL) _deliverSpooledResult
{
int copies;
NSDictionary *dict;
NSTask *task;
NSString *name, *status;
NSMutableArray *args;
NSDebugMLLog(@"GSPrinting", @"");
name = [[_printInfo printer] name];
status = [NSString stringWithFormat: @"Spooling to printer %@.", name];
[_printPanel _setStatusStringValue: status];
dict = [_printInfo dictionary];
args = [NSMutableArray array];
copies = [[dict objectForKey: NSPrintCopies] intValue];
if (copies > 1)
[args addObject: [NSString stringWithFormat: @"-#%0d", copies]];
if ([name isEqual: @"Unknown"] == NO)
{
[args addObject: @"-P"];
[args addObject: name];
}
[args addObject: _path];
task = [NSTask new];
[task setLaunchPath: @"lpr"];
[task setArguments: args];
[task launch];
[task waitUntilExit];
AUTORELEASE(task);
return YES;
}
- (NSGraphicsContext*)createContext
{
NSMutableDictionary *info;
//NSDebugMLLog(@"GSPrinting", @"_path is %@", _path);
if (_context)
{
NSDebugMLLog(@"GSPrinting", @"Already had context, returning it.");
return _context;
}
NSDebugMLLog(@"GSPrinting", @"Creating context.");
info = [_printInfo dictionary];
if (_path == nil)
{
NSString *output = [info objectForKey: NSPrintSavePath];
if (output)
{
ASSIGN(_path, output);
}
}
NSDebugMLLog(@"GSPrinting", @"_path is %@", _path);
[info setObject: _path
forKey: @"NSOutputFile"];
[info setObject: NSGraphicsContextPSFormat
forKey: NSGraphicsContextRepresentationFormatAttributeName];
_context = RETAIN([NSGraphicsContext graphicsContextWithAttributes: info]);
return _context;
}
@end

View file

@ -0,0 +1,46 @@
/*
GSLPRPrintPanel.h
Standard panel to query users for info on a print job
Copyright (C) 1996,2004 Free Software Foundation, Inc.
Author: Scott Christley <scottc@net-community.com>
Date: 1996
Modified for Printing Backend Support
Author: Chad Hardin <cehardin@mac.com>
Date: June 2004
This file is part of the GNUstep GUI Library.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; see the file COPYING.LIB.
If not, write to the Free Software Foundation,
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
#ifndef _GNUstep_H_GSLPRPrintPanel
#define _GNUstep_H_GSLPRPrintPanel
#include <AppKit/NSPrintPanel.h>
@interface GSLPRPrintPanel : NSPrintPanel
{
}
@end
#endif // _GNUstep_H_GSLPRPrintPanel

View file

@ -0,0 +1,64 @@
/** <title>GSLPRPrintPanel</title>
<abstract>Standard panel for querying user about printing.</abstract>
Copyright (C) 2001,2004 Free Software Foundation, Inc.
Written By: Adam Fedor <fedor@gnu.org>
Date: Oct 2001
Modified for Printing Backend Support
Author: Chad Hardin <cehardin@mac.com>
Date: June 2004
This file is part of the GNUstep GUI Library.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; see the file COPYING.LIB.
If not, write to the Free Software Foundation,
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
//#include "config.h"
#include <Foundation/NSDebug.h>
//#include <Foundation/NSArray.h>
//#include <Foundation/NSBundle.h>
//#include <Foundation/NSDictionary.h>
//#include <Foundation/NSValue.h>
//#include "AppKit/NSApplication.h"
//#include "AppKit/NSForm.h"
//#include "AppKit/NSNibLoading.h"
//#include "AppKit/NSPrinter.h"
//#include "AppKit/NSPrintPanel.h"
//#include "AppKit/NSPrintInfo.h"
//#include "AppKit/NSPrintOperation.h"
//#include "AppKit/NSPopUpButton.h"
//#include "AppKit/NSSavePanel.h"
//#include "AppKit/NSView.h"
//#include "GSGuiPrivate.h"
#include "GSLPRPrintPanel.h"
//#include "GNUstepGUI/GSPrinting.h"
@implementation GSLPRPrintPanel
//
// Class methods
//
+ (id) allocWithZone: (NSZone*)zone
{
NSDebugMLLog(@"GSPrinting", @"");
return NSAllocateObject(self, 0, zone);
}
@end

View file

@ -0,0 +1,47 @@
/*
NSPrinter.h
Class representing a printer's or printer model's capabilities.
Copyright (C) 1996, 1997,2004 Free Software Foundation, Inc.
Authors: Simon Frankau <sgf@frankau.demon.co.uk>
Date: June 1997
Modified for Printing Backend Support
Author: Chad Hardin <cehardin@mac.com>
Date: June 2004
This file is part of the GNUstep GUI Library.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; see the file COPYING.LIB.
If not, write to the Free Software Foundation,
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
#ifndef _GNUstep_H_GSLPRPrinter
#define _GNUstep_H_GSLPRPrinter
#include <AppKit/NSPrinter.h>
@interface GSLPRPrinter : NSPrinter <NSCoding>
{
}
@end
#endif // _GNUstep_H_GSLPRPrinter

View file

@ -0,0 +1,897 @@
/** <title>GSLPRPrinter</title>
<abstract>Class representing a printer's or printer model's capabilities.</abstract>
Copyright (C) 1996, 1997, 2004 Free Software Foundation, Inc.
Authors: Simon Frankau <sgf@frankau.demon.co.uk>
Date: June 1997
Modified for Printing Backend Support
Author: Chad Hardin <cehardin@mac.com>
Date: June 2004
This file is part of the GNUstep GUI Library.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
If you are interested in a warranty or support for this source code,
contact Scott Christley <scottc@net-community.com> for more information.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111 USA.
*/
/* NB:
* There are a few FIXMEs in the functionality left.
* Parsing of the PPDs is somewhat suboptimal.
* (I think it's best to leave optimisation until more of GNUstep is done).
* The *OpenUI, *CloseUI, *OpenGroup and *CloseGroup are not processed.
* (This is not required in the OpenStep standard, but could be useful).
*/
#include "config.h"
#include <Foundation/NSDebug.h>
#include <Foundation/NSAutoreleasePool.h>
#include <Foundation/NSArray.h>
#include <Foundation/NSDictionary.h>
#include <Foundation/NSString.h>
#include <Foundation/NSBundle.h>
#include <Foundation/NSCharacterSet.h>
#include <Foundation/NSDictionary.h>
#include <Foundation/NSException.h>
#include <Foundation/NSFileManager.h>
#include <Foundation/NSPathUtilities.h>
#include <Foundation/NSScanner.h>
#include <Foundation/NSString.h>
#include <Foundation/NSUtilities.h>
#include <Foundation/NSValue.h>
#include <Foundation/NSMapTable.h>
#include "AppKit/AppKitExceptions.h"
#include "AppKit/NSGraphics.h"
#include "GSLPRPrinter.h"
#include "GNUstepGUI/GSPrinting.h"
// The maximum level of nesting of *Include directives
#define MAX_PPD_INCLUDES 4
// A macro to skip whitespace over lines
#define skipSpace(x) [x scanCharactersFromSet:\
[NSCharacterSet whitespaceAndNewlineCharacterSet]\
intoString:NULL]
static NSString *NSPrinter_PATH = @"PostScript/PPD";
static NSString *NSPrinter_INDEXFILE = @"Printers";
//
// Class variables:
//
static NSDictionary *printerIndexDict = nil; //The list of printers from NSPrinter_INDEXFILE
static NSMutableDictionary *printerObjNameDict = nil; //Printer objects mapped to names
// An array to cache the available printer types
static NSArray *printerTypesAvailable = nil;
//
// Class variables used during scanning:
//
// Character sets used in scanning.
static NSCharacterSet *newlineSet = nil;
static NSCharacterSet *keyEndSet = nil;
static NSCharacterSet *optKeyEndSet = nil;
static NSCharacterSet *valueEndSet = nil;
// Array of Repeated Keywords (Appendix B of the PostScript Printer
// Description File Format Specification).
static NSArray *repKeys = nil;
// Array to collect the values of symbol values in.
static NSMutableDictionary *PPDSymbolValues;
// File name of the file being processed
static NSString *PPDFileName;
#ifndef LIB_FOUNDATION_LIBRARY
static void __NSRetainNothing(void *table, const void *anObject)
{
}
static void __NSReleaseNothing(void *table, void *anObject)
{
}
static NSString* __NSDescribeObjects(void *table, const void *anObject)
{
return [(NSObject*)anObject description];
}
static const NSMapTableValueCallBacks NSNonRetainedObjectMapValueCallBacks = {
(void (*)(NSMapTable *, const void *))__NSRetainNothing,
(void (*)(NSMapTable *, void *))__NSReleaseNothing,
(NSString *(*)(NSMapTable *, const void *))__NSDescribeObjects
};
#endif /* LIB_FOUNDATION_LIBRARY */
// Convert a character to a value between 0 and 15
static int gethex(unichar character)
{
switch (character)
{
case '0': return 0;
case '1': return 1;
case '2': return 2;
case '3': return 3;
case '4': return 4;
case '5': return 5;
case '6': return 6;
case '7': return 7;
case '8': return 8;
case '9': return 9;
case 'A': return 10;
case 'B': return 11;
case 'C': return 12;
case 'D': return 13;
case 'E': return 14;
case 'F': return 15;
case 'a': return 10;
case 'b': return 11;
case 'c': return 12;
case 'd': return 13;
case 'e': return 14;
case 'f': return 15;
}
[NSException
raise:NSPPDParseException
format:@"Badly formatted hexadeximal substring in PPD printer file."];
// NOT REACHED
return 0; /* Quiet compiler warnings */
}
// Function to convert hexadecimal substrings
static NSString *interpretQuotedValue(NSString *qString)
{
NSScanner *scanner;
NSCharacterSet *emptySet;
NSString *value = nil;
NSString *part;
int stringLength;
int location;
NSRange range;
// Don't bother unless there's something to convert
range = [qString rangeOfString:@"<"];
if(!range.length)
return qString;
scanner = [NSScanner scannerWithString:qString];
emptySet = [NSCharacterSet characterSetWithCharactersInString:@""];
[scanner setCharactersToBeSkipped:emptySet];
if(![scanner scanUpToString:@"<" intoString:&value])
value = [NSString string];
stringLength = [qString length];
while (![scanner isAtEnd]) {
[scanner scanString:@"<" intoString:NULL];
skipSpace(scanner);
while (![scanner scanString:@">" intoString:NULL])
{
location = [scanner scanLocation];
if (location+2 > stringLength)
{
[NSException
raise:NSPPDParseException
format:@"Badly formatted hexadecimal substring in PPD printer file."];
// NOT REACHED
}
value = [value stringByAppendingFormat:@"%c",
16 * gethex([qString characterAtIndex:location])
+ gethex([qString characterAtIndex:location+1])];
[scanner setScanLocation:location+2];
skipSpace(scanner);
}
if([scanner scanUpToString:@"<" intoString:&part])
{
value = [value stringByAppendingString:part];
}
}
return value;
}
static NSString *getFile(NSString *name, NSString *type)
{
return [NSBundle pathForLibraryResource: name
ofType: type
inDirectory: NSPrinter_PATH];
}
@interface GSLPRPrinter (private)
+ loadPrinterIndexFile;
-(id)initWithPPD:(NSString *)PPDstring
withName:(NSString *)name
withType:(NSString *)type
withHost:(NSString *)host
withNote:(NSString *)note
fromFile:(NSString *)file;
- loadPPD:(NSString *)PPDstring
inclusionNum:(int)includeNum;
- addPPDKeyword:(NSString *)mainKeyword
withScanner:(NSScanner *)PPDdata;
- addPPDUIConstraint:(NSScanner *)constraint;
- addPPDOrderDependency:(NSScanner *)dependency;
@end
@implementation GSLPRPrinter
//
// Class methods
//
+ (void)initialize
{
NSDebugMLLog(@"GSPrinting", @"");
if (self == [GSLPRPrinter class])
{
// Initial version
[self setVersion:1];
}
}
+ (id) allocWithZone: (NSZone*)zone
{
NSDebugMLLog(@"GSPrinting", @"");
return NSAllocateObject(self, 0, zone);
}
//
// Finding an NSPrinter
//
+ (NSPrinter *)printerWithName:(NSString *)name
{
NSString *path;
NSArray *printerInfo;
NSPrinter *printer;
/* Contents of printerInfo array:
* [0]: NSString of the printer's type
* [1]: NSString of the printer's host
* [2]: NSString of the printer's note
*/
NSDebugMLLog(@"GSPrinting", @"");
// Make sure the printer names dictionary etc. exists
if (!printerIndexDict)
[self loadPrinterIndexFile];
if( name == nil )
return nil;
printer = [printerObjNameDict objectForKey: name];
// If the NSPrinter object for the printer already exists, return it
if (printer)
return printer;
// Otherwise, try to find the information in the printerIndexDict
printerInfo = [printerIndexDict objectForKey: name];
// Make sure you can find the printer name in the dictionary
if (!printerInfo)
{
[NSException raise: NSGenericException
format: @"Could not find printer named %@", name];
// NOT REACHED
}
// Create it
path = getFile([printerInfo objectAtIndex:0], @"ppd");
// If not found
if (path == nil || [path length] == 0)
{
[NSException raise: NSGenericException
format: @"Could not find PPD file %@.ppd",
[printerInfo objectAtIndex:0]];
// NOT REACHED
}
printer = [(GSLPRPrinter*)[self alloc]
initWithPPD: [NSString stringWithContentsOfFile:path]
withName: name
withType: [printerInfo objectAtIndex:0]
withHost: [printerInfo objectAtIndex:1]
withNote: [printerInfo objectAtIndex:2]
fromFile: [printerInfo objectAtIndex:0]];
// Once created, set it in the dict for later use, this also retains it
[printerObjNameDict setObject: printer
forKey: name];
return [printer autorelease];
}
+ (NSArray *)printerNames
{
NSDebugMLLog(@"GSPrinting", @"");
if(!printerIndexDict)
[self loadPrinterIndexFile];
return [printerIndexDict allKeys];
}
//
// Instance methods
//
//
// Private Methods
//
//
// Allocate the printer name to PPD filename index dictionary
//
+ loadPrinterIndexFile
{
NSString *path;
NSDebugMLLog(@"GSPrinting", @"");
printerObjNameDict = [NSMutableDictionary dictionary];
// Load the index file
path = [NSBundle pathForLibraryResource: NSPrinter_INDEXFILE
ofType: nil
inDirectory: @"PostScript"];
// If not found
if (path == nil || [path length] == 0)
{
NSLog(@"Could not find index of printers, file %@", NSPrinter_INDEXFILE);
printerIndexDict = [NSDictionary dictionaryWithObject:
[NSArray arrayWithObjects: @"Apple_LaserWriter_II_NTX",
@"localhost", @"A Note", nil]
forKey: @"Unknown"];
}
else
{
printerIndexDict = [NSDictionary dictionaryWithContentsOfFile:path];
}
RETAIN(printerObjNameDict);
RETAIN(printerIndexDict);
return self;
}
//
// Initialisation method
//
// To keep loading of PPDs relatively fast, not much checking is done on it.
-(id)initWithPPD:(NSString *)PPDstring
withName:(NSString *)name
withType:(NSString *)type
withHost:(NSString *)host
withNote:(NSString *)note
fromFile:(NSString *)file
{
NSAutoreleasePool *subpool;
NSEnumerator *objEnum;
NSMutableArray *valArray;
self = [super initWithName: name
withType: type
withHost: host
withNote: note];
NSDebugMLLog(@"GSPrinting", @"");
// Create a temporary autorelease pool, as many temporary objects are used
subpool = [[NSAutoreleasePool alloc] init];
// Create character sets used during scanning
newlineSet = [NSCharacterSet characterSetWithCharactersInString:@"\n\r"];
keyEndSet = [NSCharacterSet characterSetWithCharactersInString:@"\n\r\t: "];
optKeyEndSet = [NSCharacterSet characterSetWithCharactersInString:@"\n\r:/"];
valueEndSet = [NSCharacterSet characterSetWithCharactersInString:@"\n\r/"];
// Allowed repeated keys, used during scanning.
repKeys = [NSArray arrayWithObjects:@"Emulators",
@"Extensions",
@"FaxSupport",
//@"Include", (handled separately)
@"Message",
@"PrinterError",
@"Product",
@"Protocols",
@"PSVersion",
@"Source",
@"Status",
//@"UIConstraints", (handled separately)
// Even though this is not mentioned in the list of repeated keywords,
// it's often repeated anyway, so I'm putting it here.
@"InkName",
nil];
// Set the file name to use
PPDFileName = file;
// NB: There are some structure keywords (such as OpenUI/CloseUI) that may
// be repeated, but as yet are not used. Since they are structure keywords,
// they'll probably need special processing anyway, and so aren't
// added to this list.
// Create dictionary for temporary storage of symbol values
PPDSymbolValues = [NSMutableDictionary dictionary];
// And scan the PPD itself
[self loadPPD:PPDstring inclusionNum:0];
// Search the PPD dictionary for symbolvalues, and substitute them.
objEnum = [_PPD objectEnumerator];
while ((valArray = [objEnum nextObject]))
{
NSString *oldValue;
NSString *newValue;
int i, max;
max = [valArray count];
for(i=0 ; i < max ; i++ )
{
oldValue = [valArray objectAtIndex:i];
if ([oldValue isKindOfClass:[NSString class]]
&& ![oldValue isEqual:@""]
&& [[oldValue substringToIndex:1] isEqual:@"^"])
{
newValue = [PPDSymbolValues
objectForKey:[oldValue substringFromIndex:1]];
if (!newValue)
{
[NSException raise: NSPPDParseException
format:@"Unknown symbol value, ^%@ in PPD file %@.ppd",
oldValue, PPDFileName];
// NOT REACHED
}
[valArray replaceObjectAtIndex:i withObject:newValue];
}
}
}
#if 0
// DISABLED: Though the following keywords *should* be present, there seems
// to be few problems is they are omitted. Many of the .ppd files I have
// don't have *LanguageEncoding, for example.
// Make sure all the required keys are present
objEnum = [[NSArray arrayWithObjects:@"NickName",
@"ModelName",
@"PCFileName",
@"Product",
@"PSVersion",
@"FileVersion",
@"FormatVersion",
@"LanguageEncoding",
@"LanguageVersion",
@"PageSize",
@"PageRegion",
@"ImageableArea",
@"PaperDimension",
@"PPD-Adobe",
nil] objectEnumerator];
while (checkVal = [objEnum nextObject])
{
if (![self isKey:checkVal inTable:@"PPD"])
{
[NSException raise:NSPPDParseException
format:@"Required keyword *%@ not found in PPD file %@.ppd",
checkVal, PPDFileName];
// NOT REACHED
}
}
#endif
// Release the local autoreleasePool
RELEASE(subpool);
return self;
}
- loadPPD:(NSString *)PPDstring
inclusionNum:(int)includeNum
{
NSScanner *PPDdata;
NSString *keyword;
// Set up the scanner - Appending a newline means that it should be
// able to process the last line correctly
PPDdata = [NSScanner scannerWithString:
[PPDstring stringByAppendingString:@"\n"]];
[PPDdata setCharactersToBeSkipped:[NSCharacterSet whitespaceCharacterSet]];
// Main processing starts here...
while (1) // Check it is not at end only after skipping the blanks
{
// Get to the start of a new keyword, skipping blank lines
skipSpace(PPDdata);
if ([PPDdata isAtEnd])
break;
// All new entries should starts '*'
if (![PPDdata scanString:@"*" intoString:NULL])
{
[NSException raise:NSPPDParseException
format:@"Line not starting * in PPD file %@.ppd",
PPDFileName];
// NOT REACHED
}
// Skip lines starting '*%', '*End', '*SymbolLength', or '*SymbolEnd'
if ([PPDdata scanString:@"%" intoString:NULL]
|| [PPDdata scanString:@"End" intoString:NULL]
|| [PPDdata scanString:@"SymbolLength" intoString:NULL]
|| [PPDdata scanString:@"SymbolEnd" intoString:NULL])
{
[PPDdata scanUpToCharactersFromSet:newlineSet intoString:NULL];
continue;
}
// Read main keyword, up to a colon, space or newline
[PPDdata scanUpToCharactersFromSet:keyEndSet intoString:&keyword];
// Loop if there is no value section
if ([PPDdata scanCharactersFromSet:newlineSet intoString:NULL])
continue;
// Add the line to the relevant table
if ([keyword isEqual:@"OrderDependency"])
{
[self addPPDOrderDependency:PPDdata];
}
else if ([keyword isEqual:@"UIConstraints"])
{
[self addPPDUIConstraint:PPDdata];
}
else if ([keyword isEqual:@"Include"])
{
NSString *fileName;
NSString *path;
[PPDdata scanString:@":"
intoString:NULL];
// Find the filename between two "s"
[PPDdata scanString:@"\""
intoString:NULL];
[PPDdata scanUpToString:@"\""
intoString:&fileName];
[PPDdata scanString:@"\""
intoString:NULL];
// Load the file
path = getFile(fileName, nil);
// If not found
if (path == nil || [path length] == 0)
{
[NSException raise:NSPPDIncludeNotFoundException
format:@"Could not find included PPD file %@",
fileName];
// NOT REACHED
}
includeNum++;
if (includeNum > MAX_PPD_INCLUDES)
{
[NSException raise:NSPPDIncludeStackOverflowException
format:@"Too many *Includes in PPD"];
// NOT REACHED
}
[self loadPPD:[NSString stringWithContentsOfFile:path]
inclusionNum:includeNum];
}
else if ([keyword isEqual:@"SymbolValue"])
{
NSString *symbolName;
NSString *symbolVal;
if (![PPDdata scanString:@"^" intoString:NULL])
{
[NSException raise:NSPPDParseException
format:@"Badly formatted *SymbolValue in PPD file %@.ppd",
PPDFileName];
// NOT REACHED
}
[PPDdata scanUpToString:@":"
intoString:&symbolName];
[PPDdata scanString:@":"
intoString:NULL];
[PPDdata scanString:@"\""
intoString:NULL];
[PPDdata scanUpToString:@"\""
intoString:&symbolVal];
if (!symbolVal)
symbolVal = @"";
[PPDdata scanString:@"\""
intoString:NULL];
[PPDSymbolValues setObject:symbolVal
forKey:symbolName];
}
else
{
[self addPPDKeyword:keyword
withScanner:PPDdata];
}
}
return self;
}
- addPPDKeyword:(NSString *)mainKeyword
withScanner:(NSScanner *)PPDdata
{
NSString *optionKeyword = nil;
NSString *optionTranslation = nil;
NSString *value = nil;
NSString *valueTranslation = nil;
// Scan off any optionKeyword
[PPDdata scanUpToCharactersFromSet:optKeyEndSet intoString:&optionKeyword];
if ([PPDdata scanCharactersFromSet:newlineSet intoString:NULL])
{
[NSException raise:NSPPDParseException
format:@"Keyword has optional keyword but no value in PPD file %@.ppd",
PPDFileName];
// NOT REACHED
}
if ([PPDdata scanString:@"/" intoString:NULL])
{
// Option keyword translation exists - scan it
[PPDdata scanUpToString:@":" intoString:&optionTranslation];
}
[PPDdata scanString:@":" intoString:NULL];
// Read the value part
// Values starting with a " are read until the second ", ignoring \n etc.
if ([PPDdata scanString:@"\"" intoString:NULL])
{
[PPDdata scanUpToString:@"\""
intoString:&value];
if (!value)
value = @"";
[PPDdata scanString:@"\""
intoString:NULL];
// It is a QuotedValue if it's in quotes, and there is no option
// key, or the main key is a *JCL keyword
if (!optionKeyword || [[mainKeyword substringToIndex:3]
isEqualToString:@"JCL"])
{
value = interpretQuotedValue(value);
}
}
else
{
// Otherwise, scan up to the end of line or '/'
[PPDdata scanUpToCharactersFromSet:valueEndSet
intoString:&value];
}
// If there is a value translation, scan it
if ([PPDdata scanString:@"/" intoString:NULL])
{
[PPDdata scanUpToCharactersFromSet:newlineSet
intoString:&valueTranslation];
}
// The translations also have to have any hex substrings interpreted
if (optionTranslation)
optionTranslation = interpretQuotedValue(optionTranslation);
if (valueTranslation)
valueTranslation = interpretQuotedValue(valueTranslation);
// The keyword (or keyword/option pair, if there's a option), should only
// only have one value, unless it's one of the optionless keywords which
// allow multiple instances.
// If a keyword is read twice, 'first instance is correct', according to
// the standard.
// Finally, add the strings to the tables
if (optionKeyword)
{
NSString *mainAndOptionKeyword=[mainKeyword
stringByAppendingFormat:@"/%@",
optionKeyword];
if ([self isKey:mainAndOptionKeyword inTable:@"PPD"])
return self;
[self addValue:value
andValueTranslation:valueTranslation
andOptionTranslation:optionTranslation
forKey:mainAndOptionKeyword];
// Deal with the oddities of stringForKey:inTable:
// If this method is used to find a keyword with options, using
// just the keyword it should return an empty string
// stringListForKey:inTable:, however, should return the list of
// option keywords.
// This is done by making the first item in the array an empty
// string, which will be skipped by stringListForKey:, if necessary
if (![_PPD objectForKey:mainKeyword])
{
[self addString:@""
forKey:mainKeyword
inTable:_PPD];
[self addString:@""
forKey:mainKeyword
inTable:_PPDOptionTranslation];
[self addString:@""
forKey:mainKeyword
inTable:_PPDArgumentTranslation];
}
[self addValue:optionKeyword
andValueTranslation:optionKeyword
andOptionTranslation:optionKeyword
forKey:mainKeyword];
}
else
{
if ([self isKey:mainKeyword inTable:@"PPD"] &&
![repKeys containsObject:mainKeyword])
{
return self;
}
[self addValue:value
andValueTranslation:valueTranslation
andOptionTranslation:optionTranslation
forKey:mainKeyword];
}
return self;
}
- addPPDUIConstraint:(NSScanner *)constraint
{
NSString *mainKey1 = nil;
NSString *optionKey1 = nil;
NSString *mainKey2 = nil;
NSString *optionKey2 = nil;
// UIConstraint should have no option keyword
if (![constraint scanString:@":" intoString:NULL])
{
[NSException raise:NSPPDParseException
format:@"UIConstraints has option keyword in PPDFileName %@.ppd",
PPDFileName];
// NOT REACHED
}
// Skip the '*'
[constraint scanString:@"*"
intoString:NULL];
// Scan the bits. Stuff not starting with * must be an optionKeyword
[constraint scanUpToCharactersFromSet:[NSCharacterSet whitespaceCharacterSet]
intoString:&mainKey1];
if (![constraint scanString:@"*" intoString:NULL])
{
[constraint scanUpToCharactersFromSet:
[NSCharacterSet whitespaceCharacterSet]
intoString:&optionKey1];
[constraint scanString:@"*"
intoString:NULL];
}
[constraint scanUpToCharactersFromSet:
[NSCharacterSet whitespaceAndNewlineCharacterSet]
intoString:&mainKey2];
if (![constraint scanCharactersFromSet:newlineSet intoString:NULL])
{
[constraint scanUpToCharactersFromSet:
[NSCharacterSet whitespaceAndNewlineCharacterSet]
intoString:&optionKey2];
}
else
{
optionKey2 = @"";
}
// Add to table
if (optionKey1)
mainKey1 = [mainKey1 stringByAppendingFormat:@"/%@", optionKey1];
[self addString:mainKey2
forKey:mainKey1
inTable:_PPDUIConstraints];
[self addString:optionKey2
forKey:mainKey1
inTable:_PPDUIConstraints];
return self;
}
- addPPDOrderDependency:(NSScanner *)dependency
{
NSString *realValue = nil;
NSString *section = nil;
NSString *keyword = nil;
NSString *optionKeyword = nil;
// Order dependency should have no option keyword
if (![dependency scanString:@":" intoString:NULL])
{
[NSException raise:NSPPDParseException
format:@"OrderDependency has option keyword in PPD file %@.ppd",
PPDFileName];
// NOT REACHED
}
[dependency scanUpToCharactersFromSet:[NSCharacterSet whitespaceCharacterSet]
intoString:&realValue];
[dependency scanUpToCharactersFromSet:[NSCharacterSet whitespaceCharacterSet]
intoString:&section];
[dependency scanString:@"*"
intoString:NULL];
[dependency scanUpToCharactersFromSet:
[NSCharacterSet whitespaceAndNewlineCharacterSet]
intoString:&keyword];
if (![dependency scanCharactersFromSet:newlineSet intoString:NULL])
{
// Optional keyword exists
[dependency scanUpToCharactersFromSet:
[NSCharacterSet whitespaceAndNewlineCharacterSet]
intoString:&optionKeyword];
}
// Go to next line of PPD file
[dependency scanCharactersFromSet:newlineSet
intoString:NULL];
// Add to table
if (optionKeyword)
keyword = [keyword stringByAppendingFormat:@"/%s", optionKeyword];
[self addString:realValue
forKey:keyword
inTable:_PPDOrderDependency];
[self addString:section
forKey:keyword
inTable:_PPDOrderDependency];
return self;
}
-(id) initWithCoder: (NSCoder*) coder
{
self = [super initWithCoder: coder];
return self;
}
-(void) encodeWithCoder: (NSCoder*) coder
{
[super encodeWithCoder: coder];
}
@end

View file

@ -191,7 +191,12 @@ GSTitleView.m \
GSToolbar.m \
GSToolbarView.m \
GSStandardWindowDecorationView.m \
GSWindowDecorationView.m
GSWindowDecorationView.m \
GSPrinting.m \
GSPrintOperation.m \
GSEPSPrintOperation.m \
GSPDFPrintOperation.m
# Turn off NSMenuItem warning that NSMenuItem conforms to <NSObject>,
# but does not implement <NSObject>'s methods itself (it inherits
@ -363,7 +368,11 @@ GSToolbar.h \
GSToolbarView.h \
GSNibCompatibility.h \
GSDragView.h \
GSTitleView.h
GSTitleView.h \
GSPrinting.h \
GSPrintOperation.h \
GSEPSPrintOperation.h \
GSPDFPrintOperation.h
libgnustep-gui_HEADER_FILES = ${GUI_HEADERS}

View file

@ -0,0 +1,151 @@
/*
GSEPSPrintOperation.m
Controls operations generating EPS output files.
Copyright (C) 1996, 2004 Free Software Foundation, Inc.
Author: Scott Christley <scottc@net-community.com>
Date: 1996
Author: Fred Kiefer <FredKiefer@gmx.de>
Date: November 2000
Started implementation.
Author: Chad Hardin <cehardin@mac.com>
Date: June 2004
Modified for printing backend support, split off from NSPrintOperation.m
This file is part of the GNUstep GUI Library.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; see the file COPYING.LIB.
If not, write to the Free Software Foundation,
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
#include <Foundation/NSDebug.h>
#include <Foundation/NSData.h>
#include <Foundation/NSPathUtilities.h>
#include <Foundation/NSTask.h>
#include <Foundation/NSValue.h>
#include <Foundation/NSProcessInfo.h>
#include "AppKit/NSView.h"
#include "AppKit/NSPrintInfo.h"
#include "AppKit/NSPrintOperation.h"
#include "GNUstepGUI/GSEPSPrintOperation.h"
/**
<unit>
<heading>Class Description</heading>
<p>
GSEPSPrintOperation is a subclass of NSPrintOperation
that can create eps files suitable for saving, previewing, etc.
</p>
</unit>
*/
@implementation GSEPSPrintOperation
- (id)initWithView:(NSView *)aView
insideRect:(NSRect)rect
toData:(NSMutableData *)data
printInfo:(NSPrintInfo *)aPrintInfo
{
self = [super initWithView: aView
insideRect: rect
toData: data
printInfo: aPrintInfo];
_path = [NSTemporaryDirectory() stringByAppendingPathComponent: @"GSPrint-"];
_path = [_path stringByAppendingString:
[[NSProcessInfo processInfo] globallyUniqueString]];
_path = [_path stringByAppendingPathExtension: @"ps"];
RETAIN( _path );
return self;
}
- (id) initWithView:(NSView *)aView
insideRect:(NSRect)rect
toPath:(NSString *)path
printInfo:(NSPrintInfo *)aPrintInfo
{
NSMutableData *data = [NSMutableData data];
self = [super initWithView: aView
insideRect: rect
toData: data
printInfo: aPrintInfo];
ASSIGN(_path, path);
return self;
}
- (void) _print
{
/* Save this for the view to look at. Seems like there should
be a better way to pass it to beginDocument */
[[_printInfo dictionary] setObject: [NSValue valueWithRect: _rect]
forKey: @"NSPrintSheetBounds"];
[_view beginDocument];
[_view beginPageInRect: _rect
atPlacement: NSMakePoint(0,0)];
[_view displayRectIgnoringOpacity: _rect];
[_view endDocument];
}
- (BOOL)isEPSOperation
{
return YES;
}
- (BOOL)deliverResult
{
if (_data != nil && _path != nil)
{
NSString *eps;
eps = [NSString stringWithContentsOfFile: _path];
[_data setData: [eps dataUsingEncoding:NSASCIIStringEncoding]];
}
return YES;
}
- (NSGraphicsContext*)createContext
{
NSMutableDictionary *info;
if (_context)
return _context;
info = [_printInfo dictionary];
[info setObject: _path
forKey: @"NSOutputFile"];
[info setObject: NSGraphicsContextPSFormat
forKey: NSGraphicsContextRepresentationFormatAttributeName];
_context = RETAIN([NSGraphicsContext graphicsContextWithAttributes: info]);
return _context;
}
@end

View file

@ -0,0 +1,112 @@
/*
GSPDFPrintOperation.m
Controls operations generating PDF output files.
Copyright (C) 1996, 2004 Free Software Foundation, Inc.
Author: Scott Christley <scottc@net-community.com>
Date: 1996
Author: Fred Kiefer <FredKiefer@gmx.de>
Date: November 2000
Started implementation.
Author: Chad Hardin <cehardin@mac.com>
Date: June 2004
Modified for printing backend support, split off from NSPrintOperation.m
This file is part of the GNUstep GUI Library.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; see the file COPYING.LIB.
If not, write to the Free Software Foundation,
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
#include <Foundation/NSPathUtilities.h>
#include <Foundation/NSTask.h>
#include <Foundation/NSProcessInfo.h>
#include "AppKit/NSView.h"
#include "GNUstepGUI/GSPDFPrintOperation.h"
/**
<unit>
<heading>Class Description</heading>
<p>
GSPDFPrintOperation produces PDF files for saving, previewing, etc
</p>
</unit>
*/
@implementation GSPDFPrintOperation
- (id) initWithView:(NSView *)aView
insideRect:(NSRect)rect
toData:(NSMutableData *)data
printInfo:(NSPrintInfo*)aPrintInfo
{
self = [super initWithView: aView
insideRect: rect
toData: data
printInfo: aPrintInfo];
_path = [NSTemporaryDirectory() stringByAppendingPathComponent: @"GSPrint-"];
_path = [_path stringByAppendingString:
[[NSProcessInfo processInfo] globallyUniqueString]];
_path = [_path stringByAppendingPathExtension: @"pdf"];
RETAIN( _path );
return self;
}
- (id) initWithView:(NSView *)aView
insideRect:(NSRect)rect
toPath:(NSString *)path
printInfo:(NSPrintInfo*)aPrintInfo
{
NSMutableData *data = [NSMutableData data];
self = [super initWithView: aView
insideRect: rect
toData: data
printInfo: aPrintInfo];
ASSIGN(_path, path);
return self;
}
- (NSGraphicsContext*)createContext
{
// FIXME
return nil;
}
- (void) _print
{
[_view displayRectIgnoringOpacity: _rect];
}
- (BOOL)deliverResult
{
if (_data != nil && _path != nil && [_data length])
return [_data writeToFile: _path atomically: NO];
// FIXME Until we can create PDF we shoud convert the file with GhostScript
return YES;
}
@end

171
Source/GSPrintOperation.m Normal file
View file

@ -0,0 +1,171 @@
/*
GSPrintOperation.m
Controls operations generating print jobs.
Copyright (C) 1996,2004 Free Software Foundation, Inc.
Author: Scott Christley <scottc@net-community.com>
Date: 1996
Author: Fred Kiefer <FredKiefer@gmx.de>
Date: November 2000
Started implementation.
Author: Chad Hardin <cehardin@mac.com>
Date: June 2004
Modified for printing backend support, split off from NSPrintOperation.m
This file is part of the GNUstep GUI Library.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; see the file COPYING.LIB.
If not, write to the Free Software Foundation,
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
#include <Foundation/NSData.h>
#include <Foundation/NSTask.h>
#include <Foundation/NSUserDefaults.h>
#include "AppKit/NSView.h"
#include "AppKit/NSPrintPanel.h"
#include "AppKit/NSPrintInfo.h"
#include "AppKit/NSWorkspace.h"
#include "GNUstepGUI/GSPrinting.h"
#include "GNUstepGUI/GSPrintOperation.h"
/**
<unit>
<heading>Class Description</heading>
<p>
GSPrintOperation is a generic class that should be subclasses
by printing backend classes for the purpose of controlling and
sending print jobs to a printing system.
</p>
</unit>
*/
@implementation GSPrintOperation
/** Load the appropriate bundle for the PrintInfo
(eg: GSLPRPrintInfo, GSCUPSPrintInfo).
*/
+ (id) allocWithZone: (NSZone*) zone
{
Class principalClass;
principalClass = [[GSPrinting printingBundle] principalClass];
if( principalClass == nil )
return nil;
return [[principalClass gsPrintOperationClass] allocWithZone: zone];
}
- (id)initWithView:(NSView *)aView
printInfo:(NSPrintInfo *)aPrintInfo
{
self = [self initWithView: aView
insideRect: [aView bounds]
toData: [NSMutableData data]
printInfo: aPrintInfo];
_showPanels = YES;
return self;
}
- (NSGraphicsContext*)createContext
{
[self subclassResponsibility: _cmd];
return nil;
}
/**
/ !!!Here is the method that will be overridden in the printer bundle
*/
- (BOOL) _deliverSpooledResult
{
[self subclassResponsibility: _cmd];
return NO;
}
- (BOOL) deliverResult
{
BOOL success;
NSString *job;
success = YES;
job = [_printInfo jobDisposition];
if ([job isEqual: NSPrintPreviewJob])
{
/* Check to see if there is a GNUstep app that can preview PS files.
It's not likely at this point, so also check for a standards
previewer, like gv.
*/
NSTask *task;
NSString *preview;
NSWorkspace *ws = [NSWorkspace sharedWorkspace];
[_printPanel _setStatusStringValue: @"Opening in previewer..."];
preview = [ws getBestAppInRole: @"Viewer"
forExtension: @"ps"];
if (preview)
{
[ws openFile: _path withApplication: preview];
}
else
{
NSUserDefaults *def = [NSUserDefaults standardUserDefaults];
preview = [def objectForKey: @"NSPreviewApp"];
if (preview == nil || [preview length] == 0)
preview = @"gv";
task = [NSTask new];
[task setLaunchPath: preview];
[task setArguments: [NSArray arrayWithObject: _path]];
[task launch];
AUTORELEASE(task);
}
}
else if ([job isEqual: NSPrintSpoolJob])
{
success = [self _deliverSpooledResult];
}
else if ([job isEqual: NSPrintFaxJob])
{
}
/* We can't remove the temp file because the previewer might still be
using it, perhaps the printer is also?
if ( _path )
{
[[NSFileManager defaultManager] removeFileAtPath: _path
handler: nil];
}
*/
return success;
}
@end

234
Source/GSPrinting.m Normal file
View file

@ -0,0 +1,234 @@
/** <title>GSPrinting.m</title>
<abstract>GSPrinting loads the proper bundle for the printing backend.</abstract>
Copyright (C) 2004 Free Software Foundation, Inc.
Author: Chad Elliott Hardin <cehardin@mac.com>
Date: June 2004
This file is part of the GNUstep GUI Library.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; see the file COPYING.LIB.
If not, write to the Free Software Foundation,
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
#include "GNUstepGUI/GSPrinting.h"
#include <Foundation/NSBundle.h>
#include <Foundation/NSEnumerator.h>
#include <Foundation/NSDebug.h>
#include <Foundation/NSPathUtilities.h>
#include <Foundation/NSArray.h>
#include <Foundation/NSFileManager.h>
#include <Foundation/NSUserDefaults.h>
#include "AppKit/NSPanel.h"
static NSBundle *printingBundle = nil;
/**
<unit>
<heading>Class Description</heading>
<p>
GSPrinting is used by all of the NSPrint and the NSPageLayout
class(es) so that a printing backend bundle can be loaded. It
first utilizes NSUserDefaults to find the user's preferred printing
backend bundle. It looks for the key GSPrinting. If the user's
preferred bundle cannot be loaded, it tries to load any working
printing bundle.
</p>
</unit>
*/
@implementation GSPrinting
+(NSBundle*) loadPrintingBundle: (NSString*) bundleName
{
NSString *path;
NSEnumerator *libraryPathsEnumerator;
bundleName = [bundleName stringByAppendingString: @".bundle"];
NSDebugLLog(@"GSPrinting", @"Looking for %@", bundleName);
libraryPathsEnumerator = [NSStandardLibraryPaths() objectEnumerator];
while( (path = [libraryPathsEnumerator nextObject]) )
{
path = [path stringByAppendingPathComponent: @"Bundles"];
path = [path stringByAppendingPathComponent: @"GSPrinting"];
path = [path stringByAppendingPathComponent: bundleName];
if ([[NSFileManager defaultManager] fileExistsAtPath: path])
{
NSBundle *bundle;
bundle = [NSBundle bundleWithPath: path];
if( [bundle load] == NO )
{
NSDebugLLog(@"GSPrinting", @"Error loading printing bundle at %@", path);
return nil;
}
else
{
//one last check to make sure the principle class can be loaded
if( [bundle principalClass] == Nil)
{
NSDebugLLog(@"GSPrinting", @"Error loading principal class from printing bundle at %@", path);
return nil;
}
//if we get here, finally, then everything should be ok, barring errors from later in loading resources.
NSDebugLLog(@"GSPrinting", @"Loaded printing bundle at %@", path);
return bundle;
}
}
}
NSDebugLLog(@"GSPrinting", @"Unable to find printing bundle %@", bundleName);
return nil;
}
+(NSBundle*) loadAnyWorkingPrintingBundle
{
NSBundle *bundle;
if( (bundle = [GSPrinting loadPrintingBundle: @"GSCUPS"]) )
return bundle;
if( (bundle = [GSPrinting loadPrintingBundle: @"GSLPR"]) )
return bundle;
if( (bundle = [GSPrinting loadPrintingBundle: @"GSWin32"]) )
return bundle;
return nil;
}
+ (NSBundle*) printingBundle
{
NSString *defaultBundleName;
NSBundle *bundle;
if( printingBundle )
{
return printingBundle;
}
NSDebugLLog(@"GSPrinting", @"Bundle has not been loaded. Loading in progress...");
defaultBundleName = [[NSUserDefaults standardUserDefaults] stringForKey: @"GSPrinting"];
/*Which Printing Bundle?*/
if( defaultBundleName == nil )
{
NSDebugLLog(@"GSPrinting", @"User did not set a printing bundle, trying till something works");
bundle = [GSPrinting loadAnyWorkingPrintingBundle];
if( bundle == nil )
{
NSDebugLLog(@"GSPrinting", @"Could not load any working printing bundle");
NSRunAlertPanel(@"GNUstep Printing Backend System", @"Could not open any working printing bundle. Printing will not work.", @"Ok", NULL, NULL );
return nil;
}
}
else
{
NSDebugLLog(@"GSPrinting", @"User set %@ as the printing bundle", defaultBundleName);
bundle = [GSPrinting loadPrintingBundle: defaultBundleName];
if( bundle == nil )
{
NSDebugLLog(@"GSPrinting", @"User set %@ as the printing bundle but that did not work. Will try to find anything that will work", defaultBundleName);
bundle = [GSPrinting loadAnyWorkingPrintingBundle];
if( bundle == nil )
{
NSDebugLLog(@"GSPrinting", @"Could not load any working printing bundle");
NSRunAlertPanel(@"GNUstep Printing Backend System", @"Could not open any working printing bundle. Printing will not work.", @"Ok", NULL, NULL );
return nil;
}
else
{
NSString *msg;
msg = [NSString stringWithFormat: @"Your chosen printing bundle, %@, could not be loaded. %@ was loaded instead", defaultBundleName, [[bundle bundlePath] lastPathComponent]];
NSRunAlertPanel(@"GNUstep Printing Backend System", msg, @"Ok", NULL, NULL );
}
}
}
printingBundle = bundle;
[printingBundle retain];
return printingBundle;
}
@end
/**
<unit>
<heading>Class Description</heading>
<p>
GSPrintingPrincipleClass is the base class that all
Printing backend bundles should use as their principle
class. Subclasses are responsible for the allocating
of that bundle's particular NSPrint, NSPageLayout, and
GSPrintOperation sublclassed objects.
</p>
</unit>
*/
@implementation GSPrintingPrincipalClass : NSObject
{
}
+(Class) pageLayoutClass
{
return Nil;
}
+(Class) printInfoClass
{
return Nil;
}
+(Class) printOperationClass
{
return Nil;
}
+(Class) printPanelClass
{
return Nil;
}
+(Class) printerClass
{
return Nil;
}
+(Class) gsPrintOperationClass
{
return Nil;
}
@end

View file

@ -2,10 +2,13 @@
<abstract>Standard panel for querying user about page layout.</abstract>
Copyright (C) 2001 Free Software Foundation, Inc.
Copyright (C) 2001,2004 Free Software Foundation, Inc.
Written By: Adam Fedor <fedor@gnu.org>
Date: Oct 2001
Modified for Printing Backend Support
Author: Chad Hardin <cehardin@mac.com>
Date: June 2004
This file is part of the GNUstep GUI Library.
@ -43,6 +46,7 @@
#include "AppKit/NSPageLayout.h"
#include "AppKit/NSPrinter.h"
#include "GSGuiPrivate.h"
#include "GNUstepGUI/GSPrinting.h"
static NSPageLayout *shared_instance;
@ -82,6 +86,22 @@ static NSPageLayout *shared_instance;
//
// Class methods
//
/** Load the appropriate bundle for the PageLayout
(eg: GSLPRPageLayout, GSCUPSPageLayout).
*/
+ (id) allocWithZone: (NSZone*) zone
{
Class principalClass;
principalClass = [[GSPrinting printingBundle] principalClass];
if( principalClass == nil )
return nil;
return [[principalClass pageLayoutClass] allocWithZone: zone];
}
/** Creates and returns a shared instance of the NSPageLayout panel.
*/
+ (NSPageLayout *)pageLayout
@ -403,7 +423,7 @@ static NSPageLayout *shared_instance;
- (void)pickedButton:(id)sender
{
NSLog(@"[NSPageLayout -pickedButton:] method depreciated");
[self pickedButton: sender];
//[self pickedButton: sender];
}
/** This method has been depreciated. It doesn't do anything useful.

View file

@ -3,10 +3,13 @@
Stores information used in printing
Copyright (C) 1996,1997 Free Software Foundation, Inc.
Copyright (C) 1996,1997,2004 Free Software Foundation, Inc.
Author: Simon Frankau <sgf@frankau.demon.co.uk>
Date: July 1997
Modified for Printing Backend Support
Author: Chad Hardin <cehardin@mac.com>
Date: June 2004
This file is part of the GNUstep GUI Library.
@ -35,8 +38,8 @@
#include <Foundation/NSUserDefaults.h>
#include <Foundation/NSValue.h>
#include "AppKit/NSPrinter.h"
#include "AppKit/NSPrintInfo.h"
#include "GNUstepGUI/GSPrinting.h"
#define NSNUMBER(val) [NSNumber numberWithInt: val]
#define DICTSET(dict, obj, key) \
@ -45,12 +48,8 @@
// FIXME: retain/release of dictionary with retain/release of printInfo?
// Class variables:
static NSPrintInfo *sharedPrintInfoObject = nil;
static NSMutableDictionary *printInfoDefaults = nil;
static NSPrintInfo *sharedPrintInfo = nil;
@interface NSPrintInfo (private)
+ initPrintInfoDefaults;
@end
/**
<unit>
@ -76,24 +75,36 @@ static NSMutableDictionary *printInfoDefaults = nil;
}
}
/** Load the appropriate bundle for the PrintInfo
(eg: GSLPRPrintInfo, GSCUPSPrintInfo).
*/
+ (id) allocWithZone: (NSZone*) zone
{
Class principalClass;
principalClass = [[GSPrinting printingBundle] principalClass];
if( principalClass == nil )
return nil;
return [[principalClass printInfoClass] allocWithZone: zone];
}
//
// Managing the Shared NSPrintInfo Object
//
+ (void)setSharedPrintInfo:(NSPrintInfo *)printInfo
{
sharedPrintInfoObject = printInfo;
ASSIGN(sharedPrintInfo, printInfo);
}
+ (NSPrintInfo *)sharedPrintInfo
{
if (!sharedPrintInfoObject)
{
if (!printInfoDefaults)
[NSPrintInfo initPrintInfoDefaults];
sharedPrintInfoObject = [[self alloc]
initWithDictionary:printInfoDefaults];
}
return sharedPrintInfoObject;
if (!sharedPrintInfo)
{
sharedPrintInfo = [[NSPrintInfo alloc] initWithDictionary: nil];
}
return sharedPrintInfo;
}
//
@ -109,16 +120,26 @@ static NSMutableDictionary *printInfoDefaults = nil;
//
+ (NSPrinter *)defaultPrinter
{
if (!printInfoDefaults)
[NSPrintInfo initPrintInfoDefaults];
return [printInfoDefaults objectForKey:NSPrintPrinter];
Class principalClass;
principalClass = [[GSPrinting printingBundle] principalClass];
if( principalClass == nil )
return nil;
return [[principalClass printInfoClass] defaultPrinter];
}
+ (void)setDefaultPrinter:(NSPrinter *)printer
{
if (!printInfoDefaults)
[NSPrintInfo initPrintInfoDefaults];
[printInfoDefaults setObject:printer forKey:NSPrintPrinter];
Class principalClass;
principalClass = [[GSPrinting printingBundle] principalClass];
if( principalClass == nil )
return;
[[principalClass printInfoClass] setDefaultPrinter: printer];
}
//
@ -130,7 +151,40 @@ static NSMutableDictionary *printInfoDefaults = nil;
- (id)initWithDictionary:(NSDictionary *)aDict
{
[super init];
_info = [[NSMutableDictionary alloc] initWithDictionary:aDict];
_info = [[NSMutableDictionary alloc] init];
//put in the defaults
[self setVerticalPagination: NSAutoPagination];
[self setHorizontalPagination: NSClipPagination];
[self setJobDisposition: NSPrintSpoolJob];
[self setHorizontallyCentered: YES];
[self setVerticallyCentered: YES];
[self setOrientation: NSPortraitOrientation];
if( aDict != nil )
{
[_info addEntriesFromDictionary: aDict];
if([[_info objectForKey: NSPrintPrinter] isKindOfClass: [NSString class]])
{
NSString *printerName;
NSPrinter *printer;
printerName = [_info objectForKey: NSPrintPrinter];
printer = [NSPrinter printerWithName: printerName];
if( printer )
[self setPrinter: printer];
else
[_info removeObjectForKey: NSPrintPrinter];
}
}
return self;
}
@ -330,20 +384,7 @@ static NSMutableDictionary *printInfoDefaults = nil;
- (void)setUpPrintOperationDefaultValues
{
NSEnumerator *keys, *objects;
NSString *key;
id object;
if (!printInfoDefaults)
[NSPrintInfo initPrintInfoDefaults];
keys = [printInfoDefaults keyEnumerator];
objects = [printInfoDefaults objectEnumerator];
while ((key = [keys nextObject]))
{
object = [objects nextObject];
if (![_info objectForKey:key])
[_info setObject:object forKey:key];
}
[self subclassResponsibility: _cmd];
}
//
@ -359,73 +400,34 @@ static NSMutableDictionary *printInfoDefaults = nil;
//
- (void) encodeWithCoder: (NSCoder*)aCoder
{
//There is a NSPrinter in the dict, will that work as a Property list?
NSMutableDictionary *dict;
dict = AUTORELEASE([_info mutableCopy]);
[dict setObject: [[self printer] name]
forKey: NSPrintPrinter];
[aCoder encodePropertyList: _info];
}
- (id) initWithCoder: (NSCoder*)aDecoder
{
NSString *printerName;
NSPrinter *printer;
_info = RETAIN([aDecoder decodePropertyList]);
return self;
}
//
// Private method to initialise printing defaults dictionary
//
+ initPrintInfoDefaults
{
NSUserDefaults *def;
NSString *defPrinter, *str;
NSPrinter *printer = nil;
def = [NSUserDefaults standardUserDefaults];
printInfoDefaults = [def objectForKey: @"DefaultPrinter"];
if (printInfoDefaults)
printInfoDefaults = [printInfoDefaults mutableCopy];
defPrinter = [printInfoDefaults objectForKey:NSPrintPrinter];
if (defPrinter)
printer = [NSPrinter printerWithName: defPrinter];
if (printer == nil)
defPrinter = nil;
if (printInfoDefaults == nil)
{
NSDebugLog(@"NSPrinter", @"Could not find printing defaults table");
printInfoDefaults = RETAIN([NSMutableDictionary dictionary]);
}
if (defPrinter == nil)
{
defPrinter = [[NSPrinter printerNames] objectAtIndex: 0];
DICTSET(printInfoDefaults, defPrinter, NSPrintPrinter);
}
/* Replace the printer name with a real NSPrinter object */
printer = [NSPrinter printerWithName: defPrinter];
DICTSET(printInfoDefaults, [NSPrinter printerWithName: defPrinter], NSPrintPrinter);
/* Set up other defaults from the printer object */
str = [printer stringForKey:@"DefaultPageSize" inTable: @"PPD"];
/* FIXME: Need to check for AutoSelect and probably a million other things... */
if (str == nil)
str = @"A4";
DICTSET(printInfoDefaults, str, NSPrintPaperName);
DICTSET(printInfoDefaults,
[NSValue valueWithSize: [NSPrintInfo sizeForPaperName: str]],
NSPrintPaperSize);
/* Set default margins. FIXME: Probably should check ImageableArea */
DICTSET(printInfoDefaults, NSNUMBER(36), NSPrintRightMargin);
DICTSET(printInfoDefaults, NSNUMBER(36), NSPrintLeftMargin);
DICTSET(printInfoDefaults, NSNUMBER(72), NSPrintTopMargin);
DICTSET(printInfoDefaults, NSNUMBER(72), NSPrintBottomMargin);
DICTSET(printInfoDefaults, NSNUMBER(NSPortraitOrientation),
NSPrintOrientation);
//DICTSET(printInfoDefaults, NSNUMBER(NSClipPagination),
// NSPrintHorizontalPagination);
DICTSET(printInfoDefaults, NSNUMBER(NSAutoPagination),
NSPrintVerticalPagination);
DICTSET(printInfoDefaults, NSNUMBER(1), NSPrintHorizontallyCentered);
DICTSET(printInfoDefaults, NSNUMBER(1), NSPrintVerticallyCentered);
printerName = [_info objectForKey: NSPrintPrinter];
printer = [NSPrinter printerWithName: printerName];
if( printer )
[self setPrinter: printer];
else
[_info removeObjectForKey: NSPrintPrinter];
return self;
}
@end

View file

@ -1,15 +1,18 @@
/*
NSPrintOperation.m
Controls operations generating EPS, PDF or PS print jobs.
Controls operations generating print jobs.
Copyright (C) 1996 Free Software Foundation, Inc.
Copyright (C) 1996,2004 Free Software Foundation, Inc.
Author: Scott Christley <scottc@net-community.com>
Date: 1996
Author: Fred Kiefer <FredKiefer@gmx.de>
Date: November 2000
Started implementation.
Modified for Printing Backend Support
Author: Chad Hardin <cehardin@mac.com>
Date: June 2004
This file is part of the GNUstep GUI Library.
@ -52,6 +55,9 @@
#include "AppKit/NSPrintOperation.h"
#include "AppKit/NSWorkspace.h"
#include "AppKit/PSOperators.h"
#include "GNUstepGUI/GSEPSPrintOperation.h"
#include "GNUstepGUI/GSPDFPrintOperation.h"
#include "GNUstepGUI/GSPrintOperation.h"
#define NSNUMBER(a) [NSNumber numberWithInt: (a)]
#define NSFNUMBER(a) [NSNumber numberWithFloat: (a)]
@ -75,20 +81,27 @@ typedef struct _page_info_t {
int pageDirection; /* NSPrintPageDirection */
} page_info_t;
@interface NSPrintOperation (Private)
- (id) initWithView:(NSView *)aView
insideRect:(NSRect)rect
toData:(NSMutableData *)data
printInfo:(NSPrintInfo *)aPrintInfo;
@interface NSPrintOperation (TrulyPrivate)
- (BOOL) _runOperation;
- (void) _setupPrintInfo;
- (void)_printOperationDidRun:(NSPrintOperation *)printOperation
success:(BOOL)success
contextInfo:(void *)contextInfo;
- (void) _printPaginateWithInfo: (page_info_t *)info
knowsRange: (BOOL)knowsRange;
- (NSRect) _rectForPage: (int)page info: (page_info_t *)info
xpage: (int *)xptr
ypage: (int *)yptr;
- (NSRect) _adjustPagesFirst: (int)first
last: (int)last
info: (page_info_t *)info;
- (void) _print;
@end
@interface NSPrintPanel (Private)
- (void) _setStatusStringValue: (NSString *)string;
@end
@interface NSView (NSPrintOperation)
@ -102,40 +115,7 @@ typedef struct _page_info_t {
- (void) _cleanupPrinting;
@end
// Subclass for the regular printing
@interface GSPrintOperation: NSPrintOperation
{
}
@end
// subclass for EPS output
@interface GSEPSPrintOperation: NSPrintOperation
{
}
- (id) initEPSOperationWithView:(NSView *)aView
insideRect:(NSRect)rect
toPath:(NSString *)path
printInfo:(NSPrintInfo *)aPrintInfo;
@end
// subclass for PDF output
@interface GSPDFPrintOperation: NSPrintOperation
{
}
- (id) initPDFOperationWithView:(NSView *)aView
insideRect:(NSRect)rect
toData:(NSMutableData *)data
printInfo:(NSPrintInfo*)aPrintInfo;
- (id) initPDFOperationWithView:(NSView *)aView
insideRect:(NSRect)rect
toPath:(NSString *)path
printInfo:(NSPrintInfo*)aPrintInfo;
@end
static NSString *NSPrintOperationThreadKey = @"NSPrintOperationThreadKey";
@ -186,7 +166,7 @@ static NSString *NSPrintOperationThreadKey = @"NSPrintOperationThreadKey";
toData:(NSMutableData *)data
printInfo:(NSPrintInfo *)aPrintInfo
{
return AUTORELEASE([[GSEPSPrintOperation alloc] initEPSOperationWithView: aView
return AUTORELEASE([[GSEPSPrintOperation alloc] initWithView: aView
insideRect: rect
toData: data
printInfo: aPrintInfo]);
@ -197,7 +177,7 @@ static NSString *NSPrintOperationThreadKey = @"NSPrintOperationThreadKey";
toPath:(NSString *)path
printInfo:(NSPrintInfo *)aPrintInfo
{
return AUTORELEASE([[GSEPSPrintOperation alloc] initEPSOperationWithView: aView
return AUTORELEASE([[GSEPSPrintOperation alloc] initWithView: aView
insideRect: rect
toPath: path
printInfo: aPrintInfo]);
@ -232,7 +212,7 @@ static NSString *NSPrintOperationThreadKey = @"NSPrintOperationThreadKey";
printInfo:(NSPrintInfo*)aPrintInfo
{
return AUTORELEASE([[GSPDFPrintOperation alloc]
initPDFOperationWithView: aView
initWithView: aView
insideRect: rect
toData: data
printInfo: aPrintInfo]);
@ -244,7 +224,7 @@ static NSString *NSPrintOperationThreadKey = @"NSPrintOperationThreadKey";
printInfo:(NSPrintInfo*)aPrintInfo
{
return AUTORELEASE([[GSPDFPrintOperation alloc]
initPDFOperationWithView: aView
initWithView: aView
insideRect: rect
toPath: path
printInfo: aPrintInfo]);
@ -293,7 +273,7 @@ static NSString *NSPrintOperationThreadKey = @"NSPrintOperationThreadKey";
{
RELEASE(self);
return [[GSEPSPrintOperation alloc] initEPSOperationWithView: aView
return [[GSEPSPrintOperation alloc] initWithView: aView
insideRect: rect
toData: data
printInfo: aPrintInfo];
@ -466,64 +446,6 @@ static NSString *NSPrintOperationThreadKey = @"NSPrintOperationThreadKey";
return NO;
}
/* Private method to run the printing operation. Needs to create an
autoreleaes pool to make sure the print context is destroyed before
returning (which closes the print file.) */
- (BOOL) _runOperation
{
BOOL result;
CREATE_AUTORELEASE_POOL(pool);
NSGraphicsContext *oldContext = [NSGraphicsContext currentContext];
[self createContext];
if (_context == nil)
return NO;
result = NO;
if (_pageOrder == NSUnknownPageOrder)
{
if ([[[_printInfo dictionary] objectForKey: NSPrintReversePageOrder]
boolValue] == YES)
_pageOrder = NSDescendingPageOrder;
else
_pageOrder = NSAscendingPageOrder;
}
[NSGraphicsContext setCurrentContext: _context];
NS_DURING
{
[self _print];
result = YES;
[NSGraphicsContext setCurrentContext: oldContext];
}
NS_HANDLER
{
[_view _cleanupPrinting];
[NSGraphicsContext setCurrentContext: oldContext];
NSRunAlertPanel(@"Error", @"Printing error: %@",
@"OK", NULL, NULL, localException);
}
NS_ENDHANDLER
[self destroyContext];
RELEASE(pool);
return result;
}
- (void) _setupPrintInfo
{
BOOL knowsPageRange;
NSRange viewPageRange;
NSMutableDictionary *dict = [_printInfo dictionary];
knowsPageRange = [_view knowsPageRange: &viewPageRange];
if (knowsPageRange == YES)
{
int first = viewPageRange.location;
int last = NSMaxRange(viewPageRange) - 1;
[dict setObject: NSNUMBER(first) forKey: NSPrintFirstPage];
[dict setObject: NSNUMBER(last) forKey: NSPrintLastPage];
}
}
/** Call this message to run the print operation on a view. This includes
(optionally) displaying a print panel and working with the NSView to
@ -560,31 +482,7 @@ static NSString *NSPrintOperationThreadKey = @"NSPrintOperationThreadKey";
return result;
}
- (void)_printOperationDidRun:(NSPrintOperation *)printOperation
success:(BOOL)success
contextInfo:(void *)contextInfo
{
id delegate;
SEL *didRunSelector;
NSMutableDictionary *dict;
void (*didRun)(id, SEL, BOOL, id);
if (success == YES)
{
NSPrintPanel *panel = [self printPanel];
[panel finalWritePrintInfo];
success = NO;
if ([self _runOperation])
success = [self deliverResult];
}
[self cleanUpOperation];
dict = [_printInfo dictionary];
didRunSelector = [[dict objectForKey: @"GSModalRunSelector"] pointerValue];
delegate = [dict objectForKey: @"GSModalRunDelegate"];
didRun = (void (*)(id, SEL, BOOL, id))[delegate methodForSelector:
*didRunSelector];
didRun (delegate, *didRunSelector, success, contextInfo);
}
/** Run a print operation modally with respect to a window.
*/
@ -659,8 +557,10 @@ static NSString *NSPrintOperationThreadKey = @"NSPrintOperationThreadKey";
printInfo:(NSPrintInfo *)aPrintInfo
{
if ([NSPrintOperation currentOperation] != nil)
[NSException raise: NSPrintOperationExistsException
format: @"There is already a printoperation for this thread"];
{
[NSException raise: NSPrintOperationExistsException
format: @"There is already a printoperation for this thread"];
}
ASSIGN(_view, aView);
_rect = rect;
@ -668,18 +568,105 @@ static NSString *NSPrintOperationThreadKey = @"NSPrintOperationThreadKey";
_pageOrder = NSUnknownPageOrder;
_showPanels = NO;
[self setPrintInfo: aPrintInfo];
_path = [NSTemporaryDirectory() stringByAppendingPathComponent: @"GSPrint-"];
_path = [_path stringByAppendingString:
[[NSProcessInfo processInfo] globallyUniqueString]];
_path = [_path stringByAppendingPathExtension: @"ps"];
RETAIN(_path);
_pathSet = NO;
_path = nil;
_currentPage = 0;
[NSPrintOperation setCurrentOperation: self];
return self;
}
@end
@implementation NSPrintOperation (TrulyPrivate)
/* Private method to run the printing operation. Needs to create an
autoreleaes pool to make sure the print context is destroyed before
returning (which closes the print file.) */
- (BOOL) _runOperation
{
BOOL result;
CREATE_AUTORELEASE_POOL(pool);
NSGraphicsContext *oldContext = [NSGraphicsContext currentContext];
[self createContext];
if (_context == nil)
return NO;
result = NO;
if (_pageOrder == NSUnknownPageOrder)
{
if ([[[_printInfo dictionary] objectForKey: NSPrintReversePageOrder]
boolValue] == YES)
_pageOrder = NSDescendingPageOrder;
else
_pageOrder = NSAscendingPageOrder;
}
[NSGraphicsContext setCurrentContext: _context];
NS_DURING
{
[self _print];
result = YES;
[NSGraphicsContext setCurrentContext: oldContext];
}
NS_HANDLER
{
[_view _cleanupPrinting];
[NSGraphicsContext setCurrentContext: oldContext];
NSRunAlertPanel(@"Error", @"Printing error: %@",
@"OK", NULL, NULL, localException);
}
NS_ENDHANDLER
[self destroyContext];
RELEASE(pool);
return result;
}
- (void) _setupPrintInfo
{
BOOL knowsPageRange;
NSRange viewPageRange;
NSMutableDictionary *dict = [_printInfo dictionary];
knowsPageRange = [_view knowsPageRange: &viewPageRange];
if (knowsPageRange == YES)
{
int first = viewPageRange.location;
int last = NSMaxRange(viewPageRange) - 1;
[dict setObject: NSNUMBER(first) forKey: NSPrintFirstPage];
[dict setObject: NSNUMBER(last) forKey: NSPrintLastPage];
}
}
- (void)_printOperationDidRun:(NSPrintOperation *)printOperation
success:(BOOL)success
contextInfo:(void *)contextInfo
{
id delegate;
SEL *didRunSelector;
NSMutableDictionary *dict;
void (*didRun)(id, SEL, BOOL, id);
if (success == YES)
{
NSPrintPanel *panel = [self printPanel];
[panel finalWritePrintInfo];
success = NO;
if ([self _runOperation])
success = [self deliverResult];
}
[self cleanUpOperation];
dict = [_printInfo dictionary];
didRunSelector = [[dict objectForKey: @"GSModalRunSelector"] pointerValue];
delegate = [dict objectForKey: @"GSModalRunDelegate"];
didRun = (void (*)(id, SEL, BOOL, id))[delegate methodForSelector:
*didRunSelector];
didRun (delegate, *didRunSelector, success, contextInfo);
}
static NSSize
scaleSize(NSSize size, double scale)
@ -1113,266 +1100,3 @@ scaleRect(NSRect rect, double scale)
}
@end
@implementation GSPrintOperation
- (id)initWithView:(NSView *)aView
printInfo:(NSPrintInfo *)aPrintInfo
{
NSMutableData *data = [NSMutableData data];
self = [self initWithView: aView
insideRect: [aView bounds]
toData: data
printInfo: aPrintInfo];
_showPanels = YES;
return self;
}
- (NSGraphicsContext*)createContext
{
NSMutableDictionary *info;
if (_context)
return _context;
info = [_printInfo dictionary];
if (_pathSet == NO)
{
NSString *output = [info objectForKey: NSPrintSavePath];
if (output)
{
ASSIGN(_path, output);
_pathSet = YES;
}
}
[info setObject: _path forKey: @"NSOutputFile"];
[info setObject: NSGraphicsContextPSFormat
forKey: NSGraphicsContextRepresentationFormatAttributeName];
_context = RETAIN([NSGraphicsContext graphicsContextWithAttributes: info]);
return _context;
}
- (BOOL) _deliverSpooledResult
{
int copies;
NSDictionary *dict;
NSTask *task;
NSString *name, *status;
NSMutableArray *args;
name = [[_printInfo printer] name];
status = [NSString stringWithFormat: @"Spooling to printer %@.", name];
[_printPanel _setStatusStringValue: status];
dict = [_printInfo dictionary];
args = [NSMutableArray array];
copies = [[dict objectForKey: NSPrintCopies] intValue];
if (copies > 1)
[args addObject: [NSString stringWithFormat: @"-#%0d", copies]];
if ([name isEqual: @"Unknown"] == NO)
{
[args addObject: @"-P"];
[args addObject: name];
}
[args addObject: _path];
task = [NSTask new];
[task setLaunchPath: @"lpr"];
[task setArguments: args];
[task launch];
[task waitUntilExit];
AUTORELEASE(task);
return YES;
}
- (BOOL) deliverResult
{
BOOL success;
NSString *job;
success = YES;
job = [_printInfo jobDisposition];
if ([job isEqual: NSPrintPreviewJob])
{
/* Check to see if there is a GNUstep app that can preview PS files.
It's not likely at this point, so also check for a standards
previewer, like gv.
*/
NSTask *task;
NSString *preview;
NSWorkspace *ws = [NSWorkspace sharedWorkspace];
[_printPanel _setStatusStringValue: @"Opening in previewer..."];
preview = [ws getBestAppInRole: @"Viewer" forExtension: @"ps"];
if (preview)
{
[ws openFile: _path withApplication: preview];
}
else
{
NSUserDefaults *def = [NSUserDefaults standardUserDefaults];
preview = [def objectForKey: @"NSPreviewApp"];
if (preview == nil || [preview length] == 0)
preview = @"gv";
task = [NSTask new];
[task setLaunchPath: preview];
[task setArguments: [NSArray arrayWithObject: _path]];
[task launch];
AUTORELEASE(task);
}
}
else if ([job isEqual: NSPrintSpoolJob])
{
success = [self _deliverSpooledResult];
}
else if ([job isEqual: NSPrintFaxJob])
{
}
/* We can't remove the temp file because the previewer might still be
using it, perhaps the printer is also?
if (!_pathSet)
[[NSFileManager defaultManager] removeFileAtPath: _path
handler: nil];
*/
return success;
}
@end
@implementation GSEPSPrintOperation
- (id)initEPSOperationWithView:(NSView *)aView
insideRect:(NSRect)rect
toData:(NSMutableData *)data
printInfo:(NSPrintInfo *)aPrintInfo
{
self = [self initWithView: aView
insideRect: rect
toData: data
printInfo: aPrintInfo];
_pathSet = YES; /* Use the default temp path */
return self;
}
- (id) initEPSOperationWithView:(NSView *)aView
insideRect:(NSRect)rect
toPath:(NSString *)path
printInfo:(NSPrintInfo *)aPrintInfo
{
NSMutableData *data = [NSMutableData data];
self = [self initEPSOperationWithView: aView
insideRect: rect
toData: data
printInfo: aPrintInfo];
ASSIGN(_path, path);
_pathSet = YES;
return self;
}
- (void) _print
{
/* Save this for the view to look at. Seems like there should
be a better way to pass it to beginDocument */
[[_printInfo dictionary] setObject: [NSValue valueWithRect: _rect]
forKey: @"NSPrintSheetBounds"];
[_view beginDocument];
[_view beginPageInRect: _rect atPlacement: NSMakePoint(0,0)];
[_view displayRectIgnoringOpacity: _rect];
[_view endDocument];
}
- (BOOL)isEPSOperation
{
return YES;
}
- (BOOL)deliverResult
{
if (_data != nil && _path != nil)
{
NSString *eps;
eps = [NSString stringWithContentsOfFile: _path];
[_data setData: [eps dataUsingEncoding:NSASCIIStringEncoding]];
}
return YES;
}
- (NSGraphicsContext*)createContext
{
NSMutableDictionary *info;
if (_context)
return _context;
info = [_printInfo dictionary];
[info setObject: _path forKey: @"NSOutputFile"];
[info setObject: NSGraphicsContextPSFormat
forKey: NSGraphicsContextRepresentationFormatAttributeName];
_context = RETAIN([NSGraphicsContext graphicsContextWithAttributes: info]);
return _context;
}
@end
@implementation GSPDFPrintOperation
- (id) initPDFOperationWithView:(NSView *)aView
insideRect:(NSRect)rect
toData:(NSMutableData *)data
printInfo:(NSPrintInfo*)aPrintInfo
{
self = [self initWithView: aView
insideRect: rect
toData: data
printInfo: aPrintInfo];
_pathSet = YES; /* Use the default temp path */
return self;
}
- (id) initPDFOperationWithView:(NSView *)aView
insideRect:(NSRect)rect
toPath:(NSString *)path
printInfo:(NSPrintInfo*)aPrintInfo
{
NSMutableData *data = [NSMutableData data];
self = [self initPDFOperationWithView: aView
insideRect: rect
toData: data
printInfo: aPrintInfo];
ASSIGN(_path, path);
_pathSet = YES;
return self;
}
- (NSGraphicsContext*)createContext
{
// FIXME
return nil;
}
- (void) _print
{
[_view displayRectIgnoringOpacity: _rect];
}
- (BOOL)deliverResult
{
if (_data != nil && _path != nil && [_data length])
return [_data writeToFile: _path atomically: NO];
// FIXME Until we can create PDF we shoud convert the file with GhostScript
return YES;
}
@end

View file

@ -2,10 +2,13 @@
<abstract>Standard panel for querying user about printing.</abstract>
Copyright (C) 2001 Free Software Foundation, Inc.
Copyright (C) 2001,2004 Free Software Foundation, Inc.
Written By: Adam Fedor <fedor@gnu.org>
Date: Oct 2001
Modified for Printing Backend Support
Author: Chad Hardin <cehardin@mac.com>
Date: June 2004
This file is part of the GNUstep GUI Library.
@ -42,6 +45,7 @@
#include "AppKit/NSSavePanel.h"
#include "AppKit/NSView.h"
#include "GSGuiPrivate.h"
#include "GNUstepGUI/GSPrinting.h"
static NSPrintPanel *shared_instance;
@ -71,6 +75,22 @@ static NSPrintPanel *shared_instance;
//
// Class Methods
//
/** Load the appropriate bundle for the PrintPanel
and alloc the class from that in our place
(eg: GSLPRPrintPanel, GSCUPSPrintPanel).
*/
+ (id) allocWithZone: (NSZone*) zone
{
Class principalClass;
principalClass = [[GSPrinting printingBundle] principalClass];
if( principalClass == nil )
return nil;
return [[principalClass printPanelClass] allocWithZone: zone];
}
/** Creates and returns a shared instance of the NSPrintPanel panel.
*/
+ (NSPrintPanel *)printPanel

View file

@ -2,10 +2,13 @@
<abstract>Class representing a printer's or printer model's capabilities.</abstract>
Copyright (C) 1996, 1997 Free Software Foundation, Inc.
Copyright (C) 1996, 1997, 2004 Free Software Foundation, Inc.
Authors: Simon Frankau <sgf@frankau.demon.co.uk>
Date: June 1997
Modified for Printing Backend Support
Author: Chad Hardin <cehardin@mac.com>
Date: June 2004
This file is part of the GNUstep GUI Library.
@ -51,195 +54,13 @@
#include <Foundation/NSUtilities.h>
#include <Foundation/NSValue.h>
#include <Foundation/NSMapTable.h>
#include <Foundation/NSSet.h>
#include "AppKit/AppKitExceptions.h"
#include "AppKit/NSGraphics.h"
#include "AppKit/NSPrinter.h"
// Define size used for the name and type maps - just use a small table
#define NAMEMAPSIZE 0
#define TYPEMAPSIZE 0
// The maximum level of nesting of *Include directives
#define MAX_PPD_INCLUDES 4
// A macro to skip whitespace over lines
#define skipSpace(x) [x scanCharactersFromSet:\
[NSCharacterSet whitespaceAndNewlineCharacterSet]\
intoString:NULL]
static NSString *NSPrinter_PATH = @"PostScript/PPD";
static NSString *NSPrinter_INDEXFILE = @"Printers";
//
// Class variables:
//
// Maps holding NSPrinters with the types of printers, and the real printers
static NSMapTable *typeMap = NULL;
static NSMapTable *nameMap = NULL;
// Dictionary of real printers, from which NSPrinters can be made
static NSDictionary *nameDict = nil;
// An array to cache the available printer types
static NSArray *printerTypesAvailable = nil;
//
// Class variables used during scanning:
//
// Character sets used in scanning.
static NSCharacterSet *newlineSet = nil;
static NSCharacterSet *keyEndSet = nil;
static NSCharacterSet *optKeyEndSet = nil;
static NSCharacterSet *valueEndSet = nil;
// Array of Repeated Keywords (Appendix B of the PostScript Printer
// Description File Format Specification).
static NSArray *repKeys = nil;
// Array to collect the values of symbol values in.
static NSMutableDictionary *PPDSymbolValues;
// File name of the file being processed
static NSString *PPDFileName;
#ifndef LIB_FOUNDATION_LIBRARY
static void __NSRetainNothing(void *table, const void *anObject)
{
}
static void __NSReleaseNothing(void *table, void *anObject)
{
}
static NSString* __NSDescribeObjects(void *table, const void *anObject)
{
return [(NSObject*)anObject description];
}
static const NSMapTableValueCallBacks NSNonRetainedObjectMapValueCallBacks = {
(void (*)(NSMapTable *, const void *))__NSRetainNothing,
(void (*)(NSMapTable *, void *))__NSReleaseNothing,
(NSString *(*)(NSMapTable *, const void *))__NSDescribeObjects
};
#endif /* LIB_FOUNDATION_LIBRARY */
#include "GNUstepGUI/GSPrinting.h"
// Convert a character to a value between 0 and 15
static int gethex(unichar character)
{
switch (character)
{
case '0': return 0;
case '1': return 1;
case '2': return 2;
case '3': return 3;
case '4': return 4;
case '5': return 5;
case '6': return 6;
case '7': return 7;
case '8': return 8;
case '9': return 9;
case 'A': return 10;
case 'B': return 11;
case 'C': return 12;
case 'D': return 13;
case 'E': return 14;
case 'F': return 15;
case 'a': return 10;
case 'b': return 11;
case 'c': return 12;
case 'd': return 13;
case 'e': return 14;
case 'f': return 15;
}
[NSException
raise:NSPPDParseException
format:@"Badly formatted hexadeximal substring in PPD printer file."];
// NOT REACHED
return 0; /* Quiet compiler warnings */
}
// Function to convert hexadecimal substrings
static NSString *interpretQuotedValue(NSString *qString)
{
NSScanner *scanner;
NSCharacterSet *emptySet;
NSString *value = nil;
NSString *part;
int stringLength;
int location;
NSRange range;
// Don't bother unless there's something to convert
range = [qString rangeOfString:@"<"];
if(!range.length)
return qString;
scanner = [NSScanner scannerWithString:qString];
emptySet = [NSCharacterSet characterSetWithCharactersInString:@""];
[scanner setCharactersToBeSkipped:emptySet];
if(![scanner scanUpToString:@"<" intoString:&value])
value = [NSString string];
stringLength = [qString length];
while (![scanner isAtEnd]) {
[scanner scanString:@"<" intoString:NULL];
skipSpace(scanner);
while (![scanner scanString:@">" intoString:NULL])
{
location = [scanner scanLocation];
if (location+2 > stringLength)
{
[NSException
raise:NSPPDParseException
format:@"Badly formatted hexadecimal substring in PPD printer file."];
// NOT REACHED
}
value = [value stringByAppendingFormat:@"%c",
16 * gethex([qString characterAtIndex:location])
+ gethex([qString characterAtIndex:location+1])];
[scanner setScanLocation:location+2];
skipSpace(scanner);
}
if([scanner scanUpToString:@"<" intoString:&part])
{
value = [value stringByAppendingString:part];
}
}
return value;
}
static NSString *getFile(NSString *name, NSString *type)
{
return [NSBundle pathForLibraryResource: name
ofType: type
inDirectory: NSPrinter_PATH];
}
@interface NSPrinter (private)
+ allocMaps;
- initWithPPD:(NSString *)PPDstring
withName:(NSString *)name
withType:(NSString *)type
withHost:(NSString *)host
withNote:(NSString *)note
fromFile:(NSString *)file
isReal:(BOOL)real;
- loadPPD:(NSString *)PPDstring
inclusionNum:(int)includeNum;
- addPPDKeyword:(NSString *)mainKeyword
withScanner:(NSScanner *)PPDdata;
- addPPDUIConstraint:(NSScanner *)constraint;
- addPPDOrderDependency:(NSScanner *)dependency;
- addValue:(NSString *)value
andValueTranslation:(NSString *)valueTranslation
andOptionTranslation:(NSString *)optionTranslation
forKey:(NSString *)key;
- addString:(NSString *)string
forKey:(NSString *)key
inTable:(NSMutableDictionary *)table;
@end
@implementation NSPrinter
@ -255,131 +76,108 @@ andOptionTranslation:(NSString *)optionTranslation
}
}
/** Load the appropriate bundle for the Printer
(eg: GSLPRPrinter, GSCUPSPrinter).
*/
+ (id) allocWithZone: (NSZone*) zone
{
Class principalClass;
principalClass = [[GSPrinting printingBundle] principalClass];
if( principalClass == nil )
return nil;
return [[principalClass printerClass] allocWithZone: zone];
}
//
// Finding an NSPrinter
//
+ (NSPrinter *)printerWithName:(NSString *)name
{
NSString *path;
NSArray *printerInfo;
NSPrinter *printer;
/* Contents of printerInfo array:
* [0]: NSString of the printer's type
* [1]: NSString of the printer's host
* [2]: NSString of the printer's note
*/
// Make sure the printer names dictionary etc. exists
if (!nameMap)
[self allocMaps];
printer = NSMapGet(nameMap, name);
// If the NSPrinter object for the printer already exists, return it
if (printer)
return printer;
// Otherwise, try to find the information in the nameDict
printerInfo = [nameDict objectForKey:name];
// Make sure you can find the printer name in the dictionary
if (!printerInfo)
{
[NSException raise:NSGenericException
format:@"Could not find printer named %@", name];
// NOT REACHED
}
// Create it
path = getFile([printerInfo objectAtIndex:0], @"ppd");
// If not found
if (path == nil || [path length] == 0)
{
[NSException raise:NSGenericException
format:@"Could not find PPD file %@.ppd",
[printerInfo objectAtIndex:0]];
// NOT REACHED
}
printer = AUTORELEASE([[self alloc]
initWithPPD:[NSString stringWithContentsOfFile:path]
withName:name
withType:[printerInfo objectAtIndex:0]
withHost:[printerInfo objectAtIndex:1]
withNote:[printerInfo objectAtIndex:2]
fromFile:[printerInfo objectAtIndex:0]
isReal:YES]);
// Once created, put it in the map table
NSMapInsert(nameMap, name, printer);
return printer;
Class principalClass;
principalClass = [[GSPrinting printingBundle] principalClass];
if( principalClass == nil )
return nil;
return [[principalClass printerClass] printerWithName: name];
}
//
// This now different than the OpenStep spec and instead
// follows the more useful implementation Apple choosed. In
// OpenStep, this method would read a PPD and return a NSPrinter
// based upon values from that PPD, regardless if that printer
// was actually avaiable for use or not. On the contrary, Apple's
// implementation looks
// at all avaiable printers and returns one that has the same
// type. The reason for this is because they use CUPS. CUPS
// does not work by maintaining a repository of PPDs. Instead,
// the CUPS server trasnmits PPDs as they are needed, and only
// for actual real printers. Since we cannot know how the backend
// bundles will be handling their PPDs, or if they will even be using
// PPDs for that matter, (a Win32 printing backend, for example),
// I've choosen to go with Apple's implementation. Really, I see
// little use in creating a NSPrinter for a printer that is not
// available for use in the first place, I am open for commments
// on this, of course.
+ (NSPrinter *)printerWithType:(NSString *)type
{
NSString *path;
NSPrinter *printer = nil;
// Make sure the printer types dictionary exists
if (!typeMap)
[self allocMaps];
else
printer = NSMapGet(typeMap, type);
// If the NSPrinter is already created, use it
if (printer)
return printer;
path = getFile(type, @"ppd");
// If not found
if (path == nil || [path length] == 0)
NSEnumerator *printerNamesEnum;
NSString *printerName;
printerNamesEnum = [[self printerNames] objectEnumerator];
while( (printerName = [printerNamesEnum nextObject]) )
{
[NSException raise:NSGenericException
format:@"Could not find PPD file %@.ppd", type];
// NOT REACHED
NSPrinter *printer;
printer = [self printerWithName: printerName];
if( [[printer type] isEqualToString: type] )
{
return printer;
}
}
printer = AUTORELEASE([[self alloc]
initWithPPD:[NSString stringWithContentsOfFile:path]
withName:type withType:type withHost:@"" withNote:@""
fromFile:path isReal:NO]);
// Once created, put it in the hash table
NSMapInsert(typeMap, type, printer);
return printer;
return nil;
}
+ (NSArray *)printerNames
{
if(!nameDict)
[NSPrinter allocMaps];
return [nameDict allKeys];
Class principalClass;
principalClass = [[GSPrinting printingBundle] principalClass];
if( principalClass == nil )
return nil;
return [[principalClass printerClass] printerNames];
}
// See note at +(NSPrinter *)printerWithType:(NSString *)type
+ (NSArray *)printerTypes
{
NSEnumerator *pathEnum;
NSBundle *lbdle;
NSString *lpath;
NSArray *ppdpaths;
NSMutableArray *printers;
NSString *path;
NSAutoreleasePool *subpool; // There's a lot of temp strings used...
int i, max;
if (printerTypesAvailable)
return printerTypesAvailable;
printers = RETAIN([NSMutableArray array]);
subpool = [[NSAutoreleasePool alloc] init];
pathEnum = [NSSearchPathForDirectoriesInDomains(GSLibrariesDirectory,
NSAllDomainsMask, YES) objectEnumerator];
while ((lpath = [pathEnum nextObject]))
NSMutableSet *printerTypes;
NSEnumerator *printerNamesEnum;
NSString *printerName;
NSPrinter *printer;
printerTypes = [NSMutableSet setWithCapacity:1];
printerNamesEnum = [[self printerNames] objectEnumerator];
while( (printerName = [printerNamesEnum nextObject]) )
{
lbdle = [NSBundle bundleWithPath: lpath];
ppdpaths = [lbdle pathsForResourcesOfType:@"ppd"
inDirectory:NSPrinter_PATH];
// FIXME - should get name from contents of PPD, not filename
max = [ppdpaths count];
for (i = 0; i < max; i++)
{
path = [[ppdpaths objectAtIndex:i] lastPathComponent];
[printers addObject:[path substringToIndex:[path length]-4]];
}
printer = [self printerWithName: printerName];
[printerTypes addObject: [printer type]];
}
RELEASE(subpool);
printerTypesAvailable = printers;
return printers;
return [printerTypes allObjects];
}
//
@ -390,11 +188,6 @@ andOptionTranslation:(NSString *)optionTranslation
//
- (void)dealloc
{
// Remove object from the appropriate table
if (_isRealPrinter)
NSMapRemove(nameMap, _printerName);
else
NSMapRemove(typeMap, _printerType);
RELEASE(_printerHost);
RELEASE(_printerName);
RELEASE(_printerNote);
@ -830,7 +623,6 @@ andOptionTranslation:(NSString *)optionTranslation
[aCoder encodeValueOfObjCType: @encode(int) at: &_cacheAcceptsBinary];
[aCoder encodeValueOfObjCType: @encode(int) at: &_cacheOutputOrder];
[aCoder encodeValueOfObjCType: @encode(BOOL) at: &_isRealPrinter];
[aCoder encodeObject: _PPD];
[aCoder encodeObject: _PPDOptionTranslation];
@ -850,7 +642,6 @@ andOptionTranslation:(NSString *)optionTranslation
[aDecoder decodeValueOfObjCType: @encode(int) at: &_cacheAcceptsBinary];
[aDecoder decodeValueOfObjCType: @encode(int) at: &_cacheOutputOrder];
[aDecoder decodeValueOfObjCType: @encode(BOOL) at: &_isRealPrinter];
[aDecoder decodeValueOfObjCType: @encode(id) at: &_PPD];
[aDecoder decodeValueOfObjCType: @encode(id) at: &_PPDOptionTranslation];
@ -861,467 +652,43 @@ andOptionTranslation:(NSString *)optionTranslation
return self;
}
//
// Private Methods
//
@end
///
///Private implementation of routines that will be usefull
///for the printing backend bundles that subclass us.
///
@implementation NSPrinter (Private)
//
// Allocate the printer name to PPD filename index dictionary
// Initialisation method used by backend bundles
//
+ allocMaps
-(id) initWithName:(NSString *)name
withType:(NSString *)type
withHost:(NSString *)host
withNote:(NSString *)note
{
NSString *path;
// Allocate name and type maps
typeMap = NSCreateMapTable(NSObjectMapKeyCallBacks,
NSNonRetainedObjectMapValueCallBacks,
TYPEMAPSIZE);
nameMap = NSCreateMapTable(NSObjectMapKeyCallBacks,
NSNonRetainedObjectMapValueCallBacks,
NAMEMAPSIZE);
// Load the index file
path = [NSBundle pathForLibraryResource: NSPrinter_INDEXFILE
ofType: nil
inDirectory: @"PostScript"];
// If not found
if (path == nil || [path length] == 0)
{
NSLog(@"Could not find index of printers, file %@", NSPrinter_INDEXFILE);
nameDict = [NSDictionary dictionaryWithObject:
[NSArray arrayWithObjects: @"Apple_LaserWriter_II_NTX",
@"localhost", @"A Note", nil]
forKey: @"Unknown"];
}
else
nameDict = [NSDictionary dictionaryWithContentsOfFile:path];
RETAIN(nameDict);
return self;
}
//
// Initialisation method
//
// To keep loading of PPDs relatively fast, not much checking is done on it.
- initWithPPD:(NSString *)PPDstring
withName:(NSString *)name
withType:(NSString *)type
withHost:(NSString *)host
withNote:(NSString *)note
fromFile:(NSString *)file
isReal:(BOOL)real
{
NSAutoreleasePool *subpool;
NSEnumerator *objEnum;
NSMutableArray *valArray;
self = [super init];
// Initialise instance variables
_printerName = RETAIN(name);
_printerType = RETAIN(type);
_printerHost = RETAIN(host);
_printerNote = RETAIN(note);
ASSIGN(_printerName, name);
ASSIGN(_printerType, type);
ASSIGN(_printerHost, host);
ASSIGN(_printerNote, note);
_cacheAcceptsBinary = _cacheOutputOrder = -1;
_isRealPrinter = real;
_PPD = RETAIN([NSMutableDictionary dictionary]);
_PPDOptionTranslation = RETAIN([NSMutableDictionary dictionary]);
_PPDArgumentTranslation = RETAIN([NSMutableDictionary dictionary]);
_PPDOrderDependency = RETAIN([NSMutableDictionary dictionary]);
_PPDUIConstraints = RETAIN([NSMutableDictionary dictionary]);
// Create a temporary autorelease pool, as many temporary objects are used
subpool = [[NSAutoreleasePool alloc] init];
// Create character sets used during scanning
newlineSet = [NSCharacterSet characterSetWithCharactersInString:@"\n\r"];
keyEndSet = [NSCharacterSet characterSetWithCharactersInString:@"\n\r\t: "];
optKeyEndSet = [NSCharacterSet characterSetWithCharactersInString:@"\n\r:/"];
valueEndSet = [NSCharacterSet characterSetWithCharactersInString:@"\n\r/"];
// Allowed repeated keys, used during scanning.
repKeys = [NSArray arrayWithObjects:@"Emulators",
@"Extensions",
@"FaxSupport",
//@"Include", (handled separately)
@"Message",
@"PrinterError",
@"Product",
@"Protocols",
@"PSVersion",
@"Source",
@"Status",
//@"UIConstraints", (handled separately)
// Even though this is not mentioned in the list of repeated keywords,
// it's often repeated anyway, so I'm putting it here.
@"InkName",
nil];
// Set the file name to use
PPDFileName = file;
// NB: There are some structure keywords (such as OpenUI/CloseUI) that may
// be repeated, but as yet are not used. Since they are structure keywords,
// they'll probably need special processing anyway, and so aren't
// added to this list.
// Create dictionary for temporary storage of symbol values
PPDSymbolValues = [NSMutableDictionary dictionary];
// And scan the PPD itself
[self loadPPD:PPDstring inclusionNum:0];
// Search the PPD dictionary for symbolvalues, and substitute them.
objEnum = [_PPD objectEnumerator];
while ((valArray = [objEnum nextObject]))
{
NSString *oldValue;
NSString *newValue;
int i, max;
max = [valArray count];
for(i=0 ; i < max ; i++ )
{
oldValue = [valArray objectAtIndex:i];
if ([oldValue isKindOfClass:[NSString class]]
&& ![oldValue isEqual:@""]
&& [[oldValue substringToIndex:1] isEqual:@"^"])
{
newValue = [PPDSymbolValues
objectForKey:[oldValue substringFromIndex:1]];
if (!newValue)
{
[NSException
raise:NSPPDParseException
format:@"Unknown symbol value, ^%@ in PPD file %@.ppd",
oldValue, PPDFileName];
// NOT REACHED
}
[valArray replaceObjectAtIndex:i withObject:newValue];
}
}
}
#if 0
// DISABLED: Though the following keywords *should* be present, there seems
// to be few problems is they are omitted. Many of the .ppd files I have
// don't have *LanguageEncoding, for example.
// Make sure all the required keys are present
objEnum = [[NSArray arrayWithObjects:@"NickName",
@"ModelName",
@"PCFileName",
@"Product",
@"PSVersion",
@"FileVersion",
@"FormatVersion",
@"LanguageEncoding",
@"LanguageVersion",
@"PageSize",
@"PageRegion",
@"ImageableArea",
@"PaperDimension",
@"PPD-Adobe",
nil] objectEnumerator];
while (checkVal = [objEnum nextObject])
{
if (![self isKey:checkVal inTable:@"PPD"])
{
[NSException
raise:NSPPDParseException
format:@"Required keyword *%@ not found in PPD file %@.ppd",
checkVal, PPDFileName];
// NOT REACHED
}
}
#endif
// Release the local autoreleasePool
RELEASE(subpool);
return self;
}
- loadPPD:(NSString *)PPDstring
inclusionNum:(int)includeNum
{
NSScanner *PPDdata;
NSString *keyword;
// Set up the scanner - Appending a newline means that it should be
// able to process the last line correctly
PPDdata = [NSScanner scannerWithString:
[PPDstring stringByAppendingString:@"\n"]];
[PPDdata setCharactersToBeSkipped:[NSCharacterSet whitespaceCharacterSet]];
// Main processing starts here...
while (1) // Check it is not at end only after skipping the blanks
{
// Get to the start of a new keyword, skipping blank lines
skipSpace(PPDdata);
if ([PPDdata isAtEnd])
break;
// All new entries should starts '*'
if (![PPDdata scanString:@"*" intoString:NULL])
{
[NSException raise:NSPPDParseException
format:@"Line not starting * in PPD file %@.ppd",
PPDFileName];
// NOT REACHED
}
// Skip lines starting '*%', '*End', '*SymbolLength', or '*SymbolEnd'
if ([PPDdata scanString:@"%" intoString:NULL]
|| [PPDdata scanString:@"End" intoString:NULL]
|| [PPDdata scanString:@"SymbolLength" intoString:NULL]
|| [PPDdata scanString:@"SymbolEnd" intoString:NULL])
{
[PPDdata scanUpToCharactersFromSet:newlineSet intoString:NULL];
continue;
}
// Read main keyword, up to a colon, space or newline
[PPDdata scanUpToCharactersFromSet:keyEndSet intoString:&keyword];
// Loop if there is no value section
if ([PPDdata scanCharactersFromSet:newlineSet intoString:NULL])
continue;
// Add the line to the relevant table
if ([keyword isEqual:@"OrderDependency"])
[self addPPDOrderDependency:PPDdata];
else if ([keyword isEqual:@"UIConstraints"])
[self addPPDUIConstraint:PPDdata];
else if ([keyword isEqual:@"Include"])
{
NSString *fileName;
NSString *path;
[PPDdata scanString:@":" intoString:NULL];
// Find the filename between two "s
[PPDdata scanString:@"\"" intoString:NULL];
[PPDdata scanUpToString:@"\"" intoString:&fileName];
[PPDdata scanString:@"\"" intoString:NULL];
// Load the file
path = getFile(fileName, nil);
// If not found
if (path == nil || [path length] == 0)
{
[NSException raise:NSPPDIncludeNotFoundException
format:@"Could not find included PPD file %@",
fileName];
// NOT REACHED
}
includeNum++;
if (includeNum > MAX_PPD_INCLUDES)
{
[NSException raise:NSPPDIncludeStackOverflowException
format:@"Too many *Includes in PPD"];
// NOT REACHED
}
[self loadPPD:[NSString stringWithContentsOfFile:path]
inclusionNum:includeNum];
}
else if ([keyword isEqual:@"SymbolValue"])
{
NSString *symbolName;
NSString *symbolVal;
if (![PPDdata scanString:@"^" intoString:NULL])
{
[NSException
raise:NSPPDParseException
format:@"Badly formatted *SymbolValue in PPD file %@.ppd",
PPDFileName];
// NOT REACHED
}
[PPDdata scanUpToString:@":" intoString:&symbolName];
[PPDdata scanString:@":" intoString:NULL];
[PPDdata scanString:@"\"" intoString:NULL];
[PPDdata scanUpToString:@"\"" intoString:&symbolVal];
if (!symbolVal)
symbolVal = @"";
[PPDdata scanString:@"\"" intoString:NULL];
[PPDSymbolValues setObject:symbolVal forKey:symbolName];
}
else
[self addPPDKeyword:keyword withScanner:PPDdata];
}
return self;
}
- addPPDKeyword:(NSString *)mainKeyword
withScanner:(NSScanner *)PPDdata
{
NSString *optionKeyword = nil;
NSString *optionTranslation = nil;
NSString *value = nil;
NSString *valueTranslation = nil;
// Scan off any optionKeyword
[PPDdata scanUpToCharactersFromSet:optKeyEndSet intoString:&optionKeyword];
if ([PPDdata scanCharactersFromSet:newlineSet intoString:NULL])
{
[NSException raise:NSPPDParseException
format:@"Keyword has optional keyword but no value in PPD file %@.ppd",
PPDFileName];
// NOT REACHED
}
if ([PPDdata scanString:@"/" intoString:NULL])
{
// Option keyword translation exists - scan it
[PPDdata scanUpToString:@":" intoString:&optionTranslation];
}
[PPDdata scanString:@":" intoString:NULL];
// Read the value part
// Values starting with a " are read until the second ", ignoring \n etc.
if ([PPDdata scanString:@"\"" intoString:NULL])
{
[PPDdata scanUpToString:@"\"" intoString:&value];
if (!value)
value = @"";
[PPDdata scanString:@"\"" intoString:NULL];
// It is a QuotedValue if it's in quotes, and there is no option
// key, or the main key is a *JCL keyword
if (!optionKeyword || [[mainKeyword substringToIndex:3]
isEqualToString:@"JCL"])
value = interpretQuotedValue(value);
}
else
{
// Otherwise, scan up to the end of line or '/'
[PPDdata scanUpToCharactersFromSet:valueEndSet intoString:&value];
}
// If there is a value translation, scan it
if ([PPDdata scanString:@"/" intoString:NULL])
{
[PPDdata scanUpToCharactersFromSet:newlineSet
intoString:&valueTranslation];
}
// The translations also have to have any hex substrings interpreted
if (optionTranslation)
optionTranslation = interpretQuotedValue(optionTranslation);
if (valueTranslation)
valueTranslation = interpretQuotedValue(valueTranslation);
// The keyword (or keyword/option pair, if there's a option), should only
// only have one value, unless it's one of the optionless keywords which
// allow multiple instances.
// If a keyword is read twice, 'first instance is correct', according to
// the standard.
// Finally, add the strings to the tables
if (optionKeyword)
{
NSString *mainAndOptionKeyword=[mainKeyword
stringByAppendingFormat:@"/%@",
optionKeyword];
if ([self isKey:mainAndOptionKeyword inTable:@"PPD"])
return self;
[self addValue:value
andValueTranslation:valueTranslation
andOptionTranslation:optionTranslation
forKey:mainAndOptionKeyword];
// Deal with the oddities of stringForKey:inTable:
// If this method is used to find a keyword with options, using
// just the keyword it should return an empty string
// stringListForKey:inTable:, however, should return the list of
// option keywords.
// This is done by making the first item in the array an empty
// string, which will be skipped by stringListForKey:, if necessary
if (![_PPD objectForKey:mainKeyword])
{
[self addString:@"" forKey:mainKeyword inTable:_PPD];
[self addString:@"" forKey:mainKeyword inTable:_PPDOptionTranslation];
[self addString:@"" forKey:mainKeyword
inTable:_PPDArgumentTranslation];
}
[self addValue:optionKeyword
andValueTranslation:optionKeyword
andOptionTranslation:optionKeyword
forKey:mainKeyword];
}
else
{
if ([self isKey:mainKeyword inTable:@"PPD"] &&
![repKeys containsObject:mainKeyword])
return self;
[self addValue:value
andValueTranslation:valueTranslation
andOptionTranslation:optionTranslation
forKey:mainKeyword];
}
return self;
}
- addPPDUIConstraint:(NSScanner *)constraint
{
NSString *mainKey1 = nil;
NSString *optionKey1 = nil;
NSString *mainKey2 = nil;
NSString *optionKey2 = nil;
// UIConstraint should have no option keyword
if (![constraint scanString:@":" intoString:NULL])
{
[NSException raise:NSPPDParseException
format:@"UIConstraints has option keyword in PPDFileName %@.ppd",
PPDFileName];
// NOT REACHED
}
// Skip the '*'
[constraint scanString:@"*" intoString:NULL];
// Scan the bits. Stuff not starting with * must be an optionKeyword
[constraint scanUpToCharactersFromSet:[NSCharacterSet whitespaceCharacterSet]
intoString:&mainKey1];
if (![constraint scanString:@"*" intoString:NULL])
{
[constraint scanUpToCharactersFromSet:[NSCharacterSet
whitespaceCharacterSet]
intoString:&optionKey1];
[constraint scanString:@"*" intoString:NULL];
}
[constraint scanUpToCharactersFromSet:
[NSCharacterSet whitespaceAndNewlineCharacterSet]
intoString:&mainKey2];
if (![constraint scanCharactersFromSet:newlineSet intoString:NULL])
{
[constraint scanUpToCharactersFromSet:
[NSCharacterSet whitespaceAndNewlineCharacterSet]
intoString:&optionKey2];
}
else
{
optionKey2 = @"";
}
// Add to table
if (optionKey1)
mainKey1 = [mainKey1 stringByAppendingFormat:@"/%@", optionKey1];
[self addString:mainKey2
forKey:mainKey1
inTable:_PPDUIConstraints];
[self addString:optionKey2
forKey:mainKey1
inTable:_PPDUIConstraints];
return self;
}
- addPPDOrderDependency:(NSScanner *)dependency
{
NSString *realValue = nil;
NSString *section = nil;
NSString *keyword = nil;
NSString *optionKeyword = nil;
// Order dependency should have no option keyword
if (![dependency scanString:@":" intoString:NULL])
{
[NSException raise:NSPPDParseException
format:@"OrderDependency has option keyword in PPD file %@.ppd",
PPDFileName];
// NOT REACHED
}
[dependency scanUpToCharactersFromSet:[NSCharacterSet whitespaceCharacterSet]
intoString:&realValue];
[dependency scanUpToCharactersFromSet:[NSCharacterSet whitespaceCharacterSet]
intoString:&section];
[dependency scanString:@"*" intoString:NULL];
[dependency scanUpToCharactersFromSet:
[NSCharacterSet whitespaceAndNewlineCharacterSet]
intoString:&keyword];
if (![dependency scanCharactersFromSet:newlineSet intoString:NULL])
{
// Optional keyword exists
[dependency scanUpToCharactersFromSet:
[NSCharacterSet whitespaceAndNewlineCharacterSet]
intoString:&optionKeyword];
}
// Go to next line of PPD file
[dependency scanCharactersFromSet:newlineSet intoString:NULL];
// Add to table
if (optionKeyword)
keyword = [keyword stringByAppendingFormat:@"/%s", optionKeyword];
[self addString:realValue forKey:keyword inTable:_PPDOrderDependency];
[self addString:section forKey:keyword inTable:_PPDOrderDependency];
return self;
}
//
// Adds the various values to the relevant tables, for the given key