Commits

Ronald Oussoren committed b5eb1e7

- detab the CodeGenerator scripts
- add some missing files
- make sure buildpkg.py works with the newly added InstallationCheck (untested)

Comments (0)

Files changed (14)

pyobjc/Doc/coding-style.html

 <li>Add appropriate ReST style fields to the top of the document as comments:<pre>
 # Author: David Goodger
 # Contact: goodger@users.sourceforge.net
-# Revision: $Revision: 1.13 $
-# Date: $Date: 2003/06/30 19:56:19 $
+# Revision: $Revision: 1.14 $
+# Date: $Date: 2003/07/02 17:44:52 $
 # Copyright: This module has been placed in the public domain.
 </pre>
 </li>

pyobjc/Doc/tutorial_reading.html

+<?xml version="1.0" encoding="utf-8" ?>
+<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
+<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
+<head>
+<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
+<title>
+Understanding existing PyObjC examples</title>
+</head>
+<body>
+<h2>Understanding existing PyObjC examples</h2>
+<h2><a name="introduction">Introduction</a></h2>
+<p>This tutorial is aimed primarily at people with little or no background
+in ObjC and Cocoa, and it will help you to understand PyObjC programs
+written by other people, such as the examples included with the distribution.
+This document is actually not a true tutorial: you do not get to build anything,
+only read and examine things.</p>
+<p>It is strongly suggested that you first do the
+<a href="tutorial/tutorial.html">Creating your first PyObjC application</a> tutorial to get some hands-on
+experience with PyObjC, Cocoa and especially Interface Builder.</p>
+<h2><a name="model-view-controller">Model-View-Controller</a></h2>
+<p>If you have used another GUI toolkit in the past it is essential that
+you understand that Cocoa is different. For this once this isn't marketing-speak:
+Cocoa is inherently different from common toolkits such as Tk, wxWindows,
+Carbon, win32 and all the other popular ones. Apple's documentation explains this,
+but in the introductory sections that are often quickly glanced over. It is a
+good idea to refer back to <a href="http://developer.apple.com/documentation/Cocoa/Conceptual/AppArchitecture/index.html">Application Architecture</a> after reading this section. If you really
+want you can break out of the architecture sketched in this section, but
+then you are on your own, really: Cocoa and Interface Builder really
+expect you to follow this model.</p>
+<p>Cocoa is built on the Model-View-Controller paradigm (MVC). What this means
+is that the application code is going to be split into three parts:</p>
+<ul>
+<li>The <i>Model</i> is the actual data you are manipulating, plus the operations
+on it. It can be as big as a complete database engine or a scientific
+simulation, or as small as a routine that multiplies one floating point
+number (an amount of money in currency A) by another (the conversion
+rate from currency A to currency B), as in the currency converter
+application you built in the first tutorial.</li>
+<li>The <i>View</i> is what the user sees on-screen, plus his or her interaction
+with it.</li>
+<li>The <i>Controller</i> is the glue that binds these two together. In the
+currency converter example, it is the code that gets called when the user
+presses the &quot;Convert&quot; button, whereupon it gets the data from the &quot;amount&quot;
+and &quot;rate&quot; fields from the View, passes them to the Model for computation
+and sends the result back to the View.</li>
+</ul>
+<p>To summarize: the Model knows nothing about dialogs and buttons and such,
+the View knows nothing about data and algorithms and the Controller ties it
+all together. For really tiny applications, such as the currency converter,
+you could do away with the Model and simply put that code right in the
+Controller. MVC purists say you should not do this, and it can indeed
+make your code harder to read (because the Controller will contain a mix
+of algorithms and glue code), but there is no architectural reason that
+stops you. If you combine the two classes it is customary to use the name
+you would use for your document class, so without &quot;Controller&quot;.</p>
+<p>You should have an MVC trio for every distinct unit of information in your
+program. In case of a simple dialog-style application such as Currency Converter
+you will have one such trio. Most applications, however, will have at least
+two: one for the application itself and one for the &quot;documents&quot; the application
+handles. These may be real documents (i.e. files), but they could also be more
+abstract. If your application does scientific simulation and you want to be
+able to open two simulation windows at the same time you should use the
+document model.</p>
+<h2><a name="the-nib-file">The NIB file</a></h2>
+<p>Cocoa and Interface Builder strongly encourage you to use a NIB file
+per MVC trio. Again: follow this encouragement unless you are sure what
+you are doing.</p>
+<p>This brings us to the second big difference between Cocoa and other GUI
+toolkits: almost all the boilerplate code is in the NIB, and therefore
+the source of Cocoa programs, especially example programs that do little
+real work, will look stunningly small if you are familiar with, say,
+Tkinter.</p>
+<p>The NIB file is <i>not</i> a description of dialogs and menus and buttons, as you 
+would get out of interface-builders for other toolkits. There, at startup
+something will read the description, create the buttons and hand the finished
+dialog to your code. A NIB file is more: it contains a complete set of frozen
+objects, conceptually similar to a pickle in Python. You tell Interface Builder
+knows about all the relevant classes in your application, the instances you
+want to create from those classes, and how the classes should connect to
+each other. Interface Builder the actually instantiates the classes, makes
+all the connections and at that point freezes and stores the whole lot.</p>
+<p>When your NIB is read the objects are thawed, the connections restored and
+the objects get a running start. Again, this is conceptually similar
+to how unpickling works.</p>
+<blockquote>
+<p>The section above explains a lot of the strangeness in PyObjC
+programs: why you don't create windows and other dialogs (they
+already exist); why you shouldn't do initialization in <code><span>__init__</span></code>
+(because it will be called at some undefined point in time, while
+reading the NIB) but in <code><span>awakeFromNIB</span></code> in stead; why you don't
+have to create and initialize the attributes that tie your
+objects together (they are already tied together).</p>
+</blockquote>
+<p>This also explains why you want separate NIB files for each MVC trio:
+the objects and classes in a NIB file are all unpickled together. In other
+words: if you had created your document window in your application NIB
+(even if you set it to &quot;hidden&quot; initially so it does not show up) it would
+become very difficult to create a second window for a new document.</p>
+<p>If you think about the consequences of this section for a while it will
+become clear why all the boilerplate code is missing from Cocoa applications:
+you don't need it. The NIB file usually contains all of the things that need to
+be done for the Views objects, as is often the case with other gui-builders.
+But in addition the NIB also contains a large proportion of your Model
+functionality: creating the View and Controller objects and tieing the
+lot together.</p>
+<p>XXXX Explain about delegates instead of subclassing.</p>
+<h2><a name="examining-a-nib-file">Examining a NIB file</a></h2>
+<p>Let us examine the NIB of the Currency Converter tutorial with this in mind.
+If you open it and look at the main window (the one with &quot;MainMenu.nib&quot; as
+its title) and select the &quot;Instances&quot; pane you see six objects. Two of these
+have a greyed-out name (&quot;File's Owner&quot; and &quot;First Responder&quot;): these have
+been created for you by Apple. The other four are created by you. Actually:
+&quot;Main Menu&quot; was created by Apple as a convenience, but you are free to modify
+it. The &quot;File's Owner&quot; is either the Controller or the combined Model-Controller
+object, in this case it is the application itself, an instance of <code><span>NSApplication</span></code>.
+Because this application is not a document-based application the MVC trio
+for the actual conversion window are in here too: <code><span>Converter</span></code>, <code><span>Window</span></code> and
+<code><span>ConverterController</span></code> respectively.</p>
+<p>XXXX Examine ConverterController, show how to see class and methods</p>
+<p>XXXX Show how to see connections</p>
+<p>XXXX Show how to use outline view</p>
+<h2><a name="examining-an-example">Examining an example</a></h2>
+<p>XXXX Pick one of the interesting examples and walk through it, looking at the
+NIB file and the code.</p>
+</body>
+</html>

pyobjc/Examples/EnvironmentPrefs/English.lproj/Localizable.strings

+/* No comment provided by engineer. */
+"Cancel" = "Cancel";
+
+/* No comment provided by engineer. */
+"Cannot save changes" = "Cannot save changes";
+
+/* No comment provided by engineer. */
+"Don't Save" = "Don't Save";
+
+/* No comment provided by engineer. */
+"It was not possible to save your changes" = "It was not possible to save your changes";
+
+/* No comment provided by engineer. */
+"Name exists" = "Name exists";
+
+/* No comment provided by engineer. */
+"New Value" = "New Value";
+
+/* No comment provided by engineer. */
+"New_Variable_%d" = "New_Variable_%d";
+
+/* No comment provided by engineer. */
+"OK" = "OK";
+
+/* No comment provided by engineer. */
+"Save" = "Save";
+
+/* No comment provided by engineer. */
+"Save changes?" = "Save changes?";
+
+/* No comment provided by engineer. */
+"The name %s is already used" = "The name %s is already used";
+
+/* No comment provided by engineer. */
+"There are unsaved changed, should these be saved?" = "There are unsaved changed, should these be saved?";
+

pyobjc/Examples/FieldGraph/English.lproj/MainMenu.nib/keyedobjects.nib

Binary file added.
 default on the command line.   Make sure you are installing python
 against the correct version of python.</p>
 <h2><a name="examples">Examples</a></h2>
-<p>The examples directory contains a number of projects that demonstrate
+<p>The <a href="Examples/00ReadMe.html">examples directory</a> contains a number of projects that demonstrate
 various features of the PyObjC bridge. The scripts at the top level of
-the examples directory were mostly written to test a particular
+the <a href="Examples/00ReadMe.html">examples directory</a> were mostly written to test a particular
 feature of the bridge (or document a bug until a fix could be found).</p>
 <p>CurrencyConverter and TableModel are both examples of standalone
 Cocoa-Python applications.  To build and execute:</p>
 to build the applications.</p>
 <h2><a name="project-templates">Project Templates</a></h2>
 <p>The <code><span>ProjectBuilder</span> <span>Extras</span></code> directory contains additional files that can
-be used with Project Builder. The diretory <code><span>Specifications</span></code> contains files
+be used with Project Builder. The directory <code><span>Specifications</span></code> contains files
 that enable syntax coloring for Python files in Project Builder.</p>
 <p>The <code><span>Project</span> <span>Templates</span></code> directory contains project templates for
 Project Builder.  These have to be copied to
 <blockquote>
 <p><a href="http://lists.sourceforge.net/lists/listinfo/pyobjc-dev">http://lists.sourceforge.net/lists/listinfo/pyobjc-dev</a></p>
 </blockquote>
-<p>b.bum &lt;<a href="mailto:bbum@codefab.com">bbum@codefab.com</a>&gt;    Ronald Oussoren &lt;<a href="mailto:oussoren@cistron.nl">oussoren@cistron.nl</a>&gt;</p>
+<p>b.bum &lt;<a href="mailto:bbum@codefab.com">bbum@codefab.com</a>&gt;, Ronald Oussoren &lt;<a href="mailto:oussoren@cistron.nl">oussoren@cistron.nl</a>&gt;</p>
 </body>
 </html>

pyobjc/Scripts/CodeGenerators/cocoa_generator.py

     print "Run me from the root of the PyObjC source tree"
     sys.exit(1)
 
+if not os.path.exists('build'):
+    os.mkdir('build')
+
+if not os.path.exists('build/codegen'):
+    os.mkdir('build/codegen')
+
 FRAMEWORKS="/System/Library/Frameworks"
 FOUNDATION=os.path.join(FRAMEWORKS, "Foundation.framework")
 APPKIT=os.path.join(FRAMEWORKS, "AppKit.framework")
 
     return 1
 
-enum_generator.generate(FOUNDATION_HDRS, 'Modules/Foundation/_Fnd_Enum.inc')
-enum_generator.generate(APPKIT_HDRS, 'Modules/AppKit/_App_Enum.inc')
+enum_generator.generate(FOUNDATION_HDRS, 'build/codegen/_Fnd_Enum.inc')
+enum_generator.generate(APPKIT_HDRS, 'build/codegen/_App_Enum.inc')
 enum_generator.generate(ADDRESSBOOK_HDRS,
-                        'Modules/AddressBook/_Addr_Enum.inc',
+                        'build/codegen/_Addr_Enum.inc',
                         filter=filterAddressBookHeaders)
-enum_generator.generate(PREFPANES_HDRS, 'Modules/PreferencePanes/_PreferencePanes_Enum.inc')
-enum_generator.generate(IB_HDRS, 'Modules/InterfaceBuilder/_InterfaceBuilder_Enum.inc')
-enum_generator.generate(WEBKIT_HDRS, 'Modules/WebKit/_WebKit_Enum.inc')
+enum_generator.generate(PREFPANES_HDRS, 
+                        'build/codegen/_PreferencePanes_Enum.inc')
+enum_generator.generate(IB_HDRS, 
+                        'build/codegen/_InterfaceBuilder_Enum.inc')
+enum_generator.generate(WEBKIT_HDRS, 
+                        'build/codegen/_WebKit_Enum.inc')
 
-strconst_generator.generate(FOUNDATION_HDRS, 'Modules/Foundation/_Fnd_Str.inc')
-strconst_generator.generate(APPKIT_HDRS, 'Modules/AppKit/_App_Str.inc')
+strconst_generator.generate(FOUNDATION_HDRS, 'build/codegen/_Fnd_Str.inc')
+strconst_generator.generate(APPKIT_HDRS, 'build/codegen/_App_Str.inc')
 strconst_generator.generate(ADDRESSBOOK_HDRS,
-                            'Modules/AddressBook/_Addr_Str.inc',
+                            'build/codegen/_Addr_Str.inc',
                             filter=filterAddressBookHeaders)
-strconst_generator.generate(PREFPANES_HDRS, 'Modules/PreferencePanes/_PreferencePanes_Str.inc')
-strconst_generator.generate(IB_HDRS, 'Modules/InterfaceBuilder/_InterfaceBuilder_Str.inc')
+strconst_generator.generate(PREFPANES_HDRS, 
+                        'build/codegen/_PreferencePanes_Str.inc')
+strconst_generator.generate(IB_HDRS, 'build/codegen/_InterfaceBuilder_Str.inc')
 
 # The two items on the ignore-list cause link errors, to-be-investigated.
 strconst_generator.generate(WEBKIT_HDRS,
-                            'Modules/WebKit/_WebKit_Str.inc',
-                            ignore=('WebElementImageAltStringKey', 'WebPreferencesChangedNotification')
+                            'build/codegen/_WebKit_Str.inc',
+                            ignore=('WebElementImageAltStringKey', 
+                                    'WebPreferencesChangedNotification')
 )
 
 FOUNDATION_PREFIX="FOUNDATION_EXPORT"
 FOUNDATION_IGNORE_LIST=(
-	# All have types that are not (yet) mapped to python
-	'NSZeroPoint',
-	'NSZeroSize',
-	'NSZeroRect',
-	"NSNonOwnedPointerHashCallBacks",
-	"NSNonRetainedObjectHashCallBacks",
-	"NSObjectHashCallBacks",
-	"NSOwnedObjectIdentityHashCallBacks",
-	"NSOwnedPointerHashCallBacks",
-	"NSPointerToStructHashCallBacks",
-	"NSIntMapKeyCallBacks",
-	"NSNonOwnedPointerMapKeyCallBacks",
-	"NSNonOwnedPointerOrNullMapKeyCallBacks",
-	"NSNonRetainedObjectMapKeyCallBacks",
-	"NSObjectMapKeyCallBacks",
-	"NSOwnedPointerMapKeyCallBacks",
-	"NSIntMapValueCallBacks", 
-	"NSNonOwnedPointerMapValueCallBacks",
-	"NSObjectMapValueCallBacks",
-	"NSNonRetainedObjectMapValueCallBacks",
-	"NSOwnedPointerMapValueCallBacks",
-	"NSIntHashCallBacks",
-        "NSHangOnMallocError",
+    # All have types that are not (yet) mapped to python
+    'NSZeroPoint',
+    'NSZeroSize',
+    'NSZeroRect',
+    "NSNonOwnedPointerHashCallBacks",
+    "NSNonRetainedObjectHashCallBacks",
+    "NSObjectHashCallBacks",
+    "NSOwnedObjectIdentityHashCallBacks",
+    "NSOwnedPointerHashCallBacks",
+    "NSPointerToStructHashCallBacks",
+    "NSIntMapKeyCallBacks",
+    "NSNonOwnedPointerMapKeyCallBacks",
+    "NSNonOwnedPointerOrNullMapKeyCallBacks",
+    "NSNonRetainedObjectMapKeyCallBacks",
+    "NSObjectMapKeyCallBacks",
+    "NSOwnedPointerMapKeyCallBacks",
+    "NSIntMapValueCallBacks", 
+    "NSNonOwnedPointerMapValueCallBacks",
+    "NSObjectMapValueCallBacks",
+    "NSNonRetainedObjectMapValueCallBacks",
+    "NSOwnedPointerMapValueCallBacks",
+    "NSIntHashCallBacks",
+    "NSHangOnMallocError",
 )
 
-var_generator.generate(FOUNDATION_HDRS, 'Modules/Foundation/_Fnd_Var.inc', FOUNDATION_PREFIX, FOUNDATION_IGNORE_LIST)
+var_generator.generate(FOUNDATION_HDRS, 'build/codegen/_Fnd_Var.inc', FOUNDATION_PREFIX, FOUNDATION_IGNORE_LIST)
 
 APPKIT_PREFIX="APPKIT_EXTERN"
 APPKIT_IGNORE_LIST=(
-	# First two have types that are not yet mapped
-	'NSIconSize', 
-	'NSTokenSize', 
+    # First two have types that are not yet mapped
+    'NSIconSize', 
+    'NSTokenSize', 
 
-	# NSApp is a 'real' variable, will probably add get/set functions
-	'NSApp')
+    # NSApp is a 'real' variable, will probably add get/set functions
+    'NSApp')
 
