summaryrefslogtreecommitdiffstatshomepage
path: root/src/emu/rendutil.h
blob: c5cdd7d2c4c6ef100aaba2fec7f9dadd096d83a1 (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
// license:BSD-3-Clause
// copyright-holders:Aaron Giles
/***************************************************************************

    rendutil.h

    Core rendering utilities.

***************************************************************************/

#ifndef MAME_EMU_RENDUTIL_H
#define MAME_EMU_RENDUTIL_H

#pragma once

#include "rendertypes.h"

#include <cmath>


/* ----- image formats ----- */

enum ru_imgformat
{
	RENDUTIL_IMGFORMAT_PNG,
	RENDUTIL_IMGFORMAT_JPEG,
	RENDUTIL_IMGFORMAT_MSDIB,

	RENDUTIL_IMGFORMAT_UNKNOWN,
	RENDUTIL_IMGFORMAT_ERROR
};



/***************************************************************************
    FUNCTION PROTOTYPES
***************************************************************************/

/* ----- render utilities ----- */

void render_resample_argb_bitmap_hq(bitmap_argb32 &dest, bitmap_argb32 &source, const render_color &color, bool force = false);
bool render_clip_line(render_bounds *bounds, const render_bounds *clip);
bool render_clip_quad(render_bounds *bounds, const render_bounds *clip, render_quad_texuv *texcoords);
void render_line_to_quad(const render_bounds *bounds, float width, float length_extension, render_bounds *bounds0, render_bounds *bounds1);
void render_load_msdib(bitmap_argb32 &bitmap, util::core_file &file);
void render_load_jpeg(bitmap_argb32 &bitmap, util::core_file &file);
bool render_load_png(bitmap_argb32 &bitmap, util::core_file &file, bool load_as_alpha_to_existing = false);
ru_imgformat render_detect_image(util::core_file &file);



/***************************************************************************
    INLINE FUNCTIONS
***************************************************************************/

/*-------------------------------------------------
    render_round_nearest - floating point
    round-to-nearest
-------------------------------------------------*/

static inline float render_round_nearest(float f)
{
	return floor(f + 0.5f);
}


/*-------------------------------------------------
    orientation_swap_flips - swap the X and Y
    flip flags
-------------------------------------------------*/

static inline int orientation_swap_flips(int orientation)
{
	return (orientation & ORIENTATION_SWAP_XY) |
			((orientation & ORIENTATION_FLIP_X) ? ORIENTATION_FLIP_Y : 0) |
			((orientation & ORIENTATION_FLIP_Y) ? ORIENTATION_FLIP_X : 0);
}


/*-------------------------------------------------
    orientation_reverse - compute the orientation
    that will undo another orientation
-------------------------------------------------*/

static inline int orientation_reverse(int orientation)
{
	/* if not swapping X/Y, then just apply the same transform to reverse */
	if (!(orientation & ORIENTATION_SWAP_XY))
		return orientation;

	/* if swapping X/Y, then swap X/Y flip bits to get the reverse */
	else
		return orientation_swap_flips(orientation);
}


/*-------------------------------------------------
    orientation_add - compute effective orientation
    after applying two subsequent orientations
-------------------------------------------------*/

static inline int orientation_add(int orientation1, int orientation2)
{
	/* if the 2nd transform doesn't swap, just XOR together */
	if (!(orientation2 & ORIENTATION_SWAP_XY))
		return orientation1 ^ orientation2;

	/* otherwise, we need to effectively swap the flip bits on the first transform */
	else
		return orientation_swap_flips(orientation1) ^ orientation2;
}


/*-------------------------------------------------
    apply_brightness_contrast_gamma_fp - apply
    brightness, contrast, and gamma controls to
    a single RGB component
-------------------------------------------------*/

static inline float apply_brightness_contrast_gamma_fp(float srcval, float brightness, float contrast, float gamma)
{
	/* first apply gamma */
	srcval = pow(srcval, 1.0f / gamma);

	/* then contrast/brightness */
	srcval = (srcval * contrast) + brightness - 1.0f;

	/* clamp and return */
	if (srcval < 0.0f)
		srcval = 0.0f;
	if (srcval > 1.0f)
		srcval = 1.0f;
	return srcval;
}


/*-------------------------------------------------
    apply_brightness_contrast_gamma - apply
    brightness, contrast, and gamma controls to
    a single RGB component
-------------------------------------------------*/

static inline u8 apply_brightness_contrast_gamma(u8 src, float brightness, float contrast, float gamma)
{
	float srcval = (float)src * (1.0f / 255.0f);
	float result = apply_brightness_contrast_gamma_fp(srcval, brightness, contrast, gamma);
	return u8(result * 255.0f);
}

#endif // MAME_EMU_RENDUTIL_H