1 package org.woehlke.computer.kurzweil.commons.model.fractal;
2
3 import org.woehlke.computer.kurzweil.tabs.wator.WatorModel;
4 import org.woehlke.computer.kurzweil.commons.model.turing.Point;
5
6 import java.util.ArrayDeque;
7 import java.util.Deque;
8
9
10
11
12
13
14
15
16
17
18
19 public class GaussianNumberPlane {
20
21 public final static int YET_UNCOMPUTED = -1;
22 private final static double complexWorldDimensionRealX = 3.2d;
23 private final static double complexWorldDimensionImgY = 2.34d;
24 private final static double complexCenterForMandelbrotRealX = -2.2f;
25 private final static double complexCenterForMandelbrotImgY = -1.17f;
26 private final static double complexCenterForJuliaRealX = -1.6d;
27 private final static double complexCenterForJuliaImgY = -1.17d;
28 private final Point worldDimensions;
29 public volatile int zoomLevel;
30 private volatile int[][] lattice;
31 private volatile ComplexNumber complexNumberForJuliaSetC;
32 private volatile ComplexNumber complexWorldDimensions;
33 private volatile ComplexNumber complexCenterForMandelbrot;
34 private volatile ComplexNumber complexCenterForJulia;
35 private volatile Deque<ComplexNumber> complexCenterForZoomedMandelbrot = new ArrayDeque<>();
36
37 private volatile ComplexNumber zoomCenter;
38
39
40
41
42 public GaussianNumberPlane(WatorModel model) {
43 this.worldDimensions = model.getWorldDimensions();
44 this.lattice = new int[worldDimensions.getWidth()][worldDimensions.getHeight()];
45 this.complexWorldDimensions = new ComplexNumber(
46 complexWorldDimensionRealX,
47 complexWorldDimensionImgY
48 );
49 this.complexCenterForMandelbrot = new ComplexNumber(
50 complexCenterForMandelbrotRealX,
51 complexCenterForMandelbrotImgY
52 );
53 this.complexCenterForJulia = new ComplexNumber(
54 complexCenterForJuliaRealX,
55 complexCenterForJuliaImgY
56 );
57 start();
58 }
59
60 public void setModeZoom() {
61 this.setZoomLevel(1);
62 this.setZoomCenter(complexCenterForMandelbrot);
63 }
64
65 public synchronized void start(){
66 zoomLevel = 1;
67 for(int y = 0;y < this.worldDimensions.getY(); y++){
68 for(int x=0; x < worldDimensions.getX(); x++){
69 lattice[x][y] = YET_UNCOMPUTED;
70 }
71 }
72 }
73
74 public synchronized int getCellStatusFor(int x,int y){
75 return (lattice[x][y])<0?0:lattice[x][y];
76 }
77
78 private synchronized ComplexNumber getComplexNumberFromLatticeCoordsForJulia(Point turingPosition) {
79 double realX = complexCenterForJulia.getReal()
80 + (complexWorldDimensions.getReal()*turingPosition.getX())/worldDimensions.getX();
81 double imgY = complexCenterForJulia.getImg()
82 + (complexWorldDimensions.getImg()*turingPosition.getY())/worldDimensions.getY();
83 return new ComplexNumber(realX,imgY);
84 }
85
86 private synchronized ComplexNumber getComplexNumberFromLatticeCoordsForMandelbrot(Point turingPosition) {
87 double realX = (
88 complexCenterForMandelbrot.getReal()
89 + ( complexWorldDimensions.getReal() * turingPosition.getX() )
90 / worldDimensions.getX()
91 );
92 double imgY = (
93 complexCenterForMandelbrot.getImg()
94 + ( complexWorldDimensions.getImg() * turingPosition.getY() )
95 / worldDimensions.getY()
96 );
97 return new ComplexNumber(realX,imgY);
98 }
99
100 private synchronized ComplexNumber getComplexNumberFromLatticeCoordsForZoomedMandelbrot(Point turingPosition) {
101 double realX = (
102 ( complexCenterForMandelbrot.getReal() / this.getZoomLevel() )
103 + getZoomCenter().getReal()
104 + ( complexWorldDimensions.getReal() * turingPosition.getX() )
105 / ( worldDimensions.getX() * this.getZoomLevel() )
106 );
107 double imgY = (
108 ( complexCenterForMandelbrot.getImg() / this.getZoomLevel() )
109 + getZoomCenter().getImg()
110 + ( complexWorldDimensions.getImg() * turingPosition.getY() )
111 / ( worldDimensions.getY() * this.getZoomLevel() )
112 );
113 return new ComplexNumber(realX,imgY);
114 }
115
116 public synchronized boolean isInZooomedMandelbrotSet(Point turingPosition) {
117 ComplexNumber position = this.getComplexNumberFromLatticeCoordsForZoomedMandelbrot(turingPosition);
118 lattice[turingPosition.getX()][turingPosition.getY()] = position.computeMandelbrotSet();
119 return position.isInMandelbrotSet();
120 }
121
122 public synchronized boolean isInMandelbrotSet(Point turingPosition) {
123 ComplexNumber position = this.getComplexNumberFromLatticeCoordsForMandelbrot(turingPosition);
124 lattice[turingPosition.getX()][turingPosition.getY()] = position.computeMandelbrotSet();
125 return position.isInMandelbrotSet();
126 }
127
128 public synchronized void fillTheOutsideWithColors(){
129 for(int y=0;y<worldDimensions.getY();y++){
130 for(int x=0;x<worldDimensions.getX();x++){
131 if(lattice[x][y] == YET_UNCOMPUTED){
132 this.isInMandelbrotSet(new Point(x, y));
133 }
134 }
135 }
136 }
137
138 private synchronized void computeTheJuliaSetForC(ComplexNumber c) {
139 for(int y = 0; y < worldDimensions.getY(); y++) {
140 for (int x = 0; x < worldDimensions.getX(); x++) {
141 Pointer/kurzweil/commons/model/turing/Point.html#Point">Point zPoint = new Point(x, y);
142 ComplexNumber z = this.getComplexNumberFromLatticeCoordsForJulia(zPoint);
143 lattice[x][y] = z.computeJuliaSet(c);
144 }
145 }
146 }
147
148 public synchronized void computeTheJuliaSetFor(Point pointFromMandelbrotSet) {
149 ComplexNumber c = getComplexNumberFromLatticeCoordsForMandelbrot(pointFromMandelbrotSet);
150 this.complexNumberForJuliaSetC = c;
151 computeTheJuliaSetForC(c);
152 }
153
154 public void zoomIntoTheMandelbrotSet(Point zoomPoint) {
155
156 this.inceaseZoomLevel();
157 if(this.getZoomLevel() == 2){
158 ComplexNumbermons/model/fractal/ComplexNumber.html#ComplexNumber">ComplexNumber complexCenter = new ComplexNumber(this.complexCenterForMandelbrot);
159 complexCenterForZoomedMandelbrot.push(complexCenter);
160 this.setZoomCenter(getComplexNumberFromLatticeCoordsForMandelbrot(zoomPoint));
161 } else {
162 this.setZoomCenter(getComplexNumberFromLatticeCoordsForZoomedMandelbrot(zoomPoint));
163 }
164 complexCenterForZoomedMandelbrot.push(this.getZoomCenter());
165
166
167 for(int y = 0; y < worldDimensions.getY(); y++){
168 for(int x = 0; x < worldDimensions.getX(); x++){
169 Pointomputer/kurzweil/commons/model/turing/Point.html#Point">Point p = new Point(x, y);
170 this.isInZooomedMandelbrotSet(p);
171 }
172 }
173 }
174
175 public void zoomOutOfTheMandelbrotSet() {
176
177 if(this.getZoomLevel()>1){
178 this.deceaseZoomLevel();
179 this.setZoomCenter(complexCenterForZoomedMandelbrot.pop());
180 }
181
182 for(int y = 0; y < worldDimensions.getY(); y++){
183 for(int x = 0; x < worldDimensions.getX(); x++){
184 Pointomputer/kurzweil/commons/model/turing/Point.html#Point">Point p = new Point(x, y);
185 this.isInZooomedMandelbrotSet(p);
186 }
187 }
188 }
189
190 public void zoomIntoTheJuliaSetFor(Point zoomPoint) {
191 ComplexNumber c = this.complexNumberForJuliaSetC;
192 computeTheJuliaSetForC(c);
193 }
194
195 public void zoomOutOfTheJuliaSet() {
196 }
197
198 public synchronized int getZoomLevel() {
199 return zoomLevel;
200 }
201
202 public synchronized void setZoomLevel(int zoomLevel) {
203 this.zoomLevel = zoomLevel;
204 }
205
206 public synchronized int inceaseZoomLevel() {
207 return zoomLevel *= 2;
208 }
209
210 public synchronized int deceaseZoomLevel() {
211 return zoomLevel /= 2;
212 }
213
214 public synchronized ComplexNumber getZoomCenter() {
215 return zoomCenter;
216 }
217
218 public synchronized void setZoomCenter(ComplexNumber zoomCenter) {
219 this.zoomCenter = zoomCenter;
220 }
221
222 }