////////////////////////////////////// /// Shop FFC Item with Yes/No Menu /// /// By: ZoriaRPG /// /// 26-June-2016 /// /// v0.5.5 /// /////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// /// D0 : The item ID (number) to give Link. /// /// D1 : The price of the item. /// /// D2 : The item info message (high) and the OPTIONAL alternate counter (low). /// /// --> Integer Portion (#####.xxxx) THe message to display for Item Info menu option. /// /// --> Decimal Portion (xxxxx.####) An alternate counter, instead of the default (CR_RUPEES), if desired. /// /// D3 : Alternate combo to use, if you want a generic combo for shop items. /// /// D4 : Sound to play if purchase is a success. /// /// D5 : If set to '1', Link holds the item up with one hand. If set to '2', he holds it up with two hands. /// /// Set to '0' for no item hold-up animation. /// /// D6 : This value is split between the integer portion,a nd the decimal. the decimal portion is only used for optional shop capabilities. /// /// --> Integer Portion ( #####.xxxx ) Set to '1' to sell only one time. /// /// If set to '1', a 'sold out' sign will take the place of this item when it sells. /// /// If set ABOVE 1, a REPLACEMENT item with this ID will take the place of the item when it sells. /// /// --> Decimal Portion ( xxxxx.#### ) If you wish to set a different place for a REPLACEMENT ITEM, enter it here. /// /// D7 : The Nth item in this shop. Set each in sequence, starting at '1', and ending at '9' (max) or whatever the number of items is that /// /// you have in this shop. /// /// --> Example: If a shop with three items, number one of them '1', another '2', and the last '3'. /// /////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// /// Requested By: JudasRising, with additional features requested by Dimentio, and Grayswandir. /// /////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// //General Settings const int SHOP_REGISTER = 6; //Screen->D used for shop items. //Combos and Tiles const int TILE_SOLD_SIGN = 22913; //The sold ign, if using the sell-out feature. const int SHOP_SIGNS_CHANGE_WHEN_ALL_ITEMS_SOLD = 0; //If this is set to '1', then signs will chane again if none of the itms are available to buy any longer. const int TILE_SHOP_CLOSED_FOREVER = 0; //Set to a combo of your choice if all the items are sold out, forever. //The small button icon that appears next to an item, to allow link to know he can interact with it. //THe tile should have a graphic that occupies the upper-rightmost 8x8pixels, as a 'minitile'. const int SHOP_BUY_BUTTON_TILE = 44162; //Tile of the 'R' button, or whatever button you use to activate the 'buy' menu. const int SHOP_BUY_BUTTON_TILE_CSET = 2; const int SHOP_BUY_BUTTON_TILE_OPACITY = 128; const int SHOP_BUY_BUTTON_TILE_LAYER = 2; const int SHOP_BUY_BUTTON_TILE_X_OFFSET = 9; const int SHOP_BUY_BUTTON_TILE_Y_OFFSET = - 8; const int SHOP_BUY_BUTTON_TILE_BLOCKW = 1; const int SHOP_BUY_BUTTON_TILE_BLOCKH = 1; //Rupee Icon Tile (next to price) const int SHOP_TILE_RUPEE_ICON = 0; //Tile of the rupee icon to put by the price. //! The script will only draw this if it is npt set to '0'. const int SHOP_TILE_RUPEE_ICON_LAYER = 2; const int SHOP_TILE_RUPEE_ICON_BLOCKW = 0; const int SHOP_TILE_RUPEE_ICON_BLOCKH = 0; const int SHOP_TILE_RUPEE_ICON_CSET = 0; const int SHOP_TILE_RUPEE_ICON_X_OFFSET = 4; //Position of the rupee icon offsets. const int SHOP_TILE_RUPEE_ICON_Y_OFFSET = 15; const int SHOP_TILE_RUPEE_ICON_XSCALE = 50; //Scaling factor of the tile in percent. const int SHOP_TILE_RUPEE_ICON_YSCALE = 50; //Scaling factor of the tile in percent. const int SHOP_TILE_RUPEE_ICON_OPACITY = 128; //Text Settings for shop prices const int SHOP_PRICE_FONT = 2; const int SHOP_PRICE_COLOUR_FOREGROUND = 0x0F; //Black const int SHOP_PRICE_COLOUR_BACKGROUND = 0x01; //WHite const int SHOP_PRICE_TEXT_LAYER = 2; const int SHOP_PRICE_TEXT_X_OFFSET_FOREGROUND = 12; const int SHOP_PRICE_TEXT_X_OFFSET_BACKGROUND = 13; const int SHOP_PRICE_TEXT_Y_OFFSET_FOREGROUND = 13; const int SHOP_PRICE_TEXT_Y_OFFSET_BACKGROUND = 14; const int SHOP_PRICE_SIZE = 0; //Size-scale factor. //The 'x' between the rupee icon and the price. const int SHOP_PRICE_DRAW_X_SIGN = 1; //Set to 1 to draw the 'x' between the rupee icon, and the text; 0 to disqable. const int SHOP_PRICE_DRAW_X_SIGN_LAYER = 2; const int SHOP_PRICE_DRAW_X_SIGN_COLOUR_FOREGROUND = 0x0F; //Black const int SHOP_PRICE_DRAW_X_SIGN_COLOUR_BACKGROUND = 0x01; //White const int SHOP_PRICE_DRAW_X_SIGN_SIZE = 0; const int SHOP_PRICE_DRAW_X_SIGN_X_OFFSET_FOREGROUND = 8; const int SHOP_PRICE_DRAW_X_SIGN_Y_OFFSET_FOREGROUND = 9; const int SHOP_PRICE_DRAW_X_SIGN_X_OFFSET_BACKGROUND = 13; const int SHOP_PRICE_DRAW_X_SIGN_Y_OFFSET_BACKGROUND = 14; const int SHOP_PRICE_DRAW_X_SIGN_FONT = 1; //Button Settings: THe shop will activate the menu / Link will take the item based on a button press. //Set any button that you wish to permit the player to take the 'buy' action by enabling it here. //Any button enabled will work, and you may enable any combination, one, some, or all, of them. //Set to '1' to enable, '0' to disable. const int SHOP_USE_BUTTON_R = 1; const int SHOP_USE_BUTTON_L = 0; const int SHOP_USE_BUTTON_A = 1; const int SHOP_USE_BUTTON_B = 0; const int SHOP_USE_BUTTON_EX1 = 0; const int SHOP_USE_BUTTON_EX2 = 0; const int SHOP_USE_BUTTON_EX3 = 0; const int SHOP_USE_BUTTON_EX4 = 0; //Replacement Item Tile Settings const int SHOP_REPL_ITEM_TILE_LAYER = 1; //Replacement item tiles (via Screen->Drawtile) will appear on this layer. //Sound and String const int SFX_SHOP_ERROR = 9; //Sound to play when buying an item. const int MSG_SHOP_ERROR = 10; //Message to display if Link is out of funds. //Shop Darkness Settings const int SHOP_DARK_WHEN_CLOSED = 1; //Set to '1' to close the shop by turning out the lights. const int SHOP_DARKNESS_COLOUR = 0x0F;// Black; used by shop darkness overlay. const int SHOP_DARKNESS_LAYER = 6; //Darkness effect will be drawn to this layer. const int SHOP_DARKNESS_SCALE = 100; const int SHOP_DARKNESS_OPACITY = 64; const int SHOP_DARKNESSS_NUM_LAYERS = 3; //How many draws to perform. //Shop Functionality Setings const int SHOP_LINK_PROXIMITY_X_TO_ITEM = 25; //X-Distance in pixels for required proximity to activate menu. const int SHOP_LINK_PROXIMITY_Y_TO_ITEM = 25; //Y-Distance in pixels for required proximity to activate menu. const int SHOP_LINK_MUST_FACE_ITEM = 1; //Set to 0 to disable. const int SHOP_SHOW_ZERO = 0; //Show zero value prices. '1' to show, '0' to disable. const int SHOP_SHOW_NEGATIVE_PRICE = 0; //Show negative value prices. '1' to show, '0' to disable. const int SHOP_FREE_ITEMS_NO_MENU = 0; //Set to '1' to bypass the menu for free items, giving the player the item instantly. const int SHOP_SHOW_RUPEE_X_FOR_FREE_ITEMS = 1; //Set to '0'; to disable showing rupee ICON and/or X for free items. Depends on main setting to display either. const int SHOP_ZERO_PRICE_STATES_FREE = 1; //Se tot '1' to show the string 'Free' next to 0-price items, instead of '0'. //Tango slot constants. const int WINDOW_SLOT_1 = 0; const int WINDOW_SLOT_2 = 1; const int WINDOW_SLOT_3 = 2; const int WINDOW_SLOT_4 = 3; const int WINDOW_SLOT_5 = 4; //Values that you probably should not change. //! These are the binary flags for items, used in conjunction with one-time-only sales. const int SHOP_SOLD_ITEM_1 = 000000001b; const int SHOP_SOLD_ITEM_2 = 000000010b; const int SHOP_SOLD_ITEM_3 = 000000100b; const int SHOP_SOLD_ITEM_4 = 000001000b; const int SHOP_SOLD_ITEM_5 = 000010000b; const int SHOP_SOLD_ITEM_6 = 000100000b; const int SHOP_SOLD_ITEM_7 = 001000000b; const int SHOP_SOLD_ITEM_8 = 010000000b; const int SHOP_SOLD_ITEM_9 = 100000000b; // There are certainly other ways to handle these... // Vars used by the Tango menu. int menuCommand; int menuArg; //Tango Menu Init void SetUpWindow(int slot, int style, int x, int y, int size) { SetStyleSize(style, size); Tango_ClearSlot(slot); Tango_SetSlotStyle(slot, style); Tango_SetSlotPosition(slot, x, y); } //Quick way to drop a string into a Tango dialogue box. void ShowString(int string, int slot, int style, int x, int y) { SetUpWindow(slot, style, x, y, SIZE_LARGE); Tango_LoadString(slot, string); Tango_ActivateSlot(slot); while(Tango_SlotIsActive(slot)) Waitframe(); } //The ffc that makes the screen dark. ffc script ShopDarknessFFC{ void run(){ while(true){ if ( IsShopAllSoldOut() && SHOP_DARK_WHEN_CLOSED ) ShopSoldOut(); //Draw dark layer if setting enabled. Waitframe(); } } } //The main shop ffc. ffc script ShopItemMenu{ void run(int itm, int price, int msg, int itemcombo, int sound, int holdup_type, int only_once, int itemnumber_in_shop){ int msg_str = msg << 0; //Message string is integer of D2. int counter = ( msg - ( msg << 0 )) *10000; //Alt counte ris decimal of D2. if ( counter == 0 ) counter = CR_RUPEES; //Allow an alternate counter. item it = Screen->CreateItem(only_once << 0); it->DrawXOffset = -300; it->HitXOffset = -300; it->DrawYOffset = -300; it->HitYOffset = -300; if ( only_once == 1 || only_once < 0 ) { if ( FFC_ShopFlag(SHOP_SOLD_ITEM_1) && itemnumber_in_shop == 1 ) this->Data = TILE_SOLD_SIGN; else if ( FFC_ShopFlag(SHOP_SOLD_ITEM_2) && itemnumber_in_shop == 2 ) this->Data = TILE_SOLD_SIGN; else if ( FFC_ShopFlag(SHOP_SOLD_ITEM_3) && itemnumber_in_shop == 3 ) this->Data = TILE_SOLD_SIGN; else if ( FFC_ShopFlag(SHOP_SOLD_ITEM_4) && itemnumber_in_shop == 4 ) this->Data = TILE_SOLD_SIGN; else if ( FFC_ShopFlag(SHOP_SOLD_ITEM_5) && itemnumber_in_shop == 5 ) this->Data = TILE_SOLD_SIGN; else if ( FFC_ShopFlag(SHOP_SOLD_ITEM_6) && itemnumber_in_shop == 6 ) this->Data = TILE_SOLD_SIGN; else if ( FFC_ShopFlag(SHOP_SOLD_ITEM_9) && itemnumber_in_shop == 7 ) this->Data = TILE_SOLD_SIGN; else if ( FFC_ShopFlag(SHOP_SOLD_ITEM_8) && itemnumber_in_shop == 8 ) this->Data = TILE_SOLD_SIGN; else if ( FFC_ShopFlag(SHOP_SOLD_ITEM_3) && itemnumber_in_shop == 9 ) this->Data = TILE_SOLD_SIGN; } if ( itemcombo ) this->Data = itemcombo; //If we have a specific combo ID set, use it. if ( ( ( only_once << 0 ) > 1 ) ) { //We have a replacement item when this one sells, so don't put up a sold out sign. if ( FFC_ShopFlag(SHOP_SOLD_ITEM_1) && itemnumber_in_shop == 1 ) { itm = ( only_once << 0 ); this->Data = FFCS_INVISIBLE_COMBO; } else if ( FFC_ShopFlag(SHOP_SOLD_ITEM_2) && itemnumber_in_shop == 2 ) { itm = ( only_once << 0 ); this->Data = FFCS_INVISIBLE_COMBO; } //We could offer drawtile for this. else if ( FFC_ShopFlag(SHOP_SOLD_ITEM_3) && itemnumber_in_shop == 3 ) { itm = ( only_once << 0 ); this->Data = FFCS_INVISIBLE_COMBO; } else if ( FFC_ShopFlag(SHOP_SOLD_ITEM_4) && itemnumber_in_shop == 4 ) { itm = ( only_once << 0 ); this->Data = FFCS_INVISIBLE_COMBO; } else if ( FFC_ShopFlag(SHOP_SOLD_ITEM_5) && itemnumber_in_shop == 5 ) { itm = ( only_once << 0 ); this->Data = FFCS_INVISIBLE_COMBO; } else if ( FFC_ShopFlag(SHOP_SOLD_ITEM_6) && itemnumber_in_shop == 6 ) { itm = ( only_once << 0 ); this->Data = FFCS_INVISIBLE_COMBO; } else if ( FFC_ShopFlag(SHOP_SOLD_ITEM_9) && itemnumber_in_shop == 7 ) { itm = ( only_once << 0 ); this->Data = FFCS_INVISIBLE_COMBO; } else if ( FFC_ShopFlag(SHOP_SOLD_ITEM_8) && itemnumber_in_shop == 8 ) { itm = ( only_once << 0 ); this->Data = FFCS_INVISIBLE_COMBO; } else if ( FFC_ShopFlag(SHOP_SOLD_ITEM_3) && itemnumber_in_shop == 9 ) { itm = ( only_once << 0 ); this->Data = FFCS_INVISIBLE_COMBO; } Screen->DrawTile(SHOP_REPL_ITEM_TILE_LAYER, this->X, this->Y, it->Tile, 1, 1, it->CSet, -1, -1, 0, 0, 0, 0, true, OP_OPAQUE); //Make the combo of the ffc invisible, then... //Draw a tile so that it's easier to customise what the user sees. if ( ( only_once - ( only_once << 0 )) *10000 > 0 ) price = ( only_once - ( only_once << 0 )) *10000; //Set an alternate price using the decimal portion of D6. } int str_price[6]; int free[]="Free"; if ( !SHOP_ZERO_PRICE_STATES_FREE || price != 0 ) itoa(str_price,price); //Store the price in a string to display it. else itoa(str_price,free); //Show 'Free' instead of a numeral '0'. int choice; bool pressed; bool dotile; //true if we use a tile, not a combo //Replce the item if needed. if ( ( this->Data == TILE_SOLD_SIGN || TILE_SHOP_CLOSED_FOREVER) && !SHOP_DARK_WHEN_CLOSED ) { this->Script = 0; Quit(); } //Clear the ffc if the item is sold, to prevent count of running shops from reading it. if ( ( this->Data == TILE_SOLD_SIGN || TILE_SHOP_CLOSED_FOREVER) && SHOP_DARK_WHEN_CLOSED ) { this->Script = FFC_GetShopDarkness(); Quit(); } //If shops should be dark, change the script. FFC_SetNumberShopItems(); //Store how many shops are running. while(true){ if ( ( this->Data == TILE_SOLD_SIGN || TILE_SHOP_CLOSED_FOREVER) && !SHOP_DARK_WHEN_CLOSED ){ this->Script = 0; Quit(); } if ( ( this->Data == TILE_SOLD_SIGN || TILE_SHOP_CLOSED_FOREVER) && SHOP_DARK_WHEN_CLOSED ) { this->Script = FFC_GetShopDarkness(); Quit(); } //If shops should be dark, change the script. if ( SHOP_SIGNS_CHANGE_WHEN_ALL_ITEMS_SOLD && IsShopAllSoldOut() ) this->Data = TILE_SHOP_CLOSED_FOREVER; //Draw the shop prices and icons: //If a tile is set for a rupee icon... if ( ( SHOP_TILE_RUPEE_ICON && !SHOP_SHOW_RUPEE_X_FOR_FREE_ITEMS ) || ( SHOP_TILE_RUPEE_ICON && SHOP_SHOW_RUPEE_X_FOR_FREE_ITEMS && price != 0 ) ) { Screen->DrawTile( SHOP_TILE_RUPEE_ICON_LAYER, this->X + SHOP_TILE_RUPEE_ICON_X_OFFSET, this->Y + SHOP_TILE_RUPEE_ICON_Y_OFFSET, SHOP_TILE_RUPEE_ICON, SHOP_TILE_RUPEE_ICON_BLOCKW, SHOP_TILE_RUPEE_ICON_BLOCKH, SHOP_TILE_RUPEE_ICON_CSET, SHOP_TILE_RUPEE_ICON_XSCALE, SHOP_TILE_RUPEE_ICON_YSCALE, 0, 0, 0, 0, true, SHOP_BUY_BUTTON_TILE_OPACITY); } //If the setting to draw an 'x' between the rupee icon and the price is enabled... if ( ( SHOP_PRICE_DRAW_X_SIGN && !SHOP_SHOW_RUPEE_X_FOR_FREE_ITEMS ) || ( SHOP_PRICE_DRAW_X_SIGN && SHOP_SHOW_RUPEE_X_FOR_FREE_ITEMS && price != 0 ) ) FFC_DrawShopPrice_X_Sign(this); //Draw the 'x' //Draw the actual price. if ( ( ( !SHOP_SHOW_ZERO && price !=0 ) || SHOP_SHOW_ZERO && price > -1 ) && ( ( !SHOP_SHOW_NEGATIVE_PRICE && price > -1 ) || SHOP_SHOW_NEGATIVE_PRICE ) ) //Draw the background. Screen->DrawString( SHOP_PRICE_TEXT_LAYER, this->X+SHOP_PRICE_TEXT_X_OFFSET_BACKGROUND, this->Y+SHOP_PRICE_TEXT_Y_OFFSET_BACKGROUND, SHOP_PRICE_FONT, SHOP_PRICE_COLOUR_BACKGROUND, SHOP_PRICE_SIZE, TF_NORMAL, str_price, OP_OPAQUE); //Background //Draw the foreground. Screen->DrawString( SHOP_PRICE_TEXT_LAYER, this->X+SHOP_PRICE_TEXT_X_OFFSET_FOREGROUND, this->Y+SHOP_PRICE_TEXT_Y_OFFSET_FOREGROUND, SHOP_PRICE_FONT, SHOP_PRICE_COLOUR_BACKGROUND, SHOP_PRICE_SIZE, TF_NORMAL, str_price, OP_OPAQUE); //Foreground if ( __DistX(this,SHOP_LINK_PROXIMITY_X_TO_ITEM,true) && __DistY(this,SHOP_LINK_PROXIMITY_Y_TO_ITEM,true) && ( __LinkFacing(this) || !SHOP_LINK_MUST_FACE_ITEM ) ) { //Draw the button tile overlay. if ( SHOP_BUY_BUTTON_TILE ) Screen->DrawTile( SHOP_BUY_BUTTON_TILE_LAYER, this->X + SHOP_BUY_BUTTON_TILE_X_OFFSET, this->Y + SHOP_BUY_BUTTON_TILE_Y_OFFSET, SHOP_BUY_BUTTON_TILE, SHOP_BUY_BUTTON_TILE_BLOCKW, SHOP_BUY_BUTTON_TILE_BLOCKH, SHOP_BUY_BUTTON_TILE_CSET, -1, -1, 0, 0, 0, 0, true, SHOP_BUY_BUTTON_TILE_OPACITY); //Check for input based on the button settings... if ( SHOP_USE_BUTTON_R && Link->PressR ) { pressed = true; Link->PressR = false; Link->InputR = false; } if ( SHOP_USE_BUTTON_L && Link->PressL ) { pressed = true; Link->PressL = false; Link->InputL = false; } if ( SHOP_USE_BUTTON_A && Link->PressA ) { pressed = true; Link->PressA = false; Link->InputA = false; } if ( SHOP_USE_BUTTON_B && Link->PressB ) { pressed = true; Link->PressB = false; Link->InputB = false; } if ( SHOP_USE_BUTTON_EX1 && Link->PressEx1 ) { pressed = true; Link->PressEx1 = false; Link->InputEx1 = false; } if ( SHOP_USE_BUTTON_EX2 && Link->PressEx2 ) { pressed = true; Link->PressEx2 = false; Link->InputEx2 = false; } if ( SHOP_USE_BUTTON_EX2 && Link->PressEx3 ) { pressed = true; Link->PressEx3 = false; Link->InputEx3 = false; } if ( SHOP_USE_BUTTON_EX2 && Link->PressEx4 ) { pressed = true; Link->PressEx4 = false; Link->InputEx4 = false; } //Show info on ittem, then... //yes/no menu //if ( price <= Game->Counter[CR_RUPEES] ) { //Yes/No if ( pressed ) { //If Link pressed a button that we want to use... pressed = false; //Clear pressed. if ( !SHOP_FREE_ITEMS_NO_MENU || ( SHOP_FREE_ITEMS_NO_MENU && price != 0) ) choice = BuyYesNo(msg_str,price); if ( choice == 2 || ( SHOP_FREE_ITEMS_NO_MENU && price == 0 ) ) { //Bought it. if ( Game->Counter[counter] >= price ) { //Bought and can buy it... Game->DCounter[counter] -= price; if ( sound ) Game->PlaySound(sound); item it = Screen->CreateItem(itm); it->X = Link->X; it->Y = Link->Y; it->Z = Link->Z; if ( holdup_type ) { Link->Action = holdup_type + 3; Link->HeldItem = itm; } if ( only_once ) { //Set the flags. if ( itemnumber_in_shop == 1 ) FFC_SetShopFlag(SHOP_SOLD_ITEM_1, true); if ( itemnumber_in_shop == 2 ) FFC_SetShopFlag(SHOP_SOLD_ITEM_2, true); if ( itemnumber_in_shop == 3 ) FFC_SetShopFlag(SHOP_SOLD_ITEM_3, true); if ( itemnumber_in_shop == 4 ) FFC_SetShopFlag(SHOP_SOLD_ITEM_4, true); if ( itemnumber_in_shop == 5 ) FFC_SetShopFlag(SHOP_SOLD_ITEM_5, true); if ( itemnumber_in_shop == 6 ) FFC_SetShopFlag(SHOP_SOLD_ITEM_6, true); if ( itemnumber_in_shop == 7 ) FFC_SetShopFlag(SHOP_SOLD_ITEM_7, true); if ( itemnumber_in_shop == 8 ) FFC_SetShopFlag(SHOP_SOLD_ITEM_8, true); if ( itemnumber_in_shop == 9 ) FFC_SetShopFlag(SHOP_SOLD_ITEM_9, true); //If only_once and no alternate item if ( ( only_once << 0) < 0 || ( only_once << 0 ) == 1 ) this->Data = TILE_SOLD_SIGN; else { //! Replace with the new item itm = ( only_once << 0 ); //Screen->D[SHOP_REGISTER_REPL_ITEM] = ( only_once - ( only_once << 0 )) *10000; this->Data = FFCS_INVISIBLE_COMBO; //Make this ffc combo invisible, then... Screen->DrawTile(SHOP_REPL_ITEM_TILE_LAYER, this->X, this->Y, it->Tile, 1, 1, it->CSet, -1, -1, 0, 0, 0, 0, true, OP_OPAQUE); //Draw a tile so that it's easier to customise what the user sees. if ( ( only_once - ( only_once << 0 )) *10000 > 0 ) price = ( only_once - ( only_once << 0 )) *10000; //Set an alternate price using the decimal portion of D6. } } } else { //Errors if ( SFX_SHOP_ERROR ) Game->PlaySound(SFX_SHOP_ERROR); if ( MSG_SHOP_ERROR ) Screen->Message(MSG_SHOP_ERROR); } } else choice = 0; //Clear the choice selection. } } Waitframe(); } } //The following three functions are from my std.zh update, with leading underscores added in the event that you upgrade, to prevent conflicts. bool __DistX(ffc a, int distance, bool fromcentre) { int dist; if ( a->X > Link->X ) dist = a->X - Link->X; else dist = Link->X - a->X; return ( dist <= distance ); } //Link to ffc distance bool __DistY(ffc a, int distance, bool fromcentre) { int dist; if ( a->Y > Link->Y ) dist = a->Y - Link->Y; else dist = Link->Y - a->Y; return ( dist <= distance ); } bool __LinkFacing(ffc f){ if ( Link->Dir == DIR_UP && Link->Y < f->Y ) return true; if ( Link->Dir == DIR_DOWN && Link->Y > f->Y ) return true; if ( Link->Dir == DIR_RIGHT && Link->X < f->X ) return true; if ( Link->Dir == DIR_LEFT && Link->X > f->X ) return true; return false; } } //Global Functions //Check a shop item sold-out flag. bool FFC_ShopFlag(int flag){ return ( ( Screen->D[SHOP_REGISTER]<<0 )&flag ) != 0; } //Set a shop item sold-out flag. void FFC_SetShopFlag(int flag, bool state){ int val[3]; val[0]= Screen->D[SHOP_REGISTER]; val[1]= val[0] << 0; //Integer side val[2] = val[0] - val[1]; //Decimal side. if ( state ) val[1] |= flag; else val[1] &= ~flag; Screen->D[SHOP_REGISTER] = val[1]+val[2]; //Preserve the decimal, and replace the integer. } //Returns how many shop item ffcs are running. int FFC_NumShopItems(){ ffc f; int count; int ff[]="ShopItemMenu"; int ffid = Game->GetFFCScript(ff); for ( int q = 1; q < 32; q++ ){ f = Screen->LoadFFC(q); if ( f->Script == ffid ) count++; } return count; } //Stores the number of items in the screen register. void FFC_SetNumberShopItems(){ int val[6]; val[0]= Screen->D[SHOP_REGISTER]; val[1]= val[0] << 0; //Integer side val[2] = val[0] - val[1]; //Decimal side. val[3] = val[2] * 10000; //Decimal to Int val[4] = FFC_NumShopItems(); //Read how many shops are running. val[5] = val[4] / 10000; //Turn it into a decimal. Screen->D[SHOP_REGISTER] = val[1]+val[5]; //Preserve the integer, and replace the decimal. } //Returns te stored value of the number of running shop items. int FFC_GetNumberShopItems(){ int val[3]; val[0]= Screen->D[SHOP_REGISTER]; val[1]= val[0] << 0; //Integer side val[2] = val[0] - val[1]; //Decimal side. return val[2]; } //Check if all items are sold out. Works only if there ALL items sold out. bool IsShopAllSoldOut(){ int shopsold[]={0,1,2,4,8,16,32,64,128,256}; int count; for ( int q = 0; q <= FFC_GetNumberShopItems(); q++ ) { count += shopsold[q]; } return ( Screen->D[SHOP_REGISTER] >= count ); } //Draws darkness effect if the shop is sold out, and the setting is enabled. int FFC_GetShopDarkness(){ int ff[]="ShopDarknessFFC"; return Game->GetFFCScript(ff); } //Draws the darkness layer. void ShopSoldOut(){ for ( int q = 0; q < SHOP_DARKNESSS_NUM_LAYERS; q++ ) Screen->Rectangle(SHOP_DARKNESS_LAYER, 0, 0, 255, 175, SHOP_DARKNESS_COLOUR, SHOP_DARKNESS_SCALE, 0, 0, 0, true, SHOP_DARKNESS_OPACITY); } //Draw the 'x' between the rupee icon and the price. void FFC_DrawShopPrice_X_Sign(ffc f){ int x[]="x"; Screen->DrawString(SHOP_PRICE_DRAW_X_SIGN_LAYER, f->X+SHOP_PRICE_DRAW_X_SIGN_X_OFFSET_BACKGROUND, f->Y+SHOP_PRICE_DRAW_X_SIGN_Y_OFFSET_BACKGROUND, SHOP_PRICE_DRAW_X_SIGN_FONT, SHOP_PRICE_DRAW_X_SIGN_COLOUR_BACKGROUND, SHOP_PRICE_DRAW_X_SIGN_SIZE, TF_NORMAL, x, OP_OPAQUE); //Background Screen->DrawString(SHOP_PRICE_DRAW_X_SIGN_LAYER, f->X+SHOP_PRICE_DRAW_X_SIGN_X_OFFSET_FOREGROUND, f->Y+SHOP_PRICE_DRAW_X_SIGN_Y_OFFSET_FOREGROUND, SHOP_PRICE_DRAW_X_SIGN_FONT, SHOP_PRICE_DRAW_X_SIGN_COLOUR_FOREGROUND, SHOP_PRICE_DRAW_X_SIGN_SIZE, TF_NORMAL, x, OP_OPAQUE); //Background } //The 'yes/no' menu called by the ffc. int BuyYesNo(int msg, int price) { int lineBreak[]="@26"; int line1[]="@choice(1)Item Info@26"; int line2[]="@choice(2)Buy@26@choice(3)Cancel@domenu(1)@suspend()"; int free[]="@choice(2)Take@26@choice(3)Cancel@domenu(1)@suspend()"; SetUpWindow(WINDOW_SLOT_1, WINDOW_STYLE_3, 32, 32, SIZE_LARGE); Tango_LoadString(WINDOW_SLOT_1, line1); if ( price == 0 ) Tango_AppendString(WINDOW_SLOT_1, free); else Tango_AppendString(WINDOW_SLOT_1, line2); Tango_ActivateSlot(WINDOW_SLOT_1); while(!Tango_MenuIsActive()){ Waitframe(); } // Save the state again... int slotState[278]; int menuState[960]; int cursorPos; Tango_SaveSlotState(WINDOW_SLOT_1, slotState); Tango_SaveMenuState(menuState); int done = 0; int choice; while(true){ while( Tango_MenuIsActive() ) { cursorPos=Tango_GetMenuCursorPosition(); Waitframe(); } choice = Tango_GetLastMenuChoice(); if ( choice == 1 ) { // Item Info int text[256]; Game->GetMessage(msg,text); //Load msg into the buffer. ShowString(text, WINDOW_SLOT_2, WINDOW_STYLE_3, 48, 48); } else if ( choice == 2 ) { //Buy done = choice; menuArg = choice; } else if ( choice == 3 ) { //Cancel done = choice; } else if ( Link->PressEx1 ) { done = 1; } else done = 3; if ( done ) { break; // return choice; } else { Tango_RestoreSlotState(WINDOW_SLOT_1, slotState); Tango_RestoreMenuState(menuState); Tango_SetMenuCursorPosition(cursorPos); } } Tango_ClearSlot(WINDOW_SLOT_1); return done; } //Global Scripts //Mandatory init script: If you already have an init script, merge them. global script Init { void run(){ SetCommonStyleData(WINDOW_STYLE_1); SetCommonStyleData(WINDOW_STYLE_2); SetCommonStyleData(WINDOW_STYLE_3); } } //Example global active (slot 2) script. global script Tango{ void run(){ Tango_Start(); StartGhostZH(); while(true) { UpdateGhostZH1(); Tango_Update1(); Waitdraw(); UpdateGhostZH2(); Tango_Update2(); Waitframe(); } } }