Files
haiku-beta6/src/tests/kits/game/chart/ChartWindow.h
T

434 lines
13 KiB
C++

/*
ChartWindow.h
by Pierre Raynaud-Richard.
*/
/*
Copyright 1999, Be Incorporated. All Rights Reserved.
This file may be used under the terms of the Be Sample Code License.
*/
#ifndef CHART_WINDOW_H
#define CHART_WINDOW_H
#include <DirectWindow.h>
#include <OS.h>
#include <Locker.h>
#include <StringView.h>
#include <PictureButton.h>
#include "ChartRender.h"
#include "ChartView.h"
/* This window can be used in 3 modes : window mode is just a
normal window (that you move and resize freely), fullscreen
resize the window to adjust its content area to the full
size of the screen. Demo mode resize the window to have the
animate part of it fit the full screen. */
enum {
WINDOW_MODE = 0,
FULLSCREEN_MODE = 1,
FULLDEMO_MODE = 2
};
/* Special animation mode. Comet create 2 comets flying around
randomaly. Novas add a couple start with flashing burst of
light. Battle was never implemented... */
enum {
SPECIAL_NONE = 0,
SPECIAL_COMET = 1,
SPECIAL_NOVAS = 2,
SPECIAL_BATTLE = 3
};
/* Three types of display mode : line is supposed to use line
array to draw pixel (but is not currently implemented). Bitmap
use an offscreen BBitmap and DrawBitmap for each frame. Direct
use the DirectWindow API to draw directly on the screen. */
enum {
DISPLAY_OFF = 0,
DISPLAY_LINE = 1,
DISPLAY_BITMAP = 2,
DISPLAY_DIRECT = 3
};
/* Five ways of moving the camera around : not at all, simple
rotation around the center of the starfield, slow straight
move, fast straight move, and a random move (flying around). */
enum {
ANIMATION_OFF = 0,
ANIMATION_ROTATE = 1,
ANIMATION_SLOW_MOVE = 2,
ANIMATION_FAST_MOVE = 3,
ANIMATION_FREE_MOVE = 4
};
/* Three types of star field. A new random starfield is created
everytime you change the starfield type. The first will just
put stars randomly in space. The second will concentrate
star in 10 places. The last one will put half the star in a
big spiral galaxy, and the other one in a few amas. */
enum {
SPACE_CHAOS = 0,
SPACE_AMAS = 1,
SPACE_SPIRAL = 2
};
/* All messages exchanged between the UI and the engine. */
enum {
ANIM_OFF_MSG = 1000,
ANIM_SLOW_ROT_MSG = 1001,
ANIM_SLOW_MOVE_MSG = 1002,
ANIM_FAST_MOVE_MSG = 1003,
ANIM_FREE_MOVE_MSG = 1004,
DISP_OFF_MSG = 2000,
DISP_LINE_MSG = 2001,
DISP_BITMAP_MSG = 2002,
DISP_DIRECT_MSG = 2003,
OPEN_COLOR_MSG = 3000,
OPEN_DENSITY_MSG = 3100,
OPEN_REFRESH_MSG = 3200,
SPACE_CHAOS_MSG = 3300,
SPACE_AMAS_MSG = 3301,
SPACE_SPIRAL_MSG = 3302,
FULL_SCREEN_MSG = 4000,
AUTO_DEMO_MSG = 4100,
BACK_DEMO_MSG = 4101,
SECOND_THREAD_MSG = 4200,
COLORS_RED_MSG = 5000,
COLORS_GREEN_MSG = 5001,
COLORS_BLUE_MSG = 5002,
COLORS_YELLOW_MSG = 5003,
COLORS_ORANGE_MSG = 5004,
COLORS_PINK_MSG = 5005,
COLORS_WHITE_MSG = 5006,
SPECIAL_NONE_MSG = 6000,
SPECIAL_COMET_MSG = 6001,
SPECIAL_NOVAS_MSG = 6002,
SPECIAL_BATTLE_MSG = 6003,
COLOR_PALETTE_MSG = 7000,
STAR_DENSITY_MSG = 8000,
REFRESH_RATE_MSG = 9000
};
enum {
/* Number of star used to generate the special animation */
SPECIAL_COUNT_MAX = 512,
/* Number of keypoint used for the "random" animation */
KEY_POINT_MAX = 16
};
/* Basic 3D point/vector class, used for basic vectorial
operations. */
class TPoint {
public:
float x;
float y;
float z;
TPoint operator* (const float k) const;
TPoint operator- (const TPoint& v2) const;
TPoint operator+ (const TPoint& v2) const;
TPoint operator^ (const TPoint& v2) const;
float Length() const;
};
/* Basic 3x3 matrix used for 3D transform. */
class TMatrix {
public:
float m[3][3];
TPoint operator* (const TPoint& v) const;
TPoint Axis(int32 index);
TMatrix Transpose() const;
void Set(const float alpha, const float theta, const float phi);
};
class BBox;
class BView;
/* The main window class, encapsulating both UI and engine. */
class ChartWindow : public BDirectWindow {
public:
/* standard constructor and destructor */
ChartWindow(BRect frame, const char *name);
virtual ~ChartWindow();
/* standard window members */
virtual bool QuitRequested();
virtual void MessageReceived(BMessage *message);
virtual void ScreenChanged(BRect screen_size, color_space depth);
virtual void FrameResized(float new_width, float new_height);
/* this struct embedded all user settable parameters that
can be set by the UI. The idea is to solve all possible
synchronisation problem between the UI settings and the
engine (when using DirectWindow mode) by defining a
current setting state and a next setting state. The UI
touches only the next setting state, never the one
currently use by the engine. This way the engine doesn't
have to be synchronised with the UI. */
struct setting {
/* do we want to use the second thread ? */
bool second_thread;
/* which ones of the 7 star colors are we using ? */
bool colors[7];
/* what window configuration mode are we using ? */
int32 fullscreen_mode;
/* what special mode are we using ? */
int32 special;
/* what display mode are we using ? */
int32 display;
/* what starfield model are we using ? */
int32 space_model;
/* what camera animation are we using ? */
int32 animation;
/* what is the density of the current starfield
model ? */
int32 star_density;
/* what's the current required refresh rate ? */
float refresh_rate;
/* what's the current background color for the animated
view ? */
rgb_color back_color;
/* what's the current color_space of the screen ? */
color_space depth;
/* what's the current dimension of the content area of
the window ? */
int32 width, height;
/* used to copy a whole setting in another. */
void Set(setting *master);
};
/* this union is used to store special animation information
that are defined per star. */
typedef union {
/* for the comet, it's a speed vector and to
counters to define how long the star will
continue before disappearing. */
struct {
float dx;
float dy;
float dz;
int32 count;
int32 count0;
} comet;
/* for the novas, just counters to define the
pulse cycle of the star. */
struct {
float count;
int32 count0;
} nova;
/* battle was not implemented. */
struct {
int32 count;
} battle;
} special;
/* public instance members */
/* the current instantenuous potential frame/rate
as display by the vue-meter. */
int32 fInstantLoadLevel;
/* the offscreen Bitmap used, if any. */
BBitmap *fOffscreen;
/* the current active setting used by the engine */
setting fCurrentSettings;
/* the private stuff... */
private:
/* User Interface related stuff. */
BBox *fStatusBox;
BBox *fColorsBox;
BBox *fSpecialBox;
BView *fLeftView;
BView *fTopView;
/* Find a window by its name if already opened. */
static BWindow *GetAppWindow(const char *name);
/* Used to set the content of PictureButton. */
BPicture *ButtonPicture(bool active, int32 button_type);
/* Those function create and handle the other settings
floating windows, for the background color, the star
density and the refresh rate. */
void OpenColorPalette(BPoint here);
void OpenStarDensity(BPoint here);
void OpenRefresh(BPoint here);
/* Draw the state of the instant-load vue-meter */
void DrawInstantLoad(float frame_per_second);
/* Print the performances numbers, based on the real framerate. */
void PrintStatNumbers(float fps);
/* Engine setting related functions. */
/* Init the geometry engine of the camera at startup. */
void InitGeometry();
/* Check and apply changes between a new setting state
and the currently used one. */
void ChangeSetting(setting new_set);
/* Initialise a new starfield of the specified model. */
void InitStars(int32 model);
/* Fill a star list with random stars in [0-1]x[0-1]x[0-1]. */
void FillStarList(star *list, int32 count);
/* Init a new special animation of a specific type. */
void InitSpecials(int32 code);
/* Change the star field colors depending a new set of
selected colors. */
void SetStarColors(int32 *color_list, int32 color_count);
/* Change the global geometry of the camera when the
viewing area is resized. */
void SetGeometry(int32 dh, int32 dv);
/* Change the color_space configuration of a buffer */
void SetColorSpace(buffer *buf, color_space depth);
/* Used to sync the pre-offset matrix pointer whenever the buffer
bits pointer changes. */
void SetPatternBits(buffer *buf);
/* Engine processing related functions. */
/* those functions are the two processing threads launcher */
static int32 Animation(void *data);
static int32 Animation2(void *data);
/* After every camera move or rotation, reprocess the torus
cycle of the starfield to maintain the pyramid of vision
of the camera completly inside a 1x1x1 iteration of the
starfield. */
void SetCubeOffset();
/* Process the camera animation for a specified time step */
void CameraAnimation(float time_factor);
/* Used by the random move camera animation. */
void SelectNewTarget();
void FollowTarget();
/* Process the special animation for a specified time step */
void AnimSpecials(float time_step);
/* Sync the embedded camera state with the window class camera
state (before calling the embedded C-engine in ChartRender.c */
void SyncGeo();
/* Control the star processing (done by 1 or 2 threads) and
executed by the embedded C-engine in ChartRender.c */
void RefreshStars(buffer *buf, float time_step);
/* Offscreen bitmap configuration related functions. */
/* Used to update the state of the offscreen Bitmap to stay
in sync with the current settings. */
void CheckBitmap(color_space depth, int32 width, int32 height);
/* Set the basic clipping of the offscreen Bitmap (everything
visible) */
void SetBitmapClipping(int32 width, int32 height);
/* Draw the offscreen bitmap background. */
void SetBitmapBackGround();
/* DirectWindow related functions */
/* Process a change of state in the direct access to the
frame buffer. */
void SwitchContext(direct_buffer_info *info);
public:
/* this is the hook controling direct screen connection */
virtual void DirectConnected(direct_buffer_info *info);
private:
/* Pseudo-random generator state and increment function. */
int32 fCrcAlea;
inline void CrcStep();
/* Various private instance variables. */
/* the next setting, as modified by the UI */
setting fNextSettings;
/* the buffer descriptors for the offscreen bitmap and
the DirectWindow buffer. */
buffer fBitmapBuffer;
buffer fDirectBuffer;
/* current maximal dimensions of the offscreen Bitmap buffer */
int32 fMaxWidth, fMaxHeight;
/* memorize previous state for switch between fullscreen
and window mode */
BRect fPreviousFrame;
int32 fPreviousFullscreenMode;
/* cycling threshold for the cubic torus starfield, that
guarantees that the 1x1x1 sample will contain the full
pyramid of vision. */
TPoint fCut;
/* maximal depth of the pyramid of vision */
float fDepthRef;
int32 fBackColorIndex;
/* target frame duration, in microsecond. */
bigtime_t fFrameDelay;
/* various UI object that we need to reach directly. */
BButton *fOffwindowButton;
ChartView *fChartView;
BStringView *fCpuLoadView, *fFramesView;
InstantView *fInstantLoad;
BPictureButton *fColorButton, *fDensityButton, *fRefreshButton;
/* states used to describe the camera position, rotation
and dynamic (in other case than free move). */
float fCameraAlpha, fCameraTheta, fCameraPhi;
float fDynamicAlpha;
float fDynamicTheta;
float fDynamicPhi;
int32 fCountAlpha, fCountTheta, fCountPhi;
TPoint fOrigin;
TMatrix fCamera;
TMatrix fCameraInvert;
/* the camera geometry descriptor required by the embedded
C-engine (just a copy of part of the previous states) */
geometry fGeometry;
/* states used by the free move camera animation */
int32 fTrackingTarget;
int32 fKeyPointCount;
float fSpeed, fTargetSpeed;
float fLastDynamicDelay;
TPoint fKeyPoints[KEY_POINT_MAX];
/* main starfield. */
star_packet fStars;
/* used for the special animation */
TPoint fComet[2];
TPoint fDeltaComet[2];
special *fSpecialList;
star_packet fSpecials;
/* the two processing threads. */
thread_id fAnimationThread;
thread_id fSecondAnimationThread;
/* context of the second processing thread (when used). */
float fSecondThreadThreshold;
buffer *fSecondThreadBuffer;
sem_id fSecondThreadLock;
sem_id fSecondThreadRelease;
bigtime_t fSecondThreadDelay;
star_packet fStars2;
star_packet fSpecials2;
/* Flag used to terminate the processing threads */
bool fKillThread;
/* Direct connection status */
bool fDirectConnected;
/* used to synchronise the star animation drawing. */
sem_id fDrawingLock;
};
#endif