2424import POGOProtos .Networking .Requests .Messages .NicknamePokemonMessageOuterClass .NicknamePokemonMessage ;
2525import POGOProtos .Networking .Requests .Messages .ReleasePokemonMessageOuterClass .ReleasePokemonMessage ;
2626import POGOProtos .Networking .Requests .Messages .SetFavoritePokemonMessageOuterClass .SetFavoritePokemonMessage ;
27- import POGOProtos .Networking .Requests .Messages .UpgradePokemonMessageOuterClass ;
2827import POGOProtos .Networking .Requests .Messages .UpgradePokemonMessageOuterClass .UpgradePokemonMessage ;
28+ import POGOProtos .Networking .Requests .Messages .UseItemPotionMessageOuterClass ;
29+ import POGOProtos .Networking .Requests .Messages .UseItemReviveMessageOuterClass ;
2930import POGOProtos .Networking .Requests .RequestTypeOuterClass .RequestType ;
3031import POGOProtos .Networking .Responses .EvolvePokemonResponseOuterClass .EvolvePokemonResponse ;
3132import POGOProtos .Networking .Responses .NicknamePokemonResponseOuterClass .NicknamePokemonResponse ;
33+ import POGOProtos .Networking .Responses .RecycleInventoryItemResponseOuterClass ;
3234import POGOProtos .Networking .Responses .ReleasePokemonResponseOuterClass .ReleasePokemonResponse ;
3335import POGOProtos .Networking .Responses .ReleasePokemonResponseOuterClass .ReleasePokemonResponse .Result ;
3436import POGOProtos .Networking .Responses .SetFavoritePokemonResponseOuterClass .SetFavoritePokemonResponse ;
35- import POGOProtos .Networking .Responses .UpgradePokemonResponseOuterClass ;
3637import POGOProtos .Networking .Responses .UpgradePokemonResponseOuterClass .UpgradePokemonResponse ;
38+ import POGOProtos .Networking .Responses .UseItemPotionResponseOuterClass ;
39+ import POGOProtos .Networking .Responses .UseItemReviveResponseOuterClass ;
3740import com .google .protobuf .InvalidProtocolBufferException ;
3841import com .pokegoapi .api .PokemonGo ;
42+ import com .pokegoapi .api .inventory .Item ;
3943import com .pokegoapi .api .map .pokemon .EvolutionResult ;
4044import com .pokegoapi .exceptions .LoginFailedException ;
4145import com .pokegoapi .exceptions .RemoteServerException ;
4246import com .pokegoapi .main .ServerRequest ;
4347import com .pokegoapi .util .Log ;
48+ import lombok .Getter ;
4449import lombok .Setter ;
4550
4651/**
@@ -52,13 +57,17 @@ public class Pokemon {
5257 private final PokemonGo pgo ;
5358 private PokemonData proto ;
5459 private PokemonMeta meta ;
60+ @ Getter
61+ @ Setter
62+ private int stamina ;
5563
5664 // API METHODS //
5765
5866 // DELEGATE METHODS BELOW //
5967 public Pokemon (PokemonGo api , PokemonData proto ) {
6068 this .pgo = api ;
6169 this .proto = proto ;
70+ this .stamina = proto .getStamina ();
6271 }
6372
6473 /**
@@ -124,14 +133,14 @@ public NicknamePokemonResponse.Result renamePokemon(String nickname)
124133 }
125134
126135 /**
127- * Function to mark the pokemon as favorite or not.
128- *
129- * @param markFavorite Mark Pokemon as Favorite?
130- * @return the SetFavoritePokemonResponse.Result
131- * @throws LoginFailedException the login failed exception
132- * @throws RemoteServerException the remote server exception
133- */
134- public SetFavoritePokemonResponse .Result setFavoritePokemon (boolean markFavorite )
136+ * Function to mark the pokemon as favorite or not.
137+ *
138+ * @param markFavorite Mark Pokemon as Favorite?
139+ * @return the SetFavoritePokemonResponse.Result
140+ * @throws LoginFailedException the login failed exception
141+ * @throws RemoteServerException the remote server exception
142+ */
143+ public SetFavoritePokemonResponse .Result setFavoritePokemon (boolean markFavorite )
135144 throws LoginFailedException , RemoteServerException {
136145 SetFavoritePokemonMessage reqMsg = SetFavoritePokemonMessage .newBuilder ()
137146 .setPokemonId (getId ())
@@ -250,10 +259,6 @@ public int getCp() {
250259 return proto .getCp ();
251260 }
252261
253- public int getStamina () {
254- return proto .getStamina ();
255- }
256-
257262 public int getMaxStamina () {
258263 return proto .getStaminaMax ();
259264 }
@@ -305,9 +310,10 @@ public int getIndividualDefense() {
305310 public int getIndividualStamina () {
306311 return proto .getIndividualStamina ();
307312 }
308-
313+
309314 /**
310315 * Calculates the pokemons IV ratio.
316+ *
311317 * @return the pokemons IV ratio as a double between 0 and 1.0, 1.0 being perfect IVs
312318 */
313319 public double getIvRatio () {
@@ -387,4 +393,138 @@ public double getBaseFleeRate() {
387393 public PokemonIdOuterClass .PokemonId getParent () {
388394 return getMeta ().getParentId ();
389395 }
396+
397+ /**
398+ * Check if pokemon its injured but not fainted. need potions to heal
399+ *
400+ * @return true if pokemon is injured
401+ */
402+ public boolean isInjured () {
403+ return !isFainted () && getStamina () < getMaxStamina ();
404+ }
405+
406+ /**
407+ * check if a pokemon it's died (fainted). need a revive to resurrect
408+ *
409+ * @return true if a pokemon is fainted
410+ */
411+ public boolean isFainted () {
412+ return getStamina () == 0 ;
413+ }
414+
415+ /**
416+ * Heal a pokemon, using various fallbacks for potions
417+ *
418+ * @return Result, ERROR_CANNOT_USE if the requirements arent met
419+ */
420+ public UseItemPotionResponseOuterClass .UseItemPotionResponse .Result heal ()
421+ throws LoginFailedException , RemoteServerException {
422+
423+ if (!isInjured ())
424+ return UseItemPotionResponseOuterClass .UseItemPotionResponse .Result .ERROR_CANNOT_USE ;
425+
426+ if (pgo .getInventories ().getItemBag ().getItem (ItemId .ITEM_POTION ).getCount () > 0 )
427+ return usePotion (ItemId .ITEM_POTION );
428+
429+ if (pgo .getInventories ().getItemBag ().getItem (ItemId .ITEM_SUPER_POTION ).getCount () > 0 )
430+ return usePotion (ItemId .ITEM_SUPER_POTION );
431+
432+ if (pgo .getInventories ().getItemBag ().getItem (ItemId .ITEM_HYPER_POTION ).getCount () > 0 )
433+ return usePotion (ItemId .ITEM_HYPER_POTION );
434+
435+ if (pgo .getInventories ().getItemBag ().getItem (ItemId .ITEM_MAX_POTION ).getCount () > 0 )
436+ return usePotion (ItemId .ITEM_MAX_POTION );
437+
438+ return UseItemPotionResponseOuterClass .UseItemPotionResponse .Result .ERROR_CANNOT_USE ;
439+ }
440+
441+ /**
442+ * use a potion on that pokemon. Will check if there is enough potions & if the pokemon need
443+ * to be healed.
444+ *
445+ * @return Result, ERROR_CANNOT_USE if the requirements arent met
446+ */
447+ public UseItemPotionResponseOuterClass .UseItemPotionResponse .Result usePotion (ItemId itemId )
448+ throws LoginFailedException , RemoteServerException {
449+
450+ Item potion = pgo .getInventories ().getItemBag ().getItem (itemId );
451+ //some sanity check, to prevent wrong use of this call
452+ if (!potion .isPotion () || potion .getCount () < 1 || !isInjured ())
453+ return UseItemPotionResponseOuterClass .UseItemPotionResponse .Result .ERROR_CANNOT_USE ;
454+
455+ UseItemPotionMessageOuterClass .UseItemPotionMessage reqMsg = UseItemPotionMessageOuterClass .UseItemPotionMessage
456+ .newBuilder ()
457+ .setItemId (itemId )
458+ .setPokemonId (getId ())
459+ .build ();
460+
461+ ServerRequest serverRequest = new ServerRequest (RequestType .USE_ITEM_POTION , reqMsg );
462+ pgo .getRequestHandler ().sendServerRequests (serverRequest );
463+
464+ UseItemPotionResponseOuterClass .UseItemPotionResponse response ;
465+ try {
466+ response = UseItemPotionResponseOuterClass .UseItemPotionResponse .parseFrom (serverRequest .getData ());
467+ if (response .getResult () == UseItemPotionResponseOuterClass .UseItemPotionResponse .Result .SUCCESS ) {
468+ setStamina (response .getStamina ());
469+ }
470+ return response .getResult ();
471+ } catch (InvalidProtocolBufferException e ) {
472+ throw new RemoteServerException (e );
473+ }
474+ }
475+
476+ /**
477+ * Revive a pokemon, using various fallbacks for revive items
478+ *
479+ * @return Result, ERROR_CANNOT_USE if the requirements arent met
480+ */
481+ public UseItemReviveResponseOuterClass .UseItemReviveResponse .Result revive ()
482+ throws LoginFailedException , RemoteServerException {
483+
484+ if (!isFainted ())
485+ return UseItemReviveResponseOuterClass .UseItemReviveResponse .Result .ERROR_CANNOT_USE ;
486+
487+ if (pgo .getInventories ().getItemBag ().getItem (ItemId .ITEM_REVIVE ).getCount () > 0 )
488+ return useRevive (ItemId .ITEM_REVIVE );
489+
490+ if (pgo .getInventories ().getItemBag ().getItem (ItemId .ITEM_MAX_REVIVE ).getCount () > 0 )
491+ return useRevive (ItemId .ITEM_MAX_REVIVE );
492+
493+ return UseItemReviveResponseOuterClass .UseItemReviveResponse .Result .ERROR_CANNOT_USE ;
494+ }
495+
496+ /**
497+ * Use a revive item on the pokemon. Will check if there is enough revive & if the pokemon need
498+ * to be revived.
499+ *
500+ * @return Result, ERROR_CANNOT_USE if the requirements arent met
501+ */
502+ public UseItemReviveResponseOuterClass .UseItemReviveResponse .Result useRevive (ItemId itemId )
503+ throws LoginFailedException , RemoteServerException {
504+
505+ Item item = pgo .getInventories ().getItemBag ().getItem (itemId );
506+ if (!item .isRevive () || item .getCount () < 1 || !isFainted ())
507+ return UseItemReviveResponseOuterClass .UseItemReviveResponse .Result .ERROR_CANNOT_USE ;
508+
509+ UseItemReviveMessageOuterClass .UseItemReviveMessage reqMsg = UseItemReviveMessageOuterClass .UseItemReviveMessage
510+ .newBuilder ()
511+ .setItemId (itemId )
512+ .setPokemonId (getId ())
513+ .build ();
514+
515+ ServerRequest serverRequest = new ServerRequest (RequestType .USE_ITEM_REVIVE , reqMsg );
516+ pgo .getRequestHandler ().sendServerRequests (serverRequest );
517+
518+ UseItemReviveResponseOuterClass .UseItemReviveResponse response ;
519+ try {
520+ response = UseItemReviveResponseOuterClass .UseItemReviveResponse .parseFrom (serverRequest .getData ());
521+ if (response .getResult () == UseItemReviveResponseOuterClass .UseItemReviveResponse .Result .SUCCESS ) {
522+ setStamina (response .getStamina ());
523+ }
524+ return response .getResult ();
525+ } catch (InvalidProtocolBufferException e ) {
526+ throw new RemoteServerException (e );
527+ }
528+ }
529+
390530}
0 commit comments