Exemplo n.º 1
0
void tableDestroyImpl(widget *self)
{
	// Destroy child positional info
	vectorMapAndDestroy(TABLE(self)->childPositions, free);
	
	// Call our parents destructor
	widgetDestroyImpl(self);
}
Exemplo n.º 2
0
void widgetSDLQuit()
{
	// Get the window vector
	vector *windowVector = windowGetWindowVector();

	// Release all active windows
	vectorMapAndDestroy(windowVector, (mapCallback) widgetDestroy);
	
	// Release any cached SVG images
	svgManagerQuit();
	
	// Release all patterns
	patternManagerQuit();
}
Exemplo n.º 3
0
void widgetDestroyImpl(widget *self)
{
	eventTableEntry *currEntry;

	// Release the container
	vectorMapAndDestroy(self->children, (mapCallback) widgetDestroy);

	// Release the event handler table
	while ((currEntry = vectorHead(self->eventVtbl)))
	{
		widgetRemoveEventHandler(self, currEntry->id);
	}

	vectorDestroy(self->eventVtbl);

	// Destroy the cairo context
	cairo_destroy(self->cr);

	// Destroy the texture
	glDeleteTextures(1, &self->textureId);

	// If we use a mask, destroy it
	if (self->maskEnabled)
	{
		cairo_destroy(self->maskCr);
	}

	// If GL content support is enabled, disable it
	if (self->openGLEnabled)
	{
		widgetDisableGL(self);
	}

	// Free the ID
	free((char *) self->id);

	// Free the tool-tip (if any)
	free((char *) self->toolTip);

	// Free ourself
	free(self);
}
Exemplo n.º 4
0
static bool widgetAnimationTimerCallback(widget *self, const event *evt,
                                         int handlerId, void *userData)
{
	int i;
	vector *frames = userData;
	animationFrame *currFrame;

	// Regular timer event
	if (evt->type == EVT_TIMER_PERSISTENT)
	{
		bool didInterpolate = false;

		// Currently active keyframes to be interpolated between
		struct
		{
			animationFrame *pre;
			animationFrame *post;
		} interpolateFrames[ANI_TYPE_COUNT] = { { NULL, NULL } };

		// Work out what frames we need to interpolate between
		for (i = 0; i < vectorSize(frames); i++)
		{
			currFrame = vectorAt(frames, i);

			/*
			 * We are only interested in the key frames which either directly
			 * precede now or come directly after. (As it is these frames which
			 * will be interpolated between.)
			 */
			if (currFrame->time <= evt->time)
			{
				interpolateFrames[currFrame->type].pre = currFrame;
			}
			else if (currFrame->time > evt->time
					 && !interpolateFrames[currFrame->type].post)
			{
				interpolateFrames[currFrame->type].post = currFrame;
			}
		}

		// Do the interpolation
		for (i = 0; i < ANI_TYPE_COUNT; i++)
		{
			// If there are frames to interpolate between then do so
			if (interpolateFrames[i].pre && interpolateFrames[i].post)
			{
				// Get the points to interpolate between
				animationFrame k1 = *interpolateFrames[i].pre;
				animationFrame k2 = *interpolateFrames[i].post;

				int time = evt->time;

				switch (i)
				{
					case ANI_TYPE_TRANSLATE:
					{
						// Get the new position
						point pos = widgetAnimationInterpolateTranslate(self, k1,
						                                                k2, time);

						// Set the new position
						widgetReposition(self, pos.x, pos.y);

						break;
					}
					case ANI_TYPE_ROTATE:
						// Update the widgets rotation
						self->rotate = widgetAnimationInterpolateRotate(self, k1,
						                                                k2, time);
						break;
					case ANI_TYPE_SCALE:
						// Update the widgets scale factor
						self->scale = widgetAnimationInterpolateScale(self, k1,
						                                              k2, time);
						break;
					case ANI_TYPE_ALPHA:
						// Update the widgets alpha
						self->alpha = widgetAnimationInterpolateAlpha(self, k1,
						                                              k2, time);
						break;
				}

				// Make a note that we did interpolate
				didInterpolate = true;
			}
		}

		// If there was no interpolation then the animation is over
		if (!didInterpolate)
		{
			// Remove ourself (the event handler)
			widgetRemoveEventHandler(self, handlerId);
		}
	}
	else if (evt->type == EVT_DESTRUCT)
	{
		animationFrame *lastFrame[ANI_TYPE_COUNT] = { NULL };

		// Find the last frame of each animation type
		for (i = 0; i < vectorSize(frames); i++)
		{
			currFrame = vectorAt(frames, i);

			lastFrame[currFrame->type] = currFrame;
		}

		// Set the position/rotation/scale/alpha to that of the final frame
		for (i = 0; i < ANI_TYPE_COUNT; i++)
		{
			if (lastFrame[i]) switch (i)
			{
				case ANI_TYPE_TRANSLATE:
					self->offset = lastFrame[ANI_TYPE_TRANSLATE]->data.translate;
					break;
				case ANI_TYPE_ROTATE:
					self->rotate = lastFrame[ANI_TYPE_ROTATE]->data.rotate;
					break;
				case ANI_TYPE_SCALE:
					self->scale = lastFrame[ANI_TYPE_SCALE]->data.scale;
					break;
				case ANI_TYPE_ALPHA:
					self->alpha = lastFrame[ANI_TYPE_ALPHA]->data.alpha;
					break;
				default:
					break;
			}
		}

		// Free the frames vector
		vectorMapAndDestroy(frames, free);
	}


	return true;
}