00001 // SuperTux 00002 // Copyright (C) 2009 Ingo Ruhnke <grumbel@gmx.de> 00003 // 00004 // This program is free software: you can redistribute it and/or modify 00005 // it under the terms of the GNU General Public License as published by 00006 // the Free Software Foundation, either version 3 of the License, or 00007 // (at your option) any later version. 00008 // 00009 // This program is distributed in the hope that it will be useful, 00010 // but WITHOUT ANY WARRANTY; without even the implied warranty of 00011 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00012 // GNU General Public License for more details. 00013 // 00014 // You should have received a copy of the GNU General Public License 00015 // along with this program. If not, see <http://www.gnu.org/licenses/>. 00016 00017 #include "object/brick.hpp" 00018 00019 #include "audio/sound_manager.hpp" 00020 #include "badguy/badguy.hpp" 00021 #include "object/flower.hpp" 00022 #include "object/bouncy_coin.hpp" 00023 #include "object/player.hpp" 00024 #include "object/portable.hpp" 00025 #include "sprite/sprite_manager.hpp" 00026 #include "supertux/constants.hpp" 00027 #include "supertux/sector.hpp" 00028 00029 Brick::Brick(const Vector& pos, int data) 00030 : Block(sprite_manager->create("images/objects/bonus_block/brick.sprite")), breakable(false), 00031 coin_counter(0) 00032 { 00033 bbox.set_pos(pos); 00034 if(data == 1) 00035 coin_counter = 5; 00036 else 00037 breakable = true; 00038 } 00039 00040 void 00041 Brick::hit(Player& player) 00042 { 00043 if(sprite->get_action() == "empty") 00044 return; 00045 00046 try_break(&player); 00047 } 00048 00049 HitResponse 00050 Brick::collision(GameObject& other, const CollisionHit& hit){ 00051 00052 Player* player = dynamic_cast<Player*> (&other); 00053 if (player) { 00054 if (player->does_buttjump) try_break(); 00055 } 00056 00057 BadGuy* badguy = dynamic_cast<BadGuy*> (&other); 00058 if(badguy) { 00059 // hit contains no information for collisions with blocks. 00060 // Badguy's bottom has to be below the top of the brick 00061 // SHIFT_DELTA is required to slide over one tile gaps. 00062 if( badguy->can_break() && ( badguy->get_bbox().get_bottom() > get_bbox().get_top() + SHIFT_DELTA ) ){ 00063 try_break(); 00064 } 00065 } 00066 Portable* portable = dynamic_cast<Portable*> (&other); 00067 if(portable) { 00068 MovingObject* moving = dynamic_cast<MovingObject*> (&other); 00069 if(moving->get_bbox().get_top() > get_bbox().get_bottom() - SHIFT_DELTA) { 00070 try_break(); 00071 } 00072 } 00073 return Block::collision(other, hit); 00074 } 00075 00076 void 00077 Brick::try_break(Player* player) 00078 { 00079 if(sprite->get_action() == "empty") 00080 return; 00081 00082 sound_manager->play("sounds/brick.wav"); 00083 Sector* sector = Sector::current(); 00084 Player& player_one = *(sector->player); 00085 if(coin_counter > 0) { 00086 sector->add_object(new BouncyCoin(get_pos(),true)); 00087 coin_counter--; 00088 player_one.get_status()->add_coins(1); 00089 if(coin_counter == 0) 00090 sprite->set_action("empty"); 00091 start_bounce(player); 00092 } else if(breakable) { 00093 if(player){ 00094 if(player->is_big()){ 00095 start_break(player); 00096 return; 00097 } else { 00098 start_bounce(player); 00099 return; 00100 } 00101 } 00102 break_me(); 00103 } 00104 } 00105 00106 //IMPLEMENT_FACTORY(Brick, "brick"); 00107 00108 /* EOF */