From 11828a8d0b3787e180d04b8635e3516d966ed2b5 Mon Sep 17 00:00:00 2001 From: Joshua Moerman Date: Wed, 2 Nov 2011 23:17:24 +0100 Subject: [PATCH] good system i think --- AwesomeAttractorND.xcodeproj/project.pbxproj | 2 + AwesomeAttractorND/Canvas.hpp | 196 +++++++++++++++---- AwesomeAttractorND/Tonemapper.hpp | 11 +- AwesomeAttractorND/array.hpp | 18 ++ AwesomeAttractorND/main.cpp | 2 +- 5 files changed, 186 insertions(+), 43 deletions(-) create mode 100644 AwesomeAttractorND/array.hpp diff --git a/AwesomeAttractorND.xcodeproj/project.pbxproj b/AwesomeAttractorND.xcodeproj/project.pbxproj index b8bc8e3..d01081c 100644 --- a/AwesomeAttractorND.xcodeproj/project.pbxproj +++ b/AwesomeAttractorND.xcodeproj/project.pbxproj @@ -29,6 +29,7 @@ 428EFED4145AFAB4001DBE1B /* Tonemapper.hpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.h; path = Tonemapper.hpp; sourceTree = ""; }; 42C2D1521461676B001BF28D /* Image.hpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.h; path = Image.hpp; sourceTree = ""; }; 42C2D1611461894E001BF28D /* Logging.hpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.h; path = Logging.hpp; sourceTree = ""; }; + 42C2D1621461E562001BF28D /* array.hpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.h; path = array.hpp; sourceTree = ""; }; 42D2E11D1456175C00FBC16A /* AwesomeAttractorND */ = {isa = PBXFileReference; explicitFileType = "compiled.mach-o.executable"; includeInIndex = 0; path = AwesomeAttractorND; sourceTree = BUILT_PRODUCTS_DIR; }; 42D2E1211456175C00FBC16A /* main.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; path = main.cpp; sourceTree = ""; }; 42D2E1231456175C00FBC16A /* AwesomeAttractorND.1 */ = {isa = PBXFileReference; lastKnownFileType = text.man; path = AwesomeAttractorND.1; sourceTree = ""; }; @@ -69,6 +70,7 @@ 42C2D1611461894E001BF28D /* Logging.hpp */, 42D2E12A1456176800FBC16A /* nd_array.hpp */, 428EFECF145AF6E0001DBE1B /* Canvas.hpp */, + 42C2D1621461E562001BF28D /* array.hpp */, 428EFED4145AFAB4001DBE1B /* Tonemapper.hpp */, 42C2D1521461676B001BF28D /* Image.hpp */, 42D2E1231456175C00FBC16A /* AwesomeAttractorND.1 */, diff --git a/AwesomeAttractorND/Canvas.hpp b/AwesomeAttractorND/Canvas.hpp index 0236a28..a003089 100644 --- a/AwesomeAttractorND/Canvas.hpp +++ b/AwesomeAttractorND/Canvas.hpp @@ -6,64 +6,192 @@ // Copyright 2011 Vadovas. All rights reserved. // +/* + Interface (or Concept) Canvas: + Canvas canvas(width, height, ...); Constructs a Canvas with given dimensions + canvas[x][y]...[z] Returns a (const) reference to an element + canvas.plot(position) Plots on the canvas (where position is normalized, ie in the unit-cube) + canvas.size() gives width/size for the given dimension N. + canvas.begin() .end() gives iterators to the elements (directly) + */ + #ifndef AwesomeAttractorND_Canvas_hpp #define AwesomeAttractorND_Canvas_hpp #include -#include "nd_array.hpp" +#include +#include "array.hpp" + +class Canvas2D { + typedef unsigned int value_type; + typedef std::vector Row; + typedef std::vector Storage; -class Canvas2D : public nd_array{ - typedef Canvas2D self; - typedef nd_array super; - public: Canvas2D(size_t width, size_t height) - : super(width, height) + : storage(width, Storage::value_type(height, 0)) {} + Row & operator[](size_t r){ + return storage[r]; + } + + Row const & operator[](size_t r) const { + return storage[r]; + } + void plot(double const * const position){ - const size_t width = get_size(0); - const size_t height = get_size(1); + const size_t width = size<0>(); + const size_t height = size<1>(); const size_t x = 0.5*position[0]*width + width*.5; const size_t y = 0.5*position[1]*width + height*.5; if(x < width && y < height) { - (*this)[x][y]++; + storage[x][y]++; } } -}; - -class Canvas2Db : public std::vector > { - typedef Canvas2Db self; - typedef std::vector > super; -public: - Canvas2Db(size_t width, size_t height) - : super(width, super::value_type(height, 0)) - {} + template + size_t size() const { + if ( N == 0 ) return storage.size(); + if ( N == 1 ) return storage.front().size(); + return 0; + } - void plot(double const * const position){ - const size_t width = get_size(0); - const size_t height = get_size(1); + struct iterator; + iterator begin(){ + return iterator(this); + } + iterator end(){ + return iterator(this, 0, size<1>()); + }; + + struct const_iterator; + const_iterator begin() const { + return const_iterator(this); + } + + const_iterator end() const { + return const_iterator(this, 0, size<1>()); + } + + const_iterator cbegin() const { + return const_iterator(this); + } + + const_iterator cend() const { + return const_iterator(this, 0, size<1>()); + } + + struct iterator : public std::iterator { + iterator(iterator const & rh) + : canvas(rh.canvas) + , x(rh.x) + , y(rh.y) + {} - const size_t x = 0.5*position[0]*width + width*.5; - const size_t y = 0.5*position[1]*width + height*.5; + iterator & operator++(){ + ++x; + if (x >= canvas->size<0>()) { + x = 0; + ++y; + } + return *this; + } - if(x < width && y < height) { - (*this)[x][y]++; + iterator operator++(int){ + iterator temp(*this); + ++(*this); + return temp; } - } + + bool operator==(iterator const & rh) const { + return canvas == rh.canvas && x == rh.x && y == rh.y; + } + + bool operator!=(iterator const & rh) const { + return canvas != rh.canvas || x != rh.x || y != rh.y; + } + + value_type & operator*(){ + return (*canvas)[x][y]; + } + + value_type & operator->(){ + return (*canvas)[x][y]; + } + + private: + friend class Canvas2D; + iterator(Canvas2D * canvas, size_t x = 0, size_t y = 0) + : canvas(canvas) + , x(x) + , y(y) + {} + + iterator(); + + Canvas2D * canvas; + size_t x; + size_t y; + }; - size_t get_size(size_t n) const { - switch (n) { - case 0: - return size(); - case 1: - return front().size(); + struct const_iterator : public std::iterator { + const_iterator(const_iterator const & rh) + : canvas(rh.canvas) + , x(rh.x) + , y(rh.y) + {} + + const_iterator & operator++(){ + ++x; + if (x >= canvas->size<0>()) { + x = 0; + ++y; + } + return *this; } - return 0; - } + + const_iterator operator++(int){ + const_iterator temp(*this); + ++(*this); + return temp; + } + + bool operator==(const_iterator const & rh) const { + return canvas == rh.canvas && x == rh.x && y == rh.y; + } + + bool operator!=(const_iterator const & rh) const { + return canvas != rh.canvas || x != rh.x || y != rh.y; + } + + value_type const & operator*() const { + return (*canvas)[x][y]; + } + + value_type const & operator->() const { + return (*canvas)[x][y]; + } + + private: + friend class Canvas2D; + const_iterator(Canvas2D const * canvas, size_t x = 0, size_t y = 0) + : canvas(canvas) + , x(x) + , y(y) + {} + + const_iterator(); + + Canvas2D const * canvas; + size_t x; + size_t y; + }; + +private: + Storage storage; }; #endif diff --git a/AwesomeAttractorND/Tonemapper.hpp b/AwesomeAttractorND/Tonemapper.hpp index 8e175a7..b213ccb 100644 --- a/AwesomeAttractorND/Tonemapper.hpp +++ b/AwesomeAttractorND/Tonemapper.hpp @@ -21,18 +21,13 @@ namespace Tonemappers { template void analyse(C const & canvas){ - //max = *std::max_element(canvas.cbegin(), canvas.cend()); - for (size_t x = 0; x < canvas.get_size(0); ++x) { - for (size_t y = 0; y < canvas.get_size(1); ++y) { - max = std::max(max, (unsigned int)canvas[x][y]); - } - } + max = *std::max_element(canvas.cbegin(), canvas.cend()); } template void process(C const & canvas, I & image){ - for (size_t x = 0; x < canvas.get_size(0); ++x) { - for (size_t y = 0; y < canvas.get_size(1); ++y) { + for (size_t x = 0; x < canvas.template size<0>(); ++x) { + for (size_t y = 0; y < canvas.template size<1>(); ++y) { const double grayscale = (double) canvas[x][y] / (double) max; image << typename I::pixel(std::pow(grayscale, 0.2), std::pow(grayscale, 0.6), grayscale*1.5); } diff --git a/AwesomeAttractorND/array.hpp b/AwesomeAttractorND/array.hpp new file mode 100644 index 0000000..a777857 --- /dev/null +++ b/AwesomeAttractorND/array.hpp @@ -0,0 +1,18 @@ +// +// array.hpp +// AwesomeAttractorND +// +// Created by Joshua Moerman on 11/2/11. +// Copyright 2011 Vadovas. All rights reserved. +// + +#ifndef AwesomeAttractorND_array_hpp +#define AwesomeAttractorND_array_hpp + +#include + +namespace std { + using tr1::array; +} + +#endif diff --git a/AwesomeAttractorND/main.cpp b/AwesomeAttractorND/main.cpp index ed5c034..777bef2 100644 --- a/AwesomeAttractorND/main.cpp +++ b/AwesomeAttractorND/main.cpp @@ -28,7 +28,7 @@ void fill(Canvas & canvas){ } void output(Canvas const & canvas){ - ImageFormats::bmp::bitmap_stream<> image(canvas.get_size(0), canvas.get_size(1), "test.bmp"); + ImageFormats::bmp::bitmap_stream<> image(canvas.size<0>(), canvas.size<1>(), "test.bmp"); Tonemappers::Normalizer2D tonemapper; tonemapper.analyse(canvas);