示例#1
0
SidekickAnim::SidekickAnim (CompWindow *w,
			    WindowEvent curWindowEvent,
			    float duration,
			    const AnimEffect info,
			    const CompRect &icon) :
    Animation::Animation (w, curWindowEvent, duration, info, icon),
    TransformAnim::TransformAnim (w, curWindowEvent, duration, info, icon),
    ZoomAnim::ZoomAnim (w, curWindowEvent, duration, info, icon)
{
    // determine number of rotations randomly in [0.9, 1.1] range
    mNumRotations =
	optValF (AnimationOptions::SidekickNumRotations) *
	(1.0f + 0.2f * rand () / RAND_MAX - 0.1f);

    CompRect outRect (mAWindow->savedRectsValid () ?
		      mAWindow->savedOutRect () :
		      mWindow->outputRect ());

    float winCenterX = outRect.x () + outRect.width () / 2.0;
    float iconCenterX = mIcon.x () + mIcon.width () / 2.0;

    // if window is to the right of icon, rotate clockwise instead
    // to make rotation look more pleasant
    if (winCenterX > iconCenterX)
	mNumRotations *= -1;
}
示例#2
0
void
CompositeWindow::damageTransformedRect (float          xScale,
					float          yScale,
					float          xTranslate,
					float          yTranslate,
					const CompRect &rect)
{
    int x1, x2, y1, y2;

    x1 = (short) (rect.x1 () * xScale) - 1;
    y1 = (short) (rect.y1 () * yScale) - 1;
    x2 = (short) (rect.x2 () * xScale + 0.5f) + 1;
    y2 = (short) (rect.y2 () * yScale + 0.5f) + 1;

    x1 += (short) xTranslate;
    y1 += (short) yTranslate;
    x2 += (short) (xTranslate + 0.5f);
    y2 += (short) (yTranslate + 0.5f);

    if (x2 > x1 && y2 > y1)
    {
	const CompWindow::Geometry &geom = priv->window->serverGeometry ();

	x1 += geom.x () + geom.border ();
	y1 += geom.y () + geom.border ();
	x2 += geom.x () + geom.border ();
	y2 += geom.y () + geom.border ();

	priv->cScreen->damageRegion (CompRegion (CompRect (x1, y1, x2 - x1, y2 - y1)));
    }
}
示例#3
0
bool
CompRegion::intersects (const CompRect &r) const
{
    int result;
    result = XRectInRegion (handle (), r.x (), r.y (), r.width (), r.height ());

    return result != RectangleOut;
}
示例#4
0
bool
CompRegion::contains (const CompRect &r) const
{
    int result;

    result = XRectInRegion (handle (), r.x (), r.y (), r.width (), r.height ());

    return result == RectangleIn;
}
示例#5
0
void
ResizeWindow::getStretchScale (BoxPtr pBox, float *xScale, float *yScale)
{
    CompRect rect (window->borderRect ());

    *xScale = (rect.width ())  ? (pBox->x2 - pBox->x1) /
				 (float) rect.width () : 1.0f;
    *yScale = (rect.height ()) ? (pBox->y2 - pBox->y1) /
				 (float) rect.height () : 1.0f;
}
示例#6
0
Point
ZoomAnim::getCenter ()
{
    Point center;

    if (zoomToIcon ())
    {
	getCenterScale (&center, 0);
    }
    else
    {
	float forwardProgress = progressLinear ();

	CompRect inRect (mAWindow->savedRectsValid () ?
			 mAWindow->savedInRect () :
			 mWindow->borderRect ());

	center.setX (inRect.x () + inRect.width () / 2.0);

	if (mCurWindowEvent == WindowEventShade ||
	    mCurWindowEvent == WindowEventUnshade)
	{
	    float origCenterY = (inRect.y () +
				 inRect.height () / 2.0);
	    center.setY ((1 - forwardProgress) * origCenterY +
			 forwardProgress * (inRect.y () +
					    mDecorTopHeight));
	}
	else // i.e. (un)minimizing without zooming
	{
	    center.setY (inRect.y () + inRect.height () / 2.0);
	}
    }
    return center;
}
示例#7
0
void
GridAnim::init ()
{
    initGrid ();

    CompRect outRect (mAWindow->savedRectsValid () ?
		      mAWindow->savedOutRect () :
		      mWindow->outputRect ());

    mModel = new GridModel (mWindow, mCurWindowEvent,
			    outRect.height (),
			    mGridWidth, mGridHeight,
			    mDecorTopHeight, mDecorBottomHeight);
}
示例#8
0
	void
	calculateWallOffset (const CompRect  &output,
			     const CompPoint &offsetInScreenCoords,
			     const CompPoint &vpSize,
			     const CompSize  &screenSize,
			     float           &offsetInWorldX,
			     float           &offsetInWorldY,
			     float	     &worldScaleFactorX,
			     float	     &worldScaleFactorY,
			     float           animationProgress)
	{
	    const float sx = screenSize.width () / static_cast <float> (output.width ());
	    const float sy = screenSize.height () / static_cast <float> (output.height ());
	    offsetInWorldX = 0.0;
	    offsetInWorldY = 0.0;
	    worldScaleFactorX = 1.0f;
	    worldScaleFactorY = 1.0f;

	    if (output.left () == 0)
	    {
		offsetInWorldX = ((vpSize.x () * sx) / ((float) output.width ()) * (offsetInScreenCoords.x ()) * animationProgress);
		worldScaleFactorX = 1.0f - ((float) (offsetInScreenCoords.x ()) / (float) (output.width ())) * animationProgress;
	    }

	    if (output.top () == 0)
	    {
		offsetInWorldY = ((vpSize.y () * sy) / ((float) output.height ()) * (offsetInScreenCoords.y ()) * animationProgress);
		worldScaleFactorY = 1.0f - ((float) (offsetInScreenCoords.y ()) / (float) output.height ()) * animationProgress;
	    }
	}
