home *** CD-ROM | disk | FTP | other *** search
- //
- // SpheresView.m
- //
- // Revised for NS3.0 20 Oct 1992
- // Matt Pharr- pharr@cs.yale.edu
- //
-
- #import "SpheresView.h"
- #import "SpheresWrap.c"
- #import <appkit/appkit.h>
- #import <defaults/defaults.h>
- #import <dpsclient/wraps.h>
- #import <libc.h>
- #import <stdlib.h>
-
- #define MAXSIZE 125
- #define SHOW_FILLS 1
- #define DONT_SHOW_FILLS 0
-
- @implementation SpheresView
-
- - oneStep
- {
- float red= 0.0, green= 0.0, blue= 0.0;
- float color= 0.0;
- NXPoint position;
- NXPoint hilight;
- int radius= 100;
- float dx= 0.0, dy= 0.0;
- float dcolor= 0.0;
- float dred= 0.0, dgreen= 0.0, dblue= 0.0;
-
- if (++nDrawn >= nSpheres) {
- usleep(1000000);
- nDrawn= 0;
- PSsetgray(0.0);
- NXRectFill(&bounds);
- }
-
- /* decide where to put the sphere after we draw it.. */
- position.x= (int)randBetween(bounds.origin.x - MAXSIZE / 2,
- bounds.origin.x + bounds.size.width - MAXSIZE/2);
- position.y= (int)randBetween(bounds.origin.y - MAXSIZE / 2,
- bounds.origin.y + bounds.size.height - MAXSIZE/2);
-
- radius= (int)randBetween(30, MAXSIZE);
-
- /* where to put the hilight on the sphere- always in the same relative
- place */
- hilight.x= .4 * radius;
- hilight.y= .6 * radius;
-
- /* distance by which we need to move each time when drawing the big highlight.
- basically what we do is start at the position of the hilight and draw a little
- circle that is all white there. Then we move out away from there and draw
- bigger and bigger circles that become darker and darker, until they hit the
- color we pick for the sphere below. This gives us the 3-d shading effect.
- Actually, though, we do the above in reverse, so as not to draw over the
- circles- we're actually drawing smaller and smaller concentric, filled circles.
- N.B. there's probably a more efficient way to do this...
- */
-
- dx= hilight.x / radius;
- dy= hilight.y / radius;
-
- if ([Window defaultDepthLimit] == NX_TwoBitGrayDepth) {
- /* Black and White machines */
- color= randBetween(0.0, .4);
- dcolor= (1 - color) / radius;
- }
-
- else {
- red= randBetween(0.0, .4);
- dred= (1 - red) / radius;
-
- green= randBetween(0.0, .4);
- dgreen= (1 - green) / radius;
-
- blue= randBetween(0.0, .4);
- dblue= (1 - blue) / radius;
- }
-
-
- if (showFills == NO) {
- if ([myImage lockFocus] == YES) {
- /* clear out the NXImage, but leave a transparent background, so when we
- draw it on the screen below, the square in which the sphere is drawn doesn't
- cover up other spheres on the screen unless we have actively drawn in
- the bitmap first...
- */
-
- PSsetgray(0.0);
- PSsetalpha(0.0);
- NXRectFill(&bounds);
-
- if ([Window defaultDepthLimit] == NX_TwoBitGrayDepth) {
- /* draw a sphere in black and white... */
- drawSphereBW(color, radius, dcolor, dx, dy, MAXSIZE);
- }
- else {
- /* or in color... */
- drawSphereCL(red, green, blue, radius, dred, dgreen, dblue, dx, dy, MAXSIZE);
- }
-
- [myImage unlockFocus];
- /* and put it on the screen... */
- [myImage composite:NX_SOVER toPoint:&position];
- }
- }
-
- if (showFills == YES) {
- NXRectClip(&bounds);
- /* need to do this for drawing it in a normal window... */
-
- PStranslate(position.x, position.y);
-
- if ([Window defaultDepthLimit] == NX_TwoBitGrayDepth) {
- /* draw a sphere in black and white... */
- drawSphereBW(color, radius, dcolor, dx, dy, MAXSIZE);
- }
- else {
- /* or in color... */
- drawSphereCL(red, green, blue, radius, dred, dgreen, dblue, dx, dy, MAXSIZE);
- }
-
- PStranslate(-position.x, -position.y);
- }
-
- return self;
- }
-
-
- - initFrame:(const NXRect *)frameRect
- {
- NXSize imageSize;
-
- [super initFrame:frameRect];
-
- [self inspector:self];
-
- if ((NXGetDefaultValue([NXApp appName], "sphereNumber") == NULL) ||
- (NXGetDefaultValue([NXApp appName], "sphereShowFill") == NULL)) {
- NXWriteDefault([NXApp appName], "sphereNumber", "50");
- nSpheres= 50;
- NXWriteDefault([NXApp appName], "sphereShowFill", "NO");
- showFills= NO;
- }
- else {
- nSpheres= atoi(NXGetDefaultValue([NXApp appName], "sphereNumber"));
- if (strcmp(NXGetDefaultValue([NXApp appName], "sphereShowFill"), "YES") == 0) {
- showFills= YES;
- }
- else {
- showFills= NO;
- }
- }
-
- [theSlider setIntValue:nSpheres];
- [theSlider update];
-
- if (showFills == YES) {
- [checkBox setState:SHOW_FILLS];
- }
- else {
- [checkBox setState:DONT_SHOW_FILLS];
- }
- [checkBox update];
-
-
- imageSize.width= 2 * MAXSIZE;
- imageSize.height= 2 * MAXSIZE;
- myImage= [[NXImage alloc] initSize:&imageSize];
-
- nDrawn= 0;
-
- return self;
- }
-
-
- - drawSelf:(const NXRect *)rects :(int)rectCount
- {
- if (!rects || !rectCount) {
- return self;
- }
-
- PSsetgray(0.0);
- NXRectFill(rects);
-
- return self;
- }
-
-
- - (const char *)windowTitle
- {
- return "Spheres";
- }
-
-
- - inspector:sender
- {
- char buf[MAXPATHLEN];
-
- if (!sharedInspectorPanel) {
- sprintf(buf,"%s/%s",[(BSThinker()) moduleDirectory:"Spheres"],"Spheres.nib");
- [NXApp loadNibFile:buf owner:self withNames:NO];
- }
-
- return sharedInspectorPanel;
- }
-
-
- -setNumber:sender
- {
- char temp[20];
-
- nSpheres= [sender intValue];
-
- sprintf(temp, "%d", nSpheres);
- NXWriteDefault([NXApp appName], "sphereNumber", temp);
-
- return self;
- }
-
-
- -setShowFills:sender
- {
- if ([sender state] == SHOW_FILLS) {
- showFills= YES;
- NXWriteDefault([NXApp appName], "sphereShowFill", "YES");
- }
- else {
- showFills= NO;
- NXWriteDefault([NXApp appName], "sphereShowFill", "NO");
- }
-
- return self;
- }
-
-
- @end
-
-