View difference between Paste ID: ejkj2hvm and 6C2RTMb2
SHOW: | | - or go back to the newest paste.
1-
#ifndef DRAW_H_INCLUDED
1+
2-
#define DRAW_H_INCLUDED
2+
#include "stdio.h"
3
#include "sys/stat.h"//required for setting file permissions
4-
#include <GL/gl.h>
4+
#include "fcntl.h"//required for setting create/readwrite/read only etc.
5-
#include <GL/glext.h>
5+
#include <cstring>
6
#include <stdlib.h>
7
#include <stdint.h>
8
#include <iostream>
9-
///OGL texture structs
9+
using namespace std;
10-
//textures are the format OGL blits, non editable data -(loaded sprites/images)
10+
#include "BMP.h" ///// note for other viewers: doesn't have anything other than function prototypes
11-
struct OGL_Texture{
11+
12-
	protected:
12+
13-
	bool texture_generated;
13+
void saveBMP(const char *filepath, OGL_Surface *Surface, int bpp, uint8_t compression)
14
{
15-
	public:
15+
	if (bpp==32 || bpp==4){bpp=24;}//do not support 32bit
16-
	GLuint Texture_ID;
16+
	if (bpp==3){bpp=24;}
17-
	uint32_t w,h;
17+
	int palettecols =0;// (should be included as function arg)
18
	uint32_t imgbytes = (Surface->w*Surface->h*bpp)/8;
19-
	void gen_texture(uint16_t w, uint16_t h, uint8_t *PixData);
19+
	int padding = (Surface->w*3)%4;
20
	if (padding != 0){padding=4-padding; imgbytes += Surface->h*padding;}
21-
	OGL_Texture();
21+
	uint32_t data = 0;
22-
	~OGL_Texture();
22+
23-
};
23+
	int file = open(filepath, O_CREAT | O_RDWR, S_IRWXU);
24-
//surfaces contain editable pixel data, can be cast to textures for blitting -(effects, debug/primitive data draws)
24+
	if (file < 0 ){perror("ERROR CREATING/OPENING BMP FILE");exit(1);}
25-
struct OGL_Surface : OGL_Texture{
25+
	lseek(file, 0, SEEK_SET);
26-
	uint32_t w,h;
26+
27-
	uint8_t bpp;
27+
	/// file header (14 bytes)
28-
	uint8_t *PixData;
28+
	//BitMap declaraction
29
	write(file, "BM", 2);
30-
	void Create_Surface(uint16_t w,uint16_t h, char bpp);
30+
	//complete file size in bytes. 14+40 + num bytes for image data  + (palette)
31-
	void Clear_Surface(uint8_t r, uint8_t g, uint8_t b, uint8_t a=255);
31+
	if (bpp>8){data = imgbytes + 54;}
32-
	void Set_Surface_AlphaKey(uint8_t r, uint8_t g, uint8_t b);
32+
	else{data = imgbytes + 54 + palettecols*4;}
33-
	void gen_texture();
33+
	write(file, &data, 4);
34
	//reserved nulls
35-
	OGL_Surface();
35+
	data=0;
36-
	~OGL_Surface();
36+
	write(file, &data, 4);
37-
};
37+
	//offset to actual pixel data (again 14+40) + (palette)
38
	if (bpp>8){data=54;}
39-
OGL_Texture *Texture_Cast(OGL_Surface *Surface);
39+
	else{data = 54 + palettecols*4;}
40
	write(file, &data, 4);
41-
////////
41+
42-
//BLIT//
42+
	/// file info (40 bytes)
43-
////////
43+
	//size of info data
44-
enum Image_Options{
44+
	data=40;
45-
	IMG_NORM  = 0,
45+
	write(file, &data, 4);
46-
	IMG_HFLIP = 1,
46+
	//image width, height
47-
	IMG_VFLIP = 2,
47+
	data=Surface->w;
48-
	IMG_ADD_BLEND = 3
48+
	write(file, &data, 4);
49-
};
49+
	data=Surface->h;
50-
void DrawImage(OGL_Texture *Texture, int dx, int dy, float rot=0.0,float scale_x=1.0,float scale_y=1.0,float alpha=1.0,int options=0);
50+
	write(file, &data, 4);
51-
void DrawSubImage(OGL_Texture *Texture, int sx, int sy, int sw, int sh, int dx, int dy, float rot=0.0,float scale_x=1.0,float scale_y=1.0,float alpha=1.0,int options=0);
51+
	//must be set to 1
52
	data=1;
53-
//////////
53+
	write(file, &data, 2);
54-
//COLOUR//
54+
	//bits per pixel (MAX 24!)
55-
//////////
55+
	data= min(bpp,24);
56-
uint32_t make_col(uint8_t r, uint8_t g, uint8_t b, uint8_t a);
56+
	write(file, &data, 2);
57-
uint32_t make_col(uint8_t r, uint8_t g, uint8_t b);
57+
	//compression, compression notes: http://netghost.narod.ru/gff/vendspec/micbmp/bmp.txt
58
	data=0;
59-
///////////////////
59+
	write(file, &data, 4);
60-
//DRAW PRIMITIVES//
60+
	//image size in bytes
61-
///////////////////
61+
	data=imgbytes;
62-
bool putpixel(OGL_Surface *Surface, int x, int y, uint32_t col);
62+
	write(file, &data, 4);
63-
bool getpixel(OGL_Surface *Surface, int x, int y, uint32_t &col);
63+
	//x,y pixels per meter (set to 0)
64-
//
64+
	data=0;
65-
void hline(OGL_Surface *Surface, int x, int y, int w, uint32_t col);
65+
	write(file, &data, 4);
66-
void vline(OGL_Surface *Surface, int x, int y, int h, uint32_t col);
66+
	write(file, &data, 4);
67-
void line(OGL_Surface *Surface, int x1, int y1, int x2, int y2, uint32_t col);
67+
68-
void box(OGL_Surface *Surface, int x, int y, int w, int h, uint32_t col);
68+
	/// palette (only for 1,4 and 8 bit images, 4 bytes per colour, min 8 bytes)
69-
void rect(OGL_Surface *Surface, int x, int y, int w, int h, uint32_t col);
69+
	//colours used (0=autodetect from bpp, for 8bpp or less palette will only use the amount of colours)
70-
void polyline(OGL_Surface *Surface, unsigned char n, int points[], uint32_t col);
70+
	write(file, &data, 4);
71-
void polygon(OGL_Surface *Surface, unsigned char n, int points[], uint32_t col);
71+
	//important colours (0=all are important)
72-
void circle(OGL_Surface *Surface, int x0, int y0, int radius, uint32_t col);
72+
	write(file, &data, 4);
73-
void circle_fill(OGL_Surface *Surface, int x0, int y0, int radius, uint32_t col);
73+
	//palette (should be included as function arg)
74-
//
74+
	uint32_t *palette = NULL;
75
	uint8_t r,g,b;
76-
#endif // DRAW_H_INCLUDED
76+
	if (bpp<24){
77
		for (uint8_t i = 0; i<palettecols; i++){
78
			r=(palette[i]&0x000000FF);
79
			g=(palette[i]&0x0000FF00)>>8;
80
			b=(palette[i]&0x00FF0000)>>16;
81
			write(file, &b, 1);//b
82
			write(file, &g, 1);//g
83
			write(file, &r, 1);//r
84
			write(file, 0, 1);//null
85
		}
86
	}
87
	/// pixeldata
88
	uint8_t *buffer =  new uint8_t[imgbytes];
89
	memset(buffer, 0, imgbytes);
90
	int datawidth = (Surface->w*3)+padding;
91
	int pos = 0;
92
	int buf_pos = imgbytes-datawidth;
93
	for (uint32_t y = 0; y<Surface->h; y++){
94
		for (uint32_t x = 0; x<Surface->w; x++){
95
			buffer[buf_pos]  = Surface->PixData[pos];
96
			buffer[buf_pos+1]= Surface->PixData[pos+1];
97
			buffer[buf_pos+2]= Surface->PixData[pos+2];
98
			buf_pos+=3;
99
			pos+=Surface->bpp;
100
		}
101
		//return buffer to start of line then up one line
102
		buf_pos += padding;
103
		buf_pos -= datawidth+datawidth;
104
	}
105
	write(file, buffer, imgbytes);
106
	close(file);
107
	delete [] buffer;
108
}
109
110
void loadBMP(const char *filepath, OGL_Surface *Surface)
111
{
112
113
	char BMP[3]= {0,0};
114
	int dataoffset=0;
115
	int imgbytes=0;
116
	int compression=0;
117
	char bpp= 0;
118
	int file = open(filepath, O_RDONLY, S_IRWXU);
119
	if (file < 0 ){perror("ERROR LOADING BMP FILE");exit(1);}
120
121
	/// file header
122
	//BitMap declaraction
123
	lseek(file, 0, SEEK_SET);
124
	read(file, BMP, 2);
125
	if (BMP[0] != 'B' || BMP[1] != 'M'){printf("UNSUPPORTED FILE TYPE (not BMP)");exit(1);}
126
	//skip file size, 4
127
	//skip reserved nulls, 4
128
	//offset to actual pixel data
129
	lseek(file, 10, SEEK_SET);
130
	read(file, &dataoffset, 4);
131
	//skip headersize, 4
132
	//width & height
133
	lseek(file, 18, SEEK_SET);
134
	read(file, &Surface->w, 4);
135
	read(file, &Surface->h, 4);
136
	//skip "planes", 2
137
	//bits per pixel
138
	lseek(file, 28, SEEK_SET);
139
	read(file, &bpp, 2);
140
	//compression
141
	read(file, &compression, 4);
142
	if (compression != 0){printf("FILE USING UNSUPPORTED COMPRESSION");exit(1);}
143
	//size of image data in bytes
144
	read(file, &imgbytes, 4);
145
	//skip hres, 4
146
	//skip vres, 4
147
148
	/// palette (only for 1,4 and 8 bit images)
149
	uint32_t *palette;
150
	if (bpp<24){
151
		//colours used
152
		lseek(file, 46, SEEK_SET);
153
		int palettecols;
154
		read(file, &palettecols, 4);
155
		//skip important colours, 4
156
		if (palettecols != 0){
157
			palette = new uint32_t[palettecols];
158
			memset(palette, 0, palettecols*4);
159
		}
160
		for (int i = 0; i<palettecols; i++){
161
			read(file, &palette[i], 4);
162
		}
163
	}
164
165
	/// pixeldata
166
	lseek(file, dataoffset, SEEK_SET);
167
	uint8_t *buffer =  new uint8_t[imgbytes];
168
	memset(buffer, 0, imgbytes);
169
	read(file, buffer, imgbytes);
170
	close(file);
171
172
	/// convert data to rgb format
173
	if (Surface->PixData != NULL){delete [] Surface->PixData;}
174
	Surface->PixData = new uint8_t[Surface->w*Surface->h*Surface->bpp];
175
	memset(Surface->PixData, 255, Surface->w*Surface->h*Surface->bpp);
176
	int padding = (Surface->w*3)%4;
177
	if (padding != 0){padding=4-padding;}
178
	int datawidth = (Surface->w*3)+padding;
179
	int pos = 0;
180
	int buf_pos = imgbytes-datawidth;
181
	for (uint32_t y = 0; y<Surface->h; y++){
182
		for (uint32_t x = 0; x<Surface->w; x++){
183
			Surface->PixData[pos]  = buffer[buf_pos];
184
			Surface->PixData[pos+1]= buffer[buf_pos+1];
185
			Surface->PixData[pos+2]= buffer[buf_pos+2];
186
			//if supporting alpha, set 255,0,255 to transparent
187
			if(Surface->bpp==4 && buffer[buf_pos] == 255 && buffer[buf_pos+1] == 0 && buffer[buf_pos+2] == 255){Surface->PixData[pos+3]= 0;}
188
			buf_pos+=3;
189
			pos+=Surface->bpp;
190
		}
191
		//return buffer to start of line then up one line
192
		buf_pos += padding;
193
		buf_pos -= datawidth+datawidth;
194
	}
195
	delete [] buffer;
196
}
197
198
void loadBMP(const char *filepath, OGL_Texture *Texture)
199
{
200
	OGL_Surface *Surface = new OGL_Surface;
201
	Surface->Create_Surface(1,1,4);
202
	loadBMP(filepath, Surface);
203
	Texture->gen_texture(Surface->w, Surface->h, Surface->PixData);
204
	delete Surface;
205
}