ASYLUM: Cleanup polygon class
This commit is contained in:
parent
def09b8c20
commit
5b3efe8192
6 changed files with 71 additions and 99 deletions
|
@ -117,13 +117,13 @@ void Puzzle::exitPuzzle() {
|
||||||
// Hit test functions
|
// Hit test functions
|
||||||
//////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////
|
||||||
bool Puzzle::hitTest(const Common::Point *polygonPoint, Common::Point point, uint32 index) {
|
bool Puzzle::hitTest(const Common::Point *polygonPoint, Common::Point point, uint32 index) {
|
||||||
PolyDefinitions polygon(polygonPoint[index], polygonPoint[index + 1], polygonPoint[index + 2], polygonPoint[index + 3]);
|
Polygon polygon(polygonPoint[index], polygonPoint[index + 1], polygonPoint[index + 2], polygonPoint[index + 3]);
|
||||||
|
|
||||||
return polygon.contains(point);
|
return polygon.contains(point);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool Puzzle::hitTest(const Common::Point *polygonPoint, Common::Point point) {
|
bool Puzzle::hitTest(const Common::Point *polygonPoint, Common::Point point) {
|
||||||
PolyDefinitions polygon(polygonPoint[0], polygonPoint[1], polygonPoint[2], polygonPoint[3]);
|
Polygon polygon(polygonPoint[0], polygonPoint[1], polygonPoint[2], polygonPoint[3]);
|
||||||
|
|
||||||
return polygon.contains(point);
|
return polygon.contains(point);
|
||||||
}
|
}
|
||||||
|
|
|
@ -816,10 +816,10 @@ void Actor::faceTarget(uint32 target, DirectionFrom from) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
PolyDefinitions *polygon = &getScene()->polygons()->entries[getWorld()->actions[actionIndex]->polygonIndex];
|
Polygon polygon = getScene()->polygons()->get(getWorld()->actions[actionIndex]->polygonIndex);
|
||||||
|
|
||||||
point.x = polygon->boundingRect.left + (polygon->boundingRect.right - polygon->boundingRect.left) / 2;
|
point.x = polygon.boundingRect.left + (polygon.boundingRect.right - polygon.boundingRect.left) / 2;
|
||||||
point.y = polygon->boundingRect.top + (polygon->boundingRect.bottom - polygon->boundingRect.top) / 2;
|
point.y = polygon.boundingRect.top + (polygon.boundingRect.bottom - polygon.boundingRect.top) / 2;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
@ -1177,15 +1177,15 @@ void Actor::process_401830(int32 field980, int32 actionAreaId, int32 field978, i
|
||||||
field_984 = field984;
|
field_984 = field984;
|
||||||
field_988 = field988;
|
field_988 = field988;
|
||||||
} else {
|
} else {
|
||||||
PolyDefinitions *polygon = &getScene()->polygons()->entries[_actionIdx1];
|
Polygon polygon = getScene()->polygons()->get(_actionIdx1);
|
||||||
|
|
||||||
field_984 = polygon->points[0].x;
|
field_984 = polygon.points[0].x;
|
||||||
field_988 = polygon->points[0].y;
|
field_988 = polygon.points[0].y;
|
||||||
|
|
||||||
// Iterate through points
|
// Iterate through points
|
||||||
if (polygon->count() > 1) {
|
if (polygon.count() > 1) {
|
||||||
for (uint i = 1; i < polygon->count() - 1; i++) {
|
for (uint i = 1; i < polygon.count() - 1; i++) {
|
||||||
Common::Point point = polygon->points[i];
|
Common::Point point = polygon.points[i];
|
||||||
|
|
||||||
switch (field978) {
|
switch (field978) {
|
||||||
default:
|
default:
|
||||||
|
@ -1867,15 +1867,15 @@ void Actor::updateStatusEnabled() {
|
||||||
if (areaIndex != -1) {
|
if (areaIndex != -1) {
|
||||||
|
|
||||||
ActionArea *area = getWorld()->actions[areaIndex];
|
ActionArea *area = getWorld()->actions[areaIndex];
|
||||||
PolyDefinitions *poly = &getScene()->polygons()->entries[area->polygonIndex];
|
Polygon poly = getScene()->polygons()->get(area->polygonIndex);
|
||||||
|
|
||||||
Common::Point pt(poly->boundingRect.left + rnd(poly->boundingRect.width()),
|
Common::Point pt(poly.boundingRect.left + rnd(poly.boundingRect.width()),
|
||||||
poly->boundingRect.top + rnd(poly->boundingRect.height()));
|
poly.boundingRect.top + rnd(poly.boundingRect.height()));
|
||||||
|
|
||||||
if (!getSharedData()->actorUpdateEnabledCheck) {
|
if (!getSharedData()->actorUpdateEnabledCheck) {
|
||||||
if (!isInActionArea(pt, area)) {
|
if (!isInActionArea(pt, area)) {
|
||||||
Common::Point *polyPoint = &poly->points[rnd(poly->count())];
|
Common::Point polyPoint = poly.points[rnd(poly.count())];
|
||||||
processStatus(polyPoint->x, polyPoint->y, false);
|
processStatus(polyPoint.x, polyPoint.y, false);
|
||||||
} else {
|
} else {
|
||||||
processStatus(pt.x, pt.y, false);
|
processStatus(pt.x, pt.y, false);
|
||||||
}
|
}
|
||||||
|
@ -2699,7 +2699,7 @@ bool Actor::isInActionArea(const Common::Point &pt, ActionArea *area) {
|
||||||
if (found)
|
if (found)
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
PolyDefinitions poly = getScene()->polygons()->entries[area->polygonIndex];
|
Polygon poly = getScene()->polygons()->get(area->polygonIndex);
|
||||||
if (!poly.contains(pt))
|
if (!poly.contains(pt))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
|
|
|
@ -24,15 +24,10 @@
|
||||||
|
|
||||||
namespace Asylum {
|
namespace Asylum {
|
||||||
|
|
||||||
Polygons::Polygons(Common::SeekableReadStream *stream) : size(0), numEntries(0) {
|
//////////////////////////////////////////////////////////////////////////
|
||||||
load(stream);
|
// Contains
|
||||||
}
|
//////////////////////////////////////////////////////////////////////////
|
||||||
|
bool Polygon::contains(const Common::Point &point) {
|
||||||
Polygons::~Polygons() {
|
|
||||||
entries.clear();
|
|
||||||
}
|
|
||||||
|
|
||||||
bool PolyDefinitions::contains(int16 x, int16 y) {
|
|
||||||
// Copied from backends/vkeybd/polygon.cpp
|
// Copied from backends/vkeybd/polygon.cpp
|
||||||
bool yflag0;
|
bool yflag0;
|
||||||
bool yflag1;
|
bool yflag1;
|
||||||
|
@ -41,11 +36,11 @@ bool PolyDefinitions::contains(int16 x, int16 y) {
|
||||||
Common::Point *vtx0 = &points[count() - 1];
|
Common::Point *vtx0 = &points[count() - 1];
|
||||||
Common::Point *vtx1 = &points[0];
|
Common::Point *vtx1 = &points[0];
|
||||||
|
|
||||||
yflag0 = (vtx0->y >= y);
|
yflag0 = (vtx0->y >= point.y);
|
||||||
for (uint32 pt = 0; pt < count(); pt++, vtx1++) {
|
for (uint32 pt = 0; pt < count(); pt++, vtx1++) {
|
||||||
yflag1 = (vtx1->y >= y);
|
yflag1 = (vtx1->y >= point.y);
|
||||||
if (yflag0 != yflag1) {
|
if (yflag0 != yflag1) {
|
||||||
if (((vtx1->y - y) * (vtx0->x - vtx1->x) >= (vtx1->x - x) * (vtx0->y - vtx1->y)) == yflag1) {
|
if (((vtx1->y - point.y) * (vtx0->x - vtx1->x) >= (vtx1->x - point.x) * (vtx0->y - vtx1->y)) == yflag1) {
|
||||||
inside_flag = !inside_flag;
|
inside_flag = !inside_flag;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -56,12 +51,30 @@ bool PolyDefinitions::contains(int16 x, int16 y) {
|
||||||
return inside_flag;
|
return inside_flag;
|
||||||
}
|
}
|
||||||
|
|
||||||
void Polygons::load(Common::SeekableReadStream *stream) {
|
//////////////////////////////////////////////////////////////////////////
|
||||||
size = stream->readSint32LE();
|
// Polygons
|
||||||
numEntries = stream->readSint32LE();
|
//////////////////////////////////////////////////////////////////////////
|
||||||
|
Polygons::Polygons(Common::SeekableReadStream *stream) : _size(0), _numEntries(0) {
|
||||||
|
load(stream);
|
||||||
|
}
|
||||||
|
|
||||||
for (int32 g = 0; g < numEntries; g++) {
|
Polygons::~Polygons() {
|
||||||
PolyDefinitions poly;
|
_entries.clear();
|
||||||
|
}
|
||||||
|
|
||||||
|
Polygon Polygons::get(uint32 index) {
|
||||||
|
if (index >= _entries.size())
|
||||||
|
error("[Polygons::getEntry] Invalid polygon index (was: %d, max: %d)", index, _entries.size() - 1);
|
||||||
|
|
||||||
|
return _entries[index];
|
||||||
|
}
|
||||||
|
|
||||||
|
void Polygons::load(Common::SeekableReadStream *stream) {
|
||||||
|
_size = stream->readSint32LE();
|
||||||
|
_numEntries = stream->readSint32LE();
|
||||||
|
|
||||||
|
for (int32 g = 0; g < _numEntries; g++) {
|
||||||
|
Polygon poly;
|
||||||
|
|
||||||
uint32 numPoints = stream->readUint32LE();
|
uint32 numPoints = stream->readUint32LE();
|
||||||
|
|
||||||
|
@ -80,32 +93,8 @@ void Polygons::load(Common::SeekableReadStream *stream) {
|
||||||
poly.boundingRect.right = (int16)(stream->readSint32LE() & 0xFFFF);
|
poly.boundingRect.right = (int16)(stream->readSint32LE() & 0xFFFF);
|
||||||
poly.boundingRect.bottom = (int16)(stream->readSint32LE() & 0xFFFF);
|
poly.boundingRect.bottom = (int16)(stream->readSint32LE() & 0xFFFF);
|
||||||
|
|
||||||
entries.push_back(poly);
|
_entries.push_back(poly);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
//////////////////////////////////////////////////////////////////////////
|
|
||||||
// Contains
|
|
||||||
//////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
bool Polygons::contains(Common::Point *points, uint32 count, Common::Point point, Common::Rect *boundingRect) {
|
|
||||||
error("[Polygons::contains] Not implemented!");
|
|
||||||
}
|
|
||||||
|
|
||||||
bool Polygons::contains(int32 x1, int32 y1, int32 x2, int32 y2, int32 x3, int32 y3, int32 x4, int32 y4) {
|
|
||||||
return (compareDistance(x1, y1, x2, y2, x3, y3) * compareDistance(x1, y1, x2, y2, x4, y4)) <= 0
|
|
||||||
&& (compareDistance(x3, y3, x4, y4, x1, y1) * compareDistance(x3, y3, x4, y4, x2, y2) <= 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
int32 Polygons::compareDistance(int32 x1, int32 y1, int32 x2, int32 y2, int32 x3, int32 y3) {
|
|
||||||
uint32 d1 = (y3 - y1) * (x2 - x1);
|
|
||||||
uint32 d2 = (x3 - x1) * (y2 - y1);
|
|
||||||
|
|
||||||
return (d1 <= d2) ? -1 : 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool Polygons::containsRect(Common::Point *points, uint32 count, Common::Point point, Common::Rect *boundingRect) {
|
|
||||||
error("[Polygons::containsHelper] Not implemented!");
|
|
||||||
}
|
|
||||||
|
|
||||||
} // end of namespace Asylum
|
} // end of namespace Asylum
|
||||||
|
|
|
@ -31,55 +31,38 @@
|
||||||
|
|
||||||
namespace Asylum {
|
namespace Asylum {
|
||||||
|
|
||||||
typedef struct PolyDefinitions {
|
class Polygon {
|
||||||
|
public:
|
||||||
Common::Array<Common::Point> points;
|
Common::Array<Common::Point> points;
|
||||||
Common::Rect boundingRect;
|
Common::Rect boundingRect;
|
||||||
|
|
||||||
PolyDefinitions() {};
|
Polygon() {};
|
||||||
PolyDefinitions(Common::Point point1, Common::Point point2, Common::Point point3, Common::Point point4) {
|
Polygon(Common::Point point1, Common::Point point2, Common::Point point3, Common::Point point4) {
|
||||||
points.push_back(point1);
|
points.push_back(point1);
|
||||||
points.push_back(point2);
|
points.push_back(point2);
|
||||||
points.push_back(point3);
|
points.push_back(point3);
|
||||||
points.push_back(point4);
|
points.push_back(point4);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
bool contains(const Common::Point &point);
|
||||||
* Check if the x/y coordinates exist within
|
uint32 count() { return points.size(); }
|
||||||
* the current polygon definition
|
};
|
||||||
*
|
|
||||||
* (was pointInPoly())
|
|
||||||
*/
|
|
||||||
bool contains(int16 x, int16 y);
|
|
||||||
|
|
||||||
bool contains(Common::Point point) {
|
|
||||||
return contains(point.x, point.y);
|
|
||||||
}
|
|
||||||
|
|
||||||
uint32 count() {
|
|
||||||
return points.size();
|
|
||||||
}
|
|
||||||
|
|
||||||
} PolyDefinitions;
|
|
||||||
|
|
||||||
class Polygons {
|
class Polygons {
|
||||||
public:
|
public:
|
||||||
Polygons(Common::SeekableReadStream *stream);
|
Polygons(Common::SeekableReadStream *stream);
|
||||||
virtual ~Polygons();
|
virtual ~Polygons();
|
||||||
|
|
||||||
int32 size;
|
Polygon get(uint32 index);
|
||||||
int32 numEntries; // TODO remove and use entries.size()
|
uint32 size() { return _entries.size(); }
|
||||||
|
|
||||||
Common::Array<PolyDefinitions> entries;
|
|
||||||
|
|
||||||
static bool contains(Common::Point *points, uint32 count, Common::Point point, Common::Rect *boundingRect);
|
|
||||||
static bool contains(int32 x1, int32 y1, int32 x2, int32 y2, int32 x3, int32 y3, int32 x4, int32 y4);
|
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
int32 _size;
|
||||||
|
int32 _numEntries;
|
||||||
|
|
||||||
|
Common::Array<Polygon> _entries;
|
||||||
|
|
||||||
void load(Common::SeekableReadStream *stream);
|
void load(Common::SeekableReadStream *stream);
|
||||||
|
|
||||||
static int32 compareDistance(int32 x1, int32 y1, int32 x2, int32 y2, int32 x3, int32 y3);
|
|
||||||
static bool containsRect(Common::Point *points, uint32 count, Common::Point point, Common::Rect *boundingRect);
|
|
||||||
|
|
||||||
}; // end of class Polygons
|
}; // end of class Polygons
|
||||||
|
|
||||||
} // end of namespace Asylum
|
} // end of namespace Asylum
|
||||||
|
|
|
@ -2158,7 +2158,7 @@ int32 Scene::findActionArea(ActionAreaType type, const Common::Point pt) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!found && _polygons->entries[area->polygonIndex].contains(pt))
|
if (!found && _polygons->get(area->polygonIndex).contains(pt))
|
||||||
return i;
|
return i;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
@ -2189,7 +2189,7 @@ int32 Scene::findActionArea(ActionAreaType type, const Common::Point pt) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!found && _polygons->entries[area->polygonIndex].contains(pt))
|
if (!found && _polygons->get(area->polygonIndex).contains(pt))
|
||||||
return i;
|
return i;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
@ -2482,8 +2482,8 @@ void Scene::processUpdateList() {
|
||||||
if (object->flags & kObjectFlag2) {
|
if (object->flags & kObjectFlag2) {
|
||||||
isMasked = !pointIntersectsRect(sum, *object->getRect());
|
isMasked = !pointIntersectsRect(sum, *object->getRect());
|
||||||
} else if (object->flags & kObjectFlag40) {
|
} else if (object->flags & kObjectFlag40) {
|
||||||
PolyDefinitions *poly = &_polygons->entries[object->getPolygonIndex()];
|
Polygon poly = _polygons->get(object->getPolygonIndex());
|
||||||
isMasked = poly->contains(sum);
|
isMasked = poly.contains(sum);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Adjust object flags
|
// Adjust object flags
|
||||||
|
@ -2650,7 +2650,7 @@ void Scene::debugScreenScrolling() {
|
||||||
}
|
}
|
||||||
|
|
||||||
// WALK REGION DEBUG
|
// WALK REGION DEBUG
|
||||||
void Scene::debugShowWalkRegion(PolyDefinitions *poly) {
|
void Scene::debugShowWalkRegion(Polygon *poly) {
|
||||||
Graphics::Surface surface;
|
Graphics::Surface surface;
|
||||||
surface.create(poly->boundingRect.right - poly->boundingRect.left + 1,
|
surface.create(poly->boundingRect.right - poly->boundingRect.left + 1,
|
||||||
poly->boundingRect.bottom - poly->boundingRect.top + 1,
|
poly->boundingRect.bottom - poly->boundingRect.top + 1,
|
||||||
|
@ -2675,9 +2675,9 @@ void Scene::debugShowPolygons() {
|
||||||
if (!_polygons)
|
if (!_polygons)
|
||||||
error("[Scene::debugShowPolygons] Polygons not initialized properly!");
|
error("[Scene::debugShowPolygons] Polygons not initialized properly!");
|
||||||
|
|
||||||
for (int32 p = 0; p < _polygons->numEntries; p++) {
|
for (uint32 p = 0; p < _polygons->size(); p++) {
|
||||||
Graphics::Surface surface;
|
Graphics::Surface surface;
|
||||||
PolyDefinitions poly = _polygons->entries[p];
|
Polygon poly = _polygons->get(p);
|
||||||
surface.create(poly.boundingRect.right - poly.boundingRect.left + 1,
|
surface.create(poly.boundingRect.right - poly.boundingRect.left + 1,
|
||||||
poly.boundingRect.bottom - poly.boundingRect.top + 1,
|
poly.boundingRect.bottom - poly.boundingRect.top + 1,
|
||||||
Graphics::PixelFormat::createFormatCLUT8());
|
Graphics::PixelFormat::createFormatCLUT8());
|
||||||
|
|
|
@ -42,6 +42,7 @@ class Puzzle;
|
||||||
class Cursor;
|
class Cursor;
|
||||||
class GraphicResource;
|
class GraphicResource;
|
||||||
class Polygons;
|
class Polygons;
|
||||||
|
class Polygon;
|
||||||
class ResourcePack;
|
class ResourcePack;
|
||||||
class SceneTitle;
|
class SceneTitle;
|
||||||
class Screen;
|
class Screen;
|
||||||
|
@ -56,7 +57,6 @@ struct ActionArea;
|
||||||
struct AmbientSoundItem;
|
struct AmbientSoundItem;
|
||||||
struct GraphicFrame;
|
struct GraphicFrame;
|
||||||
struct ObjectItem;
|
struct ObjectItem;
|
||||||
struct PolyDefinitions;
|
|
||||||
|
|
||||||
enum HitType {
|
enum HitType {
|
||||||
kHitNone = -1,
|
kHitNone = -1,
|
||||||
|
@ -467,7 +467,7 @@ private:
|
||||||
void debugShowPolygons();
|
void debugShowPolygons();
|
||||||
void debugShowSceneRects();
|
void debugShowSceneRects();
|
||||||
void debugScreenScrolling();
|
void debugScreenScrolling();
|
||||||
void debugShowWalkRegion(PolyDefinitions *poly);
|
void debugShowWalkRegion(Polygon *poly);
|
||||||
|
|
||||||
friend class SceneTitle;
|
friend class SceneTitle;
|
||||||
};
|
};
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue