3730 |
} |
} |
3731 |
} |
} |
3732 |
|
|
3733 |
|
|
3734 |
|
//---------------------------------------- |
3735 |
|
// Turnstile |
3736 |
|
//---------------------------------------- |
3737 |
|
namespace |
3738 |
|
{ |
3739 |
|
class Turnstile_Pivot : public Stone { |
3740 |
|
CLONEOBJ(Turnstile_Pivot); |
3741 |
|
|
3742 |
|
DirectionBits arms_present(); |
3743 |
|
bool no_stone (int xoff, int yoff); |
3744 |
|
void remove_arms (DirectionBits arms); |
3745 |
|
void set_arm (Direction dir); |
3746 |
|
public: |
3747 |
|
Turnstile_Pivot() : Stone ("st-turnstile") {} |
3748 |
|
bool rotate_left(); |
3749 |
|
bool rotate_right(); |
3750 |
|
}; |
3751 |
|
|
3752 |
|
class Turnstile_Arm : public Stone { |
3753 |
|
virtual Direction get_dir() const = 0; |
3754 |
|
|
3755 |
|
void actor_hit(const StoneContact &sc); |
3756 |
|
|
3757 |
|
Turnstile_Pivot *get_pivot() |
3758 |
|
{ |
3759 |
|
Stone *st = GetStone (move (get_pos(), reverse(get_dir()))); |
3760 |
|
return dynamic_cast<Turnstile_Pivot*>(st); |
3761 |
|
} |
3762 |
|
protected: |
3763 |
|
Turnstile_Arm (const char *kind) : Stone(kind) |
3764 |
|
{} |
3765 |
|
|
3766 |
|
}; |
3767 |
|
|
3768 |
|
class Turnstile_N : public Turnstile_Arm { |
3769 |
|
CLONEOBJ(Turnstile_N); |
3770 |
|
public: |
3771 |
|
Turnstile_N(): Turnstile_Arm("st-turnstile-n") {} |
3772 |
|
Direction get_dir () const { return NORTH; } |
3773 |
|
}; |
3774 |
|
|
3775 |
|
class Turnstile_S : public Turnstile_Arm { |
3776 |
|
CLONEOBJ(Turnstile_S); |
3777 |
|
Direction get_dir () const { return SOUTH; } |
3778 |
|
public: |
3779 |
|
Turnstile_S(): Turnstile_Arm("st-turnstile-s") {} |
3780 |
|
}; |
3781 |
|
|
3782 |
|
class Turnstile_E : public Turnstile_Arm { |
3783 |
|
CLONEOBJ(Turnstile_E); |
3784 |
|
Direction get_dir () const { return EAST; } |
3785 |
|
public: |
3786 |
|
Turnstile_E(): Turnstile_Arm("st-turnstile-e") {} |
3787 |
|
}; |
3788 |
|
|
3789 |
|
class Turnstile_W : public Turnstile_Arm { |
3790 |
|
CLONEOBJ(Turnstile_W); |
3791 |
|
Direction get_dir () const { return WEST; } |
3792 |
|
public: |
3793 |
|
Turnstile_W(): Turnstile_Arm("st-turnstile-w") {} |
3794 |
|
}; |
3795 |
|
|
3796 |
|
} |
3797 |
|
|
3798 |
|
void |
3799 |
|
Turnstile_Arm::actor_hit(const StoneContact &sc) |
3800 |
|
{ |
3801 |
|
Turnstile_Pivot *pivot = get_pivot(); |
3802 |
|
|
3803 |
|
enum Action { ROTL, ROTR, NOTHING }; |
3804 |
|
static Action actions[4][4] = { |
3805 |
|
{ NOTHING, ROTL, NOTHING, ROTR }, // west arm |
3806 |
|
{ ROTR, NOTHING, ROTL, NOTHING }, // south arm |
3807 |
|
{ NOTHING, ROTR, NOTHING, ROTL }, // east arm |
3808 |
|
{ ROTL, NOTHING, ROTR, NOTHING } // north arm |
3809 |
|
}; |
3810 |
|
|
3811 |
|
ActorInfo *ai = sc.actor->get_actorinfo(); |
3812 |
|
Direction dir = reverse(contact_face(sc)); |
3813 |
|
if (dir!=enigma::NODIR && ai->vel * sc.normal < -4) |
3814 |
|
{ |
3815 |
|
if (pivot) { |
3816 |
|
Action a = actions[get_dir()][dir]; |
3817 |
|
GridPos pos = move(get_pos(), dir); |
3818 |
|
V2 destpos (pos.x + 0.5, pos.y + 0.5); |
3819 |
|
if (a == ROTL) { |
3820 |
|
if (pivot->rotate_left ()) |
3821 |
|
world::WarpActor (sc.actor, destpos[0], destpos[1]); |
3822 |
|
} |
3823 |
|
else if (a == ROTR) { |
3824 |
|
if (pivot->rotate_right ()) |
3825 |
|
world::WarpActor (sc.actor, destpos[0], destpos[1]); |
3826 |
|
} |
3827 |
|
} |
3828 |
|
else { |
3829 |
|
// Move arms not attached to a pivot individually |
3830 |
|
MaybeMoveStone(get_pos(), dir); |
3831 |
|
} |
3832 |
|
} |
3833 |
|
} |
3834 |
|
|
3835 |
|
|
3836 |
|
DirectionBits |
3837 |
|
Turnstile_Pivot::arms_present() |
3838 |
|
{ |
3839 |
|
DirectionBits arms = NODIRBIT; |
3840 |
|
GridPos p = get_pos(); |
3841 |
|
if (dynamic_cast<Turnstile_N*>(GetStone(move(p, NORTH)))) |
3842 |
|
px::set_flags (arms, NORTHBIT); |
3843 |
|
if (dynamic_cast<Turnstile_S*>(GetStone(move(p, SOUTH)))) |
3844 |
|
px::set_flags (arms, SOUTHBIT); |
3845 |
|
if (dynamic_cast<Turnstile_E*>(GetStone(move(p, EAST)))) |
3846 |
|
px::set_flags (arms, EASTBIT); |
3847 |
|
if (dynamic_cast<Turnstile_W*>(GetStone(move(p, WEST)))) |
3848 |
|
px::set_flags (arms, WESTBIT); |
3849 |
|
return arms; |
3850 |
|
} |
3851 |
|
|
3852 |
|
bool |
3853 |
|
Turnstile_Pivot::no_stone (int xoff, int yoff) |
3854 |
|
{ |
3855 |
|
GridPos p = get_pos(); |
3856 |
|
p.x += xoff; |
3857 |
|
p.y += yoff; |
3858 |
|
return (0 == GetStone(p)); |
3859 |
|
} |
3860 |
|
|
3861 |
|
void |
3862 |
|
Turnstile_Pivot::remove_arms (DirectionBits arms) |
3863 |
|
{ |
3864 |
|
GridPos p = get_pos(); |
3865 |
|
if (arms & NORTHBIT) KillStone (move (p, NORTH)); |
3866 |
|
if (arms & EASTBIT) KillStone (move (p, EAST)); |
3867 |
|
if (arms & SOUTHBIT) KillStone (move (p, SOUTH)); |
3868 |
|
if (arms & WESTBIT) KillStone (move (p, WEST)); |
3869 |
|
} |
3870 |
|
|
3871 |
|
void |
3872 |
|
Turnstile_Pivot::set_arm (Direction dir) |
3873 |
|
{ |
3874 |
|
char *names[4] = { "st-turnstile-w", |
3875 |
|
"st-turnstile-s", |
3876 |
|
"st-turnstile-e", |
3877 |
|
"st-turnstile-n" }; |
3878 |
|
Stone *st = MakeStone(names[dir]); |
3879 |
|
SetStone (move(get_pos(), dir), st); |
3880 |
|
} |
3881 |
|
|
3882 |
|
bool |
3883 |
|
Turnstile_Pivot::rotate_left() |
3884 |
|
{ |
3885 |
|
cout << "rotating left\n"; |
3886 |
|
DirectionBits arms = arms_present(); |
3887 |
|
bool can_rotate = true; |
3888 |
|
|
3889 |
|
if (arms & NORTHBIT) { |
3890 |
|
can_rotate &= no_stone(-1,-1); |
3891 |
|
if (! (arms & WESTBIT)) |
3892 |
|
can_rotate &= no_stone(-1,0); |
3893 |
|
} |
3894 |
|
if (arms & WESTBIT) { |
3895 |
|
can_rotate &= no_stone(-1,+1); |
3896 |
|
if (! (arms & SOUTHBIT)) |
3897 |
|
can_rotate &= no_stone(0,+1); |
3898 |
|
} |
3899 |
|
if (arms & SOUTHBIT) { |
3900 |
|
can_rotate &= no_stone(+1,+1); |
3901 |
|
if (! (arms & EASTBIT)) |
3902 |
|
can_rotate &= no_stone(+1,0); |
3903 |
|
} |
3904 |
|
if (arms & EASTBIT) { |
3905 |
|
can_rotate &= no_stone(+1,-1); |
3906 |
|
if (! (arms & NORTHBIT)) |
3907 |
|
can_rotate &= no_stone(0,-1); |
3908 |
|
} |
3909 |
|
|
3910 |
|
if (can_rotate) { |
3911 |
|
play_sound("rotate-left"); |
3912 |
|
remove_arms(arms); |
3913 |
|
if (arms & NORTHBIT) set_arm (WEST); |
3914 |
|
if (arms & EASTBIT) set_arm (NORTH); |
3915 |
|
if (arms & SOUTHBIT) set_arm (EAST); |
3916 |
|
if (arms & WESTBIT) set_arm (SOUTH); |
3917 |
|
} |
3918 |
|
return can_rotate; |
3919 |
|
} |
3920 |
|
|
3921 |
|
bool |
3922 |
|
Turnstile_Pivot::rotate_right() |
3923 |
|
{ |
3924 |
|
cout << "rotating right\n"; |
3925 |
|
DirectionBits arms = arms_present(); |
3926 |
|
bool can_rotate = true; |
3927 |
|
|
3928 |
|
if (arms & NORTHBIT) { |
3929 |
|
can_rotate &= no_stone(+1,-1); |
3930 |
|
if (! (arms & EASTBIT)) |
3931 |
|
can_rotate &= no_stone(+1,0); |
3932 |
|
} |
3933 |
|
if (arms & WESTBIT) { |
3934 |
|
can_rotate &= no_stone(-1,-1); |
3935 |
|
if (! (arms & NORTHBIT)) |
3936 |
|
can_rotate &= no_stone(0,-1); |
3937 |
|
} |
3938 |
|
if (arms & SOUTHBIT) { |
3939 |
|
can_rotate &= no_stone(-1,+1); |
3940 |
|
if (! (arms & WESTBIT)) |
3941 |
|
can_rotate &= no_stone(-1,0); |
3942 |
|
} |
3943 |
|
if (arms & EASTBIT) { |
3944 |
|
can_rotate &= no_stone(+1,+1); |
3945 |
|
if (! (arms & SOUTHBIT)) |
3946 |
|
can_rotate &= no_stone(0,+1); |
3947 |
|
} |
3948 |
|
|
3949 |
|
if (can_rotate) { |
3950 |
|
play_sound("rotate-right"); |
3951 |
|
remove_arms(arms); |
3952 |
|
if (arms & NORTHBIT) set_arm (EAST); |
3953 |
|
if (arms & EASTBIT) set_arm (SOUTH); |
3954 |
|
if (arms & SOUTHBIT) set_arm (WEST); |
3955 |
|
if (arms & WESTBIT) set_arm (NORTH); |
3956 |
|
} |
3957 |
|
return can_rotate; |
3958 |
|
} |
3959 |
|
|
3960 |
|
|
3961 |
//---------------------------------------------------------------------- |
//---------------------------------------------------------------------- |
3962 |
// OBJECT REPOSITORY |
// OBJECT REPOSITORY |
3963 |
//---------------------------------------------------------------------- |
//---------------------------------------------------------------------- |
4005 |
add_templ("fl-gradient13", new Gradient(22)); |
add_templ("fl-gradient13", new Gradient(22)); |
4006 |
add_templ("fl-gradient14", new Gradient(21)); |
add_templ("fl-gradient14", new Gradient(21)); |
4007 |
add_templ("fl-gradient15", new Gradient(24)); |
add_templ("fl-gradient15", new Gradient(24)); |
4008 |
add_templ("fl-gradient16", new Gradient(13)); |
add_templ("fl-gradient16", new Gradient(23)); |
4009 |
|
|
4010 |
// Stones |
// Stones |
4011 |
add_templ(new BlackStone); |
add_templ(new BlackStone); |
4059 |
add_templ(new ScissorsStone); |
add_templ(new ScissorsStone); |
4060 |
add_templ(new ThiefStone); |
add_templ(new ThiefStone); |
4061 |
add_templ(new TimerStone); |
add_templ(new TimerStone); |
4062 |
|
|
4063 |
|
add_templ (new Turnstile_Pivot); |
4064 |
|
add_templ (new Turnstile_N); |
4065 |
|
add_templ (new Turnstile_S); |
4066 |
|
add_templ (new Turnstile_E); |
4067 |
|
add_templ (new Turnstile_W); |
4068 |
|
|
4069 |
add_templ(new WhiteStone); |
add_templ(new WhiteStone); |
4070 |
add_templ(new WhiteStone2); |
add_templ(new WhiteStone2); |
4071 |
add_templ(new WhiteStone3); |
add_templ(new WhiteStone3); |