My old project for strange attractors, new approach
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
This repo is archived. You can view files and clone it, but cannot push or open issues/pull-requests.
 
 

201 lines
3.9 KiB

//
// Canvas.hpp
// AwesomeAttractorND
//
// Created by Joshua Moerman on 10/28/11.
// 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<N>() 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 <vector>
#include <iterator>
#include "array.hpp"
class Canvas2D {
typedef unsigned int value_type;
typedef std::vector<value_type> Row;
typedef std::vector<Row> Storage;
public:
Canvas2D(size_t width, size_t 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 = size<0>();
const size_t height = size<1>();
const size_t c = 0.5*(0.3*position[0])*width + width*.5;
const size_t r = 0.5*(0.3*position[1])*width + height*.5;
if(c < width && r < height) {
storage[r][c]++;
}
}
size_t size() const {
return size<0>() * size<1>();
}
template <size_t N>
size_t size() const {
if ( N == 0 ) return storage.size();
if ( N == 1 ) return storage.front().size();
return 0;
}
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<std::forward_iterator_tag, value_type> {
iterator(iterator const & rh)
: canvas(rh.canvas)
, c(rh.c)
, r(rh.r)
{}
iterator & operator++(){
++c;
if (c >= canvas->size<0>()) {
c = 0;
++r;
}
return *this;
}
iterator operator++(int){
iterator temp(*this);
++(*this);
return temp;
}
bool operator==(iterator const & rh) const {
return canvas == rh.canvas && c == rh.c && r == rh.r;
}
bool operator!=(iterator const & rh) const {
return canvas != rh.canvas || c != rh.c || r != rh.r;
}
value_type & operator*(){
return (*canvas)[r][c];
}
value_type & operator->(){
return (*canvas)[r][c];
}
private:
friend class Canvas2D;
iterator(Canvas2D * canvas, size_t c = 0, size_t r = 0)
: canvas(canvas)
, c(c)
, r(r)
{}
iterator();
Canvas2D * canvas;
size_t c;
size_t r;
};
struct const_iterator : public std::iterator<std::forward_iterator_tag, value_type const> {
const_iterator(const_iterator const & rh)
: canvas(rh.canvas)
, c(rh.c)
, r(rh.r)
{}
const_iterator & operator++(){
++c;
if (c >= canvas->size<0>()) {
c = 0;
++r;
}
return *this;
}
const_iterator operator++(int){
const_iterator temp(*this);
++(*this);
return temp;
}
bool operator==(const_iterator const & rh) const {
return canvas == rh.canvas && c == rh.c && r == rh.r;
}
bool operator!=(const_iterator const & rh) const {
return canvas != rh.canvas || c != rh.c || r != rh.r;
}
value_type const & operator*() const {
return (*canvas)[r][c];
}
value_type const & operator->() const {
return (*canvas)[r][c];
}
private:
friend class Canvas2D;
const_iterator(Canvas2D const * canvas, size_t c = 0, size_t r = 0)
: canvas(canvas)
, c(c)
, r(r)
{}
const_iterator();
Canvas2D const * canvas;
size_t c;
size_t r;
};
private:
Storage storage;
};
#endif