-var_generator.generate(APPKIT_HDRS, 'Modules/AppKit/_App_Var.inc', APPKIT_PREFIX, APPKIT_IGNORE_LIST)
+var_generator.generate(APPKIT_HDRS, 
+            'build/codegen/_App_Var.inc', APPKIT_PREFIX, APPKIT_IGNORE_LIST)
 
 FOUNDATION_IGNORE_LIST=(
-	# Private functions 
-	'_NSAddHandler2(',
-	'_NSRemoveHandler2(',
-	'_NSExceptionObjectFromHandler2(',
-        '_NSAutoreleaseNoPool(',
-        '_NSAutoreleaseFreedObject(',
-        '_NSAutoreleaseHighWaterLog(',
-        'NXReadNSObjectFromCoder(',
+    # Private functions 
+    '_NSAddHandler2(',
+    '_NSRemoveHandler2(',
+    '_NSExceptionObjectFromHandler2(',
+    '_NSAutoreleaseNoPool(',
+    '_NSAutoreleaseFreedObject(',
+    '_NSAutoreleaseHighWaterLog(',
+    'NXReadNSObjectFromCoder(',
 
 
-        # List of functions that are not usefull from Python:
-        'NSFrameAddress(',
-        'NSReturnAddress(',
-        'NSRecordAllocationEvent(',
-        'NSCreateHashTableWithZone(',
-        'NSCreateHashTable(',
-        'NSFreeHashTable(',
-        'NSResetHashTable(',
-        'NSCompareHashTables(',
-        'NSCopyHashTableWithZone(',
-        'NSHashGet(',
-        'NSHashInsert(',
-        'NSHashInsertKnownAbsent(',
-        'NSHashInsertIfAbsent(',
-        'NSHashRemove(',
-        'NSEnumerateHashTable(',
-        'NSNextHashEnumeratorItem(',
-        'NSEndHashTableEnumeration(',
-        'NSCountHashTable(',
-        'NSStringFromHashTable(',
-        'NSAllHashTableObjects(',
-        'NSJavaClassesFromPath(',
-        'NSJavaClassesForBundle(',
-        'NSCreateMapTableWithZone(',
-        'NSCreateMapTable(',
-        'NSFreeMapTable(',
-        'NSResetMapTable(',
-        'NSCompareMapTables(',
-        'NSCopyMapTableWithZone(',
-        'NSMapMember(',
-        'NSMapGet(',
-        'NSMapInsert(',
-        'NSMapInsertKnownAbsent(',
-        'NSMapInsertIfAbsent(',
-        'NSMapRemove(',
-        'NSEnumerateMapTable(',
-        'NSNextMapEnumeratorPair(',
-        'NSEndMapTableEnumeration(',
-        'NSCountMapTable(',
-        'NSStringFromMapTable(',
-        'NSAllMapTableKeys(',
-        'NSAllMapTableValues(',
-        'NSGetSizeAndAlignment(', # Hmm, shouldn't we use this in the bridge?
-        'NSLogv(',
-        'NSAllocateObject(',
-        'NSCopyObject(',
-        'NSShouldRetainWithZone(',
-        'NSAllocateMemoryPages(',
-        'NSDeallocateMemoryPages(',
-        'NSCopyMemoryPages(',
+    # List of functions that are not usefull from Python:
+    'NSFrameAddress(',
+    'NSReturnAddress(',
+    'NSRecordAllocationEvent(',
+    'NSCreateHashTableWithZone(',
+    'NSCreateHashTable(',
+    'NSFreeHashTable(',
+    'NSResetHashTable(',
+    'NSCompareHashTables(',
+    'NSCopyHashTableWithZone(',
+    'NSHashGet(',
+    'NSHashInsert(',
+    'NSHashInsertKnownAbsent(',
+    'NSHashInsertIfAbsent(',
+    'NSHashRemove(',
+    'NSEnumerateHashTable(',
+    'NSNextHashEnumeratorItem(',
+    'NSEndHashTableEnumeration(',
+    'NSCountHashTable(',
+    'NSStringFromHashTable(',
+    'NSAllHashTableObjects(',
+    'NSJavaClassesFromPath(',
+    'NSJavaClassesForBundle(',
+    'NSCreateMapTableWithZone(',
+    'NSCreateMapTable(',
+    'NSFreeMapTable(',
+    'NSResetMapTable(',
+    'NSCompareMapTables(',
+    'NSCopyMapTableWithZone(',
+    'NSMapMember(',
+    'NSMapGet(',
+    'NSMapInsert(',
+    'NSMapInsertKnownAbsent(',
+    'NSMapInsertIfAbsent(',
+    'NSMapRemove(',
+    'NSEnumerateMapTable(',
+    'NSNextMapEnumeratorPair(',
+    'NSEndMapTableEnumeration(',
+    'NSCountMapTable(',
+    'NSStringFromMapTable(',
+    'NSAllMapTableKeys(',
+    'NSAllMapTableValues(',
+    'NSGetSizeAndAlignment(', # Hmm, shouldn't we use this in the bridge?
+    'NSLogv(',
+    'NSAllocateObject(',
+    'NSCopyObject(',
+    'NSShouldRetainWithZone(',
+    'NSAllocateMemoryPages(',
+    'NSDeallocateMemoryPages(',
+    'NSCopyMemoryPages(',
 
 
-        # List of manually wrapped functions:
-        'NSFileTypeForHFSTypeCode(',
-        'NSHFSTypeCodeFromFileType(',
-        'NSStringFromPoint',
+    # List of manually wrapped functions:
+    'NSFileTypeForHFSTypeCode(',
+    'NSHFSTypeCodeFromFileType(',
+    'NSStringFromPoint',
 
-        # NSDecimal support, should wrap type
-        'NSDecimalCopy(',
-        'NSDecimalCompact(',
-        'NSDecimalCompare(',
-        'NSDecimalRound(',
-        'NSDecimalNormalize(',
-        'NSDecimalAdd(',
-        'NSDecimalSubtract(',
-        'NSDecimalMultiply(',
-        'NSDecimalDivide(',
-        'NSDecimalPower(',
-        'NSDecimalMultiplyByPowerOf10(',
-        'NSDecimalString(',
+    # NSDecimal support, should wrap type
+    'NSDecimalCopy(',
+    'NSDecimalCompact(',
+    'NSDecimalCompare(',
+    'NSDecimalRound(',
+    'NSDecimalNormalize(',
+    'NSDecimalAdd(',
+    'NSDecimalSubtract(',
+    'NSDecimalMultiply(',
+    'NSDecimalDivide(',
+    'NSDecimalPower(',
+    'NSDecimalMultiplyByPowerOf10(',
+    'NSDecimalString(',
 
-        # Zones might be usefull someday
-        'NSCreateZone(',
-        'NSRecycleZone(',
-        'NSSetZoneName(',
-        'NSZoneName(',
-        'NSZoneFromPointer(',
-        'NSZoneMalloc(',
-        'NSZoneCalloc(',
-        'NSZoneRealloc(',
-        'NSZoneFree(',
+    # Zones might be usefull someday
+    'NSCreateZone(',
+    'NSRecycleZone(',
+    'NSSetZoneName(',
+    'NSZoneName(',
+    'NSZoneFromPointer(',
+    'NSZoneMalloc(',
+    'NSZoneCalloc(',
+    'NSZoneRealloc(',
+    'NSZoneFree(',
 
 
-        # TODO
-        'NSUncaughtExceptionHandler(',
-        'NSSetUncaughtExceptionHandler(',
-        'NSGetUncaughtExceptionHandler(',
-        'NSDivideRect(',
-        'NSDefaultMallocZone(',
+    # TODO
+    'NSUncaughtExceptionHandler(',
+    'NSSetUncaughtExceptionHandler(',
+    'NSGetUncaughtExceptionHandler(',
+    'NSDivideRect(',
+    'NSDefaultMallocZone(',
 )
 
 
 APPKIT_IGNORE_LIST=(
+    # List of manually wrapped functions:
+    'NSApplicationMain(',
+    'NSCountWindows(',
+    'NSCountWindowsForContext(',
+    'NSAvailableWindowDepths(',
+    'NSRectFillList(',
+    'NSGetWindowServerMemory(',
 
-        # List of manually wrapped functions:
-        'NSApplicationMain(',
-        'NSCountWindows(',
-        'NSCountWindowsForContext(',
-        'NSAvailableWindowDepths(',
-        'NSRectFillList(',
-        'NSGetWindowServerMemory(',
 
+    #TODO:
+    'NSBestDepth (',
+    'NSAvailableWindowDepths (',
+    'NSRectFillListWithGrays(',
+    'NSRectFillListWithColors(',
+    'NSRectFillListUsingOperation(',
+    'NSRectFillListWithColorsUsingOperation(',
+    'NSRectClipList(',
+    'NSDrawTiledRects(',
+    'NSDrawBitmap(',
+    'NSWindowList(',
+    'NSWindowListForContext(',
+    'NSDrawColorTiledRects(',
+)
+func_collector.generate(FOUNDATION_HDRS, 'build/codegen/Foundation.prototypes', 
+    FOUNDATION_PREFIX, FOUNDATION_IGNORE_LIST)
+func_collector.generate(APPKIT_HDRS, 'build/codegen/AppKit.prototypes', 
+    APPKIT_PREFIX, APPKIT_IGNORE_LIST)
 
