00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021 #include <landscapemap/MovementMap.h>
00022 #include <landscapemap/LandscapeMaps.h>
00023 #include <landscapedef/LandscapeTex.h>
00024 #include <landscapedef/LandscapeDefn.h>
00025 #include <weapons/AccessoryStore.h>
00026 #include <weapons/Shield.h>
00027 #include <weapons/WeaponMoveTank.h>
00028 #include <target/TargetContainer.h>
00029 #include <engine/ScorchedContext.h>
00030 #include <common/FixedVector.h>
00031 #include <common/OptionsScorched.h>
00032 #include <common/Defines.h>
00033 #include <tank/TankContainer.h>
00034 #include <tank/TankPosition.h>
00035 #include <tank/TankAccessories.h>
00036 #include <target/TargetShield.h>
00037 #include <target/TargetLife.h>
00038 #include <target/TargetSpace.h>
00039 #include <image/ImageFactory.h>
00040 #include <memory.h>
00041
00042 MovementMap::MovementMap(
00043 Tank *tank,
00044 ScorchedContext &context) :
00045 tank_(tank), context_(context)
00046 {
00047 arenaX_ = context_.getLandscapeMaps().getGroundMaps().getArenaX();
00048 arenaY_ = context_.getLandscapeMaps().getGroundMaps().getArenaY();
00049 arenaWidth_ = context_.getLandscapeMaps().getGroundMaps().getArenaWidth();
00050 arenaHeight_ = context_.getLandscapeMaps().getGroundMaps().getArenaHeight();
00051 landscapeWidth_ = context_.getLandscapeMaps().getGroundMaps().getLandscapeWidth();
00052 landscapeHeight_ = context_.getLandscapeMaps().getGroundMaps().getLandscapeHeight();
00053
00054
00055 entries_ = new MovementMapEntry[(landscapeWidth_ + 1) * (landscapeHeight_ + 1)];
00056 memset(entries_, (int) eNotInitialized, sizeof(MovementMapEntry) * (landscapeWidth_ + 1) * (landscapeHeight_ + 1));
00057
00058
00059 minHeight_ = getWaterHeight();
00060
00061
00062
00063 std::map<unsigned int, Target *>::iterator targetItor;
00064 std::map<unsigned int, Target *> &targets =
00065 context.getTargetContainer().getTargets();
00066 for (targetItor = targets.begin();
00067 targetItor != targets.end();
00068 targetItor++)
00069 {
00070 Target *target = (*targetItor).second;
00071 if (movementProof(context, target, tank))
00072 {
00073 checkTargets_.push_back(target);
00074 }
00075 }
00076 }
00077
00078 MovementMap::~MovementMap()
00079 {
00080 delete [] entries_;
00081 entries_ = 0;
00082 }
00083
00084 unsigned int MovementMap::POINT_TO_UINT(unsigned int x, unsigned int y)
00085 {
00086 return (x << 16) | (y & 0xffff);
00087 }
00088
00089 MovementMap::MovementMapEntry &MovementMap::getEntry(int w, int h)
00090 {
00091 if (w>=arenaX_ && h>=arenaY_ && w<=arenaX_ + arenaWidth_ && h<=arenaY_ + arenaHeight_)
00092 {
00093 MovementMapEntry &entry = entries_[(landscapeWidth_+1) * h + w];
00094 return entry;
00095 }
00096 static MovementMapEntry entry(eNoMovement, fixed(1000), 0, 0);
00097 entry.type = eNoMovement;
00098
00099 return entry;
00100 }
00101
00102 MovementMap::MovementMapEntry &MovementMap::getAndCheckEntry(int w, int h)
00103 {
00104 MovementMapEntry &entry = getEntry(w, h);
00105
00106
00107 if (entry.type == eNotInitialized)
00108 {
00109 fixed height =
00110 context_.getLandscapeMaps().getGroundMaps().getHeight(w, h);
00111 FixedVector position(w, h, height);
00112 entry.type = eNotSeen;
00113
00114
00115 if (height < minHeight_)
00116 {
00117 entry.type = eNoMovement;
00118 }
00119 else
00120 {
00121
00122 std::list<Target *>::iterator targetItor;
00123 for (targetItor = checkTargets_.begin();
00124 targetItor != checkTargets_.end();
00125 targetItor++)
00126 {
00127 Target *target = (*targetItor);
00128 if (inShield(target, tank_, position))
00129 {
00130 entry.type = eNoMovement;
00131 break;
00132 }
00133 }
00134 }
00135 }
00136 return entry;
00137 }
00138
00139 void MovementMap::addPoint(unsigned int x, unsigned int y,
00140 fixed height, fixed dist,
00141 std::list<unsigned int> &edgeList,
00142 unsigned int sourcePt,
00143 unsigned int epoc)
00144 {
00145
00146 if (x < (unsigned int) (arenaX_ + 5) ||
00147 y < (unsigned int) (arenaY_ + 5) ||
00148 x > (unsigned int) (arenaX_ + arenaWidth_ - 5) ||
00149 y > (unsigned int) (arenaY_ + arenaHeight_ - 5)) return;
00150
00151
00152
00153
00154 MovementMapEntry &priorEntry = getAndCheckEntry(x, y);
00155
00156 if (priorEntry.type == eNoMovement)
00157 {
00158 return;
00159 }
00160 if (priorEntry.type == eMovement &&
00161 priorEntry.epoc < epoc)
00162 {
00163 return;
00164 }
00165
00166
00167
00168 fixed newHeight = context_.getLandscapeMaps().getGroundMaps().getHeight(
00169 x, y);
00170
00171
00172 if (newHeight < minHeight_)
00173 {
00174 return;
00175 }
00176
00177
00178 fixed MaxTankClimbHeight = fixed(context_.getOptionsGame().
00179 getMaxClimbingDistance()) / fixed(10);
00180 if (newHeight - height > MaxTankClimbHeight)
00181 {
00182 return;
00183 }
00184
00185
00186 if (priorEntry.epoc == epoc)
00187 {
00188
00189 if (dist < priorEntry.dist)
00190 {
00191
00192 priorEntry = MovementMap::MovementMapEntry(
00193 MovementMap::eMovement,
00194 dist,
00195 sourcePt,
00196 epoc);
00197 }
00198 }
00199 else
00200 {
00201
00202 unsigned int pt = POINT_TO_UINT(x, y);
00203
00204
00205 edgeList.push_back(pt);
00206 priorEntry = MovementMap::MovementMapEntry(
00207 MovementMap::eMovement,
00208 dist,
00209 sourcePt,
00210 epoc);
00211 }
00212 }
00213
00214 bool MovementMap::movementProof(ScorchedContext &context, Target *target, Tank *tank)
00215 {
00216 if (!target->getAlive() ||
00217 !target->getShield().getCurrentShield()) return false;
00218
00219 Shield *shield = (Shield *)
00220 (target->getShield().getCurrentShield()->getAction());
00221
00222 bool movementProof = true;
00223 switch (shield->getMovementProof())
00224 {
00225 case Shield::ShieldMovementAll:
00226 movementProof = false;
00227 break;
00228 case Shield::ShieldMovementNone:
00229 movementProof = true;
00230 break;
00231 case Shield::ShieldMovementSame:
00232 if (target->getPlayerId() == tank->getPlayerId())
00233 {
00234 movementProof = false;
00235 }
00236 else if (context.getOptionsGame().getTeams() > 1 &&
00237 !target->isTarget())
00238 {
00239 Tank *targetTank = (Tank *) target;
00240 if (targetTank->getTeam() == tank->getTeam())
00241 {
00242 movementProof = false;
00243 }
00244 }
00245 break;
00246 case Shield::ShieldMovementTeam1:
00247 if (tank->getTeam() == 1 ||
00248 tank->getTeam() == 0) movementProof = false;
00249 break;
00250 case Shield::ShieldMovementTeam2:
00251 if (tank->getTeam() == 2 ||
00252 tank->getTeam() == 0) movementProof = false;
00253 break;
00254 case Shield::ShieldMovementTeam3:
00255 if (tank->getTeam() == 3 ||
00256 tank->getTeam() == 0) movementProof = false;
00257 break;
00258 case Shield::ShieldMovementTeam4:
00259 if (tank->getTeam() == 4 ||
00260 tank->getTeam() == 0) movementProof = false;
00261 break;
00262 }
00263 return movementProof;
00264 }
00265
00266 bool MovementMap::inShield(Target *target, Tank *tank, FixedVector &position)
00267 {
00268 Shield *shield = (Shield *)
00269 (target->getShield().getCurrentShield()->getAction());
00270
00271 FixedVector offset = position - target->getLife().getTargetPosition();
00272 offset[0] = offset[0].abs();
00273 offset[1] = offset[1].abs();
00274 offset[2] = fixed(0);
00275 FixedVector surround = offset.Normalize() * fixed(2);
00276 offset[0] = MAX(fixed(0), offset[0] - surround[0]);
00277 offset[1] = MAX(fixed(0), offset[1] - surround[1]);
00278
00279 return shield->inShield(offset);
00280 }
00281
00282 bool MovementMap::allowedPosition(ScorchedContext &context, Tank *tank, FixedVector &position)
00283 {
00284 std::map<unsigned int, Target *>::iterator targetItor;
00285 std::map<unsigned int, Target *> targets;
00286 context.getTargetSpace().getCollisionSet(position, fixed(1), targets);
00287 for (targetItor = targets.begin();
00288 targetItor != targets.end();
00289 targetItor++)
00290 {
00291 Target *target = (*targetItor).second;
00292
00293 if (movementProof(context, target, tank) &&
00294 inShield(target, tank, position))
00295 {
00296 return false;
00297 }
00298 }
00299 return true;
00300 }
00301
00302 fixed MovementMap::getWaterHeight()
00303 {
00304
00305 fixed waterHeight = (-10);
00306 if (context_.getOptionsGame().getMovementRestriction() ==
00307 OptionsGame::MovementRestrictionLand ||
00308 context_.getOptionsGame().getMovementRestriction() ==
00309 OptionsGame::MovementRestrictionLandOrAbove)
00310 {
00311 LandscapeTex &tex = *context_.getLandscapeMaps().getDefinitions().getTex();
00312 if (tex.border->getType() == LandscapeTexType::eWater)
00313 {
00314 LandscapeTexBorderWater *water =
00315 (LandscapeTexBorderWater *) tex.border;
00316
00317 waterHeight = water->height;
00318 }
00319 }
00320
00321 if (context_.getOptionsGame().getMovementRestriction() ==
00322 OptionsGame::MovementRestrictionLandOrAbove)
00323 {
00324 if (waterHeight > tank_->getPosition().getTankPosition()[2] - fixed(true, 1000))
00325 {
00326 waterHeight = tank_->getPosition().getTankPosition()[2] - fixed(true, 1000);
00327 }
00328 }
00329 return waterHeight;
00330 }
00331
00332 fixed MovementMap::getFuel(WeaponMoveTank *weapon)
00333 {
00334 fixed fuel = fixed(0);
00335 int numberFuel = tank_->getAccessories().getAccessoryCount(weapon->getParent());
00336 if (numberFuel == -1)
00337 {
00338 fuel = weapon->getMaximumRange();
00339 }
00340 else
00341 {
00342 fuel = MIN(weapon->getMaximumRange(), numberFuel);
00343 }
00344 return fuel;
00345 }
00346
00347 bool MovementMap::tankBurried()
00348 {
00349 fixed landscapeHeight = context_.getLandscapeMaps().getGroundMaps().getInterpHeight(
00350 tank_->getPosition().getTankPosition()[0],
00351 tank_->getPosition().getTankPosition()[1]);
00352 fixed tankHeight =
00353 tank_->getPosition().getTankPosition()[2];
00354 fixed MaxTankClimbHeight = fixed(context_.getOptionsGame().
00355 getMaxClimbingDistance()) / fixed(10);
00356 if (landscapeHeight > tankHeight + MaxTankClimbHeight)
00357 {
00358 return true;
00359 }
00360 return false;
00361 }
00362
00363 bool MovementMap::QueuePosition::operator<(const QueuePosition &rhs) const
00364 {
00365 return fixed(distance) > fixed(rhs.distance);
00366 }
00367
00368 fixed inline calcDistance(unsigned int pt, FixedVector &position)
00369 {
00370 unsigned int x = pt >> 16;
00371 unsigned int y = pt & 0xffff;
00372 FixedVector pos1((int) x, (int) y, 0);
00373 FixedVector pos2(position[0], position[1], 0);
00374 return (pos1-pos2).Magnitude();
00375 }
00376
00377 void MovementMap::addPoint(unsigned int x, unsigned int y,
00378 fixed height, fixed dist,
00379 std::priority_queue<QueuePosition,
00380 std::vector<QueuePosition>,
00381 std::less<QueuePosition> > &priorityQueue,
00382 unsigned int sourcePt,
00383 FixedVector &position)
00384 {
00385
00386 if (x < (unsigned int) (arenaX_ + 5) ||
00387 y < (unsigned int) (arenaY_ + 5) ||
00388 x > (unsigned int) (arenaX_ + arenaWidth_ - 5) ||
00389 y > (unsigned int) (arenaY_ + arenaHeight_ - 5)) return;
00390
00391
00392
00393 MovementMapEntry &priorEntry = getAndCheckEntry(x, y);
00394
00395 if (priorEntry.type == eNoMovement ||
00396 priorEntry.type == eMovement) return;
00397
00398
00399
00400 fixed newHeight = context_.getLandscapeMaps().getGroundMaps().getHeight(x, y);
00401
00402
00403 if (newHeight < minHeight_) return;
00404
00405
00406 fixed MaxTankClimbHeight = fixed(context_.getOptionsGame().
00407 getMaxClimbingDistance()) / fixed(10);
00408 if (newHeight - height > MaxTankClimbHeight) return;
00409
00410
00411 unsigned int pt = POINT_TO_UINT(x, y);
00412 QueuePosition queuePosition;
00413 queuePosition.square = pt;
00414 queuePosition.distance = calcDistance(pt, position) + dist;
00415 priorityQueue.push(queuePosition);
00416
00417
00418 priorEntry = MovementMap::MovementMapEntry(
00419 MovementMap::eMovement,
00420 dist,
00421 sourcePt,
00422 0);
00423 }
00424
00425 bool MovementMap::calculatePosition(FixedVector &position, fixed fuel)
00426 {
00427
00428 if (tankBurried()) return false;
00429
00430
00431 std::priority_queue<QueuePosition,
00432 std::vector<QueuePosition>,
00433 std::less<QueuePosition> > priorityQueue;
00434
00435
00436 unsigned int posX = (unsigned int)
00437 tank_->getPosition().getTankPosition()[0].asInt();
00438 unsigned int posY = (unsigned int)
00439 tank_->getPosition().getTankPosition()[1].asInt();
00440 unsigned int startPt = POINT_TO_UINT(posX, posY);
00441 unsigned int endPt = POINT_TO_UINT(
00442 (unsigned int)position[0].asInt(),
00443 (unsigned int)position[1].asInt());
00444
00445
00446 if (getAndCheckEntry(posX, posY).type == eNotSeen)
00447 {
00448
00449 getEntry(posX, posY) =
00450 MovementMap::MovementMapEntry(
00451 MovementMap::eMovement,
00452 fixed(0),
00453 0,
00454 0);
00455
00456
00457 QueuePosition queuePosition;
00458 queuePosition.square = startPt;
00459 queuePosition.distance = calcDistance(startPt, position);
00460 priorityQueue.push(queuePosition);
00461 }
00462
00463
00464 while (!priorityQueue.empty())
00465 {
00466 QueuePosition queuePosition = priorityQueue.top();
00467 priorityQueue.pop();
00468
00469 unsigned int pt = queuePosition.square;
00470 unsigned int x = pt >> 16;
00471 unsigned int y = pt & 0xffff;
00472
00473 if (pt == endPt) return true;
00474
00475 MovementMapEntry &priorEntry = getAndCheckEntry(x, y);
00476 fixed dist = priorEntry.dist;
00477 if (dist <= fuel)
00478 {
00479 fixed height =
00480 context_.getLandscapeMaps().getGroundMaps().getHeight(x, y);
00481
00482 addPoint(x+1, y, height, dist + 1, priorityQueue, pt, position);
00483 addPoint(x, y+1, height, dist + 1, priorityQueue, pt, position);
00484 addPoint(x-1, y, height, dist + 1, priorityQueue, pt, position);
00485 addPoint(x, y-1, height, dist + 1, priorityQueue, pt, position);
00486 addPoint(x+1, y+1, height, dist + fixed(true, 14000), priorityQueue, pt, position);
00487 addPoint(x-1, y+1, height, dist + fixed(true, 14000), priorityQueue, pt, position);
00488 addPoint(x-1, y-1, height, dist + fixed(true, 14000), priorityQueue, pt, position);
00489 addPoint(x+1, y-1, height, dist + fixed(true, 14000), priorityQueue, pt, position);
00490 }
00491 }
00492
00493 return false;
00494 }
00495
00496 void MovementMap::calculateAllPositions(fixed fuel)
00497 {
00498
00499 if (tankBurried()) return;
00500
00501 std::list<unsigned int> edgeList;
00502 unsigned int epoc = 0;
00503
00504
00505 unsigned int posX = (unsigned int)
00506 tank_->getPosition().getTankPosition()[0].asInt();
00507 unsigned int posY = (unsigned int)
00508 tank_->getPosition().getTankPosition()[1].asInt();
00509
00510
00511 if (getAndCheckEntry(posX, posY).type == eNotSeen)
00512 {
00513
00514 getEntry(posX, posY) =
00515 MovementMap::MovementMapEntry(
00516 MovementMap::eMovement,
00517 fixed(0),
00518 0,
00519 epoc);
00520
00521
00522 unsigned int pt = POINT_TO_UINT(posX, posY);
00523 edgeList.push_back(pt);
00524 }
00525
00526
00527 while (!edgeList.empty())
00528 {
00529 epoc++;
00530
00531 std::list<unsigned int> tmpEdgeList = edgeList;
00532 edgeList.clear();
00533
00534 std::list<unsigned int>::iterator edgeItor;
00535 for (edgeItor = tmpEdgeList.begin();
00536 edgeItor != tmpEdgeList.end();
00537 edgeItor++)
00538 {
00539 unsigned int pt = (*edgeItor);
00540 unsigned int x = pt >> 16;
00541 unsigned int y = pt & 0xffff;
00542
00543 MovementMapEntry &priorEntry = getAndCheckEntry(x, y);
00544 fixed dist = priorEntry.dist;
00545 if (dist <= fuel)
00546 {
00547 fixed height =
00548 context_.getLandscapeMaps().getGroundMaps().getHeight(x, y);
00549
00550 addPoint(x+1, y, height, dist + 1, edgeList, pt, epoc);
00551 addPoint(x, y+1, height, dist + 1, edgeList, pt, epoc);
00552 addPoint(x-1, y, height, dist + 1, edgeList, pt, epoc);
00553 addPoint(x, y-1, height, dist + 1, edgeList, pt, epoc);
00554 addPoint(x+1, y+1, height, dist + fixed(true, 14000), edgeList, pt, epoc);
00555 addPoint(x-1, y+1, height, dist + fixed(true, 14000), edgeList, pt, epoc);
00556 addPoint(x-1, y-1, height, dist + fixed(true, 14000), edgeList, pt, epoc);
00557 addPoint(x+1, y-1, height, dist + fixed(true, 14000), edgeList, pt, epoc);
00558 }
00559 }
00560 }
00561 }
00562
00563 #ifndef S3D_SERVER
00564 #include <landscape/Landscape.h>
00565 #include <client/ScorchedClient.h>
00566
00567 void MovementMap::movementTexture()
00568 {
00569 ImageHandle newMap = ImageFactory::createBlank(
00570 Landscape::instance()->getMainMap().getWidth(),
00571 Landscape::instance()->getMainMap().getHeight());
00572
00573 float landscapeWidth = (float)
00574 ScorchedClient::instance()->getLandscapeMaps().getGroundMaps().getLandscapeWidth();
00575 float landscpeHeight = (float)
00576 ScorchedClient::instance()->getLandscapeMaps().getGroundMaps().getLandscapeHeight();
00577
00578 GLubyte *src = Landscape::instance()->getMainMap().getBits();
00579 GLubyte *dest = newMap.getBits();
00580 for (int y=0; y<newMap.getHeight(); y++)
00581 {
00582 int y1 = y + 1;
00583 if (y1 == newMap.getHeight()) y1--;
00584
00585 int posY = int(float(y) / float(newMap.getHeight()) * landscpeHeight);
00586 int posY1 = int(float(y1) / float(newMap.getHeight()) * landscpeHeight);
00587 for (int x=0; x<newMap.getWidth(); x++)
00588 {
00589 int x1 = x + 1;
00590 if (x1 == newMap.getWidth()) x1--;
00591
00592 int posX = int(float(x) / float(newMap.getWidth()) * landscapeWidth);
00593 int posX1 = int(float(x1) / float(newMap.getWidth()) * landscapeWidth);
00594
00595 MovementMapEntryType type1 = getEntry(posX1, posY).type;
00596 MovementMapEntryType type2 = getEntry(posX, posY).type;
00597 MovementMapEntryType type3 = getEntry(posX, posY1).type;
00598
00599 if ((type1 == eMovement && type2 != eMovement) ||
00600 (type1 != eMovement && type2 == eMovement) ||
00601 (type3 == eMovement && type2 != eMovement) ||
00602 (type3 != eMovement && type2 == eMovement))
00603 {
00604 dest[0] = 255;
00605 dest[1] = 0;
00606 dest[2] = 0;
00607 }
00608 else if (type2 != eMovement)
00609 {
00610 dest[0] = src[0] / 4;
00611 dest[1] = src[1] / 4;
00612 dest[2] = src[2] / 4;
00613 }
00614 else
00615 {
00616 dest[0] = src[0];
00617 dest[1] = src[1];
00618 dest[2] = src[2];
00619 }
00620
00621 src+=3;
00622 dest+=3;
00623 }
00624 }
00625
00626 Landscape::instance()->getMainTexture().replace(newMap, false);
00627 Landscape::instance()->setTextureType(Landscape::eOther);
00628 }
00629
00630 void MovementMap::limitTexture(FixedVector ¢er, int limit)
00631 {
00632 ImageHandle newMap = ImageFactory::createBlank(
00633 Landscape::instance()->getMainMap().getWidth(),
00634 Landscape::instance()->getMainMap().getHeight());
00635
00636 float landscapeWidth = (float)
00637 ScorchedClient::instance()->getLandscapeMaps().getGroundMaps().getLandscapeWidth();
00638 float landscpeHeight = (float)
00639 ScorchedClient::instance()->getLandscapeMaps().getGroundMaps().getLandscapeHeight();
00640
00641 int arenaX =
00642 ScorchedClient::instance()->getLandscapeMaps().getGroundMaps().getArenaX();
00643 int arenaY =
00644 ScorchedClient::instance()->getLandscapeMaps().getGroundMaps().getArenaY();
00645 int arenaWidth =
00646 ScorchedClient::instance()->getLandscapeMaps().getGroundMaps().getArenaWidth();
00647 int arenaHeight =
00648 ScorchedClient::instance()->getLandscapeMaps().getGroundMaps().getArenaHeight();
00649
00650 GLubyte *src = Landscape::instance()->getMainMap().getBits();
00651 GLubyte *dest = newMap.getBits();
00652 for (int y=0; y<newMap.getHeight(); y++)
00653 {
00654 int y1 = y + 1;
00655 if (y1 == newMap.getHeight()) y1--;
00656
00657 int posY = int(float(y) / float(newMap.getHeight()) * landscpeHeight);
00658 int posY1 = int(float(y1) / float(newMap.getHeight()) * landscpeHeight);
00659 for (int x=0; x<newMap.getWidth(); x++)
00660 {
00661 int x1 = x + 1;
00662 if (x1 == newMap.getWidth()) x1--;
00663
00664 int posX = int(float(x) / float(newMap.getWidth()) * landscapeWidth);
00665 int posX1 = int(float(x1) / float(newMap.getWidth()) * landscapeWidth);
00666
00667 bool in1 = false;
00668 bool in2 = false;
00669 bool in3 = false;
00670 if (posX > arenaX &&
00671 posY > arenaY &&
00672 posX > arenaX + arenaWidth &&
00673 posY > arenaY + arenaHeight)
00674 {
00675 FixedVector position1(posX1, posY, 0);
00676 FixedVector position2(posX, posY, 0);
00677 FixedVector position3(posX, posY1, 0);
00678
00679 in1 = (position1 - center).Magnitude() < limit;
00680 in2 = (position2 - center).Magnitude() < limit;
00681 in3 = (position3 - center).Magnitude() < limit;
00682 }
00683
00684 if (in1 != in2 || in2 != in3)
00685 {
00686 dest[0] = 255;
00687 dest[1] = 0;
00688 dest[2] = 0;
00689 }
00690 else if (!in2)
00691 {
00692 dest[0] = src[0] / 4;
00693 dest[1] = src[1] / 4;
00694 dest[2] = src[2] / 4;
00695 }
00696 else
00697 {
00698 dest[0] = src[0];
00699 dest[1] = src[1];
00700 dest[2] = src[2];
00701 }
00702
00703 src+=3;
00704 dest+=3;
00705 }
00706 }
00707
00708 Landscape::instance()->getMainTexture().replace(newMap, false);
00709 Landscape::instance()->setTextureType(Landscape::eOther);
00710 }
00711
00712 #endif // #ifndef S3D_SERVER