Skip to content
GitLab
Menu
Projects
Groups
Snippets
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
Menu
Open sidebar
ACGL
acgl
Commits
ecbe0c85
Commit
ecbe0c85
authored
Apr 05, 2013
by
Robert Menzel
Browse files
added ppm loading to new texture loading functions
parent
ea1be458
Changes
3
Show whitespace changes
Inline
Side-by-side
include/ACGL/OpenGL/Data/TextureDataLoadStore.hh
View file @
ecbe0c85
...
...
@@ -47,14 +47,19 @@ inline bool saveScreenshot( const std::string _fileEnding = "png" ) {
SharedTextureData
loadTextureDataFromLodepng
(
const
std
::
string
&
_filename
);
#ifdef ACGL_COMPILE_WITH_QT
//! loads from the QT library
//! loads
various formats
from the QT library
SharedTextureData
loadTextureDataFromQT
(
const
std
::
string
&
_filename
);
#endif
//! loads RGBE aka Radiance files
SharedTextureData
loadTextureDataFromRGBE
(
const
std
::
string
&
_filename
);
//! loads EXR / OpenEXR files iff the library is present AT RUNTIME (linux only)
SharedTextureData
loadTextureDataFromEXR
(
const
std
::
string
&
_filename
);
//! loads PNM / PPM files:
SharedTextureData
loadTextureDataFromPNM
(
const
std
::
string
&
_filename
);
///////////////////////////////////////////////////////////////////////////////////////////////////
// library specific save
///////////////////////////////////////////////////////////////////////////////////////////////////
...
...
src/ACGL/OpenGL/Data/GeometryDataLoadStore.cc
View file @
ecbe0c85
...
...
@@ -31,7 +31,7 @@ SharedGeometryData loadGeometryData(const std::string& _filename)
}
else
{
error
()
<<
"file format of "
<<
_filename
<<
" not supported"
<<
std
::
endl
;
error
()
<<
"
geometry
file format of "
<<
_filename
<<
" not supported"
<<
std
::
endl
;
}
return
SharedGeometryData
();
...
...
src/ACGL/OpenGL/Data/TextureDataLoadStore.cc
View file @
ecbe0c85
...
...
@@ -63,6 +63,8 @@ SharedTextureData loadTextureData(const std::string &_filename)
return
loadTextureDataFromRGBE
(
_filename
);
}
else
if
(
fileEnding
==
"exr"
)
{
return
loadTextureDataFromEXR
(
_filename
);
}
else
if
(
fileEnding
==
"ppm"
)
{
return
loadTextureDataFromPNM
(
_filename
);
}
#ifdef ACGL_COMPILE_WITH_QT
else
if
(
fileEnding
==
"bmp"
||
fileEnding
==
"jpg"
||
fileEnding
==
"jpeg"
...
...
@@ -73,7 +75,7 @@ SharedTextureData loadTextureData(const std::string &_filename)
}
#endif
else
{
error
()
<<
"file format of "
<<
_filename
<<
" not supported"
<<
std
::
endl
;
error
()
<<
"
texture
file format of "
<<
_filename
<<
" not supported"
<<
std
::
endl
;
}
return
SharedTextureData
();
...
...
@@ -98,7 +100,7 @@ bool saveTextureData(const SharedTextureData &_textureData, const std::string &_
else
if
(
fileEnding
==
"ppm"
)
{
return
saveTextureDataToPPM
(
_textureData
,
_filename
);
}
else
{
error
()
<<
"file format of "
<<
_filename
<<
" not supported"
<<
std
::
endl
;
error
()
<<
"
texture
file format of "
<<
_filename
<<
" not supported"
<<
std
::
endl
;
}
return
false
;
...
...
@@ -289,6 +291,204 @@ SharedTextureData loadTextureDataFromEXR(const std::string &_filename)
#endif
}
enum
loadTextureDataFromPNM_InputDataFormat
{
PLAIN_TEXT_BITMAP
,
// used by P1
PLAIN_TEXT_DECIMAL
,
// used by P2 and P3
BINARY_PACKED
,
// used by P4
BINARY_BYTES
,
// used by P5 and P6
BINARY_WORDS
// used by P5 and P6
};
void
loadTextureDataFromPNM_skipWhitespace
(
std
::
istream
&
_in
,
uint_t
_max
=
std
::
numeric_limits
<
std
::
streamsize
>::
max
())
{
uint_t
skipped
=
0
;
while
(
isspace
(
_in
.
peek
())
&&
skipped
<
_max
)
{
_in
.
ignore
(
1
);
skipped
++
;
}
}
std
::
istream
&
loadTextureDataFromPNM_filterPNMComments
(
std
::
istream
&
_in
)
{
loadTextureDataFromPNM_skipWhitespace
(
_in
);
// When the stream starts with a #, throw away all following characters until the next newline
// TODO: this does not entirely conform to the PNM specs, where # characters may appear anywhere, not just at the beginning of fields
while
(
_in
.
peek
()
==
'#'
)
{
_in
.
ignore
(
std
::
numeric_limits
<
std
::
streamsize
>::
max
(),
'\n'
);
loadTextureDataFromPNM_skipWhitespace
(
_in
);
}
return
_in
;
}
SharedTextureData
loadTextureDataFromPNM
(
const
std
::
string
&
_filename
)
{
std
::
ifstream
fileStream
(
_filename
,
std
::
ifstream
::
in
);
if
(
!
fileStream
.
good
())
{
error
()
<<
"could not open file "
<<
_filename
<<
std
::
endl
;
return
SharedTextureData
();
}
SharedTextureData
texture
=
SharedTextureData
(
new
TextureData
()
);
// Read the PNM header
std
::
string
header
;
loadTextureDataFromPNM_filterPNMComments
(
fileStream
)
>>
header
;
// The header version determines the format of the data
loadTextureDataFromPNM_InputDataFormat
inputDataFormat
=
BINARY_BYTES
;
// set it to something to prevent 'may be uninitialized' warnings (which can't occur here)
uint_t
components
;
if
(
header
==
"P1"
)
{
components
=
1
;
inputDataFormat
=
PLAIN_TEXT_BITMAP
;
}
else
if
(
header
==
"P2"
)
{
components
=
1
;
inputDataFormat
=
PLAIN_TEXT_DECIMAL
;
}
else
if
(
header
==
"P3"
)
{
components
=
3
;
inputDataFormat
=
PLAIN_TEXT_DECIMAL
;
}
else
if
(
header
==
"P4"
)
{
components
=
1
;
inputDataFormat
=
BINARY_PACKED
;
}
else
if
(
header
==
"P5"
)
{
components
=
1
;
/* the data format will be determined later */
}
else
if
(
header
==
"P6"
)
{
components
=
3
;
/* the data format will be determined later */
}
else
{
error
()
<<
"could not load "
<<
_filename
<<
": invalid header"
<<
std
::
endl
;
fileStream
.
close
();
return
SharedTextureData
();
}
// Read the width and height of the image
uint_t
width
,
height
;
loadTextureDataFromPNM_filterPNMComments
(
fileStream
)
>>
width
;
loadTextureDataFromPNM_filterPNMComments
(
fileStream
)
>>
height
;
if
(
!
fileStream
.
good
()
||
width
==
0
||
height
==
0
)
{
error
()
<<
"could not load "
<<
_filename
<<
": invalid image size"
<<
std
::
endl
;
fileStream
.
close
();
return
SharedTextureData
();
}
// The max value is only present in the P2, P3, P5, P6 versions of the PNM format
uint_t
maxValue
=
1
;
if
(
header
==
"P2"
||
header
==
"P3"
||
header
==
"P5"
||
header
==
"P6"
)
{
loadTextureDataFromPNM_filterPNMComments
(
fileStream
)
>>
maxValue
;
if
(
!
fileStream
.
good
()
||
maxValue
==
0
)
{
error
()
<<
"could not load "
<<
_filename
<<
": invalid value range"
<<
std
::
endl
;
fileStream
.
close
();
return
SharedTextureData
();
}
}
// The binary formats P5 and P6 use either bytes or words of data for each element, depending on the maxValue
if
(
header
==
"P5"
||
header
==
"P6"
)
{
if
(
maxValue
<
256
)
{
inputDataFormat
=
BINARY_BYTES
;
}
else
if
(
maxValue
<
65536
)
{
inputDataFormat
=
BINARY_WORDS
;
}
else
{
error
()
<<
"could not load "
<<
_filename
<<
": max value out of bounds"
<<
std
::
endl
;
fileStream
.
close
();
return
SharedTextureData
();
}
}
// If the image data has maxValue of 255 or 1, we return a GL_UNSIGNED_BYTE texture,
// otherwise the values are normalized and returned as a GL_FLOAT texture
GLenum
outputDataType
=
GL_FLOAT
;
if
(
maxValue
==
255
||
maxValue
==
1
)
outputDataType
=
GL_UNSIGNED_BYTE
;
// The data section is separated by a single whitespace
loadTextureDataFromPNM_skipWhitespace
(
fileStream
,
1
);
// Now, read in the data
// No comments (#) are expected during this section
unsigned
char
*
data
=
new
unsigned
char
[
width
*
height
*
components
*
getGLTypeSize
(
outputDataType
)];
uint_t
elementsRead
=
0
;
while
(
fileStream
.
good
()
&&
elementsRead
<
(
width
*
height
*
components
))
{
// Read in one element
// The exact procedure is based on the input data format
uint_t
elem
;
if
(
inputDataFormat
==
PLAIN_TEXT_DECIMAL
)
{
fileStream
>>
elem
;
}
else
if
(
inputDataFormat
==
BINARY_BYTES
)
{
uint8_t
byte
;
fileStream
.
read
((
char
*
)
&
byte
,
1
);
elem
=
byte
;
}
else
if
(
inputDataFormat
==
BINARY_WORDS
)
{
uint8_t
word
;
fileStream
.
read
((
char
*
)
&
word
,
2
);
elem
=
word
;
}
else
if
(
inputDataFormat
==
PLAIN_TEXT_BITMAP
)
{
loadTextureDataFromPNM_skipWhitespace
(
fileStream
);
char
c
;
fileStream
.
read
(
&
c
,
1
);
if
(
c
==
'0'
)
elem
=
0
;
else
if
(
c
==
'1'
)
elem
=
1
;
else
break
;
}
else
if
(
inputDataFormat
==
BINARY_PACKED
)
{
uint_t
offset
=
elementsRead
%
8
;
uint8_t
byte
=
fileStream
.
peek
();
if
(
byte
&
1
<<
(
7
-
offset
))
elem
=
1
;
else
elem
=
0
;
if
(
offset
==
7
)
fileStream
.
ignore
(
1
);
}
if
(
!
fileStream
.
good
())
break
;
// Store the element in the data array
if
(
outputDataType
==
GL_UNSIGNED_BYTE
)
{
if
(
maxValue
==
1
)
elem
*=
255
;
// Bitmap values are normalized to 0..255
data
[
elementsRead
*
getGLTypeSize
(
outputDataType
)]
=
(
GLubyte
)
elem
;
}
else
if
(
outputDataType
==
GL_FLOAT
)
{
// Float values are normalized to 0..1
GLfloat
normalized
=
(
GLfloat
)
elem
/
(
GLfloat
)
maxValue
;
GLfloat
*
position
=
(
GLfloat
*
)
&
data
[
elementsRead
*
getGLTypeSize
(
outputDataType
)];
*
position
=
normalized
;
}
elementsRead
++
;
}
fileStream
.
close
();
if
(
elementsRead
!=
width
*
height
*
components
)
{
error
()
<<
"could not load "
<<
_filename
<<
": unexpected EOF"
<<
std
::
endl
;
return
SharedTextureData
();
}
texture
->
setData
(
data
);
// data will get deleted by the TextureData destructor!
texture
->
setDepth
(
1
);
// 2D so, depth is 1
texture
->
setHeight
(
height
);
texture
->
setWidth
(
width
);
#ifdef ACGL_OPENGL_ES
texture
->
setFormat
(
GL_RGB
);
#else
texture
->
setFormat
(
components
==
3
?
GL_RGB
:
GL_RED
);
#endif
texture
->
setType
(
outputDataType
);
return
texture
;
}
///////////////////////////////////////////////////////////////////////////////////////////////////
// library specific save
///////////////////////////////////////////////////////////////////////////////////////////////////
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
.
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment