straightedge 0.1.0 → 0.1.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.gitignore +1 -0
- data/.ruby-version +1 -0
- data/Gemfile +7 -0
- data/README.md +44 -2
- data/gemspec.yml +3 -0
- data/lib/straightedge.rb +33 -11
- data/lib/straightedge/aspects.rb +3 -0
- data/lib/straightedge/aspects/colorable.rb +8 -0
- data/lib/straightedge/aspects/figural.rb +12 -0
- data/lib/straightedge/aspects/positional.rb +10 -0
- data/lib/straightedge/colors.rb +72 -0
- data/lib/straightedge/config.rb +6 -0
- data/lib/straightedge/director.rb +39 -0
- data/lib/straightedge/extend/array.rb +2 -13
- data/lib/straightedge/figures.rb +8 -0
- data/lib/straightedge/{adapters.rb → figures/circle.rb} +0 -0
- data/lib/straightedge/figures/figure.rb +44 -0
- data/lib/straightedge/figures/grid.rb +65 -0
- data/lib/straightedge/figures/grid_cell.rb +0 -0
- data/lib/straightedge/figures/hexagon.rb +33 -0
- data/lib/straightedge/figures/label.rb +13 -0
- data/lib/straightedge/figures/line.rb +25 -0
- data/lib/straightedge/figures/mark.rb +23 -0
- data/lib/straightedge/figures/quadrilateral.rb +20 -0
- data/lib/straightedge/motor/adapter.rb +54 -0
- data/lib/straightedge/motor/engine.rb +16 -0
- data/lib/straightedge/origin.rb +3 -0
- data/lib/straightedge/presenter.rb +29 -0
- data/lib/straightedge/scene.rb +20 -0
- data/lib/straightedge/surface.rb +21 -0
- data/lib/straightedge/toolkit/compass.rb +19 -0
- data/lib/straightedge/toolkit/rose.rb +60 -0
- data/lib/straightedge/toolkit/ruler.rb +23 -0
- data/lib/straightedge/tools.rb +3 -0
- data/lib/straightedge/version.rb +1 -1
- data/spec/spec_helper.rb +4 -1
- data/spec/straightedge/adapter_spec.rb +14 -0
- data/spec/straightedge/director_spec.rb +10 -0
- data/spec/straightedge/extend/array_spec.rb +1 -6
- data/spec/straightedge/{figure_spec.rb → figures/figure_spec.rb} +0 -5
- data/spec/straightedge/figures/grid_spec.rb +31 -0
- data/spec/straightedge/figures/hexagon_spec.rb +7 -0
- data/spec/straightedge/motor/engine_spec.rb +11 -0
- data/spec/straightedge/scene_spec.rb +27 -0
- data/spec/straightedge/{compass_spec.rb → toolkit/compass_spec.rb} +0 -4
- data/spec/straightedge/{rose_spec.rb → toolkit/rose_spec.rb} +0 -5
- data/spec/straightedge/toolkit/ruler_spec.rb +14 -0
- data/spec/straightedge_spec.rb +35 -0
- metadata +54 -16
- data/.rvmrc +0 -1
- data/lib/straightedge/compass.rb +0 -17
- data/lib/straightedge/figure.rb +0 -28
- data/lib/straightedge/grid.rb +0 -34
- data/lib/straightedge/line.rb +0 -21
- data/lib/straightedge/mark.rb +0 -26
- data/lib/straightedge/rose.rb +0 -44
- data/lib/straightedge/ruler.rb +0 -21
- data/spec/straightedge/grid_spec.rb +0 -33
- data/spec/straightedge/ruler_spec.rb +0 -11
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: f8b2f60d62255936247fe75932dc27426760a1e9
|
4
|
+
data.tar.gz: 05cc12291ebbf0518a608b1f1e0f3ef6f0ca376d
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 176f4ae297d81ab3c94e6daf7a0ea0aa3ad94cd12594ead81123822e0704ba6b7dd56f2026a1e9094e5840eb0320fc7c64c2e8b49787e1468f52e2e2c8e059aa
|
7
|
+
data.tar.gz: 8e600b22c8cf4463e7a55e5d1883da258e81ea4668e8e686f36af5dbbe0bc35e9e7b277c39a651f6431dbe3ce81703143d14167b630567ddc4b857a1998c9ab6
|
data/.gitignore
CHANGED
data/.ruby-version
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
ruby-2.1.5
|
data/Gemfile
CHANGED
data/README.md
CHANGED
@@ -1,28 +1,70 @@
|
|
1
1
|
# straightedge
|
2
2
|
|
3
|
+
[](https://codeclimate.com/github/jweissman/straightedge)
|
4
|
+
|
3
5
|
* [Homepage](https://rubygems.org/gems/straightedge)
|
4
6
|
* [Documentation](http://rubydoc.info/gems/straightedge/frames)
|
5
7
|
* [Email](mailto:jweissman1986 at gmail.com)
|
6
8
|
|
7
9
|
## Description
|
8
10
|
|
9
|
-
|
11
|
+
Give me a compass and straightedge and I will conquer the world
|
12
|
+
|
13
|
+
[](http://xkcd.com/866/)
|
14
|
+
|
15
|
+
Geometry primitives and graphical app (game) framework framework.
|
10
16
|
|
11
17
|
## Features
|
12
18
|
|
19
|
+
* Geometry toolkit
|
20
|
+
- extensible Compass
|
21
|
+
- Ruler (for measuring distances)
|
22
|
+
|
23
|
+
* Figures composed of points called Marks
|
24
|
+
- Line
|
25
|
+
- Quadrilateral
|
26
|
+
- Hexagon
|
27
|
+
|
28
|
+
* Some fledgling support for grids
|
29
|
+
|
30
|
+
* Some reactor-pattern framework platform components
|
31
|
+
to help standardize interfaces (see straightedge-gosu
|
32
|
+
and straightedge-canvas for examples)
|
33
|
+
|
13
34
|
## Examples
|
14
35
|
|
15
36
|
require 'straightedge'
|
16
37
|
|
38
|
+
# you need an adapter to actually render something
|
39
|
+
require 'straightedge-gosu'
|
40
|
+
|
41
|
+
class Example::GameController < Straightedge::Director
|
42
|
+
def current_scene
|
43
|
+
{
|
44
|
+
[200,300] => Quadrilateral.new(dimensions: [200,100], color: :green),
|
45
|
+
[200,305] => "rectangle",
|
46
|
+
|
47
|
+
[400,300] => Hexagon.new(scale: 40.0, color: :blue),
|
48
|
+
[400,305] => "hexagon"
|
49
|
+
}
|
50
|
+
end
|
51
|
+
end
|
52
|
+
|
17
53
|
## Requirements
|
18
54
|
|
55
|
+
Ruby 2.x should be enough
|
56
|
+
|
19
57
|
## Install
|
20
58
|
|
21
59
|
$ gem install straightedge
|
22
60
|
|
23
61
|
## Synopsis
|
24
62
|
|
25
|
-
|
63
|
+
Eventually it would be nice to support a CLI that wraps around tasks (note: not implemented yet)
|
64
|
+
|
65
|
+
$ straightedge create [app] — builds an example app skeleton
|
66
|
+
$ straightedge serve — stands up a canvas webserver
|
67
|
+
$ straightedge play — connects to local instance or plays through OpenGL adapter… etc
|
26
68
|
|
27
69
|
## Copyright
|
28
70
|
|
data/gemspec.yml
CHANGED
data/lib/straightedge.rb
CHANGED
@@ -1,17 +1,39 @@
|
|
1
|
-
require '
|
2
|
-
|
3
|
-
require 'straightedge/compass'
|
4
|
-
require 'straightedge/rose'
|
5
|
-
require 'straightedge/ruler'
|
6
|
-
|
7
|
-
require 'straightedge/mark'
|
8
|
-
require 'straightedge/line'
|
9
|
-
require 'straightedge/figure'
|
1
|
+
require 'mini/config'
|
10
2
|
|
11
|
-
|
12
|
-
require 'straightedge/
|
3
|
+
require 'straightedge/version'
|
4
|
+
require 'straightedge/config'
|
5
|
+
require 'straightedge/origin'
|
6
|
+
require 'straightedge/aspects'
|
7
|
+
require 'straightedge/tools'
|
8
|
+
require 'straightedge/figures'
|
9
|
+
require 'straightedge/colors'
|
10
|
+
require 'straightedge/scene'
|
11
|
+
require 'straightedge/presenter'
|
13
12
|
|
14
13
|
require 'straightedge/extend/array'
|
15
14
|
|
15
|
+
# for integration with viewing/gaming engines...
|
16
|
+
# TODO try to downstream as much of this to supporting libs
|
17
|
+
# as possible
|
18
|
+
require 'straightedge/motor/engine'
|
19
|
+
require 'straightedge/motor/adapter'
|
20
|
+
require 'straightedge/director'
|
21
|
+
require 'straightedge/surface'
|
22
|
+
|
16
23
|
module Straightedge
|
24
|
+
include Toolkit
|
25
|
+
include Figures
|
26
|
+
|
27
|
+
# create constructors around out configured default components
|
28
|
+
class << self
|
29
|
+
%w[ engine agent surface adapter ].each do |elem|
|
30
|
+
define_method("new_#{elem}") do |*args|
|
31
|
+
Straightedge.config.send("#{elem}_class").new(*args)
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
35
|
+
|
36
|
+
def self.bootstrap
|
37
|
+
new_engine.boot
|
38
|
+
end
|
17
39
|
end
|
@@ -0,0 +1,72 @@
|
|
1
|
+
module Straightedge
|
2
|
+
module Colors
|
3
|
+
class Palette
|
4
|
+
extend Forwardable
|
5
|
+
|
6
|
+
attr_reader :names_and_values
|
7
|
+
def initialize(names_and_hex_values={})
|
8
|
+
@names_and_values = names_and_hex_values
|
9
|
+
end
|
10
|
+
|
11
|
+
|
12
|
+
def list; @names_and_values.keys end
|
13
|
+
def_delegator :list, :sample
|
14
|
+
|
15
|
+
def hex_value_for(name)
|
16
|
+
raise "no such color: #{name}" unless list.include?(name)
|
17
|
+
@names_and_values[name]
|
18
|
+
end
|
19
|
+
|
20
|
+
def self.base
|
21
|
+
@core ||= new({
|
22
|
+
white: 0xFFFFFFFF,
|
23
|
+
black: 0xFF000000,
|
24
|
+
none: 0x00000000,
|
25
|
+
})
|
26
|
+
end
|
27
|
+
|
28
|
+
# http://paletton.com/#uid=b5C4c2O0kfUu76fODb3COkppkonk+
|
29
|
+
def self.clean_rgb
|
30
|
+
@smooth_rgb ||= new(base.names_and_values.merge({
|
31
|
+
red: 0xFFEE787B, red1: 0xFFFECDCE, red2: 0xFFFDA6A8, red3: 0xFFC8494C, red4: 0xFFA6282B,
|
32
|
+
blue: 0xFF6C5DA5, blue1: 0xFFC2BAE0, blue2: 0xFF9488C3, blue3: 0xFF4D3D8B, blue4: 0xFF362673,
|
33
|
+
green: 0xFF67C262, green1: 0xFFC0ECBE, green2: 0xFF93DA8F, green3: 0xFF40A33B, green4: 0xFF258720
|
34
|
+
}))
|
35
|
+
end
|
36
|
+
|
37
|
+
# Palette URL: http://paletton.com/#uid=72s0u0k8kpR26GB4Wuzc2lNfjho
|
38
|
+
#
|
39
|
+
# the '4' is closer to the base color, we may want to rethink the naming strategy
|
40
|
+
# also -- we need a color concept and to generate these but that's another day!
|
41
|
+
def self.pleasant_pastels
|
42
|
+
@pastels ||= new(base.names_and_values.merge({
|
43
|
+
tan: 0xFFA9BD8C, tan1: 0xFFEBF2E2, tan2: 0xFFD2E0BD, tan3: 0xFF87A063, tan4: 0xFF667F42,
|
44
|
+
green: 0xFF71987D, green1: 0xFFC7D5CB, green2: 0xFF98B4A1, green3: 0xFF50805F, green4: 0xFF356644,
|
45
|
+
pink: 0xFFCEA098, pink1: 0xFFFFF1EE, pink2: 0xFFF4D3CE, pink3: 0xFFAE756C, pink4: 0xFF8B5148,
|
46
|
+
purple: 0xFFAD8095, purple1: 0xFFE5D6DD, purple2: 0xFFCDADBC, purple3: 0xFF925B74, purple4: 0xFF743D56,
|
47
|
+
}))
|
48
|
+
end
|
49
|
+
end
|
50
|
+
|
51
|
+
# expose module-level wrappers around the currently-configured palette
|
52
|
+
#
|
53
|
+
def self.palette
|
54
|
+
@current_palette ||= Straightedge.config.palette
|
55
|
+
end
|
56
|
+
|
57
|
+
def self.all
|
58
|
+
palette.list
|
59
|
+
end
|
60
|
+
|
61
|
+
def self.pick
|
62
|
+
palette.sample
|
63
|
+
end
|
64
|
+
|
65
|
+
def self.hex_value(color)
|
66
|
+
palette.hex_value_for color
|
67
|
+
end
|
68
|
+
end
|
69
|
+
|
70
|
+
# assign a basic rgb default color palette
|
71
|
+
config.palette = Colors::Palette.clean_rgb
|
72
|
+
end
|
@@ -0,0 +1,39 @@
|
|
1
|
+
module Straightedge
|
2
|
+
class Director
|
3
|
+
extend Forwardable
|
4
|
+
include Straightedge::Figures
|
5
|
+
|
6
|
+
def prepare_stage(geometry)
|
7
|
+
@width, @height = *geometry
|
8
|
+
@space = Grid.new([30,30], scale: 20.0)
|
9
|
+
@space.paint!
|
10
|
+
end
|
11
|
+
|
12
|
+
def orchestrate
|
13
|
+
@space.paint!
|
14
|
+
end
|
15
|
+
|
16
|
+
def current_scene
|
17
|
+
Scene.new({
|
18
|
+
ORIGIN => @space,
|
19
|
+
[10,10] => "grid",
|
20
|
+
|
21
|
+
[200,300] => Quadrilateral.new(dimensions: [200,100], color: :green),
|
22
|
+
[200,305] => "rectangle",
|
23
|
+
|
24
|
+
[400,300] => Hexagon.new(scale: 40.0, color: :blue),
|
25
|
+
[400,305] => "hexagon"
|
26
|
+
})
|
27
|
+
end
|
28
|
+
|
29
|
+
## handle custom events from the surface (clicks)...
|
30
|
+
# how should we handle socket/player connects?
|
31
|
+
#
|
32
|
+
def handle(evt_name, *args)
|
33
|
+
#puts "--- got event #{evt_name} with args #{args}"
|
34
|
+
send(evt_name.to_sym, *args)
|
35
|
+
end
|
36
|
+
end
|
37
|
+
|
38
|
+
config.agent_class = Director
|
39
|
+
end
|
@@ -1,5 +1,6 @@
|
|
1
1
|
class Array
|
2
|
-
|
2
|
+
include Straightedge::Aspects::Positional
|
3
|
+
include Straightedge::Aspects::Figural
|
3
4
|
|
4
5
|
def sum
|
5
6
|
inject(&:+)
|
@@ -8,16 +9,4 @@ class Array
|
|
8
9
|
def mean
|
9
10
|
sum / size
|
10
11
|
end
|
11
|
-
|
12
|
-
# consider the array as a vector in n-space (where n is the self.length)
|
13
|
-
def to_point
|
14
|
-
Straightedge::Mark.new(*self)
|
15
|
-
end
|
16
|
-
def_delegators :to_point, :x, :y
|
17
|
-
|
18
|
-
# consider the array as an array of points
|
19
|
-
def to_points
|
20
|
-
Straightedge::Figure.new(self)
|
21
|
-
end
|
22
|
-
def_delegators :to_points, :adjacent, :center
|
23
12
|
end
|
@@ -0,0 +1,8 @@
|
|
1
|
+
require 'straightedge/figures/figure'
|
2
|
+
require 'straightedge/figures/mark'
|
3
|
+
require 'straightedge/figures/label'
|
4
|
+
require 'straightedge/figures/line'
|
5
|
+
require 'straightedge/figures/quadrilateral'
|
6
|
+
require 'straightedge/figures/hexagon'
|
7
|
+
require 'straightedge/figures/grid'
|
8
|
+
|
File without changes
|
@@ -0,0 +1,44 @@
|
|
1
|
+
module Straightedge
|
2
|
+
module Figures
|
3
|
+
# TODO the idea is that a figure is a collection of marks (and possibly other figures...?)
|
4
|
+
# marks should be represented relative to the *figural* origin
|
5
|
+
class Figure
|
6
|
+
include Straightedge::Aspects::Colorable
|
7
|
+
|
8
|
+
extend Forwardable
|
9
|
+
include Enumerable
|
10
|
+
|
11
|
+
def_delegators :marks, :each
|
12
|
+
def_delegators :compass, :project
|
13
|
+
def_delegators :location, :x, :y
|
14
|
+
|
15
|
+
attr_accessor :marks, :color, :location
|
16
|
+
|
17
|
+
def initialize(marks=[], location: nil, color: :none)
|
18
|
+
@marks = marks
|
19
|
+
@color = color
|
20
|
+
@location = location
|
21
|
+
end
|
22
|
+
|
23
|
+
def compass; @compass ||= Straightedge::Toolkit::Compass.default end
|
24
|
+
|
25
|
+
def adjacent
|
26
|
+
approximate_adjacent = map(&method(:project)).flatten(1).uniq
|
27
|
+
actual_adjacent = approximate_adjacent.reject(&method(:include?))
|
28
|
+
actual_adjacent.sort_by(&method(:distance_from_center))
|
29
|
+
end
|
30
|
+
|
31
|
+
|
32
|
+
# note this is center of the collection of raw marks
|
33
|
+
# in terms of their own space; not displaced by location
|
34
|
+
# or scaled by dimensions
|
35
|
+
def center
|
36
|
+
[map(&:x).mean, map(&:y).mean]
|
37
|
+
end
|
38
|
+
|
39
|
+
def distance_from_center(xy)
|
40
|
+
Straightedge::Toolkit::Ruler.distance(xy,center)
|
41
|
+
end
|
42
|
+
end
|
43
|
+
end
|
44
|
+
end
|
@@ -0,0 +1,65 @@
|
|
1
|
+
module Straightedge
|
2
|
+
module Figures
|
3
|
+
class Grid < Figure
|
4
|
+
include Enumerable
|
5
|
+
def_delegators :to_a, :sample, :map!
|
6
|
+
def_delegator :dimensions, :x, :width
|
7
|
+
def_delegator :dimensions, :y, :height
|
8
|
+
|
9
|
+
attr_reader :dimensions, :scale, :figure
|
10
|
+
|
11
|
+
def initialize(dimensions=[1,1], opts={})
|
12
|
+
@dimensions = dimensions
|
13
|
+
@scale = opts.delete(:scale) { 1.0 }
|
14
|
+
super(to_a, opts)
|
15
|
+
end
|
16
|
+
|
17
|
+
def at(xy)
|
18
|
+
[xy.x, xy.y]
|
19
|
+
end
|
20
|
+
|
21
|
+
def each
|
22
|
+
Grid.each_coordinate([width, height]) do |x, y|
|
23
|
+
yield(at([x,y]))
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
def cell_at(xy)
|
28
|
+
@cells ||= {}
|
29
|
+
@cells[xy] ||= Figures::Quadrilateral.new(dimensions: [@scale, @scale], location: to_pixels(xy)) #[xy.x+1,xy.y+1])) #to_pixels(xy))
|
30
|
+
end
|
31
|
+
|
32
|
+
def each_cell
|
33
|
+
each { |xy| yield cell_at(xy) }
|
34
|
+
end
|
35
|
+
|
36
|
+
def paint!
|
37
|
+
#each(&:to_point)
|
38
|
+
each_cell(&:paint)
|
39
|
+
end
|
40
|
+
|
41
|
+
def clip(xys=[])
|
42
|
+
xys.reject do |xy|
|
43
|
+
_x,_y = *xy
|
44
|
+
_x < 0 || _y < 0 || x >= _x || y >= _y
|
45
|
+
end
|
46
|
+
end
|
47
|
+
|
48
|
+
def self.each_coordinate(dimensions)
|
49
|
+
dimensions.x.times do |x|
|
50
|
+
dimensions.y.times do |y|
|
51
|
+
yield [x,y]
|
52
|
+
end
|
53
|
+
end
|
54
|
+
end
|
55
|
+
|
56
|
+
def to_pixels(xy)
|
57
|
+
[xy.x * (@scale/2), xy.y * (@scale/2)]
|
58
|
+
end
|
59
|
+
|
60
|
+
#def to_coords(xy)
|
61
|
+
# [xy.x / (@scale/2), xy.y / (@scale/2) ]
|
62
|
+
#end
|
63
|
+
end
|
64
|
+
end
|
65
|
+
end
|