Rev 285 | Rev 297 | Go to most recent revision | Show entire file | Ignore whitespace | Details | Blame | Last modification | View Log | RSS feed
Rev 285 | Rev 295 | ||
---|---|---|---|
Line 135... | Line 135... | ||
135 | 135 | ||
136 | /// helper function for gluing the edges together
|
136 | /// helper function for gluing the edges together
|
137 | /// index: index at grid
|
137 | /// index: index at grid
|
138 | /// count: number of pixels that are the simulation area (e.g. 100m and 2m pixel -> 50)
|
138 | /// count: number of pixels that are the simulation area (e.g. 100m and 2m pixel -> 50)
|
139 | /// buffer: size of buffer around simulation area (in pixels)
|
139 | /// buffer: size of buffer around simulation area (in pixels)
|
140 | int torusIndex(int index, int count, int buffer) |
- | |
- | 140 | inline int torusIndex(int index, int count, int buffer, int ru_index) |
|
141 | {
|
141 | {
|
142 | return buffer + (index-buffer+count)%count; |
- | |
- | 142 | return buffer + ru_index + (index-buffer+count)%count; |
|
143 | }
|
143 | }
|
144 | 144 | ||
145 | 145 | ||
146 | /** Apply LIPs. This "Torus" functions wraps the influence at the edges of a 1ha simulation area.
|
146 | /** Apply LIPs. This "Torus" functions wraps the influence at the edges of a 1ha simulation area.
|
147 | */
|
147 | */
|
148 | void Tree::applyLIP_torus() |
148 | void Tree::applyLIP_torus() |
149 | {
|
149 | {
|
150 | if (!mStamp) |
150 | if (!mStamp) |
151 | return; |
151 | return; |
152 | Q_ASSERT(mGrid!=0 && mStamp!=0 && mRU!=0); |
152 | Q_ASSERT(mGrid!=0 && mStamp!=0 && mRU!=0); |
- | 153 | int bufferOffset = mGrid->indexAt(QPointF(0.,0.)).x(); // offset of buffer |
|
- | 154 | QPoint pos = QPoint((mPositionIndex.x()-bufferOffset)%50 + bufferOffset, |
|
- | 155 | (mPositionIndex.y()-bufferOffset)%50 + bufferOffset); // offset within the ha |
|
- | 156 | QPoint ru_offset = QPoint(mPositionIndex.x() - pos.x(), mPositionIndex.y() - pos.y()); // offset of the corner of the resource index |
|
153 | 157 | ||
154 | QPoint pos = mPositionIndex; |
- | |
155 | int offset = mStamp->offset(); |
158 | int offset = mStamp->offset(); |
156 | pos-=QPoint(offset, offset); |
159 | pos-=QPoint(offset, offset); |
157 | 160 | ||
158 | float local_dom; // height of Z* on the current position |
161 | float local_dom; // height of Z* on the current position |
159 | int x,y; |
162 | int x,y; |
Line 163... | Line 166... | ||
163 | float *grid_value; |
166 | float *grid_value; |
164 | if (!mGrid->isIndexValid(pos) || !mGrid->isIndexValid(pos+QPoint(gr_stamp, gr_stamp))) { |
167 | if (!mGrid->isIndexValid(pos) || !mGrid->isIndexValid(pos+QPoint(gr_stamp, gr_stamp))) { |
165 | // todo: in this case we should use another algorithm!!! necessary????
|
168 | // todo: in this case we should use another algorithm!!! necessary????
|
166 | return; |
169 | return; |
167 | }
|
170 | }
|
168 | int bufferOffset = mGrid->indexAt(QPointF(0.,0.)).x(); // offset of buffer |
- | |
- | 171 | ||
169 | int xt, yt; // wraparound coordinates |
172 | int xt, yt; // wraparound coordinates |
170 | for (y=0;y<gr_stamp; ++y) { |
173 | for (y=0;y<gr_stamp; ++y) { |
171 | grid_y = pos.y() + y; |
174 | grid_y = pos.y() + y; |
172 | yt = torusIndex(grid_y, 50,bufferOffset); // 50 cells per 100m |
- | |
- | 175 | yt = torusIndex(grid_y, 50,bufferOffset, ru_offset.y()); // 50 cells per 100m |
|
173 | for (x=0;x<gr_stamp;++x) { |
176 | for (x=0;x<gr_stamp;++x) { |
174 | // suppose there is no stamping outside
|
177 | // suppose there is no stamping outside
|
175 | grid_x = pos.x() + x; |
178 | grid_x = pos.x() + x; |
176 | xt = torusIndex(grid_x,50,bufferOffset); |
- | |
- | 179 | xt = torusIndex(grid_x,50,bufferOffset, ru_offset.x()); |
|
177 | 180 | ||
178 | local_dom = mHeightGrid->valueAtIndex(xt/5,yt/5).height; |
181 | local_dom = mHeightGrid->valueAtIndex(xt/5,yt/5).height; |
179 | value = (*mStamp)(x,y); // stampvalue |
182 | value = (*mStamp)(x,y); // stampvalue |
180 | value = 1. - value*mOpacity / local_dom; // calculated value |
183 | value = 1. - value*mOpacity / local_dom; // calculated value |
181 | value = qMax(value, 0.02f); // limit value |
184 | value = qMax(value, 0.02f); // limit value |
Line 314... | Line 317... | ||
314 | {
|
317 | {
|
315 | // height of Z*
|
318 | // height of Z*
|
316 | const float cellsize = mHeightGrid->cellsize(); |
319 | const float cellsize = mHeightGrid->cellsize(); |
317 | 320 | ||
318 | QPoint p = QPoint(mPositionIndex.x()/5, mPositionIndex.y()/5); // pos of tree on height grid |
321 | QPoint p = QPoint(mPositionIndex.x()/5, mPositionIndex.y()/5); // pos of tree on height grid |
- | 322 | int bufferOffset = mHeightGrid->indexAt(QPointF(0.,0.)).x(); // offset of buffer |
|
319 | 323 | ||
320 | // count trees that are on height-grid cells (used for stockable area)
|
324 | // count trees that are on height-grid cells (used for stockable area)
|
321 | mHeightGrid->valueAtIndex(p).increaseCount(); |
325 | mHeightGrid->valueAtIndex(p).increaseCount(); |
- | 326 | ||
- | 327 | // torus coordinates
|
|
- | 328 | p.setX((p.x()-bufferOffset)%10 + bufferOffset); |
|
- | 329 | p.setY((p.y()-bufferOffset)%10 + bufferOffset); |
|
- | 330 | QPoint ru_offset =QPoint(mPositionIndex.x()/5 - p.x(), mPositionIndex.y()/5 - p.y()); |
|
322 | 331 | ||
323 | int index_eastwest = mPositionIndex.x() % 5; // 4: very west, 0 east edge |
332 | int index_eastwest = mPositionIndex.x() % 5; // 4: very west, 0 east edge |
324 | int index_northsouth = mPositionIndex.y() % 5; // 4: northern edge, 0: southern edge |
333 | int index_northsouth = mPositionIndex.y() % 5; // 4: northern edge, 0: southern edge |
325 | int dist[9]; |
334 | int dist[9]; |
326 | dist[3] = index_northsouth * 2 + 1; // south |
335 | dist[3] = index_northsouth * 2 + 1; // south |
Line 339... | Line 348... | ||
339 | 348 | ||
340 | 349 | ||
341 | int ringcount = int(floor(mHeight / cellsize)) + 1; |
350 | int ringcount = int(floor(mHeight / cellsize)) + 1; |
342 | int ix, iy; |
351 | int ix, iy; |
343 | int ring; |
352 | int ring; |
344 | QPoint pos;
|
- | |
345 | float hdom; |
353 | float hdom; |
346 | int bufferOffset = mHeightGrid->indexAt(QPointF(0.,0.)).x(); // offset of buffer |
- | |
347 | for (ix=-ringcount;ix<=ringcount;ix++) |
354 | for (ix=-ringcount;ix<=ringcount;ix++) |
348 | for (iy=-ringcount; iy<=+ringcount; iy++) { |
355 | for (iy=-ringcount; iy<=+ringcount; iy++) { |
349 | ring = qMax(abs(ix), abs(iy)); |
356 | ring = qMax(abs(ix), abs(iy)); |
350 | QPoint pos(ix+p.x(), iy+p.y()); |
357 | QPoint pos(ix+p.x(), iy+p.y()); |
351 | if (mHeightGrid->isIndexValid(pos)) { |
- | |
352 | float &rHGrid = mHeightGrid->valueAtIndex(torusIndex(pos.x(),10,bufferOffset), torusIndex(pos.y(),10,bufferOffset)).height; |
- | |
- | 358 | QPoint p_torus(torusIndex(pos.x(),10,bufferOffset,ru_offset.x()), |
|
- | 359 | torusIndex(pos.y(),10,bufferOffset,ru_offset.y())); |
|
- | 360 | if (mHeightGrid->isIndexValid(p_torus)) { |
|
- | 361 | float &rHGrid = mHeightGrid->valueAtIndex(p_torus.x(),p_torus.y()).height; |
|
353 | if (rHGrid > mHeight) // skip calculation if grid is higher than tree |
362 | if (rHGrid > mHeight) // skip calculation if grid is higher than tree |
354 | continue; |
363 | continue; |
355 | int direction = 4 + (ix?(ix<0?-3:3):0) + (iy?(iy<0?-1:1):0); // 4 + 3*sgn(x) + sgn(y) |
364 | int direction = 4 + (ix?(ix<0?-3:3):0) + (iy?(iy<0?-1:1):0); // 4 + 3*sgn(x) + sgn(y) |
356 | hdom = mHeight - dist[direction]; |
365 | hdom = mHeight - dist[direction]; |
357 | if (ring>1) |
366 | if (ring>1) |
Line 368... | Line 377... | ||
368 | if (!mStamp) |
377 | if (!mStamp) |
369 | return; |
378 | return; |
370 | const Stamp *reader = mStamp->reader(); |
379 | const Stamp *reader = mStamp->reader(); |
371 | if (!reader) |
380 | if (!reader) |
372 | return; |
381 | return; |
373 | QPoint pos_reader = mPositionIndex; |
- | |
- | 382 | int bufferOffset = mGrid->indexAt(QPointF(0.,0.)).x(); // offset of buffer |
|
- | 383 | ||
- | 384 | QPoint pos_reader = QPoint((mPositionIndex.x()-bufferOffset)%50 + bufferOffset, |
|
- | 385 | (mPositionIndex.y()-bufferOffset)%50 + bufferOffset); // offset within the ha |
|
- | 386 | QPoint ru_offset = QPoint(mPositionIndex.x() - pos_reader.x(), mPositionIndex.y() - pos_reader.y()); // offset of the corner of the resource index |
|
374 | 387 | ||
375 | int offset_reader = reader->offset(); |
388 | int offset_reader = reader->offset(); |
376 | int offset_writer = mStamp->offset(); |
389 | int offset_writer = mStamp->offset(); |
377 | int d_offset = offset_writer - offset_reader; // offset on the *stamp* to the crown-cells |
390 | int d_offset = offset_writer - offset_reader; // offset on the *stamp* to the crown-cells |
378 | 391 | ||
379 | QPoint pos_writer=pos_reader - QPoint(offset_writer, offset_writer); |
- | |
380 | pos_reader-=QPoint(offset_reader, offset_reader); |
392 | pos_reader-=QPoint(offset_reader, offset_reader); |
381 | QPoint p;
|
- | |
382 | 393 | ||
383 | //float dom_height = (*m_dominanceGrid)[m_Position];
|
- | |
384 | float local_dom; |
394 | float local_dom; |
385 | 395 | ||
386 | int x,y; |
396 | int x,y; |
387 | double sum=0.; |
397 | double sum=0.; |
388 | double value, own_value; |
398 | double value, own_value; |
389 | float *grid_value; |
399 | float *grid_value; |
390 | int reader_size = reader->size(); |
400 | int reader_size = reader->size(); |
391 | int rx = pos_reader.x(); |
401 | int rx = pos_reader.x(); |
392 | int ry = pos_reader.y(); |
402 | int ry = pos_reader.y(); |
393 | int xt, yt; // wrapped coords |
403 | int xt, yt; // wrapped coords |
394 | int bufferOffset = mGrid->indexAt(QPointF(0.,0.)).x(); // offset of buffer |
- | |
395 | 404 | ||
396 | for (y=0;y<reader_size; ++y, ++ry) { |
405 | for (y=0;y<reader_size; ++y, ++ry) { |
397 | grid_value = mGrid->ptr(rx, ry); |
406 | grid_value = mGrid->ptr(rx, ry); |
398 | for (x=0;x<reader_size;++x) { |
407 | for (x=0;x<reader_size;++x) { |
399 | xt = torusIndex(rx+x,50, bufferOffset); |
- | |
400 | yt = torusIndex(ry+y,50, bufferOffset); |
- | |
- | 408 | xt = torusIndex(rx+x,50, bufferOffset, ru_offset.x()); |
|
- | 409 | yt = torusIndex(ry+y,50, bufferOffset, ru_offset.y()); |
|
401 | grid_value = mGrid->ptr(xt,yt); |
410 | grid_value = mGrid->ptr(xt,yt); |
402 | //p = pos_reader + QPoint(x,y);
|
411 | //p = pos_reader + QPoint(x,y);
|
403 | //if (m_grid->isIndexValid(p)) {
|
412 | //if (m_grid->isIndexValid(p)) {
|
404 | local_dom = mHeightGrid->valueAtIndex(xt/5, yt/5).height; // ry: gets ++ed in outer loop, rx not |
413 | local_dom = mHeightGrid->valueAtIndex(xt/5, yt/5).height; // ry: gets ++ed in outer loop, rx not |
405 | //local_dom = m_dominanceGrid->valueAt( m_grid->cellCoordinates(p) );
|
414 | //local_dom = m_dominanceGrid->valueAt( m_grid->cellCoordinates(p) );
|