[PD-cvs] externals/gridflow/format quartz.m,NONE,1.1
Mathieu Bouchard
matju at users.sourceforge.net
Tue Oct 4 04:15:33 CEST 2005
Update of /cvsroot/pure-data/externals/gridflow/format
In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv23852/format
Added Files:
quartz.m
Log Message:
oops.
--- NEW FILE: quartz.m ---
/*
$Id: quartz.m,v 1.1 2005/10/04 02:15:31 matju Exp $
GridFlow
Copyright (c) 2001,2002,2003 by Mathieu Bouchard
This program 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.
See file ../COPYING for further informations on licensing terms.
This program 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 General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
/*
This is written in Objective C++, which is the union of C++ and Objective C;
Their intersection is C or almost. They add quite different sets of features.
I need Objective C here because the Cocoa API is for Objective C and Java only,
and the Objective C one was the easiest to integrate in GridFlow.
The next best possibility may be using RubyCocoa, a port of the Cocoa API to Ruby;
However I haven't checked whether Quartz is wrapped, and how easy it is to
process images.
*/
#include <stdio.h>
#include <objc/Object.h>
/* wrapping name conflict */
#define T_DATA T_COCOA_DATA
#include <Cocoa/Cocoa.h>
#undef T_DATA
#include "../base/grid.h.fcs"
@interface GFView: NSView {
Pt<uint8> imdata;
int imwidth;
int imheight;
}
- (id) drawRect: (NSRect)rect;
- (id) imageHeight: (int)w width: (int)h;
- (uint8 *) imageData;
- (int) imageDataSize;
@end
@implementation GFView
- (uint8 *) imageData { return imdata; }
- (int) imageDataSize { return imwidth*imheight*4; }
- (id) imageHeight: (int)h width: (int)w {
if (imheight==h && imwidth==w) return self;
gfpost("new size: y=%d x=%d",h,w);
imheight=h;
imwidth=w;
if (imdata) delete imdata.p;
int size = [self imageDataSize];
imdata = ARRAY_NEW(uint8,size);
uint8 *p = imdata;
CLEAR(imdata,size);
NSSize s = {w,h};
[[self window] setContentSize: s];
return self;
}
- (id) initWithFrame: (NSRect)r {
[super initWithFrame: r];
imdata=Pt<uint8>(); imwidth=-1; imheight=-1;
[self imageHeight: 240 width: 320];
return self;
}
- (id) drawRect: (NSRect)rect {
[super drawRect: rect];
if (![self lockFocusIfCanDraw]) return self;
CGContextRef g = (CGContextRef)
[[NSGraphicsContext graphicsContextWithWindow: [self window]]
graphicsPort];
CGColorSpaceRef cs = CGColorSpaceCreateDeviceRGB();
CGDataProviderRef dp = CGDataProviderCreateWithData(
NULL, imdata, imheight*imwidth*4, NULL);
CGImageRef image = CGImageCreate(imwidth, imheight, 8, 32, imwidth*4,
cs, kCGImageAlphaFirst, dp, NULL, 0, kCGRenderingIntentDefault);
CGDataProviderRelease(dp);
CGColorSpaceRelease(cs);
CGRect rectangle = CGRectMake(0,0,imwidth,imheight);
CGContextDrawImage(g,rectangle,image);
CGImageRelease(image);
[self unlockFocus];
return self;
}
@end
/* workaround: bus error in gcc */
Pt<uint8> GFView_imageData(GFView *self) {
return Pt<uint8>([self imageData], [self imageDataSize]);
}
void GFView_imageHeight_width(GFView *self, int height, int width) {
[self imageHeight: height width: width];
}
void GFView_display(GFView *self) {
NSRect r = {{0,0},{self->imheight,self->imwidth}};
[self displayRect: r];
[self setNeedsDisplay: YES];
[self display];
}
\class FormatQuartz < Format
struct FormatQuartz : Format {
NSWindow *window;
NSWindowController *wc;
GFView *widget; /* GridFlow's Cocoa widget */
NSDate *distantFuture;
\decl void initialize (Symbol mode);
\decl void delete_m ();
\decl void close ();
\decl void call ();
\grin 0
};
static NSDate *distantFuture, *distantPast;
\def void call() {
NSEvent *e = [NSApp nextEventMatchingMask: NSAnyEventMask
// untilDate: distantFuture // blocking
untilDate: distantPast // nonblocking
inMode: NSDefaultRunLoopMode
dequeue: YES];
if (e) {
NSLog(@"%@", e);
[NSApp sendEvent: e];
}
[NSApp updateWindows];
[this->window flushWindowIfNeeded];
IEVAL(rself,"@clock.delay 20");
}
template <class T, class S>
static void convert_number_type(int n, Pt<T> out, Pt<S> in) {
for (int i=0; i<n; i++) out[i]=(T)in[i];
}
GRID_INLET(FormatQuartz,0) {
if (in->dim->n!=3) RAISE("expecting 3 dims, not %d", in->dim->n);
int c=in->dim->get(2);
if (c!=3&&c!=4) RAISE("expecting 3 or 4 channels, not %d", in->dim->get(2));
// [widget imageHeight: in->dim->get(0) width: in->dim->get(1) ];
GFView_imageHeight_width(widget,in->dim->get(0),in->dim->get(1));
in->set_factor(in->dim->prod(1));
} GRID_FLOW {
int off = in->dex/in->dim->prod(2);
int c=in->dim->get(2);
NSView *w = widget;
Pt<uint8> data2 = GFView_imageData(w)+off*4;
// convert_number_type(n,data2,data);
if (c==3) {
while(n) {
data2[0]=255;
data2[1]=data[0];
data2[2]=data[1];
data2[3]=data[2];
data+=3; data2+=4; n-=3;
}
} else {
while(n) {
data2[0]=255;
data2[1]=data[0];
data2[2]=data[1];
data2[3]=data[2];
data+=4; data2+=4; n-=4;
}
}
} GRID_FINISH {
GFView_display(widget);
} GRID_END
\def void initialize (Symbol mode) {
rb_call_super(argc,argv);
NSRect r = {{0,0}, {320,240}};
window = [[NSWindow alloc]
initWithContentRect: r
styleMask: NSTitledWindowMask | NSMiniaturizableWindowMask | NSClosableWindowMask
backing: NSBackingStoreBuffered
defer: YES
];
widget = [[GFView alloc] initWithFrame: r];
[window setContentView: widget];
[window setTitle: @"GridFlow"];
[window makeKeyAndOrderFront: NSApp];
[window orderFrontRegardless];
wc = [[NSWindowController alloc]
initWithWindow: window];
IEVAL(rself,"@clock = Clock.new self");
[window makeFirstResponder: widget];
gfpost("mainWindow = %08lx",(long)[NSApp mainWindow]);
gfpost(" keyWindow = %08lx",(long)[NSApp keyWindow]);
NSColor *color = [NSColor clearColor];
[window setBackgroundColor: color];
}
\def void delete_m () {
[window autorelease];
}
\def void close () {
IEVAL(rself,"@clock.unset");
rb_call_super(argc,argv);
[window autorelease];
[window setReleasedWhenClosed: YES];
[window close];
}
\classinfo {
NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
distantFuture = [NSDate distantFuture];
distantPast = [NSDate distantPast];
[NSApplication sharedApplication];
IEVAL(rself,
\ruby
install '#io:quartz',1,1
@comment = "Apple Quartz/Cocoa"
@flags = 2
\end ruby
);}
\end class FormatQuartz
void startup_quartz () {
\startall
}
More information about the Pd-cvs
mailing list