Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit ef8e81e

Browse files
committed
Initial import of CocoaAgg.
The Matplotlib.nib bundle is the gui as built in Interface Builder. The backend directory seemed the most logical place to put the nib. Edited setup.py to install the nib file only if on a mac. svn path=/trunk/matplotlib/; revision=1469
1 parent 3e18c47 commit ef8e81e

File tree

7 files changed

+217
-5
lines changed

7 files changed

+217
-5
lines changed

lib/matplotlib/__init__.py

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -816,9 +816,9 @@ def rcdefaults():
816816
# flag)
817817

818818
_knownBackends = {
819-
'Agg2':1, 'Agg':1, 'Cairo':1, 'FltkAgg':1, 'GD':1, 'GDK':1, 'GTK':1, 'GTKAgg':1,
820-
'GTKCairo':1, 'Paint':1, 'PS':1, 'LaTeX':1, 'QtAgg':1, 'SVG':1, 'Template':1,
821-
'TkAgg':1, 'WX':1, 'WXAgg':1, }
819+
'Agg2':1, 'Agg':1, 'Cairo':1, 'CocoaAgg':1, 'FltkAgg':1, 'GD':1, 'GDK':1,
820+
'GTK':1, 'GTKAgg':1, 'GTKCairo':1, 'Paint':1, 'PS':1, 'LaTeX':1, 'QtAgg':1,
821+
'SVG':1, 'Template':1, 'TkAgg':1, 'WX':1, 'WXAgg':1, }
822822

823823

824824
known = _knownBackends.keys()

lib/matplotlib/backends/Matplotlib.nib/classes.nib

Lines changed: 13 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

lib/matplotlib/backends/Matplotlib.nib/info.nib

Lines changed: 22 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.
Binary file not shown.

lib/matplotlib/backends/__init__.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -4,8 +4,8 @@
44
__all__ = ['backend','show','draw_if_interactive',
55
'new_figure_manager', 'backend_version']
66

7-
interactive_bk = ['GTK','GTKAgg','GTKCairo','FltkAgg','QtAgg', 'TkAgg',
8-
'WX','WXAgg',]
7+
interactive_bk = ['GTK','GTKAgg','GTKCairo','FltkAgg','QtAgg','TkAgg',
8+
'WX','WXAgg','CocoaAgg']
99
non_interactive_bk = ['Agg2', 'Agg','Cairo','GD','GDK','Paint','PS', 'LaTeX', 'SVG','Template']
1010
all_backends = interactive_bk + non_interactive_bk
1111

