- add untransform, transform, and specialized transforms to Model class
- reset viewport on window resize events - add boolean assignment operator to Switch class - throw error if GL object is generated before GL context is created - add Selection container - add string conversion to Box
This commit is contained in:
parent
3ba3be4496
commit
7140e8a3eb
|
@ -606,6 +606,10 @@ std::string Box::string() const
|
|||
return output.str();
|
||||
}
|
||||
|
||||
Box::operator std::string() const
|
||||
{
|
||||
return string();
|
||||
}
|
||||
|
||||
/* Feed a string representation of the box to the passed ostream */
|
||||
std::ostream& std::operator<<(std::ostream& out, const Box& box)
|
||||
|
|
|
@ -100,6 +100,13 @@ public:
|
|||
virtual std::string class_name() const { return "Box"; }
|
||||
std::string string() const;
|
||||
|
||||
/*!
|
||||
* Convert the box to a string when it is passed in a string context.
|
||||
*
|
||||
* @return string representation of the box
|
||||
*/
|
||||
operator std::string() const;
|
||||
|
||||
};
|
||||
|
||||
namespace std
|
||||
|
|
|
@ -45,7 +45,8 @@ void Configuration::set_defaults()
|
|||
{"debug", false},
|
||||
{"show-cursor", false},
|
||||
{"render-test-spacing", 2},
|
||||
{"render driver", "opengl"}
|
||||
{"render driver", "opengl"},
|
||||
{"fluid resize", false}
|
||||
};
|
||||
config["audio"] = {
|
||||
{"default-sfx-root", "resource/sfx"},
|
||||
|
|
|
@ -1,19 +1,20 @@
|
|||
/* /\ +--------------------------------------------------------------+
|
||||
____/ \____ /| - zlib/MIT/Unlicenced game framework licensed to freely use, |
|
||||
\ / / | copy, and modify without restriction |
|
||||
+--\ ^__^ /--+ | |
|
||||
| ~/ \~ | | - originally created at [http://nugget.fun] |
|
||||
| ~~~~~~~~~~~~ | +--------------------------------------------------------------+
|
||||
| SPACE ~~~~~ | /
|
||||
| ~~~~~~~ BOX |/
|
||||
+-------------*/
|
||||
/* +------------------------------------------------------+
|
||||
____/ \____ /| - Open source game framework licensed to freely use, |
|
||||
\ / / | copy, modify and sell without restriction |
|
||||
+--\ ^__^ /--+ | |
|
||||
| ~/ \~ | | - created for <https://foam.shampoo.ooo> |
|
||||
| ~~~~~~~~~~~~ | +------------------------------------------------------+
|
||||
| SPACE ~~~~~ | /
|
||||
| ~~~~~~~ BOX |/
|
||||
+-------------*/
|
||||
|
||||
#include "Display.hpp"
|
||||
|
||||
/* Create a Display instance and subscribe to commands */
|
||||
sb::Display::Display(Node* parent) : Node(parent)
|
||||
{
|
||||
get_delegate().subscribe(&Display::respond, this);
|
||||
delegate().subscribe(&Display::respond, this);
|
||||
delegate().subscribe(&Display::respond, this, SDL_WINDOWEVENT);
|
||||
}
|
||||
|
||||
/* Return the (x, y) size in pixels of the window as an integer vector */
|
||||
|
@ -154,13 +155,30 @@ SDL_Surface* sb::Display::screen_surface_from_pixels(unsigned char* pixels, bool
|
|||
return surface;
|
||||
}
|
||||
|
||||
/* Handle fullscreen request */
|
||||
void sb::Display::respond(SDL_Event& event)
|
||||
{
|
||||
if (get_delegate().compare(event, "fullscreen"))
|
||||
{
|
||||
toggle_fullscreen();
|
||||
}
|
||||
else if (event.type == SDL_WINDOWEVENT)
|
||||
{
|
||||
/* Handle a full window resize event, and only handle intermediate size change events if fluid resize is enabled. */
|
||||
if (event.window.event == SDL_WINDOWEVENT_RESIZED || (event.window.event == SDL_WINDOWEVENT_SIZE_CHANGED && configuration()["display"]["fluid resize"]))
|
||||
{
|
||||
std::ostringstream message;
|
||||
message << "Resizing window to " << event.window.data1 << "x" << event.window.data2;
|
||||
sb::Log::Level level = event.window.event == SDL_WINDOWEVENT_RESIZED ? sb::Log::INFO : sb::Log::DEBUG;
|
||||
sb::Log::log(message, level);
|
||||
|
||||
/* Resize the GL viewport */
|
||||
if (SDL_GL_GetCurrentContext() != nullptr)
|
||||
{
|
||||
glViewport(0, 0, event.window.data1, event.window.data2);
|
||||
sb::Log::gl_errors("After glViewport resize");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* Use SDL window flags to determine if fullscreen is on or off and use SDL fullscreen
|
||||
|
|
|
@ -39,7 +39,18 @@ namespace sb
|
|||
void screen_pixels(unsigned char*, int, int, int = 0, int = 0) const;
|
||||
SDL_Surface* screen_surface() const;
|
||||
SDL_Surface* screen_surface_from_pixels(unsigned char*, bool) const;
|
||||
void respond(SDL_Event&);
|
||||
|
||||
/*!
|
||||
* Respond to full screen requests and window resize events. If fluid resize is enabled in the configuration, respond to
|
||||
* resize events as the screen is being resized, otherwise respond once when the resize is finished.
|
||||
*
|
||||
* The dispay object subscribes to SDL events in its constructor, so this function will be called automatically by
|
||||
* sb::Delegate::dispatch when an event happens.
|
||||
*
|
||||
* @param event an SDL event
|
||||
*/
|
||||
void respond(SDL_Event& event);
|
||||
|
||||
void toggle_fullscreen() const;
|
||||
|
||||
};
|
||||
|
|
|
@ -35,12 +35,19 @@ GLObject::GLObject(deleter_function deleter) : deleter(deleter) {}
|
|||
*/
|
||||
void GLObject::generate(generator_function generator)
|
||||
{
|
||||
GLuint id;
|
||||
generator(1, &id);
|
||||
this->id(id);
|
||||
std::ostringstream message;
|
||||
message << "Generated ID " << this->id() << " for GL object";
|
||||
sb::Log::log(message, sb::Log::DEBUG);
|
||||
if (SDL_GL_GetCurrentContext() != nullptr)
|
||||
{
|
||||
GLuint id;
|
||||
generator(1, &id);
|
||||
this->id(id);
|
||||
std::ostringstream message;
|
||||
message << "Generated ID " << this->id() << " for GL object";
|
||||
sb::Log::log(message, sb::Log::DEBUG);
|
||||
}
|
||||
else
|
||||
{
|
||||
throw std::runtime_error("Cannot generate ID for GL object before GL context is created");
|
||||
}
|
||||
}
|
||||
|
||||
/* Set the shared pointer to point to a new GLuint with specified ID value */
|
||||
|
|
|
@ -114,7 +114,7 @@ Game::Game()
|
|||
/* Create a window with dimensions set in the config, centered, and flagged to be usable in OpenGL context */
|
||||
_window = SDL_CreateWindow(
|
||||
configuration()["display"]["title"].get_ref<const std::string&>().c_str(), SDL_WINDOWPOS_CENTERED,
|
||||
SDL_WINDOWPOS_CENTERED, window_size.x, window_size.y, SDL_WINDOW_OPENGL);
|
||||
SDL_WINDOWPOS_CENTERED, window_size.x, window_size.y, SDL_WINDOW_OPENGL | SDL_WINDOW_RESIZABLE);
|
||||
if (_window == nullptr)
|
||||
{
|
||||
sb::Log::sdl_error("Could not create window");
|
||||
|
|
|
@ -48,7 +48,7 @@ sb::Model::Model(const std::initializer_list<std::string>& names)
|
|||
* Can be used to iterate through the attributes. */
|
||||
std::map<std::string, std::shared_ptr<sb::Attributes>>& sb::Model::attributes()
|
||||
{
|
||||
return model_attributes;
|
||||
return _attributes;
|
||||
}
|
||||
|
||||
/* Get the attributes under name, wrapped in the shared pointer held by this object. This
|
||||
|
@ -108,7 +108,7 @@ void sb::Model::disable()
|
|||
/* Return a reference to the texture container. */
|
||||
std::map<std::string, sb::Texture>& sb::Model::textures()
|
||||
{
|
||||
return model_textures;
|
||||
return _textures;
|
||||
}
|
||||
|
||||
/* Get the texture at name. This can be used to read the texture memory, share ownership of it, or
|
||||
|
@ -151,18 +151,44 @@ void sb::Model::texture(const sb::Texture& texture)
|
|||
this->texture(texture, DEFAULT_TEXTURE_NAME);
|
||||
}
|
||||
|
||||
/* Get the model's transformation matrix. */
|
||||
const glm::mat4& sb::Model::transformation() const
|
||||
{
|
||||
return model_transformation;
|
||||
return _transformation;
|
||||
}
|
||||
|
||||
/* Set the model's transformation matrix. */
|
||||
void sb::Model::transformation(const glm::mat4& transformation)
|
||||
const glm::mat4& sb::Model::transform(const glm::mat4& transformation)
|
||||
{
|
||||
model_transformation = transformation;
|
||||
_transformation *= transformation;
|
||||
return this->transformation();
|
||||
}
|
||||
|
||||
const glm::mat4& sb::Model::untransform()
|
||||
{
|
||||
_transformation = glm::mat4(1.0f);
|
||||
return transformation();
|
||||
}
|
||||
|
||||
const glm::mat4& sb::Model::scale(const glm::vec3& scale)
|
||||
{
|
||||
return transform(glm::scale(scale));
|
||||
}
|
||||
|
||||
const glm::mat4& sb::Model::scale(float scale)
|
||||
{
|
||||
return this->scale(glm::vec3(scale));
|
||||
}
|
||||
|
||||
const glm::mat4& sb::Model::rotate(float angle, glm::vec3 axis)
|
||||
{
|
||||
return transform(glm::rotate(angle, axis));
|
||||
}
|
||||
|
||||
const glm::mat4& sb::Model::translate(glm::vec3 translation)
|
||||
{
|
||||
return transform(glm::translate(translation));
|
||||
}
|
||||
|
||||
|
||||
/* Return the size in bytes of the sum of the attributes. */
|
||||
std::size_t sb::Model::size()
|
||||
{
|
||||
|
@ -177,7 +203,7 @@ std::size_t sb::Model::size()
|
|||
/* Return the transformation matrix. */
|
||||
sb::Model::operator glm::mat4() const
|
||||
{
|
||||
return model_transformation;
|
||||
return _transformation;
|
||||
}
|
||||
|
||||
sb::PlaneDoubleBuffer::PlaneDoubleBuffer() : Plane()
|
||||
|
|
|
@ -40,9 +40,9 @@ namespace sb
|
|||
private:
|
||||
|
||||
inline static const std::string DEFAULT_TEXTURE_NAME = "default";
|
||||
std::map<std::string, sb::Texture> model_textures;
|
||||
std::map<std::string, std::shared_ptr<sb::Attributes>> model_attributes;
|
||||
glm::mat4 model_transformation {1.0f};
|
||||
std::map<std::string, sb::Texture> _textures;
|
||||
std::map<std::string, std::shared_ptr<sb::Attributes>> _attributes;
|
||||
glm::mat4 _transformation {1.0f};
|
||||
|
||||
public:
|
||||
|
||||
|
@ -62,8 +62,64 @@ namespace sb
|
|||
sb::Texture& texture();
|
||||
void texture(const sb::Texture&, const std::string&);
|
||||
void texture(const sb::Texture&);
|
||||
|
||||
/*!
|
||||
* @return a constanst reference to the model's transformation matrix
|
||||
*/
|
||||
const glm::mat4& transformation() const;
|
||||
void transformation(const glm::mat4&);
|
||||
|
||||
/*!
|
||||
* Apply the given transformation matrix to the model's current transformation matrix.
|
||||
*
|
||||
* @return the model's new transformation matrix
|
||||
*/
|
||||
const glm::mat4& transform(const glm::mat4& transformation);
|
||||
|
||||
/*!
|
||||
* Resets the model's transformation to the identity matrix.
|
||||
*
|
||||
* @return the model's new transformation matrix, the identity matrix
|
||||
*/
|
||||
const glm::mat4& untransform();
|
||||
|
||||
/*!
|
||||
* Specialized version of transform(const glm::mat4&) that builds a scale transformation from an x, y, z vector and
|
||||
* applies it to the model's transformation matrix.
|
||||
*
|
||||
* @param scale x, y, z scale
|
||||
* @return the model's new transformation matrix
|
||||
*/
|
||||
const glm::mat4& scale(const glm::vec3& scale);
|
||||
|
||||
/*!
|
||||
* Scale all dimensions by the same amount.
|
||||
|
||||
* @overload scale(const glm::vec3&)
|
||||
*/
|
||||
const glm::mat4& scale(float scale);
|
||||
|
||||
/*!
|
||||
* Specialized version of transform(const glm::mat4&) that builds a rotation matrix from an angle in radians and an axis
|
||||
* vector and applies it to the model's transformation matrix.
|
||||
*
|
||||
* The axis is the vector around which the model will be rotated. For example, to rotate a 2D plane around the origin, use
|
||||
* the z-axis: `glm::vec3(0.0f, 0.0f, 1.0f)`.
|
||||
*
|
||||
* @param angle angle in radians
|
||||
* @param axis axis to rotate the model around
|
||||
* @return the model's new transformation matrix
|
||||
*/
|
||||
const glm::mat4& rotate(float angle, glm::vec3 axis);
|
||||
|
||||
/*!
|
||||
* Specialized version of transform(const glm::mat4&) that builds a translation matrix from a 3D translation vector
|
||||
* indicating the distance to translate along each axis and applies it to the model's transformation matrix.
|
||||
*
|
||||
* @param translation distance to translate in the x, y, and z dimensions
|
||||
* @return the model's new transformation matrix
|
||||
*/
|
||||
const glm::mat4& translate(glm::vec3 translation);
|
||||
|
||||
std::size_t size();
|
||||
operator glm::mat4() const;
|
||||
|
||||
|
|
|
@ -0,0 +1,85 @@
|
|||
/* +------------------------------------------------------+
|
||||
____/ \____ /| - Open source game framework licensed to freely use, |
|
||||
\ / / | copy, modify and sell without restriction |
|
||||
+--\ ^__^ /--+ | |
|
||||
| ~/ \~ | | - created for <https://foam.shampoo.ooo> |
|
||||
| ~~~~~~~~~~~~ | +------------------------------------------------------+
|
||||
| SPACE ~~~~~ | /
|
||||
| ~~~~~~~ BOX |/
|
||||
+-------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <cstdint>
|
||||
#include <iterator>
|
||||
#include "utility.hpp"
|
||||
|
||||
namespace sb
|
||||
{
|
||||
|
||||
template<typename Container>
|
||||
class Selection
|
||||
{
|
||||
|
||||
private:
|
||||
|
||||
std::uint32_t offset = 0;
|
||||
const Container& container;
|
||||
|
||||
public:
|
||||
|
||||
Selection(const Container& container) : container(container) {}
|
||||
|
||||
auto current() const
|
||||
{
|
||||
auto location = container.begin();
|
||||
if (location != container.end())
|
||||
{
|
||||
std::advance(location, offset);
|
||||
return location;
|
||||
}
|
||||
else
|
||||
{
|
||||
throw std::out_of_range("No options currently in selection");
|
||||
}
|
||||
}
|
||||
|
||||
void next()
|
||||
{
|
||||
offset = ++offset % container.size();
|
||||
}
|
||||
|
||||
void previous()
|
||||
{
|
||||
offset = sb::mod(--offset, container.size());
|
||||
}
|
||||
|
||||
void increment(int amount)
|
||||
{
|
||||
offset = sb::mod(offset + amount, container.size());
|
||||
}
|
||||
|
||||
void beginning()
|
||||
{
|
||||
offset = 0;
|
||||
}
|
||||
|
||||
void end()
|
||||
{
|
||||
offset = container.size() - 1;
|
||||
}
|
||||
|
||||
/* Return true if the selection currently points to the location at the beginning of the container. */
|
||||
bool at_beginning() const
|
||||
{
|
||||
return offset == 0;
|
||||
}
|
||||
|
||||
/* Return true if the selection currently points to the location at the end of the container. */
|
||||
bool at_end()
|
||||
{
|
||||
return offset >= container.size() - 1;
|
||||
}
|
||||
|
||||
};
|
||||
}
|
|
@ -99,6 +99,8 @@ namespace sb
|
|||
*/
|
||||
Switch(Reaction reaction = Reaction()) : reaction(reaction) {}
|
||||
|
||||
Switch(bool state, Reaction reaction = Reaction()) : state(state), reaction(reaction) {}
|
||||
|
||||
return_type flip(arguments... args)
|
||||
{
|
||||
state = !state;
|
||||
|
@ -115,14 +117,6 @@ namespace sb
|
|||
this->reaction = reaction;
|
||||
}
|
||||
|
||||
/*!
|
||||
* @return true if state is Switch::STATE_ON, false otherwise
|
||||
*/
|
||||
bool on()
|
||||
{
|
||||
return state;
|
||||
}
|
||||
|
||||
/*!
|
||||
* @return when called as a boolean, return state
|
||||
*/
|
||||
|
@ -131,5 +125,24 @@ namespace sb
|
|||
return on();
|
||||
}
|
||||
|
||||
/*!
|
||||
* Assign the switch object's state using the assignment operator with a boolean value.
|
||||
*
|
||||
* @param state state the switch will be set to
|
||||
*/
|
||||
Switch<return_type, arguments...>& operator=(bool state)
|
||||
{
|
||||
this->state = state;
|
||||
return *this;
|
||||
}
|
||||
|
||||
/*!
|
||||
* @return true if state is Switch::STATE_ON, false otherwise
|
||||
*/
|
||||
bool on()
|
||||
{
|
||||
return state;
|
||||
}
|
||||
|
||||
};
|
||||
}
|
||||
|
|
|
@ -55,6 +55,8 @@
|
|||
|
||||
namespace sb
|
||||
{
|
||||
static inline const glm::vec3 ZAXIS {0.0f, 0.0f, 1.0f};
|
||||
|
||||
/*!
|
||||
* Convert a vector described by the given angle and magnitude to an X and Y offset vector.
|
||||
*
|
||||
|
|
Loading…
Reference in New Issue