Package com.aldaviva.autorpg.game

Source Code of com.aldaviva.autorpg.game.QuestManager

package com.aldaviva.autorpg.game;

import java.util.HashSet;
import java.util.List;

import org.apache.commons.math.stat.descriptive.SummaryStatistics;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.dao.EmptyResultDataAccessException;
import org.springframework.stereotype.Component;
import org.springframework.transaction.annotation.Transactional;

import com.aldaviva.autorpg.AutoRPGException.NotEnoughPlayersError;
import com.aldaviva.autorpg.Utils;
import com.aldaviva.autorpg.data.entities.Character;
import com.aldaviva.autorpg.data.entities.Item;
import com.aldaviva.autorpg.data.entities.Quest;
import com.aldaviva.autorpg.display.bulletin.Bulletin;
import com.aldaviva.autorpg.display.bulletin.BulletinManager;
import com.aldaviva.autorpg.display.bulletin.Message;

@Component
public class QuestManager implements PeriodicUpdater {

  private static final Logger LOGGER = LoggerFactory.getLogger(QuestManager.class);
 
  @Autowired
  private BulletinManager bulletinManager;
 
  @Autowired
  private CharacterItemManager characterItemManager;
 
  @Transactional
  public Quest start(){
    try {
      Quest quest = Quest.findRandomByInactive();
   
      List<Character> characters = Character.findRandomByOnline(Quest.CHARACTERS_PER_QUEST);
      quest.setCharacters(new HashSet<Character>(characters));
      for(Character character : quest.getCharacters()){
        character.setQuest(quest);
      }
      quest.setExpRemaining(quest.getExpTotal());
      quest.setStep(1);
      stepReached(quest);
     
      bulletinManager.publish(stepReached(quest));
     
      quest.merge();
     
      return quest;
    } catch (NotEnoughPlayersError e) {
      return null;
    } catch (EmptyResultDataAccessException e){
      return null;
    }
  }
 
  @Transactional
  public void update(){
    List<Quest> quests = Quest.findByActive();
    for(Quest quest : quests){
      updateQuest(quest);
      quest.merge();
    }
  }
 
  private void updateQuest(Quest quest){
    int onlineCharacters = quest.countOnlineCharacters();
    if(onlineCharacters == 0){
      remove(quest);
      bulletinManager.publish(new Bulletin("Every character in this quest is offline. Quest over."));
    } else {
      int experienceDelta = (onlineCharacters * onlineCharacters);
      quest.setExpRemaining(quest.getExpRemaining() - experienceDelta);
     
      int step = quest.calculateCurrentStep();
      if(quest.getStep() != step){
        quest.setStep(step);
        bulletinManager.publish(stepReached(quest));
      }
    }
  }
 
  private Bulletin stepReached(Quest quest){
    Bulletin result = new Bulletin();
   
    LOGGER.debug("quest reached step "+quest.getStep());
   
    switch(quest.getStep()){
      case 1: //just starting the quest
        result.add(new Message.QuestHasCharacters(quest));
        result.add(quest.getMission());
        result.add(quest.getStep1());
        break;
      case 2:
        result.add(quest.getStep1done());
        result.add(quest.getStep2());
        break;
      case 3:
        result.add(quest.getStep2done());
        result.add(quest.getStep3());
        break;
      case 4: //done
        result.add(quest.getStep3done());
        giveReward(quest);
        remove(quest);
        break;
      default:
        throw new IllegalStateException("Quest state is not in the range [1, 4].");
    }
   
    return result;
  }
 
  private Bulletin giveReward(Quest quest){
    Bulletin bulletin;
    LOGGER.debug("Giving rewards for quest completion");
   
    switch(quest.getReward()){
      case EXPERIENCE:
        SummaryStatistics stats = new SummaryStatistics();
        for(Character character : quest.getCharacters()){
          stats.addValue(character.getExperience());
        }
       
        double avgTeamExperience = stats.getMean();
        int reward = (int) Math.round(avgTeamExperience * ((double)Utils.getRandomInt(10, 25)/100));
       
        for(Character character : quest.getCharacters()){
          character.setExperience(character.getExperience() + reward);
        }
        bulletin = new Bulletin(new Message.CharactersAllGainExperience(quest.getCharacters(), reward));
        break;
       
      case RARE_ITEM:
        bulletin = new Bulletin(new Message.CharactersFoundItems(quest.getCharacters()));
        for(Character character : quest.getCharacters()){
          Item newItem = Item.findRandomByRarity(true);
          characterItemManager.offerCharacterAnItem(newItem, character);
          bulletin.add(new Message.CharacterFoundItem(character, newItem));
        }
        break;
       
      default:
        throw new IllegalStateException("Quest reward must be EXPERIENCE or RARE_ITEM.");
    }
    return bulletin;
  }
 
  private void remove(Quest quest){
    quest.getCharacters().clear();
    quest.setStep(0);
    quest.merge();
  }
 
}
TOP

Related Classes of com.aldaviva.autorpg.game.QuestManager

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.