Lines changed: 171 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,171 @@
1+
from __future__ import division
2+
"""
3+
backend_cocoaagg.py
4+
5+
A native Cocoa backend via PyObjC in OSX.
6+
7+
Author: Charles Moad ([email protected])
8+
9+
Notes:
10+
- THIS IS STILL IN DEVELOPMENT!
11+
- Requires PyObjC (currently testing v1.3.6)
12+
- Only works with 10.3 at this time (10.4 is high priority)
13+
"""
14+
15+
import os, sys
16+
17+
try:
18+
import objc
19+
except:
20+
print >>sys.stderr, 'The CococaAgg backend required PyObjC to be installed!'
21+
sys.exit()
22+
23+
from Foundation import *
24+
from AppKit import *
25+
from PyObjCTools import NibClassBuilder, AppHelper
26+
27+
import matplotlib
28+
from matplotlib.figure import Figure
29+
from matplotlib.backend_bases import FigureManagerBase
30+
from backend_agg import FigureCanvasAgg
31+
import pylab
32+
33+
mplBundle = NSBundle.bundleWithPath_(matplotlib.get_data_path())
34+
35+
def new_figure_manager(num, *args, **kwargs):
36+
thisFig = Figure( *args, **kwargs )
37+
canvas = FigureCanvasAgg(thisFig)
38+
return FigureManagerCocoaAgg(canvas, num)
39+
40+
def show():
41+
# Let the cocoa run loop take over
42+
NSApplication.sharedApplication().run()
43+
44+
def draw_if_interactive():
45+
if matplotlib.is_interactive():
46+
print >>sys.stderr, 'Not implemented yet'
47+
48+
NibClassBuilder.extractClasses('Matplotlib.nib', mplBundle)
49+
50+
class MatplotlibController(NibClassBuilder.AutoBaseClass):
51+
# available outlets:
52+
# NSWindow plotWindow
53+
# NSImageView plotView
54+
55+
def awakeFromNib(self):
56+
self.plotView.setImageFrameStyle_(NSImageFrameGroove)
57+
# Get a reference to the active canvas
58+
self.canvas = pylab.get_current_fig_manager().canvas
59+
# Issue a update
60+
self.windowDidResize_(None)
61+
62+
def updatePlot(self):
63+
self.canvas.draw() # tell the agg to render
64+
65+
w,h = self.canvas.figure.get_width_height()
66+
67+
image = NSImage.alloc().initWithSize_((w,h))
68+
brep = NSBitmapImageRep.alloc().initWithBitmapDataPlanes_pixelsWide_pixelsHigh_bitsPerSample_samplesPerPixel_hasAlpha_isPlanar_colorSpaceName_bytesPerRow_bitsPerPixel_(
69+
(self.canvas.buffer_rgba(),'','','',''), # Image data
70+
int(w), # width
71+
int(h), # height
72+
8, # bits per pixel
73+
4, # components per pixel
74+
True, # has alpha?
75+
False, # is planar?
76+
NSCalibratedRGBColorSpace, # color space
77+
0, # row bytes (should be 0 for non planar)
78+
32) # bits per pixel
79+
80+
image.addRepresentation_(brep)
81+
self.plotView.setImage_(image)
82+
self.plotView.setNeedsDisplay_(True)
83+
84+
def saveFigure_(self, sender):
85+
pass
86+
87+
def quit_(self, sender):
88+
pass
89+
90+
def windowDidResize_(self, sender):
91+
w,h = self.plotView.frame().size
92+
dpi = self.canvas.figure.dpi.get()
93+
self.canvas.figure.set_figsize_inches(w / dpi, h / dpi)
94+
self.updatePlot()
95+
96+
class MPLBootstrap(NSObject):
97+
def startWithBundle_(self, bundle):
98+
NSApplicationLoad()
99+
if not bundle.loadNibFile_externalNameTable_withZone_(
100+
'Matplotlib.nib',
101+
{},
102+
None):
103+
print >>sys.stderr, 'Unable to load Matplotlib Cocoa UI!'
104+
sys.exit()
105+
106+
class FigureManagerCocoaAgg(FigureManagerBase):
107+
def __init__(self, canvas, num):
108+
FigureManagerBase.__init__(self, canvas, num)
109+
if not WMEnable('Matplotlib'):
110+
print >>sys.stderr, 'Unable to hook to native window manager!'
111+
sys.exit()
112+
113+
MPLBootstrap.alloc().init().performSelectorOnMainThread_withObject_waitUntilDone_(
114+
'startWithBundle:',
115+
mplBundle,
116+
False)
117+
118+
FigureManager = FigureManagerCocoaAgg
119+
120+
#### Everything below taken from PyObjC examples
121+
#### This is a hack to allow python scripts to access
122+
#### the window manager without running pythonw.
123+
def S(*args):
124+
return ''.join(args)
125+
126+
OSErr = objc._C_SHT
127+
OUTPSN = 'o^{ProcessSerialNumber=LL}'
128+
INPSN = 'n^{ProcessSerialNumber=LL}'
129+
FUNCTIONS=[
130+
# These two are public API
131+
( u'GetCurrentProcess', S(OSErr, OUTPSN) ),
132+
( u'SetFrontProcess', S(OSErr, INPSN) ),
133+
# This is undocumented SPI
134+
( u'CPSSetProcessName', S(OSErr, INPSN, objc._C_CHARPTR) ),
135+
( u'CPSEnableForegroundOperation', S(OSErr, INPSN) ),
136+
]
137+
def WMEnable(name='Python'):
138+
if isinstance(name, unicode):
139+
name = name.encode('utf8')
140+
mainBundle = NSBundle.mainBundle()
141+
bPath = os.path.split(os.path.split(os.path.split(sys.executable)[0])[0])[0]
142+
if mainBundle.bundlePath() == bPath:
143+
return True
144+
bndl = NSBundle.bundleWithPath_(objc.pathForFramework('/System/Library/Frameworks/ApplicationServices.framework'))
145+
if bndl is None:
146+
print >>sys.stderr, 'ApplicationServices missing'
147+
return False
148+
d = {}
149+
objc.loadBundleFunctions(bndl, d, FUNCTIONS)
150+
for (fn, sig) in FUNCTIONS:
151+
if fn not in d:
152+
print >>sys.stderr, 'Missing', fn
153+
return False
154+
err, psn = d['GetCurrentProcess']()
155+
if err:
156+
print >>sys.stderr, 'GetCurrentProcess', (err, psn)
157+
return False
158+
err = d['CPSSetProcessName'](psn, name)
159+
if err:
160+
print >>sys.stderr, 'CPSSetProcessName', (err, psn)
161+
return False
162+
err = d['CPSEnableForegroundOperation'](psn)
163+
if err:
164+
print >>sys.stderr, 'CPSEnableForegroundOperation', (err, psn)
165+
return False
166+
err = d['SetFrontProcess'](psn)
167+
if err:
168+
print >>sys.stderr, 'SetFrontProcess', (err, psn)
169+
return False
170+
return True
171+

setup.py

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -86,6 +86,12 @@
8686

8787
data_files=[('share/matplotlib', data),]
8888

89+
# Bundle the CocoaAgg nib only if on a mac
90+
if sys.platform == 'darwin':
91+
data_files.append(('share/matplotlib/Matplotlib.nib',
92+
glob.glob('lib/matplotlib/backends/Matplotlib.nib/*.nib')))
93+
94+
8995
# Figure out which array packages to provide binary support for
9096
# and define the NUMERIX value: Numeric, numarray, or both.
9197
try:

0 commit comments

Comments
 (0)