Skip to content

Commit

Permalink
Merge pull request #40 from RnDome/filters
Browse files Browse the repository at this point in the history
Adds filters

Closes #22
  • Loading branch information
kpp committed Jun 3, 2017
2 parents 31cea82 + 82cfe59 commit 8de7bdd
Show file tree
Hide file tree
Showing 8 changed files with 109 additions and 25 deletions.
29 changes: 14 additions & 15 deletions example/Dll.c
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,13 @@ void onEnd(AIModule* module, bool isWinner) {
Game_sendText(Broodwar, "Game ended");
}

bool isMineralField(Unit* unit) {
int type_id = Unit_getType(unit).id;
return type_id == 176 // Resource_Mineral_Field
|| type_id == 177 // Resource_Mineral_Field_Type_2
|| type_id == 178; // Resource_Mineral_Field_Type_3
}

void onFrame(AIModule* self) {
const int frame_count = Game_getFrameCount(Broodwar);
CoordinateType CoordinateType_None = { .id = 0 };
Expand All @@ -45,6 +52,9 @@ void onFrame(AIModule* self) {
Unit* const unit = (Unit*) Iterator_get(units);
assert(unit);

if ( !Unit_exists(unit) )
continue;

const UnitType type = Unit_getType(unit);

switch (type.id) {
Expand All @@ -55,22 +65,10 @@ void onFrame(AIModule* self) {
if (Unit_isCarryingGas(unit) || Unit_isCarryingMinerals(unit)) {
Unit_returnCargo(unit, false);
} else {
Iterator* const minerals = (Iterator*) Game_getMinerals(Broodwar);
assert(minerals);

Unit* closest_mineral = NULL;
for (; Iterator_valid(minerals); Iterator_next(minerals)) {
Unit* const mineral = (Unit*) Iterator_get(minerals);
assert(mineral);

if (!closest_mineral || Unit_getDistance_Unit(unit, mineral) < Unit_getDistance_Unit(unit, closest_mineral))
closest_mineral = mineral;
}
Unit* const closest_mineral = Unit_getClosestUnit(unit, &isMineralField, /*radius*/ 999999);

if (closest_mineral)
Unit_rightClick_Unit(unit, closest_mineral, false);

Iterator_release(minerals);
}
}
break;
Expand Down Expand Up @@ -132,8 +130,9 @@ static AIModule_vtable module_vtable = {
onUnitComplete
};

__declspec(dllexport) void gameInit(BWAPI_Game* BroodwarPtr) {
Broodwar = (Game*) BroodwarPtr;
__declspec(dllexport) void gameInit(BWAPI_Game* game) {
Broodwar = (Game*) game;
BWAPIC_setBroodwarPtr(Broodwar);
}
__declspec(dllexport) BWAPI_AIModule* newAIModule() {
ExampleAIModule* const module = (ExampleAIModule*) malloc( sizeof(ExampleAIModule) );
Expand Down
16 changes: 10 additions & 6 deletions include/Game.h
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,10 @@
extern "C" {
#endif

/// Pass pointer from gameInit to initialize BWAPI::BroodwarPtr
void BWAPIC_setBroodwarPtr(Game* game);
Game* BWAPIC_getBroodwarPtr();

ForceIterator* Game_getForces(Game* self);
PlayerIterator* Game_getPlayers(Game* self);
UnitIterator* Game_getAllUnits(Game* self);
Expand Down Expand Up @@ -39,12 +43,12 @@ void Game_setScreenPosition(Game* self, Position p);
void Game_pingMinimap(Game* self, Position p);
bool Game_isFlagEnabled(Game* self, int flag);
void Game_enableFlag(Game* self, int flag);
// TODO Unitset getUnitsOnTile(BWAPI::TilePosition tile, const UnitFilter &pred);
// TODO Unitset getUnitsInRectangle(BWAPI::Position topLeft, BWAPI::Position bottomRight, const UnitFilter &pred);
// TODO Unitset getUnitsInRadius(BWAPI::Position center, int radius, const UnitFilter &pred);
// TODO Unit getClosestUnit(Position center, const UnitFilter &pred, int radius = 999999);
// TODO Unit getClosestUnitInRectangle(Position center, const UnitFilter &pred, int left, int top, int right = 999999, int bottom = 999999);
// TODO Unit getBestUnit(const BestUnitFilter &best, const UnitFilter &pred, Position center = Positions::Origin, int radius = 999999);
UnitIterator* Game_getUnitsOnTile(Game* self, TilePosition tile, UnaryUnitFilter pred);
UnitIterator* Game_getUnitsInRectangle(Game* self, Position topLeft, Position bottomRight, UnaryUnitFilter pred);
UnitIterator* Game_getUnitsInRadius(Game* self, Position center, int radius, UnaryUnitFilter pred);
Unit* Game_getClosestUnit(Game* self, Position center, UnaryUnitFilter pred, int radius);
Unit* Game_getClosestUnitInRectangle(Game* self, Position center, UnaryUnitFilter pred, int left, int top, int right, int bottom);
Unit* Game_getBestUnit(Game* self, BestUnitFilter best, UnaryUnitFilter pred, Position center, int radius);

Error Game_getLastError(Game* self);
bool Game_setLastError(Game* self, Error e);
Expand Down
2 changes: 1 addition & 1 deletion include/Region.h
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ int Region_getBoundsBottom(Region* self);
Region* Region_getClosestAccessibleRegion(Region* self);
Region* Region_getClosestInaccessibleRegion(Region* self);
int Region_getDistance(Region* self, Region* other);
//TODO Unitset getUnits(const UnitFilter &pred = nullptr) const;
UnitIterator* Region_getUnits(Region* self, UnaryUnitFilter pred);

#ifdef __cplusplus
} // extern "C"
Expand Down
10 changes: 10 additions & 0 deletions include/Types.h
Original file line number Diff line number Diff line change
Expand Up @@ -61,6 +61,16 @@ typedef struct ForceIterator_ ForceIterator;
typedef struct BulletIterator_ BulletIterator;
typedef struct RegionIterator_ RegionIterator;

// Filter types. Implement filters on your own

// A unit is passed into this filter
// The filter should return true if the unit satisfies all conditions
typedef bool (*UnaryUnitFilter)(Unit* unit);

// Two units are passed into this filter
// The filter should return the best of them
typedef Unit* (*BestUnitFilter)(Unit* left, Unit* right);

#ifdef __cplusplus
} // extern "C"
#endif
6 changes: 3 additions & 3 deletions include/Unit.h
Original file line number Diff line number Diff line change
Expand Up @@ -93,9 +93,9 @@ Unit* Unit_getCarrier(Unit* self);
UnitIterator* Unit_getInterceptors(Unit* self);
Unit* Unit_getHatchery(Unit* self);
UnitIterator* Unit_getLarva(Unit* self);
// TODO Unitset getUnitsInRadius(int radius, const UnitFilter &pred)
// TODO Unitset getUnitsInWeaponRange(WeaponType weapon, const UnitFilter &pred)
// TODO Unit* getClosestUnit(const UnitFilter &pred, int radius)
UnitIterator* Unit_getUnitsInRadius(Unit* self, int radius, UnaryUnitFilter pred);
UnitIterator* Unit_getUnitsInWeaponRange(Unit* self, WeaponType weapon, UnaryUnitFilter pred);
Unit* Unit_getClosestUnit(Unit* self, UnaryUnitFilter pred, int radius);
bool Unit_hasNuke(Unit* self);
bool Unit_isAccelerating(Unit* self);
bool Unit_isAttacking(Unit* self);
Expand Down
45 changes: 45 additions & 0 deletions src/Game.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,14 @@
#include "CoordinateType.hpp"
#include "IteratorImpl.hpp"

void BWAPIC_setBroodwarPtr(Game* game) {
BWAPI::BroodwarPtr = reinterpret_cast<BWAPI::Game*>(game);
}

Game* BWAPIC_getBroodwarPtr() {
return reinterpret_cast<Game*>(BWAPI::BroodwarPtr);
}

ForceIterator* Game_getForces(Game* self) {
const auto& forces = reinterpret_cast<BWAPI::Game*>(self)->getForces();
return as_iter<ForceIterator>(forces);
Expand Down Expand Up @@ -144,6 +152,43 @@ void Game_enableFlag(Game* self, int flag) {
reinterpret_cast<BWAPI::Game*>(self)->enableFlag(flag);
}

UnitIterator* Game_getUnitsOnTile(Game* self, TilePosition tile, UnaryUnitFilter pred) {
auto pred_filter = reinterpret_cast<bool (*)(BWAPI::Unit)>(pred);
auto&& units = reinterpret_cast<BWAPI::Game*>(self)->getUnitsOnTile(tileposition_to_bw(tile), pred_filter);
return into_iter<UnitIterator>(std::move(units));
}

UnitIterator* Game_getUnitsInRectangle(Game* self, Position topLeft, Position bottomRight, UnaryUnitFilter pred) {
auto pred_filter = reinterpret_cast<bool (*)(BWAPI::Unit)>(pred);
auto&& units = reinterpret_cast<BWAPI::Game*>(self)->getUnitsInRectangle(position_to_bw(topLeft), position_to_bw(bottomRight), pred_filter);
return into_iter<UnitIterator>(std::move(units));
}

UnitIterator* Game_getUnitsInRadius(Game* self, Position center, int radius, UnaryUnitFilter pred) {
auto pred_filter = reinterpret_cast<bool (*)(BWAPI::Unit)>(pred);
auto&& units = reinterpret_cast<BWAPI::Game*>(self)->getUnitsInRadius(position_to_bw(center), radius, pred_filter);
return into_iter<UnitIterator>(std::move(units));
}

Unit* Game_getClosestUnit(Game* self, Position center, UnaryUnitFilter pred, int radius) {
auto pred_filter = reinterpret_cast<bool (*)(BWAPI::Unit)>(pred);
auto unit = reinterpret_cast<BWAPI::Game*>(self)->getClosestUnit(position_to_bw(center), pred_filter, radius);
return reinterpret_cast<Unit*>(unit);
}

Unit* Game_getClosestUnitInRectangle(Game* self, Position center, UnaryUnitFilter pred, int left, int top, int right, int bottom) {
auto pred_filter = reinterpret_cast<bool (*)(BWAPI::Unit)>(pred);
auto unit = reinterpret_cast<BWAPI::Game*>(self)->getClosestUnitInRectangle(position_to_bw(center), pred_filter, left, top, right, bottom);
return reinterpret_cast<Unit*>(unit);
}

Unit* Game_getBestUnit(Game* self, BestUnitFilter best, UnaryUnitFilter pred, Position center, int radius) {
auto best_filter = reinterpret_cast<BWAPI::Unit (*)(BWAPI::Unit, BWAPI::Unit)>(best);
auto pred_filter = reinterpret_cast<bool (*)(BWAPI::Unit)>(pred);
auto unit = reinterpret_cast<BWAPI::Game*>(self)->getBestUnit(best_filter, pred_filter, position_to_bw(center), radius);
return reinterpret_cast<Unit*>(unit);
}

Error Game_getLastError(Game* self) {
return error_from_bw( reinterpret_cast<BWAPI::Game*>(self)->getLastError() );
}
Expand Down
7 changes: 7 additions & 0 deletions src/Region.cpp
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
#include <Region.h>
#include <BWAPI/Region.h>
#include <BWAPI/Regionset.h>
#include <BWAPI/Unitset.h>

#include "Position.hpp"
#include "IteratorImpl.hpp"
Expand Down Expand Up @@ -61,3 +62,9 @@ Region* Region_getClosestInaccessibleRegion(Region* self) {
int Region_getDistance(Region* self, Region* other) {
return reinterpret_cast<BWAPI::Region>(self)->getDistance(reinterpret_cast<BWAPI::Region>(other));
}

UnitIterator* Region_getUnits(Region* self, UnaryUnitFilter pred) {
auto pred_filter = reinterpret_cast<bool (*)(BWAPI::Unit)>(pred);
auto&& units = reinterpret_cast<BWAPI::Region>(self)->getUnits(pred_filter);
return into_iter<UnitIterator>(std::move(units));
}
19 changes: 19 additions & 0 deletions src/Unit.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
#include "Order.hpp"
#include "TechType.hpp"
#include "UpgradeType.hpp"
#include "WeaponType.hpp"
#include "UnitType.hpp"
#include "UnitCommand.hpp"
#include "IteratorImpl.hpp"
Expand Down Expand Up @@ -321,6 +322,24 @@ UnitIterator* Unit_getLarva(Unit* self) {
return into_iter<UnitIterator>(std::move(larva));
}

UnitIterator* Unit_getUnitsInRadius(Unit* self, int radius, UnaryUnitFilter pred) {
auto pred_filter = reinterpret_cast<bool (*)(BWAPI::Unit)>(pred);
auto&& units = reinterpret_cast<BWAPI::Unit>(self)->getUnitsInRadius(radius, pred_filter);
return into_iter<UnitIterator>(std::move(units));
}

UnitIterator* Unit_getUnitsInWeaponRange(Unit* self, WeaponType weapon, UnaryUnitFilter pred) {
auto pred_filter = reinterpret_cast<bool (*)(BWAPI::Unit)>(pred);
auto&& units = reinterpret_cast<BWAPI::Unit>(self)->getUnitsInWeaponRange(weapontype_to_bw(weapon), pred_filter);
return into_iter<UnitIterator>(std::move(units));
}

Unit* Unit_getClosestUnit(Unit* self, UnaryUnitFilter pred, int radius) {
auto pred_filter = reinterpret_cast<bool (*)(BWAPI::Unit)>(pred);
auto unit = reinterpret_cast<BWAPI::Unit>(self)->getClosestUnit(pred_filter, radius);
return reinterpret_cast<Unit*>(unit);
}

bool Unit_hasNuke(Unit* self) {
return reinterpret_cast<BWAPI::Unit>(self)->hasNuke();
}
Expand Down

0 comments on commit 8de7bdd

Please sign in to comment.