-        #TODO:
-        'NSBestDepth (',
-        'NSAvailableWindowDepths (',
-        'NSRectFillListWithGrays(',
-        'NSRectFillListWithColors(',
-        'NSRectFillListUsingOperation(',
-        'NSRectFillListWithColorsUsingOperation(',
-        'NSRectClipList(',
-        'NSDrawTiledRects(',
-        'NSDrawBitmap(',
-        'NSWindowList(',
-        'NSWindowListForContext(',
-        'NSDrawColorTiledRects(',
-)
-func_collector.generate(FOUNDATION_HDRS, 'Modules/Foundation/Foundation.prototypes', 
-	FOUNDATION_PREFIX, FOUNDATION_IGNORE_LIST)
-func_collector.generate(APPKIT_HDRS, 'Modules/AppKit/AppKit.prototypes', 
-	APPKIT_PREFIX, APPKIT_IGNORE_LIST)
-
-# Add easy to handle types in Foundation:
-#func_builder.SIMPLE_TYPES['NSHashTable*'] = (
-#	'\tresult = PyCObject_New(%(varname)s);\n\t if (result == NULL) return NULL;',
-#	'O&',
-#	'convert_NSHashtable, &%(varname)s',
-#)
 
 func_builder.INT_ALIASES.extend([
-	'NSSearchPathDomainMask', 'NSCalculationError',
-	'NSComparisonResult', 'NSInsertionPosition',
-	'NSNotificationCoalescing', 'NSNotificationCoalescing',
-	'NSRectEdge', 'NSRelativePosition',
-	'NSRoundingMode', 'NSSaveOptions', 'NSSearchPathDirectory',
-	'NSSearchPathDomainMask', 'NSTestComparisonOperation',
-	'NSURLHandleStatus', 'NSWhoseSubelementIdentifier']
+    'NSSearchPathDomainMask', 'NSCalculationError',
+    'NSComparisonResult', 'NSInsertionPosition',
+    'NSNotificationCoalescing', 'NSNotificationCoalescing',
+    'NSRectEdge', 'NSRelativePosition',
+    'NSRoundingMode', 'NSSaveOptions', 'NSSearchPathDirectory',
+    'NSSearchPathDomainMask', 'NSTestComparisonOperation',
+    'NSURLHandleStatus', 'NSWhoseSubelementIdentifier']
 )
 func_builder.IGNORE_VARARGS.extend([
-        # Some of these are Foundation some are AppKit
-        'NSGetInformationalAlertPanel',
-        'NSLog',
-        'NSRunAlertPanel',
-        'NSRunInformationalAlertPanel',
-        'NSRunCriticalAlertPanel',
-        'NSRunAlertPanelRelativeToWindow',
-        'NSRunInformationalAlertPanelRelativeToWindow',
-        'NSRunCriticalAlertPanelRelativeToWindow',
-        'NSBeginAlertSheet',
-        'NSBeginInformationalAlertSheet',
-        'NSBeginCriticalAlertSheet',
-        'NSGetAlertPanel',
-        'NSGetCriticalAlertPanel',
+    # Some of these are Foundation some are AppKit
+    'NSGetInformationalAlertPanel',
+    'NSLog',
+    'NSRunAlertPanel',
+    'NSRunInformationalAlertPanel',
+    'NSRunCriticalAlertPanel',
+    'NSRunAlertPanelRelativeToWindow',
+    'NSRunInformationalAlertPanelRelativeToWindow',
+    'NSRunCriticalAlertPanelRelativeToWindow',
+    'NSBeginAlertSheet',
+    'NSBeginInformationalAlertSheet',
+    'NSBeginCriticalAlertSheet',
+    'NSGetAlertPanel',
+    'NSGetCriticalAlertPanel',
 ])
 
 def BeginSheetMapper(funcname, args):
 func_builder.FUNC_MAP['NSBeginInformationalAlertSheet'] = BeginSheetMapper
 func_builder.FUNC_MAP['NSBeginCriticalAlertSheet'] = BeginSheetMapper
 