void
LeafSpreadAnim::init ()
{
    if (!tessellateIntoRectangles (20, 14, 15.0f))
	return;

    CompRect outRect (mAWindow->savedRectsValid () ?
		      mAWindow->savedOutRect () :
		      mWindow->outputRect ());

    float fadeDuration = 0.26;
    float life = 0.4;
    float spreadFac = 3.5;
    float randYMax = 0.07;
    float winFacX = outRect.width () / 800.0;
    float winFacY = outRect.height () / 800.0;
    float winFacZ = (outRect.height () + outRect.width ()) / 2.0 / 800.0;

    float screenSizeFactor = (0.8 * DEFAULT_Z_CAMERA * ::screen->width ());

    foreach (PolygonObject *p, mPolygons)
    {
	p->rotAxis.set (RAND_FLOAT (), RAND_FLOAT (), RAND_FLOAT ());

	float speed = screenSizeFactor / 10 * (0.2 + RAND_FLOAT ());

	float xx = 2 * (p->centerRelPos.x () - 0.5);
	float yy = 2 * (p->centerRelPos.y () - 0.5);

	float x = speed * winFacX * spreadFac * (xx +
						 0.5 * (RAND_FLOAT () - 0.5));
	float y = speed * winFacY * spreadFac * (yy +
						 0.5 * (RAND_FLOAT () - 0.5));
	float z = speed * winFacZ * 7 * ((RAND_FLOAT () - 0.5) / 0.5);

	p->finalRelPos.set (x, y, z);

	p->moveStartTime =
	    p->centerRelPos.y () * (1 - fadeDuration - randYMax) +
	    randYMax * RAND_FLOAT ();
	p->moveDuration = 1;

	p->fadeStartTime = p->moveStartTime + life;
	if (p->fadeStartTime > 1 - fadeDuration)
	    p->fadeStartTime = 1 - fadeDuration;
	p->fadeDuration = fadeDuration;

	p->finalRotAng = 150;
    }
示例#10
0
void
PrivateGLWindow::updateWindowRegions ()
{
    CompRect input (window->serverInputRect ());

    if (regions.size () != textures.size ())
	regions.resize (textures.size ());
    for (unsigned int i = 0; i < textures.size (); i++)
    {
	regions[i] = CompRegion (*textures[i]);
	regions[i].translate (input.x (), input.y ());
	regions[i] &= window->region ();
    }
    updateState &= ~(UpdateRegion);
}
示例#11
0
CompRegion::CompRegion (const CompRect &r)
{
    priv = new PrivateRegion ();
    priv->box.extents = r.region ()->extents;
    priv->box.numRects = 1;
    priv->box.rects = &priv->box.extents;
}
示例#12
0
void
CompOutput::setWorkArea (const CompRect &workarea)
{
    mWorkArea = workarea;

    if (workarea.x ()  < static_cast <int> (x1 ()))
	mWorkArea.setX (x1 ());

    if (workarea.y ()  < static_cast <int> (y1 ()))
	mWorkArea.setY (y1 ());

    if (workarea.x2 () > static_cast <int> (x2 ()))
	mWorkArea.setWidth (x2 ()  - mWorkArea.x ());

    if (workarea.y2 () > static_cast <int> (y2 ()))
	mWorkArea.setHeight (y2 () - mWorkArea.y ());
}
示例#13
0
void
CompOutput::setWorkArea (const CompRect& workarea)
{
    mWorkArea = workarea;

    if (workarea.x () < (int) x1 ())
	mWorkArea.setX (x1 ());

    if (workarea.y () < (int) y1 ())
	mWorkArea.setY (y1 ());

    if (workarea.x2 () > (int) x2 ())
	mWorkArea.setWidth (x2 () - mWorkArea.x ());

    if (workarea.y2 () > (int) y2 ())
	mWorkArea.setHeight (y2 () - mWorkArea.y ());
}
示例#14
0
CompRegion
CompRegion::united (const CompRect &r) const
{
    CompRegion rv;
    rv.priv->makeReal ();
    XUnionRegion (handle (), r.region (), rv.handle ());
    return rv;
}
示例#15
0
CompRegion
CompRegion::subtracted (const CompRect &r) const
{
    CompRegion rv;
    rv.priv->makeReal ();
    XSubtractRegion (handle (), r.region (), rv.handle ());
    return rv;
}
示例#16
0
void
PrivateGLWindow::setWindowMatrix ()
{
    CompRect input (window->inputRect ());

    if (textures.size () != matrices.size ())
	matrices.resize (textures.size ());

    for (unsigned int i = 0; i < textures.size (); i++)
    {
	matrices[i] = textures[i]->matrix ();
	matrices[i].x0 -= (input.x () * matrices[i].xx);
	matrices[i].y0 -= (input.y () * matrices[i].yy);
    }

    updateState &= ~(UpdateMatrix);
}
示例#17
0
ZoomAnim::ZoomAnim (CompWindow *w,
		    WindowEvent curWindowEvent,
		    float duration,
		    const AnimEffect info,
		    const CompRect &icon) :
    Animation::Animation (w, curWindowEvent, duration, info, icon),
    TransformAnim::TransformAnim (w, curWindowEvent, duration, info, icon),
    FadeAnim::FadeAnim (w, curWindowEvent, duration, info, icon)
{
    CompRect outRect (mAWindow->savedRectsValid () ?
		      mAWindow->savedOutRect () :
		      mWindow->outputRect ());

    if (isZoomFromCenter ())
    {
	mIcon.setX (outRect.x () + outRect.width () / 2 - mIcon.width () / 2);
	mIcon.setY (outRect.y () + outRect.height () / 2 - mIcon.height () / 2);
    }
}
示例#18
0
void
SvgWindow::updateSvgMatrix ()
{
    SvgTexture        *texture;
    GLTexture::Matrix *m;
    unsigned int      i;
    CompRect          rect;

    rect = context->box.boundingRect ();
    texture = &context->texture[0];

    if (texture->matrices.size () != texture->textures.size ())
	texture->matrices.resize (texture->textures.size ());

    for (i = 0; i < texture->textures.size (); i++)
    {
	m = &texture->matrices[i];
	*m = texture->textures[i]->matrix ();

	m->xx *= (float) texture->size.width ()  / rect.width ();
	m->yy *= (float) texture->size.height () / rect.height ();

	m->x0 -= (rect.x () * m->xx);
	m->y0 -= (rect.y () * m->yy);
    }

    texture = &context->texture[1];

    if (texture->matrices.size () != texture->textures.size ())
	texture->matrices.resize (texture->textures.size ());

    for (i = 0; i < texture->textures.size (); i++)
    {
	m = &texture->matrices[i];
	*m = texture->textures[i]->matrix ();

	m->xx *= (float) texture->size.width ()  / context->rect.width ();
	m->yy *= (float) texture->size.height () / context->rect.height ();

	m->x0 -= (context->rect.x () * m->xx);
	m->y0 -= (context->rect.y () * m->yy);
    }
}
void
reserveStruts (CompRect &workArea)
{
    workArea.setLeft (workArea.left () + 24);
    workArea.setTop (workArea.top () + 24);
    workArea.setBottom (workArea.bottom () - 24);
}
示例#20
0
void
CompositeWindow::addDamageRect (const CompRect &rect)
{
    if (priv->cScreen->damageMask () & COMPOSITE_SCREEN_DAMAGE_ALL_MASK)
	return;

    if (!damageRect (false, rect))
    {
	int x, y;

	x = rect.x ();
	y = rect.y ();

	const CompWindow::Geometry &geom = priv->window->geometry ();
	x += geom.x () + geom.border ();
	y += geom.y () + geom.border ();

	priv->cScreen->damageRegion (CompRegion (CompRect (x, y,
							   rect.width (),
							   rect.height ())));
    }
}
示例#21
0
void
WSNamesScreen::drawText (const GLMatrix &matrix)
{
    GLfloat  alpha;
    float    x, y, border = 10.0f;
    CompRect oe = screen->getCurrentOutputExtents ();

    x = oe.centerX () - textData.getWidth () / 2;

    /* assign y (for the lower corner!) according to the setting */
    switch (optionGetTextPlacement ())
    {
    case WorkspacenamesOptions::TextPlacementCenteredOnScreen:
        y = oe.centerY () + textData.getHeight () / 2;
        break;
    case WorkspacenamesOptions::TextPlacementTopOfScreen:
    case WorkspacenamesOptions::TextPlacementBottomOfScreen:
    {
        CompRect workArea = screen->currentOutputDev ().workArea ();

        if (optionGetTextPlacement () ==
                WorkspacenamesOptions::TextPlacementTopOfScreen)
            y = oe.y1 () + workArea.y () +
                (2 * border) + textData.getHeight ();
        else
            y = oe.y1 () + workArea.y () +
                workArea.height () - (2 * border);
    }
    break;
    default:
        return;
        break;
    }

    if (timer)
        alpha = timer / (optionGetFadeTime () * 1000.0f);
    else
        alpha = 1.0f;

    textData.draw (matrix, floor (x), floor (y), alpha);
}
示例#22
0
void
ZoomAnim::getCenterScaleFull (Point *pCurCenter, Point *pCurScale,
			      Point *pWinCenter, Point *pIconCenter,
			      float *pMoveProgress)
{
    CompRect outRect (mAWindow->savedRectsValid () ?
		      mAWindow->savedOutRect () :
		      mWindow->outputRect ());

    Point winCenter ((outRect.x () + outRect.width () / 2.0),
		     (outRect.y () + outRect.height () / 2.0));
    Point iconCenter (mIcon.x () + mIcon.width () / 2.0,
		      mIcon.y () + mIcon.height () / 2.0);
    Point winSize (outRect.width (), outRect.height ());

    winSize.setX (winSize.x () == 0 ? 1 : winSize.x ());
    winSize.setY (winSize.y () == 0 ? 1 : winSize.y ());

    float scaleProgress;
    float moveProgress;

    getZoomProgress (&moveProgress, &scaleProgress, neverSpringy ());

    Point curCenter
	((1 - moveProgress) * winCenter.x () + moveProgress * iconCenter.x (),
	 (1 - moveProgress) * winCenter.y () + moveProgress * iconCenter.y ());
    Point curScale
	(((1 - scaleProgress) * winSize.x () +
	  scaleProgress * mIcon.width ()) / winSize.x (),
	 ((1 - scaleProgress) * winSize.y () +
	  scaleProgress * mIcon.height ()) / winSize.y ());

    // Copy calculated variables
    if (pCurCenter)
	*pCurCenter = curCenter;
    if (pCurScale)
	*pCurScale = curScale;
    if (pWinCenter)
	*pWinCenter = winCenter;
    if (pIconCenter)
	*pIconCenter = iconCenter;
    if (pMoveProgress)
	*pMoveProgress = moveProgress;
}
示例#23
0
void
BurnAnim::step ()
{
    CompRect outRect (mAWindow->savedRectsValid () ?
		      mAWindow->savedOutRect () :
		      mWindow->outputRect ());

    float timestep = mIntenseTimeStep;
    float old = 1 - (mRemainingTime) / (mTotalTime - timestep);
    float stepSize;

    mRemainingTime -= timestep;
    if (mRemainingTime <= 0)
	mRemainingTime = 0;	// avoid sub-zero values
    float newProgress = 1 - (mRemainingTime) / (mTotalTime - timestep);

    stepSize = newProgress - old;

    if (mCurWindowEvent == WindowEventOpen ||
	mCurWindowEvent == WindowEventUnminimize ||
	mCurWindowEvent == WindowEventUnshade)
    {
	newProgress = 1 - newProgress;
    }

    if (mRemainingTime > 0)
    {
	CompRect rect;

	switch (mDirection)
	{
	case AnimDirectionUp:
	    rect = CompRect (0, 0,
	                     outRect.width (),
	                     outRect.height () -
	                     (newProgress * outRect.height ()));
	    break;
	case AnimDirectionRight:
	    rect = CompRect (newProgress * outRect.width (),
			     0,
			     outRect.width () -
			     (newProgress * outRect.width ()),
			     outRect.height ());
	    break;
	case AnimDirectionLeft:
	    rect = CompRect (0, 0,
			     outRect.width () -
			     (newProgress * outRect.width ()),
			     outRect.height ());
	    break;
	case AnimDirectionDown:
	default:
	    rect = CompRect (0,
			     newProgress * outRect.height (),
			     outRect.width (),
			     outRect.height () -
			     (newProgress * outRect.height ()));
	    break;
	}
	rect.setX (rect.x () + outRect.x ());
	rect.setY (rect.y () + outRect.y ());

	mDrawRegion = CompRegion (rect);
    }
    else
    {
	mDrawRegion = emptyRegion;
    }
    mUseDrawRegion = (fabs (newProgress) > 1e-5);

    if (mRemainingTime > 0)
    {
	switch (mDirection)
	{
	case AnimDirectionUp:
	    if (mHasSmoke)
		genNewSmoke (outRect.x (),
			     outRect.y () + ((1 - newProgress) * outRect.height ()),
			     outRect.width (), 1, outRect.width () / 40.0,
			     mTimeSinceLastPaint);
	    genNewFire (outRect.x (),
			outRect.y () + ((1 - newProgress) * outRect.height ()),
			outRect.width (), (stepSize) * outRect.height (),
			outRect.width () / 40.0,
			mTimeSinceLastPaint);
	    break;
	case AnimDirectionLeft:
	    if (mHasSmoke)
		genNewSmoke (outRect.x () + ((1 - newProgress) * outRect.width ()),
			     outRect.y (),
			     (stepSize) * outRect.width (),
			     outRect.height (), outRect.height () / 40.0,
			     mTimeSinceLastPaint);
	    genNewFire (outRect.x () + ((1 - newProgress) * outRect.width ()),
			outRect.y (), (stepSize) * outRect.width (),
			outRect.height (), outRect.height () / 40.0,
			mTimeSinceLastPaint);
	    break;
	case AnimDirectionRight:
	    if (mHasSmoke)
		genNewSmoke (outRect.x () + (newProgress * outRect.width ()),
			     outRect.y (),
			     (stepSize) * outRect.width (),
			     outRect.height (), outRect.height () / 40.0,
			     mTimeSinceLastPaint);
	    genNewFire (outRect.x () + (newProgress * outRect.width ()),
			outRect.y (), (stepSize) * outRect.width (),
			outRect.height (), outRect.height () / 40.0,
			mTimeSinceLastPaint);
	    break;
	case AnimDirectionDown:
	default:
	    if (mHasSmoke)
		genNewSmoke (outRect.x (),
			     outRect.y () + (newProgress * outRect.height ()),
			     outRect.width (), 1, outRect.width () / 40.0,
			     mTimeSinceLastPaint);
	    genNewFire (outRect.x (),
			outRect.y () + (newProgress * outRect.height ()),
			outRect.width (), (stepSize) * outRect.height (),
			outRect.width () / 40.0,
			mTimeSinceLastPaint);
	    break;
	}

    }
    if (mRemainingTime <= 0 &&
	(mParticleSystems[0].active () ||
	 (mHasSmoke && mParticleSystems[1].active ())))
	// force animation to continue until particle systems are done
	mRemainingTime = timestep;

    Particle *part;

    if (mRemainingTime > 0)
    {
	int nParticles;
	if (mHasSmoke)
	{
	    float partxg = outRect.width () / 40.0;
	    float partxgNeg = -partxg;

	    vector<Particle> &particles = mParticleSystems[mSmokePSId].particles ();
	    nParticles = particles.size ();
	    part = &particles[0];

	    for (int i = 0; i < nParticles; i++, part++)
		part->xg = (part->x < part->xo) ? partxg : partxgNeg;

	    mParticleSystems[mSmokePSId].setOrigin (outRect.x (), outRect.y ());
	}

	vector<Particle> &particles = mParticleSystems[mFirePSId].particles ();
	nParticles = particles.size ();
	part = &particles[0];

	for (int i = 0; i < nParticles; i++, part++)
	    part->xg = (part->x < part->xo) ? 1.0 : -1.0;
    }
    mParticleSystems[mFirePSId].setOrigin (outRect.x (), outRect.y ());
}
void
HorizontalFoldsAnim::step ()
{
    GridZoomAnim::step ();

    CompRect winRect (mAWindow->savedRectsValid () ?
		      mAWindow->saveWinRect () :
		      mWindow->geometry ());
    CompRect inRect (mAWindow->savedRectsValid () ?
		     mAWindow->savedInRect () :
		     mWindow->inputRect ());
    CompRect outRect (mAWindow->savedRectsValid () ?
		      mAWindow->savedOutRect () :
		      mWindow->outputRect ());
    CompWindowExtents outExtents (mAWindow->savedRectsValid () ?
				  mAWindow->savedOutExtents () :
				  mWindow->output ());

    int wx = winRect.x ();
    int wy = winRect.y ();

    int oy = outRect.y ();
    int owidth = outRect.width ();
    int oheight = outRect.height ();

    float winHeight = 0;
    if (mCurWindowEvent == WindowEventShade ||
	mCurWindowEvent == WindowEventUnshade)
    {
	winHeight = winRect.height ();
    }
    else
    {
	winHeight = inRect.height ();
    }
    int nHalfFolds =
	2.0 * optValI (AnimationOptions::HorizontalFoldsNumFolds);
    float foldMaxAmp =
	0.3 * pow ((winHeight / nHalfFolds) / ::screen->height (), 0.3) *
	optValF (AnimationOptions::HorizontalFoldsAmpMult);

    float forwardProgress = getActualProgress ();

    float sinForProg = sin (forwardProgress * M_PI / 2);

    GridModel::GridObject *object = mModel->objects ();
    unsigned int n = mModel->numObjects ();
    for (unsigned int i = 0; i < n; ++i, ++object)
    {
	Point3d &objPos = object->position ();

	if (i % 2 == 0) // object is at the left side
	{
	    float objGridY = object->gridPosition ().y ();

	    int rowNo = (int)i / mGridWidth;
	    float origy = (wy +
			   (oheight * objGridY -
			    outExtents.top) * mModel->scale ().y ());
	    if (mCurWindowEvent == WindowEventShade ||
		mCurWindowEvent == WindowEventUnshade)
	    {
		// Execute shade mode

		if (objGridY == 0)
		{
		    objPos.setY (oy);
		    objPos.setZ (0);
		}
		else if (objGridY == 1)
		{
		    objPos.setY (
			(1 - forwardProgress) * origy +
			forwardProgress *
			(oy + mDecorTopHeight + mDecorBottomHeight));
		    objPos.setZ (0);
		}
		else
		{
		    float relDistToFoldCenter = (rowNo % 2 == 1 ? 0.5 : 0);

		    objPos.setY (
			(1 - forwardProgress) * origy +
			forwardProgress * (oy + mDecorTopHeight));
		    objPos.setZ (
			getObjectZ (mModel, forwardProgress, sinForProg,
				    relDistToFoldCenter, foldMaxAmp));
		}
	    }
	    else
	    {
		// Execute normal mode

		float relDistToFoldCenter = (rowNo % 2 == 0 ? 0.5 : 0);

		objPos.setY (
		    (1 - forwardProgress) * origy +
		    forwardProgress * (inRect.y () + inRect.height () / 2.0));
		objPos.setZ (
			getObjectZ (mModel, forwardProgress, sinForProg,
				    relDistToFoldCenter, foldMaxAmp));
	    }
	}
	else // object is at the right side
	{
	    // Set y/z position to the y/z position of the object at the left
	    // on the same row (previous object)
	    Point3d &leftObjPos = (object - 1)->position ();
	    objPos.setY (leftObjPos.y ());
	    objPos.setZ (leftObjPos.z ());
	}

	float origx = (wx +
		       (owidth * object->gridPosition ().x () -
			outExtents.left) * mModel->scale ().x ());
	objPos.setX (origx);
    }
}
示例#25
0
bool
SvgWindow::glDraw (const GLMatrix     &transform,
		   const GLWindowPaintAttrib &attrib,
		   const CompRegion   &region,
		   unsigned int       mask)
{
    bool status = gWindow->glDraw (transform, attrib, region, mask);

    if (!status)
	return status;

    const CompRegion &reg = (mask & PAINT_WINDOW_TRANSFORMED_MASK) ?
			    infiniteRegion : region;

    if (context && reg.numRects ())
    {
	GLTexture::MatrixList matrix (1);
	int		      x1, y1, x2, y2;
	CompRect              rect = context->box.boundingRect ();

	x1 = MIN (rect.x1 (), sScreen->zoom.x1 ());
	y1 = MIN (rect.y1 (), sScreen->zoom.y1 ());
	x2 = MAX (rect.x2 (), sScreen->zoom.x2 ());
	y2 = MAX (rect.y2 (), sScreen->zoom.y2 ());

	rect.setGeometry (x1, y1, x2 - x1, y2 - y1);

	for (unsigned int i = 0; i < context->texture[0].textures.size (); i++)
	{
	    matrix[0] = context->texture[0].matrices[i];

	    gWindow->vertexBuffer ()->begin ();
	    gWindow->glAddGeometry (matrix, context->box, reg);
	    gWindow->vertexBuffer ()->end ();

	    if (mask & PAINT_WINDOW_TRANSLUCENT_MASK)
		mask |= PAINT_WINDOW_BLEND_MASK;

	    gWindow->glDrawTexture (context->texture[0].textures[i], transform,
	                            attrib, mask);

	    if (rect.width () > 0 && rect.height () > 0)
	    {
		float    xScale, yScale;
		float    dx, dy;
		int      width, height;

		rect.setGeometry (rect.x1 () - 1,
				  rect.y1 () - 1,
				  rect.width () + 1,
				  rect.height () + 1);

		xScale = screen->width  () /
		         (float) (sScreen->zoom.width ());
		yScale = screen->height () /
		         (float) (sScreen->zoom.height ());

		dx = rect.width ();
		dy = rect.height ();

		width  = dx * xScale + 0.5f;
		height = dy * yScale + 0.5f;

		if (rect   != context->rect          ||
		    width  != context->size.width () ||
		    height != context->size.height ())
		{
		    float x1, y1, x2, y2;

		    context->rect = rect;
		    context->size.setWidth (width);
		    context->size.setHeight (height);

		    dx = context->box.boundingRect ().width ();
		    dy = context->box.boundingRect ().height ();

		    x1 = (rect.x1 () - context->box.boundingRect ().x ()) / dx;
		    y1 = (rect.y1 () - context->box.boundingRect ().y ()) / dy;
		    x2 = (rect.x2 () - context->box.boundingRect ().x ()) / dx;
		    y2 = (rect.y2 () - context->box.boundingRect ().y ()) / dy;

		    finiTexture (context->texture[1]);

		    if (initTexture (context->source, context->texture[1],
				     context->size))
		    {
			renderSvg (context->source, context->texture[1],
				   context->size, x1, y1, x2, y2);

			updateSvgMatrix ();
		    }
		}

		for (unsigned int j = 0; j < context->texture[1].textures.size (); j++)
		{
		    GLTexture::Filter saveFilter;
		    CompRegion        r (rect);

		    matrix[0] = context->texture[1].matrices[j];

		    saveFilter = gScreen->filter (SCREEN_TRANS_FILTER);
		    gScreen->setFilter (SCREEN_TRANS_FILTER, GLTexture::Good);

		    gWindow->vertexBuffer ()->begin ();
		    gWindow->glAddGeometry (matrix, r, reg);
		    gWindow->vertexBuffer ()->end ();

		    gWindow->glDrawTexture (context->texture[1].textures[j],
					    transform, attrib, mask);

		    gScreen->setFilter (SCREEN_TRANS_FILTER, saveFilter);
		}
	    }
	    else if (context->texture[1].size.width ())
	    {
		finiTexture (context->texture[1]);
		initTexture (source, context->texture[1], CompSize ());

		memset (&context->rect, 0, sizeof (BoxRec));
		context->size.setWidth (0);
		context->size.setHeight (0);
	    }
	}
    }

    return status;
}
示例#26
0
void
GridAnim::addGeometry (const GLTexture::MatrixList &matrix,
		       const CompRegion            &region,
		       const CompRegion            &clip,
		       unsigned int                maxGridWidth,
		       unsigned int                maxGridHeight)
{
    unsigned int nMatrix = matrix.size ();
    int nVertices, nIndices;
    GLushort *i;
    GLfloat *v;
    int x1, y1, x2, y2;
    float winContentsY, winContentsHeight;
    float deformedX, deformedY;
    float deformedZ = 0;
    int nVertX, nVertY;
    int vSize;
    float gridW, gridH;
    bool rect = true;
    bool notUsing3dCoords = !using3D ();

    if (region.isEmpty ()) // nothing to do
	return;

    GLWindow::Geometry &geometry = GLWindow::get (mWindow)->geometry ();

    for (unsigned int it = 0; it < nMatrix; it++)
    {
	if (matrix[it].xy != 0.0f || matrix[it].yx != 0.0f)
	{
	    rect = false;
	    break;
	}
    }

    CompRect outRect (mAWindow->savedRectsValid () ?
		      mAWindow->savedOutRect () :
		      mWindow->outputRect ());
    CompWindowExtents outExtents (mAWindow->savedRectsValid () ?
				  mAWindow->savedOutExtents () :
				  mWindow->output ());

    // window output (contents + decorations + shadows) coordinates and size
    int ox = outRect.x ();
    int oy = outRect.y ();
    int owidth = outRect.width ();
    int oheight = outRect.height ();

    // to be used if event is shade/unshade
    winContentsY = oy + outExtents.top;
    winContentsHeight = oheight - outExtents.top - outExtents.bottom;

    geometry.texUnits = (int)nMatrix;

    if (geometry.vCount == 0)
    {
	// reset
	geometry.indexCount = 0;
	geometry.texCoordSize = 4;
    }
    geometry.vertexStride = 3 + geometry.texUnits * geometry.texCoordSize;
    vSize = geometry.vertexStride;

    nVertices = geometry.vCount;
    nIndices = geometry.indexCount;

    v = geometry.vertices + (nVertices * vSize);
    i = geometry.indices + nIndices;

    // For each clip passed to this function
    foreach (const CompRect &pClip, region.rects ())
    {
	x1 = pClip.x1 ();
	y1 = pClip.y1 ();
	x2 = pClip.x2 ();
	y2 = pClip.y2 ();

	gridW = (float)owidth / (mGridWidth - 1);

	if (mCurWindowEvent == WindowEventShade ||
	    mCurWindowEvent == WindowEventUnshade)
	{
	    if (y1 < winContentsY)	// if at top part
	    {
		gridH = mDecorTopHeight;
	    }
	    else if (y2 > winContentsY + winContentsHeight)  // if at bottom
	    {
		gridH = mDecorBottomHeight;
	    }
	    else			// in window contents (only in Y coords)
	    {
		float winContentsHeight =
		    oheight - (mDecorTopHeight + mDecorBottomHeight);
		gridH = winContentsHeight / (mGridHeight - 3);
	    }
	}
	else
	    gridH = (float)oheight / (mGridHeight - 1);

	// nVertX, nVertY: number of vertices for this clip in x and y dimensions
	// + 2 to avoid running short of vertices in some cases
	nVertX = ceil ((x2 - x1) / gridW) + 2;
	nVertY = (gridH ? ceil ((y2 - y1) / gridH) : 0) + 2;

	// Allocate 4 indices for each quad
	int newIndexSize = nIndices + ((nVertX - 1) * (nVertY - 1) * 4);

	if (newIndexSize > geometry.indexSize)
	{
	    if (!geometry.moreIndices (newIndexSize))
		return;

	    i = geometry.indices + nIndices;
	}
	// Assign quad vertices to indices
	for (int jy = 0; jy < nVertY - 1; jy++)
	{
	    for (int jx = 0; jx < nVertX - 1; jx++)
	    {
		*i++ = nVertices + nVertX * (2 * jy + 1) + jx;
		*i++ = nVertices + nVertX * (2 * jy + 1) + jx + 1;
		*i++ = nVertices + nVertX * 2 * jy + jx + 1;
		*i++ = nVertices + nVertX * 2 * jy + jx;

		nIndices += 4;
	    }
	}

	// Allocate vertices
	int newVertexSize =
	    (nVertices + nVertX * (2 * nVertY - 2)) * vSize;
	if (newVertexSize > geometry.vertexSize)
	{
	    if (!geometry.moreVertices (newVertexSize))
		return;

	    v = geometry.vertices + (nVertices * vSize);
	}

	float rowTexCoordQ = 1;
	float prevRowCellWidth = 0;	// this initial value won't be used
	float rowCellWidth = 0;
	int clipRowSize = nVertX * vSize;

	// For each vertex
	float y = y1;
	for (int jy = 0; jy < nVertY; jy++)
	{
	    float topiyFloat;
	    bool applyOffsets = true;

	    if (y > y2)
		y = y2;

	    // Do calculations for y here to avoid repeating
	    // them unnecessarily in the x loop

	    if (mCurWindowEvent == WindowEventShade ||
		mCurWindowEvent == WindowEventUnshade)
	    {
		if (y1 < winContentsY)	// if at top part
		{
		    topiyFloat = (y - oy) / mDecorTopHeight;
		    topiyFloat = MIN (topiyFloat, 0.999);	// avoid 1.0
		    applyOffsets = false;
		}
		else if (y2 > winContentsY + winContentsHeight)	// if at bottom
		{
		    topiyFloat = (mGridHeight - 2) +
			(mDecorBottomHeight ? (y - winContentsY -
					       winContentsHeight) /
			 mDecorBottomHeight : 0);
		    applyOffsets = false;
		}
		else		// in window contents (only in Y coords)
		{
		    topiyFloat = (mGridHeight - 3) *
			(y - winContentsY) / winContentsHeight + 1;
		}
	    }
	    else
	    {
		topiyFloat = (mGridHeight - 1) * (y - oy) / oheight;
	    }
	    // topiy should be at most (mGridHeight - 2)
	    int topiy = (int)(topiyFloat + 1e-4);

	    if (topiy == mGridHeight - 1)
		topiy--;
	    int bottomiy = topiy + 1;
	    float iny = topiyFloat - topiy;
	    float inyRest = 1 - iny;

	    // End of calculations for y

	    float x = x1;
	    for (int jx = 0; jx < nVertX; jx++)
	    {
		if (x > x2)
		    x = x2;

		// find containing grid cell (leftix rightix) x (topiy bottomiy)
		float leftixFloat =
		    (mGridWidth - 1) * (x - ox) / owidth;
		int leftix = (int)(leftixFloat + 1e-4);

		if (leftix == mGridWidth - 1)
		    leftix--;
		int rightix = leftix + 1;

		// GridModel::GridObjects that are at top, bottom, left, right corners of quad
		GridModel::GridObject *objToTopLeft =
		    &(mModel->mObjects[topiy * mGridWidth + leftix]);
		GridModel::GridObject *objToTopRight =
		    &(mModel->mObjects[topiy * mGridWidth + rightix]);
		GridModel::GridObject *objToBottomLeft =
		    &(mModel->mObjects[bottomiy * mGridWidth + leftix]);
		GridModel::GridObject *objToBottomRight =
		    &(mModel->mObjects[bottomiy * mGridWidth + rightix]);

		Point3d &objToTopLeftPos = objToTopLeft->mPosition;
		Point3d &objToTopRightPos = objToTopRight->mPosition;
		Point3d &objToBottomLeftPos = objToBottomLeft->mPosition;
		Point3d &objToBottomRightPos = objToBottomRight->mPosition;

		// find position in cell by taking remainder of flooring
		float inx = leftixFloat - leftix;
		float inxRest = 1 - inx;

		// Interpolate to find deformed coordinates

		float hor1x = (inxRest * objToTopLeftPos.x () +
			       inx * objToTopRightPos.x ());
		float hor1y = (inxRest * objToTopLeftPos.y () +
			       inx * objToTopRightPos.y ());
		float hor1z = (notUsing3dCoords ? 0 :
			       inxRest * objToTopLeftPos.z () +
			       inx * objToTopRightPos.z ());
		float hor2x = (inxRest * objToBottomLeftPos.x () +
			       inx * objToBottomRightPos.x ());
		float hor2y = (inxRest * objToBottomLeftPos.y () +
			       inx * objToBottomRightPos.y ());
		float hor2z = (notUsing3dCoords ? 0 :
			       inxRest * objToBottomLeftPos.z () +
			       inx * objToBottomRightPos.z ());

		deformedX = inyRest * hor1x + iny * hor2x;
		deformedY = inyRest * hor1y + iny * hor2y;
		deformedZ = inyRest * hor1z + iny * hor2z;

		// Texture coordinates (s, t, r, q)

		if (mUseQTexCoord)
		{
		    if (jx == 1)
			rowCellWidth = deformedX - v[-3];

		    // do only once per row for all rows except row 0
		    if (jy > 0 && jx == 1)
		    {
			rowTexCoordQ = (rowCellWidth / prevRowCellWidth);

			for (unsigned int it = 0; it < nMatrix; it++, v += 4)
			{
			    // update first column
			    // (since we didn't know rowTexCoordQ before)
			    v[-vSize]     *= rowTexCoordQ; // multiply s & t by q
			    v[-vSize + 1] *= rowTexCoordQ;
			    v[-vSize + 3] = rowTexCoordQ;  // copy q
			}
			v -= nMatrix * 4;
		    }
		}

		// Loop for each texture element
		// (4 texture coordinates for each one)
		for (unsigned int it = 0; it < nMatrix; it++, v += 4)
		{
		    float offsetY = 0;

		    if (rect)
		    {
			if (applyOffsets && y < y2)
			    offsetY = objToTopLeft->mOffsetTexCoordForQuadAfter.y ();
			v[0] = COMP_TEX_COORD_X (matrix[it], x); // s
			v[1] = COMP_TEX_COORD_Y (matrix[it], y + offsetY); // t
		    }
		    else
		    {
			if (applyOffsets && y < y2)
			    // FIXME:
			    // The correct y offset below produces wrong
			    // texture coordinates for some reason.
			    offsetY = 0;
			    // offsetY = objToTopLeft->offsetTexCoordForQuadAfter.y;
			v[0] = COMP_TEX_COORD_XY (matrix[it], x, y + offsetY); // s
			v[1] = COMP_TEX_COORD_YX (matrix[it], x, y + offsetY); // t
		    }
		    v[2] = 0; // r

		    if (0 < jy && jy < nVertY - 1)
		    {
			// copy s, t, r to duplicate row
			memcpy (v + clipRowSize, v, 3 * sizeof (GLfloat));
			v[3 + clipRowSize] = 1; // q
		    }

		    if (applyOffsets &&
			objToTopLeft->mOffsetTexCoordForQuadBefore.y () != 0)
		    {
			// After copying to next row, update texture y coord
			// by following object's offset
			offsetY = objToTopLeft->mOffsetTexCoordForQuadBefore.y ();
			if (rect)
			{
			    v[1] = COMP_TEX_COORD_Y (matrix[it], y + offsetY);
			}
			else
			{
			    v[0] = COMP_TEX_COORD_XY (matrix[it],
						      x, y + offsetY);
			    v[1] = COMP_TEX_COORD_YX (matrix[it],
						      x, y + offsetY);
			}
		    }
		    if (mUseQTexCoord)
		    {
			v[3] = rowTexCoordQ; // q

			if (jx > 0)	// since column 0 is updated when jx == 1
			{
			    // multiply s & t by q
			    v[0] *= rowTexCoordQ;
			    v[1] *= rowTexCoordQ;
			}
		    }
		    else
		    {
			v[3] = 1; // q
		    }
		}

		v[0] = deformedX;
		v[1] = deformedY;
		v[2] = deformedZ;

		// Copy vertex coordinates to duplicate row
		if (0 < jy && jy < nVertY - 1)
		    memcpy (v + clipRowSize, v, 3 * sizeof (GLfloat));

		nVertices++;

		// increment x properly (so that coordinates fall on grid intersections)
		x = rightix * gridW + ox;

		v += 3; // move on to next vertex
	    }
	    if (mUseQTexCoord)
		prevRowCellWidth = rowCellWidth;

	    if (0 < jy && jy < nVertY - 1)
	    {
		v += clipRowSize;	// skip the duplicate row
		nVertices += nVertX;
	    }
	    // increment y properly (so that coordinates fall on grid intersections)
	    if (mCurWindowEvent == WindowEventShade ||
		mCurWindowEvent == WindowEventUnshade)
	    {
		y += gridH;
	    }
	    else
	    {
		y = bottomiy * gridH + oy;
	    }
	}
    }
    geometry.vCount = nVertices;
    geometry.indexCount = nIndices;
}
示例#27
0
void
RollUpAnim::step ()
{
    float forwardProgress = progressEaseInEaseOut ();
    bool fixedInterior = optValB (AnimationOptions::RollupFixedInterior);

    CompRect outRect (mAWindow->savedRectsValid () ?
		      mAWindow->savedOutRect () :
		      mWindow->outputRect ());

    int ox = outRect.x ();
    int oy = outRect.y ();
    int owidth = outRect.width ();
    int oheight = outRect.height ();

    GridModel::GridObject *object = mModel->objects ();
    unsigned int n = mModel->numObjects ();
    for (unsigned int i = 0; i < n; i++, object++)
    {
	// Executing shade mode

	Point3d &objPos = object->position ();

	if (i % 2 == 0) // object is at the left side
	{
	    float objGridY = object->gridPosition ().y ();

	    if (objGridY == 0)
	    {
		objPos.setY (oy);
	    }
	    else if (objGridY == 1)
	    {
		objPos.setY (
		    (1 - forwardProgress) * (oy + oheight * objGridY) +
		    forwardProgress * (oy +
				       mDecorTopHeight + mDecorBottomHeight));
	    }
	    else
	    {
		// find position in window contents
		// (window contents correspond to 0.0-1.0 range)
		float relPosInWinContents =
		    (objGridY * oheight -
		     mDecorTopHeight) / mWindow->height ();

		if (relPosInWinContents > forwardProgress)
		{
		    objPos.setY (
			(1 - forwardProgress) * (oy + oheight * objGridY) +
			forwardProgress * (oy + mDecorTopHeight));

		    if (fixedInterior)
			object->offsetTexCoordForQuadBefore ().
			    setY (-forwardProgress * mWindow->height ());
		}
		else
		{
		    objPos.setY (oy + mDecorTopHeight);
		    if (!fixedInterior)
			object->offsetTexCoordForQuadAfter ().
			    setY ((forwardProgress - relPosInWinContents) *
				  mWindow->height ());
		}
	    }
	}
	else // object is at the right side
	{
	    // Set y position to the y position of the object at the left
	    // on the same row (previous object)
	    objPos.setY ((object - 1)->position ().y ());

	    // Also copy offset texture y coordinates
	    object->offsetTexCoordForQuadBefore ().
		setY ((object - 1)->offsetTexCoordForQuadBefore ().y ());
	    object->offsetTexCoordForQuadAfter ().
		setY ((object - 1)->offsetTexCoordForQuadAfter ().y ());
	}

	float origx = ox + owidth * object->gridPosition ().x ();

	objPos.setX (origx);
    }
}
示例#28
0
int
OutputDevices::outputDeviceForGeometry (
	const CompWindow::Geometry& gm,
	int strategy,
	CompSize* screen) const
{
    int          overlapAreas[outputDevs.size ()];
    int          highest, seen, highestScore;
    int          x, y;
    unsigned int i;
    CompRect     geomRect;

    if (outputDevs.size () == 1)
	return 0;


    if (strategy == CoreOptions::OverlappingOutputsSmartMode)
    {
	/* We're only going to use geomRect for overlapping area calculations,
	   so the window rectangle is enough. We don't need to consider
	   anything more like the border because it will never be significant
	   to the result */
	geomRect = gm;
    }
    else
    {
	/* for biggest/smallest modes, only use the window center to determine
	   the correct output device */
	x = (gm.x () + (gm.width () / 2) + gm.border ()) % screen->width ();
	if (x < 0)
	    x += screen->width ();
	y = (gm.y () + (gm.height () / 2) + gm.border ()) % screen->height ();
	if (y < 0)
	    y += screen->height ();

	geomRect.setGeometry (x, y, 1, 1);
    }

    /* get amount of overlap on all output devices */
    for (i = 0; i < outputDevs.size (); i++)
    {
	CompRect overlap = outputDevs[i] & geomRect;
	overlapAreas[i] = overlap.area ();
    }

    /* find output with largest overlap */
    for (i = 0, highest = 0, highestScore = 0;
	 i < outputDevs.size (); i++)
    {
	if (overlapAreas[i] > highestScore)
	{
	    highest = i;
	    highestScore = overlapAreas[i];
	}
    }

    /* look if the highest score is unique */
    for (i = 0, seen = 0; i < outputDevs.size (); i++)
	if (overlapAreas[i] == highestScore)
	    seen++;

    if (seen > 1)
    {
	/* it's not unique, select one output of the matching ones and use the
	   user preferred strategy for that */
	unsigned int currentSize, bestOutputSize;
	bool         searchLargest;

	searchLargest =
	    (strategy != CoreOptions::OverlappingOutputsPreferSmallerOutput);

	if (searchLargest)
	    bestOutputSize = 0;
	else
	    bestOutputSize = UINT_MAX;

	for (i = 0, highest = 0; i < outputDevs.size (); i++)
	    if (overlapAreas[i] == highestScore)
	    {
		bool bestFit;

		currentSize = outputDevs[i].area ();

		if (searchLargest)
		    bestFit = (currentSize > bestOutputSize);
		else
		    bestFit = (currentSize < bestOutputSize);

		if (bestFit)
		{
		    highest = i;
		    bestOutputSize = currentSize;
		}
	    }
    }

    return highest;
}
示例#29
0
文件: ghost.cpp 项目: hedmo/compiz
void
GhostAnim::step ()
{
    float t = 1. - progressLinear ();
    if (mCurWindowEvent == WindowEventClose)
	t = 1. - t;

    CompRect winRect (mAWindow->savedRectsValid () ?
                      mAWindow->saveWinRect () :
                      mWindow->geometry ());
    CompRect outRect (mAWindow->savedRectsValid () ?
                      mAWindow->savedOutRect () :
                      mWindow->outputRect ());
    CompWindowExtents outExtents (mAWindow->savedRectsValid () ?
			          mAWindow->savedOutExtents () :
			          mWindow->output ());

    int wx = winRect.x ();
    int wy = winRect.y ();

    int owidth = outRect.width ();
    int oheight = outRect.height ();

    AnimJCScreen *ajs = AnimJCScreen::get (screen);

    float waveAmp = 3 * ajs->optionGetGhostAmplitude ();
    float waveLengthX1 = 0.4;
    float waveLengthX2 = 0.3;
    float waveLengthY1 = 0.45;
    float waveLengthY2 = 0.35;
    float wavePositionX1 =  0.25 * t * ajs->optionGetGhostWaveSpeed ();
    float wavePositionX2 = -0.25 * t * ajs->optionGetGhostWaveSpeed ();
    float wavePositionY1 =  0.25 * t * ajs->optionGetGhostWaveSpeed ();
    float wavePositionY2 = -0.25 * t * ajs->optionGetGhostWaveSpeed ();

    GridModel::GridObject *object = mModel->objects ();
    unsigned int n = mModel->numObjects ();
    for (unsigned int i = 0; i < n; i++, object++)
    {
	Point3d &objPos = object->position ();

	float origx = wx + mModel->scale ().x () *
		(owidth * object->gridPosition ().x () -
		outExtents.left);

	float origy = wy + mModel->scale ().y () *
		(oheight * object->gridPosition ().y () -
		outExtents.top);

	float x = object->gridPosition ().x ();
	float y = object->gridPosition ().y ();

	float distFromWaveX1 = x - wavePositionX1;
	float distFromWaveX2 = x - wavePositionX2;
	float distFromWaveY1 = y - wavePositionY1;
	float distFromWaveY2 = y - wavePositionY2;

	objPos.setX (origx +
		     waveAmp * sin (distFromWaveX1 / waveLengthX1 * 2 * M_PI) +
		     waveAmp * sin (distFromWaveX2 / waveLengthX2 * 2 * M_PI));

	objPos.setY (origy +
		     waveAmp * sin (distFromWaveY1 / waveLengthY1 * 2 * M_PI) +
		     waveAmp * sin (distFromWaveY2 / waveLengthY2 * 2 * M_PI));

	objPos.setZ (0);
    }
}
示例#30
0
void
GridAnim::addGeometry (const GLTexture::MatrixList &matrix,
		       const CompRegion            &region,
		       const CompRegion            &clip,
		       unsigned int                maxGridWidth,
		       unsigned int                maxGridHeight)
{
    if (region.isEmpty ()) // nothing to do
	return;

    GLfloat *v, *vMax;
    bool notUsing3dCoords = !using3D ();

    CompRect outRect (mAWindow->savedRectsValid () ?
		      mAWindow->savedOutRect () :
		      mWindow->outputRect ());
    CompWindowExtents outExtents (mAWindow->savedRectsValid () ?
				  mAWindow->savedOutExtents () :
				  mWindow->output ());

    // window output (contents + decorations + shadows) coordinates and size
    int ox = outRect.x ();
    int oy = outRect.y ();
    int owidth = outRect.width ();
    int oheight = outRect.height ();

    // to be used if event is shade/unshade
    float winContentsY = oy + outExtents.top;
    float winContentsHeight = oheight - outExtents.top - outExtents.bottom;

    GLWindow *gWindow = GLWindow::get (mWindow);
    GLVertexBuffer *vertexBuffer = gWindow->vertexBuffer ();
    int vSize = vertexBuffer->getVertexStride ();

    // Indentation kept to provide a clean diff with the old code, for now...
    {
	int y1 = outRect.y1 ();
	int x2 = outRect.x2 ();
	int y2 = outRect.y2 ();

	float gridW = (float)owidth / (mGridWidth - 1);
	float gridH;

	if (mCurWindowEvent == WindowEventShade ||
	    mCurWindowEvent == WindowEventUnshade)
	{
	    if (y1 < winContentsY)	// if at top part
		gridH = mDecorTopHeight;
	    else if (y2 > winContentsY + winContentsHeight)  // if at bottom
		gridH = mDecorBottomHeight;
	    else			// in window contents (only in Y coords)
	    {
		float winContentsHeight =
		    oheight - (mDecorTopHeight + mDecorBottomHeight);
		gridH = winContentsHeight / (mGridHeight - 3);
	    }
	}
	else
	    gridH = (float)oheight / (mGridHeight - 1);

	int oldCount = vertexBuffer->countVertices ();
	gWindow->glAddGeometry (matrix, region, clip, gridW, gridH);
	int newCount = vertexBuffer->countVertices ();
	v = vertexBuffer->getVertices () + (oldCount * vSize);
	vMax = vertexBuffer->getVertices () + (newCount * vSize);
 
	float x, y, topiyFloat;
	// For each vertex
	for (; v < vMax; v += vSize)
	{
	    x = v[0];
	    y = v[1];

	    if (y > y2)
		y = y2;

	    if (mCurWindowEvent == WindowEventShade ||
		mCurWindowEvent == WindowEventUnshade)
	    {
		if (y1 < winContentsY)	// if at top part
		{
		    topiyFloat = (y - oy) / mDecorTopHeight;
		    topiyFloat = MIN (topiyFloat, 0.999);	// avoid 1.0
		}
		else if (y2 > winContentsY + winContentsHeight)	// if at bottom
		    topiyFloat = (mGridHeight - 2) +
			(mDecorBottomHeight ? (y - winContentsY -
					       winContentsHeight) /
			 mDecorBottomHeight : 0);
		else		// in window contents (only in Y coords)
		    topiyFloat = (mGridHeight - 3) *
			(y - winContentsY) / winContentsHeight + 1;
	    }
	    else
		topiyFloat = (mGridHeight - 1) * (y - oy) / oheight;

	    // topiy should be at most (mGridHeight - 2)
	    int topiy = (int)(topiyFloat + 1e-4);

	    if (topiy == mGridHeight - 1)
		--topiy;

	    int   bottomiy = topiy + 1;
	    float iny      = topiyFloat - topiy;
	    float inyRest  = 1 - iny;

	    // End of calculations for y

	    // Indentation kept to provide a clean diff with the old code...
	    {
		if (x > x2)
		    x = x2;

		// find containing grid cell (leftix rightix) x (topiy bottomiy)
		float leftixFloat = (mGridWidth - 1) * (x - ox) / owidth;
		int leftix = (int)(leftixFloat + 1e-4);

		if (leftix == mGridWidth - 1)
		    --leftix;

		int rightix = leftix + 1;

		// GridModel::GridObjects that are at top, bottom, left, right corners of quad
		GridModel::GridObject *objToTopLeft =
		    &(mModel->mObjects[topiy * mGridWidth + leftix]);
		GridModel::GridObject *objToTopRight =
		    &(mModel->mObjects[topiy * mGridWidth + rightix]);
		GridModel::GridObject *objToBottomLeft =
		    &(mModel->mObjects[bottomiy * mGridWidth + leftix]);
		GridModel::GridObject *objToBottomRight =
		    &(mModel->mObjects[bottomiy * mGridWidth + rightix]);

		Point3d &objToTopLeftPos = objToTopLeft->mPosition;
		Point3d &objToTopRightPos = objToTopRight->mPosition;
		Point3d &objToBottomLeftPos = objToBottomLeft->mPosition;
		Point3d &objToBottomRightPos = objToBottomRight->mPosition;

		// find position in cell by taking remainder of flooring
		float inx = leftixFloat - leftix;
		float inxRest = 1 - inx;

		// Interpolate to find deformed coordinates

		float hor1x = (inxRest * objToTopLeftPos.x () +
			       inx * objToTopRightPos.x ());
		float hor1y = (inxRest * objToTopLeftPos.y () +
			       inx * objToTopRightPos.y ());
		float hor1z = (notUsing3dCoords ? 0 :
			       inxRest * objToTopLeftPos.z () +
			       inx * objToTopRightPos.z ());
		float hor2x = (inxRest * objToBottomLeftPos.x () +
			       inx * objToBottomRightPos.x ());
		float hor2y = (inxRest * objToBottomLeftPos.y () +
			       inx * objToBottomRightPos.y ());
		float hor2z = (notUsing3dCoords ? 0 :
			       inxRest * objToBottomLeftPos.z () +
			       inx * objToBottomRightPos.z ());

		float deformedX = inyRest * hor1x + iny * hor2x;
		float deformedY = inyRest * hor1y + iny * hor2y;
		float deformedZ = inyRest * hor1z + iny * hor2z;

		v[0] = deformedX;
		v[1] = deformedY;
		v[2] = deformedZ;

	    }
	}
    }
}