-fd = dupfile('Modules/Foundation/_Fnd_Functions.inc', 'w')
+fd = dupfile('build/codegen/_Fnd_Functions.inc', 'w')
 structs = ['NSPoint', 'NSSize', 'NSRect', 'NSRange']
 for s in structs:
-	func_builder.SIMPLE_TYPES[s] = (
-		'\tresult = PyObjC_ObjCToPython(@encode(%s), (void*)&%%(varname)s); \n\tif (result == NULL) return NULL;'%s,
-		'O&',
-		'convert_%s, &%%(varname)s'%s
-	)
-	fd.write('''\
+    func_builder.SIMPLE_TYPES[s] = (
+        '\tresult = PyObjC_ObjCToPython(@encode(%s), (void*)&%%(varname)s); \n\tif (result == NULL) return NULL;'%s,
+        'O&',
+        'convert_%s, &%%(varname)s'%s
+    )
+    fd.write('''\
+
 static inline int convert_%(type)s(PyObject* object, void* pvar)
 {
-	int err;
+        int err;
 
-	err = PyObjC_PythonToObjC(@encode(%(type)s), object, pvar);
-	if (err == -1) {
-		return 0;
-	}
-	return 1;
+        err = PyObjC_PythonToObjC(@encode(%(type)s), object, pvar);
+        if (err == -1) {
+                return 0;
+        }
+        return 1;
 }
 '''%{'type': s })
 
 
-func_builder.process_list(fd , file('Modules/Foundation/Foundation.prototypes'))
+func_builder.process_list(fd , file('build/codegen/Foundation.prototypes'))
 fd = None
 for s in structs:
-	del func_builder.SIMPLE_TYPES[s]
+    del func_builder.SIMPLE_TYPES[s]
 
-fd = dupfile('Modules/AppKit/_App_Functions.inc', 'w')
+fd = dupfile('build/codegen/_App_Functions.inc', 'w')
 structs = ['NSAffineTransformStruct', 'NSRect', 'NSPoint']
 for s in structs:
-	func_builder.SIMPLE_TYPES[s] = (
-		'\tresult = PyObjC_ObjCToPython(@encode(%s), (void*)&%%(varname)s); \n\tif (result == NULL) return NULL;'%s,
-		'O&',
-		'convert_%s, &%%(varname)s'%s
-	)
-	fd.write('''\
+    func_builder.SIMPLE_TYPES[s] = (
+        '\tresult = PyObjC_ObjCToPython(@encode(%s), (void*)&%%(varname)s); \n\tif (result == NULL) return NULL;'%s,
+        'O&',
+        'convert_%s, &%%(varname)s'%s
+    )
+    fd.write('''\
 static inline int convert_%(type)s(PyObject* object, void* pvar)
 {
-	int err;
+        int err;
 
-	err = PyObjC_PythonToObjC(@encode(%(type)s), object, pvar);
-	if (err == -1) {
-		return 0;
-	}
-	return 1;
+        err = PyObjC_PythonToObjC(@encode(%(type)s), object, pvar);
+        if (err == -1) {
+                return 0;
+        }
+        return 1;
 }
 '''%{'type': s })
 
 func_builder.INT_ALIASES.extend([
-	'NSApplicationTerminateReply', 'NSBackingStoreType',
-	'NSBezelStyle', 'NSBezierPathElement',
-	'NSBitmapImageFileType', 'NSBorderType', 'NSBoxType',
-	'NSButtonType', 'NSCellAttribute', 'NSCellImagePosition',
-	'NSCellStateValue', 'NSCellType', 'NSCompositingOperation',
-	'NSControlSize', 'NSControlTint', 'NSDocumentChangeType',
-	'NSDragOperation', 'NSDrawerState', 'NSEventType',
-	'NSFocusRingPlacement', 'NSFontAction', 'NSFontTraitMask',
-	'NSGlyph', 'NSGlyphInscription', 'NSGlyphLayoutMode',
-	'NSGlyphRelation', 'NSGradientType', 'NSImageAlignment',
-	'NSImageFrameStyle', 'NSImageInterpolation', 'NSImageScaling',
-	'NSInterfaceStyle', 'NSLayoutDirection', 'NSLayoutStatus',
-	'NSLineBreakMode', 'NSLineCapStyle', 'NSLineJoinStyle',
-	'NSLineMovementDirection', 'NSLineSweepDirection',
-	'NSMatrixMode', 'NSMultibyteGlyphPacking', 'NSOpenGLContextParameter',
-	'NSOpenGLGlobalOption', 'NSOpenGLPixelFormatAttribute',
-	'NSPopUpArrowPosition', 'NSPrinterTableStatus',
-	'NSPrintingOrientation', 'NSPrintingPageOrder', 
-	'NSPrintingPaginationMode', 'NSProgressIndicatorThickness',
-	'NSQTMovieLoopMode', 'NSRequestUserAttentionType',
-	'NSRulerOrientation', 'NSSaveOperationType',
-	'NSScrollArrowPosition', 'NSScrollerArrow',
-	'NSScrollerPart', 'NSSelectionAffinity',
-	'NSSelectionDirection', 'NSSelectionGranularity',
-	'NSTabState', 'NSTabViewState', 'NSTableViewDropOperation',
-	'NSTextAlignment', 'NSTextTabType', 'NSTickMarkPosition',
-	'NSTIFFCompression', 'NSTitlePosition', 'NSToolbarDisplayMode',
-	'NSToolTipTag', 'NSTrackingRectTag', 'NSUsableScrollerParts',
-	'NSWindingRule', 'NSWindowDepth', 'NSWindowOrderingMode',
+    'NSApplicationTerminateReply', 'NSBackingStoreType',
+    'NSBezelStyle', 'NSBezierPathElement',
+    'NSBitmapImageFileType', 'NSBorderType', 'NSBoxType',
+    'NSButtonType', 'NSCellAttribute', 'NSCellImagePosition',
+    'NSCellStateValue', 'NSCellType', 'NSCompositingOperation',
+    'NSControlSize', 'NSControlTint', 'NSDocumentChangeType',
+    'NSDragOperation', 'NSDrawerState', 'NSEventType',
+    'NSFocusRingPlacement', 'NSFontAction', 'NSFontTraitMask',
+    'NSGlyph', 'NSGlyphInscription', 'NSGlyphLayoutMode',
+    'NSGlyphRelation', 'NSGradientType', 'NSImageAlignment',
+    'NSImageFrameStyle', 'NSImageInterpolation', 'NSImageScaling',
+    'NSInterfaceStyle', 'NSLayoutDirection', 'NSLayoutStatus',
+    'NSLineBreakMode', 'NSLineCapStyle', 'NSLineJoinStyle',
+    'NSLineMovementDirection', 'NSLineSweepDirection',
+    'NSMatrixMode', 'NSMultibyteGlyphPacking', 'NSOpenGLContextParameter',
+    'NSOpenGLGlobalOption', 'NSOpenGLPixelFormatAttribute',
+    'NSPopUpArrowPosition', 'NSPrinterTableStatus',
+    'NSPrintingOrientation', 'NSPrintingPageOrder', 
+    'NSPrintingPaginationMode', 'NSProgressIndicatorThickness',
+    'NSQTMovieLoopMode', 'NSRequestUserAttentionType',
+    'NSRulerOrientation', 'NSSaveOperationType',
+    'NSScrollArrowPosition', 'NSScrollerArrow',
+    'NSScrollerPart', 'NSSelectionAffinity',
+    'NSSelectionDirection', 'NSSelectionGranularity',
+    'NSTabState', 'NSTabViewState', 'NSTableViewDropOperation',
+    'NSTextAlignment', 'NSTextTabType', 'NSTickMarkPosition',
+    'NSTIFFCompression', 'NSTitlePosition', 'NSToolbarDisplayMode',
+    'NSToolTipTag', 'NSTrackingRectTag', 'NSUsableScrollerParts',
+    'NSWindingRule', 'NSWindowDepth', 'NSWindowOrderingMode',
 ])
 
 
-func_builder.process_list(fd, file('Modules/AppKit/AppKit.prototypes'))
+func_builder.process_list(fd, file('build/codegen/AppKit.prototypes'))
 for s in structs:
-	del func_builder.SIMPLE_TYPES[s]
+    del func_builder.SIMPLE_TYPES[s]

pyobjc/Scripts/CodeGenerators/enum_generator.py

 BLOCK_E_RE=re.compile('\*/')
 
 def entry(fp, val):
-	fp.write('\t { "%s", %s },\n'%(val, val))
+    fp.write('\t { "%s", %s },\n'%(val, val))
 
 def process_file(outfp, filename):
-	fp = open(filename, 'r')
+    fp = open(filename, 'r')
 
-	outfp.write("\n\t/* From: %s */\n"%os.path.basename(filename))
+    outfp.write("\n\t/* From: %s */\n"%os.path.basename(filename))
 
-	in_enum = 0
-	in_comment = 0
+    in_enum = 0
+    in_comment = 0
 
-	for ln in fp.xreadlines():
-		if not in_enum:
-			m = SINGLE_LINE_RE.search(ln)
-			if m:
-				values = m.group(1)
-				values = values.split(',')
+    for ln in fp.xreadlines():
+        if not in_enum:
+                m = SINGLE_LINE_RE.search(ln)
+                if m:
+                    values = m.group(1)
+                    values = values.split(',')
 
-				for v in values:
-					m = IDENT_RE.search(v)
-					if not m:
-						continue
+                    for v in values:
+                        m = IDENT_RE.search(v)
+                        if not m:
+                            continue
 
-					ident = v[m.start():m.end()]
-					entry(outfp, ident)
-			elif START_RE.search(ln):
-				in_enum = 1
-		else:
-			if in_comment:
-				m = BLOCK_E_RE.search(ln)
-				if not m:
-					continue
-				ln = ln[m.end():]
-				in_comment = 0
+                        ident = v[m.start():m.end()]
+                        entry(outfp, ident)
+                elif START_RE.search(ln):
+                    in_enum = 1
+        else:
+                if in_comment:
+                    m = BLOCK_E_RE.search(ln)
+                    if not m:
+                        continue
+                    ln = ln[m.end():]
+                    in_comment = 0
 
-			if END_RE.match(ln):
-				in_enum = 0
-				continue
+                if END_RE.match(ln):
+                    in_enum = 0
+                    continue
 
-			ln = LINE_COMMENT_RE.sub('', ln)	
-			ln = BLOCK_1_RE.sub('', ln)
-			m = BLOCK_S_RE.search(ln)
-			if m:
-				in_comment = 1
-				ln = ln[:m.start()]
+                ln = LINE_COMMENT_RE.sub('', ln)        
+                ln = BLOCK_1_RE.sub('', ln)
+                m = BLOCK_S_RE.search(ln)
+                if m:
+                    in_comment = 1
+                    ln = ln[:m.start()]
 
-			m = IDENT_RE.search(ln)
-			if not m:
-				continue
+                m = IDENT_RE.search(ln)
+                if not m:
+                    continue
 
-			ident = ln[m.start():m.end()]
-			if not ident in ['if', 'endif', 'else']:
-				entry(outfp, ident)
+                ident = ln[m.start():m.end()]
+                if not ident in ['if', 'endif', 'else']:
+                    entry(outfp, ident)
 
 
 def generate(dirname, fn = None, filter = lambda x: 1):
-	if not os.path.exists(dirname): return
+        if not os.path.exists(dirname): return
 
-	if fn:
-		fp = dupfile(fn, 'w')
-	else:
-		fp = sys.stdout
+        if fn:
+            fp = dupfile(fn, 'w')
+        else:
+            fp = sys.stdout
 
-	fp.write("/*\n")
-	fp.write(" * Enumeration constants. This file is generated from files in\n")
-	fp.write(" * %s\n"%dirname)
-	fp.write(" */\n")
-	fp.write("static struct inttable enum_table[] = {\n")
-	fnames = [ os.path.join(dirname, fn)
-				for fn in os.listdir(dirname)
-				if fn.endswith('.h') and filter(fn) ]
-	for f in fnames:
-		process_file(fp, f)
-	fp.write("\t{0, 0} /* Sentinel */\n")
-	fp.write("};\n")
+        fp.write("/*\n")
+        fp.write(" * Enumeration constants. This file is generated from files in\n")
+        fp.write(" * %s\n"%dirname)
+        fp.write(" */\n")
+        fp.write("static struct inttable enum_table[] = {\n")
+        fnames = [ os.path.join(dirname, fn)
+                            for fn in os.listdir(dirname)
+                            if fn.endswith('.h') and filter(fn) ]
+        for f in fnames:
+            process_file(fp, f)
+        fp.write("\t{0, 0} /* Sentinel */\n")
+        fp.write("};\n")
         fp.close()
 
 if __name__ == "__main__":
-	import sys
-	generate(sys.argv[1])
+    import sys
+    generate(sys.argv[1])

pyobjc/Scripts/CodeGenerators/func_builder.py

 
 static inline int convert_char(PyObject* object, void* pvar)
 {
-	char* pchar = (char*)pvar;
+    char* pchar = (char*)pvar;
 
-	if (!PyString_Check(object)) {
-		PyErr_SetString(PyExc_TypeError, "Expecting string of len 1");
-		return 0;
-	}
+    if (!PyString_Check(object)) {
+        PyErr_SetString(PyExc_TypeError, "Expecting string of len 1");
+        return 0;
+    }
 
-	if (PyString_Size(object) != 1) {
-		PyErr_SetString(PyExc_TypeError, "Expecting string of len 1");
-		return 0;
-	}
+    if (PyString_Size(object) != 1) {
+        PyErr_SetString(PyExc_TypeError, "Expecting string of len 1");
+        return 0;
+    }
 
-	*pchar = *PyString_AsString(object);
-	return 1;
+    *pchar = *PyString_AsString(object);
+    return 1;
 }
 
 static inline int convert_id(PyObject* object, void* pvar)
 {
-	id* pid = (id*)pvar;
+    id* pid = (id*)pvar;
 
-	*pid = PyObjC_PythonToId(object);
+    *pid = PyObjC_PythonToId(object);
 
-        if (PyErr_Occurred()) {
-            return 0;
-        } 
-        return 1;
+    if (PyErr_Occurred()) {
+        return 0;
+    } 
+    return 1;
 }
 
 static inline int convert_SEL(PyObject* object, void* pvar)
 {
-        if (object == Py_None) {
-            *(SEL*)pvar = NULL;
-            return 1;
-        }
-        if (PyObjCSelector_Check(object)) {
-            *(SEL*)pvar = PyObjCSelector_GetSelector(object);
-            return 1;
-        }
-	if (!PyString_Check(object)) {
-		PyErr_SetString(PyExc_TypeError, "Expected string");
-		return 0;
-	}
+    if (object == Py_None) {
+        *(SEL*)pvar = NULL;
+        return 1;
+    }
+    if (PyObjCSelector_Check(object)) {
+        *(SEL*)pvar = PyObjCSelector_GetSelector(object);
+        return 1;
+    }
+    if (!PyString_Check(object)) {
+        PyErr_SetString(PyExc_TypeError, "Expected string");
+        return 0;
+    }
 
-	*(SEL*)pvar = SELUID(PyString_AsString(object));
-	return 1;
+    *(SEL*)pvar = SELUID(PyString_AsString(object));
+    return 1;
 }
 
 static inline int convert_Class(PyObject* object, void* pvar)
 {
-	if (!PyObjCClass_Check(object)) {
-		PyErr_SetString(PyExc_TypeError, "Expected objective-C class");
-		return 0;
-	}
+    if (!PyObjCClass_Check(object)) {
+        PyErr_SetString(PyExc_TypeError, "Expected objective-C class");
+        return 0;
+    }
 
-	*(Class*)pvar = PyObjCClass_GetClass(object);
-	if (*(Class*)pvar == NULL) return 0;
-	return 1;
+    *(Class*)pvar = PyObjCClass_GetClass(object);
+    if (*(Class*)pvar == NULL) return 0;
+    return 1;
 }
 
 """
 
 PTR_RE=re.compile('[ \t]+\*')
 def simplify_type(typestr):
-	typestr = PTR_RE.sub('*', typestr)
+    typestr = PTR_RE.sub('*', typestr)
 
-	return typestr
+    return typestr
 
 PROT_MATCHER=re.compile('<[A-Za-z0-9_ \t,]*>')
 def is_id(typestr):
-	# Remove protocol 'declarations' (id <NSObject, NSString>)
-	typestr = PROT_MATCHER.sub('', typestr).strip()
+    # Remove protocol 'declarations' (id <NSObject, NSString>)
+    typestr = PROT_MATCHER.sub('', typestr).strip()
 
 
-	if typestr == 'id':
-		return 1
-	elif typestr[-1] != '*':
-		return 0
-	
-        if objc != None:
-            try:
-                    objc.lookUpClass(typestr[:-1])
-                    return 1
-            except:
-                    return 0
-        else:
-            # These types are used in function definition (OSX 10.2), this
-            # list is necessary for people that build without an installed
-            # PyObjC.
-            if typestr[:-1] in ('NSString', 'NSArray', 'NSWindow', 'NSColor', 'NSPasteboard', 'NSBundle', 'NSDictionary', 'NSResponder'):
-                return 1
+    if typestr == 'id':
+        return 1
+    elif typestr[-1] != '*':
+        return 0
+    
+    if objc != None:
+        try:
+            objc.lookUpClass(typestr[:-1])
+            return 1
+        except:
             return 0
+    else:
+        # These types are used in function definition (OSX 10.2), this
+        # list is necessary for people that build without an installed
+        # PyObjC.
+        if typestr[:-1] in ('NSString', 'NSArray', 'NSWindow', 'NSColor', 'NSPasteboard', 'NSBundle', 'NSDictionary', 'NSResponder'):
+            return 1
+        return 0
 
 # TODO: actually use this, and add more types (when using: always check here
 # first, and then special logic (like handling 'id'-like values)
 SIMPLE_TYPES={
-	# key: ( 'to_python', 'parse_fmt', 'parse_args' ) 
-	#      items in the tuple are either None (not needed), a string or
-	#      a function. The string will be %-expanded with a dict containing
-	#      the key 'varname', and varname will be the only argument to
-	#      the function that must return a string.
-	'char': (
-		'\tresult = PyString_FromStringAndSize(&(%(varname)s), 1);\n\tif (result == NULL) return NULL;',
-		'O&', 		
-		'convert_char, &%(varname)s', 
-	),
-	'SEL': (
-		'\tresult = PyString_FromString(SELNAME(%(varname)s));\n\tif (result == NULL) return NULL;',
-		'O&', 		
-		'convert_SEL, &%(varname)s', 
-	),
-	'Class': (
-		'\tresult = PyObjCClass_New(%(varname)s);\n\tif (result == NULL) return NULL;',
-		'O&', 		
-		'convert_Class, &%(varname)s', 
-	),
-	'int': (
-		"\tresult = PyInt_FromLong(%(varname)s);\n\tif (result == NULL) return NULL;",
-		'i',
-		'&%(varname)s',
-		None
-	),
-	'PYOBJC_VOIDPTR': (
-		"\tresult = PyInt_FromLong(%(varname)s);\n\tif (result == NULL) return NULL;",
-		'i',
-		'&%(varname)s',
-		None
-	),
-	'BOOL': (
-		"\tresult = PyObjCBool_FromLong(%(varname)s);\n\tif (result == NULL) return NULL;",
-		'O&', 		
-		'convert_BOOL, &%(varname)s', 
-		None
-	),
-	'unsigned': (
-		"\tresult = PyInt_FromLong(%(varname)s);\n\tif (result == NULL) return NULL;",
-		'i',
-		'&%(varname)s',
-		None
-	),
-	'short': (
-		"\tresult = PyInt_FromLong(%(varname)s);\n\tif (result == NULL) return NULL;",
-		'h',
-		'&%(varname)s',
-		None
-	),
-	'long': (
-		"\tresult = PyInt_FromLong(%(varname)s);\n\tif (result == NULL) return NULL;",
-		'l',
-		'&%(varname)s',
-		None
-	),
-	'float': (
-		"\tresult = PyFloat_FromDouble(%(varname)s);\n\tif (result == NULL) return NULL;",
-		'f',
-		'&%(varname)s',
-		None
-	),
-	'double': (
-		"\tresult = PyFloat_FromDouble(%(varname)s);\n\tif (result == NULL) return NULL;",
-		'd',
-		'&%(varname)s',
-		None
-	),
+    # key: ( 'to_python', 'parse_fmt', 'parse_args' ) 
+    #      items in the tuple are either None (not needed), a string or
+    #      a function. The string will be %-expanded with a dict containing
+    #      the key 'varname', and varname will be the only argument to
+    #      the function that must return a string.
+    'char': (
+        '\tresult = PyString_FromStringAndSize(&(%(varname)s), 1);\n\tif (result == NULL) return NULL;',
+        'O&',                 
+        'convert_char, &%(varname)s', 
+    ),
+    'SEL': (
+        '\tresult = PyString_FromString(SELNAME(%(varname)s));\n\tif (result == NULL) return NULL;',
+        'O&',                 
+        'convert_SEL, &%(varname)s', 
+    ),
+    'Class': (
+        '\tresult = PyObjCClass_New(%(varname)s);\n\tif (result == NULL) return NULL;',
+        'O&',                 
+        'convert_Class, &%(varname)s', 
+    ),
+    'int': (
+        "\tresult = PyInt_FromLong(%(varname)s);\n\tif (result == NULL) return NULL;",
+        'i',
+        '&%(varname)s',
+        None
+    ),
+    'PYOBJC_VOIDPTR': (
+        "\tresult = PyInt_FromLong(%(varname)s);\n\tif (result == NULL) return NULL;",
+        'i',
+        '&%(varname)s',
+        None
+    ),
+    'BOOL': (
+        "\tresult = PyObjCBool_FromLong(%(varname)s);\n\tif (result == NULL) return NULL;",
+        'O&',                 
+        'convert_BOOL, &%(varname)s', 
+        None
+    ),
+    'unsigned': (
+        "\tresult = PyInt_FromLong(%(varname)s);\n\tif (result == NULL) return NULL;",
+        'i',
+        '&%(varname)s',
+        None
+    ),
+    'short': (
+        "\tresult = PyInt_FromLong(%(varname)s);\n\tif (result == NULL) return NULL;",
+        'h',
+        '&%(varname)s',
+        None
+    ),
+    'long': (
+        "\tresult = PyInt_FromLong(%(varname)s);\n\tif (result == NULL) return NULL;",
+        'l',
+        '&%(varname)s',
+        None
+    ),
+    'float': (
+        "\tresult = PyFloat_FromDouble(%(varname)s);\n\tif (result == NULL) return NULL;",
+        'f',
+        '&%(varname)s',
+        None
+    ),
+    'double': (
+        "\tresult = PyFloat_FromDouble(%(varname)s);\n\tif (result == NULL) return NULL;",
+        'd',
+        '&%(varname)s',
+        None
+    ),
 }
-		
+                
 def simple_to_python(varname, typestr):
-	if typestr.startswith('const ') or typestr.startswith('const\t'):
-		typestr = typestr[6:].strip()
+    if typestr.startswith('const ') or typestr.startswith('const\t'):
+        typestr = typestr[6:].strip()
 
-	if is_id(typestr):
-		return "\tresult = PyObjC_IdToPython(%(varname)s); if (result == NULL) return NULL;"%{ 'varname': varname }
+    if is_id(typestr):
+        return "\tresult = PyObjC_IdToPython(%(varname)s); if (result == NULL) return NULL;"%{ 'varname': varname }
 
-	if typestr in INT_ALIASES:
-		x = SIMPLE_TYPES['int']
-	else:
-		x = SIMPLE_TYPES[typestr]
+    if typestr in INT_ALIASES:
+        x = SIMPLE_TYPES['int']
+    else:
+        x = SIMPLE_TYPES[typestr]
 
-	if x[0] is None:
-		return
-	elif isinstance(x[0], str):
-		return x[0]%{'varname': varname }
-	elif isinstance(x[0], types.FunctionType):
-		return x[0](varname)
-	else:
-		raise ValueError, "Bad config for %s"%typestr
+    if x[0] is None:
+        return
+    elif isinstance(x[0], str):
+        return x[0]%{'varname': varname }
+    elif isinstance(x[0], types.FunctionType):
+        return x[0](varname)
+    else:
+        raise ValueError, "Bad config for %s"%typestr
 
 def parsetuple_fmt(typestr):
-	if typestr.startswith('const ') or typestr.startswith('const\t'):
-		typestr = typestr[6:].strip()
+    if typestr.startswith('const ') or typestr.startswith('const\t'):
+        typestr = typestr[6:].strip()
 
-	if is_id(typestr):
-		return 'O&';
+    if is_id(typestr):
+        return 'O&';
 
-	if typestr in INT_ALIASES:
-		x = SIMPLE_TYPES['int']
-	else:
-		x = SIMPLE_TYPES[typestr]
-	return x[1]
+    if typestr in INT_ALIASES:
+        x = SIMPLE_TYPES['int']
+    else:
+        x = SIMPLE_TYPES[typestr]
+    return x[1]
 
 def parsetuple_arguments(typestr, varname):
-	if typestr.startswith('const ') or typestr.startswith('const\t'):
-		typestr = typestr[6:].strip()
+    if typestr.startswith('const ') or typestr.startswith('const\t'):
+        typestr = typestr[6:].strip()
 
-	if is_id(typestr):
-		return "convert_id, &%(varname)s"%{ 'varname': varname }
+    if is_id(typestr):
+        return "convert_id, &%(varname)s"%{ 'varname': varname }
 
-	if typestr in INT_ALIASES:
-		x = SIMPLE_TYPES['int']
-	else:
-		x = SIMPLE_TYPES[typestr]
+    if typestr in INT_ALIASES:
+        x = SIMPLE_TYPES['int']
+    else:
+        x = SIMPLE_TYPES[typestr]
 
-	if x[2] is None:
-		return
-	elif isinstance(x[2], str):
-		return x[2]%{'varname': varname }
-	elif isinstance(x[2], types.FunctionType):
-		return x[2](varname)
-	else:
-		raise ValueError, "Bad config for %s"%typestr
+    if x[2] is None:
+        return
+    elif isinstance(x[2], str):
+        return x[2]%{'varname': varname }
+    elif isinstance(x[2], types.FunctionType):
+        return x[2](varname)
+    else:
+        raise ValueError, "Bad config for %s"%typestr
 
 def is_simple_type(typestr):
-	if typestr.startswith('const ') or typestr.startswith('const\t'):
-		typestr = typestr[6:].strip()
-	
-	if typestr in INT_ALIASES:
-		return 1
+    if typestr.startswith('const ') or typestr.startswith('const\t'):
+        typestr = typestr[6:].strip()
+        
+    if typestr in INT_ALIASES:
+        return 1
 
-	elif typestr in SIMPLE_TYPES:
-		return 1
+    elif typestr in SIMPLE_TYPES:
+        return 1
 
-	else:
-		return is_id(typestr)
+    else:
+        return is_id(typestr)
 
 
 def parse_prototype(protostr):
-	protostr = protostr.strip()
-	idx = protostr.index('(')
+    protostr = protostr.strip()
+    idx = protostr.index('(')
 
-	arguments = [ x.strip() for x in protostr[idx+1:-2].split(',') ]
-	before = protostr[:idx].strip()
-	idx=len(before)-1
-	while before[idx].isalnum() or before[idx] == '_':
-		idx -= 1
-	
-	funcname = before[idx+1:].strip()
-	retval = simplify_type(before[:idx+1].strip())
+    arguments = [ x.strip() for x in protostr[idx+1:-2].split(',') ]
+    before = protostr[:idx].strip()
+    idx=len(before)-1
+    while before[idx].isalnum() or before[idx] == '_':
+        idx -= 1
+    
+    funcname = before[idx+1:].strip()
+    retval = simplify_type(before[:idx+1].strip())
 
-	if not is_simple_type(retval) and retval != 'void':
-		raise ValueError, "Complex function (retval)"
+    if not is_simple_type(retval) and retval != 'void':
+        raise ValueError, "Complex function (retval)"
 
-	new_arguments = []
-	if len(arguments)  != 1 or arguments[0] != 'void':
-		for a in arguments:
-			if a == '...':
-                                if funcname in IGNORE_VARARGS:
-                                    continue
-				raise ValueError, "Complex function (varargs)"
-			idx = len(a)-1
-			while a[idx].isalnum() or a[idx] == '_':
-				idx -= 1
-			new_arguments.append((simplify_type(a[:idx+1].strip()), a[idx+1:].strip()))
-	arguments = tuple(new_arguments)
+    new_arguments = []
+    if len(arguments)  != 1 or arguments[0] != 'void':
+        for a in arguments:
+            if a == '...':
+                if funcname in IGNORE_VARARGS:
+                    continue
+                raise ValueError, "Complex function (varargs)"
+            idx = len(a)-1
+            while a[idx].isalnum() or a[idx] == '_':
+                idx -= 1
+            new_arguments.append((simplify_type(a[:idx+1].strip()), a[idx+1:].strip()))
+    arguments = tuple(new_arguments)
 
-        if FUNC_MAP.has_key(funcname):
-            arguments = FUNC_MAP[funcname](funcname, arguments)
+    if FUNC_MAP.has_key(funcname):
+        arguments = FUNC_MAP[funcname](funcname, arguments)
 
-	for tp, name in arguments:
-		if not is_simple_type(tp):
-			raise ValueError, "Complex function (arg of type %s)"%(tp,)
+    for tp, name in arguments:
+        if not is_simple_type(tp):
+            raise ValueError, "Complex function (arg of type %s)"%(tp,)
 
-	return retval, funcname, arguments
+    return retval, funcname, arguments
 
 
 def process_function(fp, protostr):
-	retval, funcname, arguments = parse_prototype(protostr)
+    retval, funcname, arguments = parse_prototype(protostr)
 
-	fp.write("/* %s */\n"%protostr)
-	fp.write("static PyObject* objc_%s(PyObject* self __attribute__((__unused__)), PyObject* args, PyObject* kwds)\n"%funcname)
-	fp.write("{\n")
-	keywords = [ a[1] for a in arguments ]
-	keywords = '", "'.join(keywords)
-	if keywords:
-		keywords = '"%s", '%keywords
-	fp.write("static\tchar* keywords[] = { %sNULL };\n"%keywords)
-	fp.write("\tPyObject* result;\n")
-	if retval != 'void':
-		fp.write("\t%s objc_result;\n"%retval)
-	
-	fmt = ''
-	arglist = ''
-	for tp, name in arguments:
-		fmt += parsetuple_fmt(tp)
-		v =parsetuple_arguments(tp, "objc_%s"%name)
-		if v:
-			arglist += ", %s"%v
+    fp.write("/* %s */\n"%protostr)
+    fp.write("static PyObject* objc_%s(PyObject* self __attribute__((__unused__)), PyObject* args, PyObject* kwds)\n"%funcname)
+    fp.write("{\n")
+    keywords = [ a[1] for a in arguments ]
+    keywords = '", "'.join(keywords)
+    if keywords:
+        keywords = '"%s", '%keywords
+    fp.write("static\tchar* keywords[] = { %sNULL };\n"%keywords)
+    fp.write("\tPyObject* result;\n")
+    if retval != 'void':
+        fp.write("\t%s objc_result;\n"%retval)
+    
+    fmt = ''
+    arglist = ''
+    for tp, name in arguments:
+        fmt += parsetuple_fmt(tp)
+        v =parsetuple_arguments(tp, "objc_%s"%name)
+        if v:
+            arglist += ", %s"%v
 
-		if is_id(tp):
-			fp.write("\tid objc_%s;\n"%name)
-		else:
-			fp.write("\t%s objc_%s;\n"%(tp, name))
+        if is_id(tp):
+            fp.write("\tid objc_%s;\n"%name)
+        else:
+            fp.write("\t%s objc_%s;\n"%(tp, name))
 
-	fp.write("\n")
+    fp.write("\n")
 
-	fp.write('\tif (!PyArg_ParseTupleAndKeywords(args, kwds, "%s:%s", keywords%s)) return NULL;\n'%(fmt, funcname, arglist))
+    fp.write('\tif (!PyArg_ParseTupleAndKeywords(args, kwds, "%s:%s", keywords%s)) return NULL;\n'%(fmt, funcname, arglist))
 
-	fp.write("\tNS_DURING\n")
-	if retval != 'void':
-		fp.write("\t\tobjc_result = %s(\n"%funcname,)
-	else:
-		fp.write("\t\t%s(\n"%funcname,)
-	sep = ""
-	for tp, name in arguments:
-		fp.write("%sobjc_%s"%(sep, name))
-		sep = ", "
-	fp.write(");\n")
-	fp.write("\tNS_HANDLER\n")
-	fp.write("\t\tPyObjCErr_FromObjC(localException);\n")
-	fp.write("\t\treturn NULL;\n")
-	fp.write("\tNS_ENDHANDLER\n")
+    fp.write("\tNS_DURING\n")
+    if retval != 'void':
+        fp.write("\t\tobjc_result = %s(\n"%funcname,)
+    else:
+        fp.write("\t\t%s(\n"%funcname,)
+    sep = ""
+    for tp, name in arguments:
+        fp.write("%sobjc_%s"%(sep, name))
+        sep = ", "
+    fp.write(");\n")
+    fp.write("\tNS_HANDLER\n")
+    fp.write("\t\tPyObjCErr_FromObjC(localException);\n")
+    fp.write("\t\treturn NULL;\n")
+    fp.write("\tNS_ENDHANDLER\n")
 
-	if retval != 'void':
-		fp.write("\t%s\n"%simple_to_python("objc_result", retval))
-	else:
-		fp.write("\tresult = Py_None;\n\tPy_INCREF(Py_None);\n");
+    if retval != 'void':
+        fp.write("\t%s\n"%simple_to_python("objc_result", retval))
+    else:
+        fp.write("\tresult = Py_None;\n\tPy_INCREF(Py_None);\n");
 
-	fp.write("\treturn result;\n")
-	fp.write("}\n")
-	return funcname
+    fp.write("\treturn result;\n")
+    fp.write("}\n")
+    return funcname
 
 
 def process_list(fp, lst):
-	ok_count = 0
-	total_count = 0
-	funcs=[]
+    ok_count = 0
+    total_count = 0
+    funcs=[]
 
-	fp.write(HDR)
+    fp.write(HDR)
 
-	for l in lst:
-		l = l.strip()
-		if not l: continue
-		if l[0] == '#': continue
-		total_count += 1
-		try:
+    for l in lst:
+        l = l.strip()
+        if not l: continue
+        if l[0] == '#': continue
+        total_count += 1
+        try:
+            funcs.append((process_function(fp, l), l))
+            if verbose:
+                sys.stderr.write("Converting '%s' ..."%l.strip())
+                sys.stderr.write("done\n")
+            sys.stderr.flush()
+            ok_count += 1
 
-			funcs.append((process_function(fp, l), l))
-                        if verbose:
-			    sys.stderr.write("Converting '%s' ..."%l.strip())
-                            sys.stderr.write("done\n")
-			sys.stderr.flush()
-			ok_count += 1
-		except ValueError, msg:
-			sys.stderr.write("Converting '%s' ..."%l.strip())
-			sys.stderr.write("failed: %s\n"%msg)
-			sys.stderr.flush()
+        except ValueError, msg:
+            sys.stderr.write("Converting '%s' ..."%l.strip())
+            sys.stderr.write("failed: %s\n"%msg)
+            sys.stderr.flush()
 
+    fp.write("\n")
 
-	fp.write("\n")
+    if not funcs:
+        fp.write("#define METHOD_TABLE_ENTRIES\n")
+    else:
+        fp.write("#define METHOD_TABLE_ENTRIES \\\n")
+        for f in funcs:
+            fp.write('\t{ "%(funcname)s", (PyCFunction)objc_%(funcname)s, METH_VARARGS|METH_KEYWORDS, "%(funcproto)s" }, \\\n'%{'funcname':f[0], 'funcproto':f[1]})
+        fp.write("\t/* END */\n")
 
-	if not funcs:
-		fp.write("#define METHOD_TABLE_ENTRIES\n")
-	else:
-		fp.write("#define METHOD_TABLE_ENTRIES \\\n")
-		for f in funcs:
-			fp.write('\t{ "%(funcname)s", (PyCFunction)objc_%(funcname)s, METH_VARARGS|METH_KEYWORDS, "%(funcproto)s" }, \\\n'%{'funcname':f[0], 'funcproto':f[1]})
-		fp.write("\t/* END */\n")
 
-
-        if verbose:
-            sys.stderr.write("Converted %d of %d functions\n"%(ok_count, total_count))
+    if verbose:
+        sys.stderr.write("Converted %d of %d functions\n"%(ok_count, total_count))
 
 if __name__ == "__main__":
-	import sys
-	INT_ALIASES.append('NSWindowDepth')
-	process_list(sys.stdout, file(sys.argv[1]))
+    import sys
+    INT_ALIASES.append('NSWindowDepth')
+    process_list(sys.stdout, file(sys.argv[1]))

pyobjc/Scripts/CodeGenerators/func_collector.py

 
 def process_file(outfp, filename, match_prefix='', ignore_list=()):
 
-	MATCH_RE=re.compile('%(match_prefix)s(.*\(.*\);)'%{'match_prefix':match_prefix, 'IDENT':IDENT})
+    MATCH_RE=re.compile('%(match_prefix)s(.*\(.*\);)'%{
+            'match_prefix':match_prefix, 'IDENT':IDENT})
 
-	fp = open(filename, 'r')
+    fp = open(filename, 'r')
 
-	outfp.write("\n# From: %s\n"%os.path.basename(filename))
+    outfp.write("\n# From: %s\n"%os.path.basename(filename))
 
-	in_class = 0
+    in_class = 0
 
-	for ln in fp.xreadlines():
+    for ln in fp.xreadlines():
 
-		# Skip declarations in objective-C class definitions
-		if not in_class:
-			if ln.startswith("@interface"):
-				in_class = 1
-				continue
-		else:
-			if ln.startswith("@end"):
-				in_class = 0
-			continue
+        # Skip declarations in objective-C class definitions
+        if not in_class:
+            if ln.startswith("@interface"):
+                in_class = 1
+                continue
+        else:
+            if ln.startswith("@end"):
+                in_class = 0
+            continue
 
-		m = MATCH_RE.match(ln)
-		if not m: continue
+        m = MATCH_RE.match(ln)
+        if not m: continue
 
-                prototype=m.group(1).strip()
+        prototype=m.group(1).strip()
 
-                ign = 0
-                for i in ignore_list:
-                    if prototype.find(i) != -1:
-                        ign=1
-                        break
+        ign = 0
+        for i in ignore_list:
+            if prototype.find(i) != -1:
+                ign=1
+                break
 
-                if not ign:
-                    outfp.write('%s\n'%prototype)
+        if not ign:
+            outfp.write('%s\n'%prototype)
 
 def generate(dirname, fn = None, match_prefix='', ignore_list=()):
-	if fn:
-		fp = dupfile(fn, 'w')
-	else:
-		import sys
-		fp = sys.stdout
-		del sys
+    if fn:
+        fp = dupfile(fn, 'w')
+    else:
+        import sys
+        fp = sys.stdout
+        del sys
 
-	fp.write("#\n")
-	fp.write("# List of functions. Generated from files in \n")
-	fp.write("# %s\n"%dirname)
-	fp.write("# \n")
-	fp.write("# Used to check for new functions\n")
-	fp.write("# \n")
+    fp.write("#\n")
+    fp.write("# List of functions. Generated from files in \n")
+    fp.write("# %s\n"%dirname)
+    fp.write("# \n")
+    fp.write("# Used to check for new functions\n")
+    fp.write("# \n")
 
-	fnames = [ os.path.join(dirname, fn)
-				for fn in os.listdir(dirname)
-				if fn.endswith('.h') ]
-	for f in fnames:
-		process_file(fp, f, match_prefix, ignore_list)
+    fnames = [ os.path.join(dirname, fn)
+                        for fn in os.listdir(dirname)
+                        if fn.endswith('.h') ]
+    for f in fnames:
+        process_file(fp, f, match_prefix, ignore_list)
 
-        fp.close()
+    fp.close()
 
 if __name__ == "__main__":
-	import sys
-	generate(sys.argv[1], match_prefix=sys.argv[2])
+    import sys
+    generate(sys.argv[1], match_prefix=sys.argv[2])

pyobjc/Scripts/CodeGenerators/strconst_generator.py

 MATCH_RE=re.compile('NSString \*([ ]*const[ ]+)?([A-Za-z_][A-Za-z0-9_]*([ ]*,[ ]*\*[ ]*[A-Za-z_][A-Za-z0-9_]*)*);')
 
 def entry(fp, val, ignore):
-	vals = val.split(',')
-	if len(vals) == 1:
-                if val in ignore: return
-		fp.write('\t { @"%s", @encode(NSString*) },\n'%(val, ))
-	else:
-		for  v in vals:
-			v = v.strip()
-			if v[0] == '*':
-				v = v[1:].strip()
-                        if v in ignore: continue
-			fp.write('\t { @"%s", @encode(NSString*) },\n'%(v, ))
+    vals = val.split(',')
+    if len(vals) == 1:
+        if val in ignore: return
+        fp.write('\t { @"%s", @encode(NSString*) },\n'%(val, ))
+    else:
+        for  v in vals:
+            v = v.strip()
+            if v[0] == '*':
+                v = v[1:].strip()
+            if v in ignore: continue
+            fp.write('\t { @"%s", @encode(NSString*) },\n'%(v, ))
 
 def process_file(outfp, filename, ignore):
-	fp = open(filename, 'r')
+    fp = open(filename, 'r')
 
-	outfp.write("\n\t/* From: %s */\n"%os.path.basename(filename))
+    outfp.write("\n\t/* From: %s */\n"%os.path.basename(filename))
 
-	in_class = 0
+    in_class = 0
 
-	for ln in fp.xreadlines():
+    for ln in fp.xreadlines():
 
-		# Skip declarations in objective-C class definitions
-		if not in_class:
-			if ln.startswith("@interface"):
-				in_class = 1
-				continue
-		else:
-			if ln.startswith("@end"):
-				in_class = 0
-			continue
+        # Skip declarations in objective-C class definitions
+        if not in_class:
+            if ln.startswith("@interface"):
+                in_class = 1
+                continue
+        else:
+            if ln.startswith("@end"):
+                in_class = 0
+            continue
 
-		
+        m = MATCH_RE.search(ln)
+        if not m: continue
 
-		m = MATCH_RE.search(ln)
-		if not m: continue
-
-		ident = m.group(2)
-		entry(outfp, ident, ignore)
+        ident = m.group(2)
+        entry(outfp, ident, ignore)
 
 def generate(dirname, fn = None, ignore=(), filter = lambda x: 1):
-	if not os.path.exists(dirname): return
+    if not os.path.exists(dirname): return
 
-	if fn:
-		fp = dupfile(fn, 'w')
-	else:
-		import sys
-		fp = sys.stdout
-		del sys
+    if fn:
+        fp = dupfile(fn, 'w')
+    else:
+        import sys
+        fp = sys.stdout
+        del sys
 
-	fp.write("/*\n")
-	fp.write(" * String constants. This file is generated from files in\n")
-	fp.write(" * %s\n"%dirname)
-	fp.write(" */\n")
-	fp.write("static struct vartable string_table[] = {\n")
-	fnames = [ os.path.join(dirname, fn)
-				for fn in os.listdir(dirname)
-				if fn.endswith('.h') and filter(fn) ]
-	for f in fnames:
-		process_file(fp, f, ignore)
-	fp.write("\t{0, 0} /* Sentinel */\n")
-	fp.write("};\n")
+    fp.write("/*\n")
+    fp.write(" * String constants. This file is generated from files in\n")
+    fp.write(" * %s\n"%dirname)
+    fp.write(" */\n")
+    fp.write("static struct vartable string_table[] = {\n")
+    fnames = [ os.path.join(dirname, fn)
+                        for fn in os.listdir(dirname)
+                        if fn.endswith('.h') and filter(fn) ]
+    for f in fnames:
+        process_file(fp, f, ignore)
+    fp.write("\t{0, 0} /* Sentinel */\n")
+    fp.write("};\n")
 
 if __name__ == "__main__":
-	import sys
-	generate(sys.argv[1])
+    import sys
+    generate(sys.argv[1])

pyobjc/Scripts/CodeGenerators/var_generator.py

 
 IDENT='[A-Za-z_][A-Za-z0-9_]*'
 
-
-
-
 def process_file(outfp, filename, match_prefix='', ignore_list=()):
 
-	MATCH_RE=re.compile('%(match_prefix)s[ ]+(const[ ]+)?(%(IDENT)s)[ ]+(%(IDENT)s[ ]*(,[ ]*%(IDENT)s)*)[ ]*;'%{'match_prefix':match_prefix, 'IDENT':IDENT})
+    MATCH_RE=re.compile('%(match_prefix)s[ ]+(const[ ]+)?(%(IDENT)s)[ ]+(%(IDENT)s[ ]*(,[ ]*%(IDENT)s)*)[ ]*;'%{'match_prefix':match_prefix, 'IDENT':IDENT})
 
-	fp = open(filename, 'r')
+    fp = open(filename, 'r')
 
-	outfp.write("\n\t/* From: %s */\n"%os.path.basename(filename))
+    outfp.write("\n\t/* From: %s */\n"%os.path.basename(filename))
 
-	in_class = 0
+    in_class = 0
 
-	for ln in fp.xreadlines():
+    for ln in fp.xreadlines():
 
-		# Skip declarations in objective-C class definitions
-		if not in_class:
-			if ln.startswith("@interface"):
-				in_class = 1
-				continue
-		else:
-			if ln.startswith("@end"):
-				in_class = 0
-			continue
+        # Skip declarations in objective-C class definitions
+        if not in_class:
+            if ln.startswith("@interface"):
+                in_class = 1
+                continue
+        else:
+            if ln.startswith("@end"):
+                in_class = 0
+            continue
 
-		m = MATCH_RE.search(ln)
-		if not m: continue
+        m = MATCH_RE.search(ln)
+        if not m: continue
 
-		tp = m.group(2)
-		ident = m.group(3)
+        tp = m.group(2)