Esempio n. 1
0
        /// <summary>
        /// Gets a lookup dictionary to translate order Ids into order numbers
        /// </summary>
        /// <param name="orderIds">An array of order Ids</param>
        /// <returns>A dictionary where the key is the OrderId and the value is the OrderNumber</returns>
        public static Dictionary <int, int> LookupOrderNumbers(int[] orderIds)
        {
            Dictionary <int, int> orderNumberLookup = new Dictionary <int, int>();

            if ((orderIds == null) || (orderIds.Length == 0))
            {
                return(orderNumberLookup);
            }
            if (orderIds.Length == 1)
            {
                orderNumberLookup.Add(orderIds[0], LookupOrderNumber(orderIds[0]));
                return(orderNumberLookup);
            }
            string   orderIdList = AlwaysConvert.ToList(",", orderIds);
            Database database    = Token.Instance.Database;

            using (DbCommand selectCommand = database.GetSqlStringCommand("SELECT OrderId,OrderNumber FROM ac_Orders WHERE StoreId = @storeId AND OrderId IN (" + orderIdList + ")"))
            {
                database.AddInParameter(selectCommand, "@storeId", System.Data.DbType.Int32, Token.Instance.StoreId);
                using (IDataReader dr = database.ExecuteReader(selectCommand))
                {
                    while (dr.Read())
                    {
                        orderNumberLookup.Add(dr.GetInt32(0), dr.GetInt32(1));
                    }
                    dr.Close();
                }
            }
            return(orderNumberLookup);
        }
        private void SaveCustomViewState()
        {
            UrlEncodedDictionary customViewState = new UrlEncodedDictionary();

            if (_SelectedProductIds.Count > 0)
            {
                customViewState["SP"] = AlwaysConvert.ToList(",", _SelectedProductIds.ToArray());
            }
            else
            {
                customViewState["SP"] = string.Empty;
            }
            VS.Value = EncryptionHelper.EncryptAES(customViewState.ToString());
        }
Esempio n. 3
0
        /// <summary>
        /// Checks the list of kit products and updates as necessary.
        /// </summary>
        /// <param name="kitList">The list of kit products to refresh.</param>
        /// <returns>An updated list of kit products.</returns>
        /// <remarks>
        /// 1. Ensures any included kit products are in the list
        /// 2. Any kit products that are no longer associated to the kit are removed.
        /// </remarks>
        internal string RefreshKitProducts(string kitList)
        {
            // PARSE THE ORIGINAL KIT LIST
            List <int> kitProductIds = new List <int>();

            if (!string.IsNullOrEmpty(kitList))
            {
                kitProductIds.AddRange(AlwaysConvert.ToIntArray(kitList));
            }

            // REMOVE INVALID KITPRODUCTS
            RemoveInvalidKitProducts(kitProductIds);

            // ENSURE REQUIRED CHOICES ARE IN THE KITLIST
            foreach (ProductKitComponent pkc in _Product.ProductKitComponents)
            {
                KitComponent kc = pkc.KitComponent;
                if (kc.InputType == KitInputType.IncludedShown || kc.InputType == KitInputType.IncludedHidden)
                {
                    // THIS IS AN INCLUDED COMPONENT, SO ALL ITEMS ARE REQUIRED
                    foreach (KitProduct kp in kc.KitProducts)
                    {
                        if (!kitProductIds.Contains(kp.KitProductId))
                        {
                            kitProductIds.Add(kp.KitProductId);
                        }
                    }
                }
                else if ((kc.InputType == KitInputType.DropDown || kc.InputType == KitInputType.RadioButton) &&
                         string.IsNullOrEmpty(kc.HeaderOption) && kc.KitProducts.Count == 1)
                {
                    // THIS TYPE OF CONTROL WITHOUT A HEADER OPTION AND A SINGLE KITPRODUCT FORCES CHOICE
                    KitProduct kp = kc.KitProducts[0];
                    if (!kitProductIds.Contains(kp.KitProductId))
                    {
                        kitProductIds.Add(kp.KitProductId);
                    }
                }
            }

            // RETURN THE REFRESHED KITLIST
            if (kitProductIds.Count == 0)
            {
                return(string.Empty);
            }
            return(AlwaysConvert.ToList(",", kitProductIds.ToArray()));
        }
        /// <summary>
        /// Identify the products from the basket that have product level discounts
        /// </summary>
        /// <param name="basketId">basket to check for product level discounts</param>
        /// <param name="productsToExclude">products that should not be checked for discounts</param>
        /// <returns>An array of discounted products in the basket</returns>
        private static DiscountedBasketProduct[] GetDiscountedBasketProducts(int basketId, List <int> productsToExclude)
        {
            //BUILD CRITERIA FOR PRODUCTS TO EXCLUDE FROM QUERY
            string excludedProducts = string.Empty;

            if (productsToExclude.Count > 0)
            {
                if (productsToExclude.Count == 1)
                {
                    excludedProducts = " WHERE ProductId <> " + productsToExclude[0].ToString();
                }
                else
                {
                    excludedProducts = " WHERE ProductId NOT IN (" + AlwaysConvert.ToList(",", productsToExclude.ToArray()) + ")";
                }
            }

            //EXECUTE THE QUERY
            Database  database = Token.Instance.Database;
            DbCommand command  = database.GetSqlStringCommand("SELECT ProductId,AVG(Price),SUM(Quantity) FROM ac_BasketItems WHERE BasketId = @basketId AND ProductId IN (SELECT DISTINCT ProductId FROM ac_ProductVolumeDiscounts" + excludedProducts + ") GROUP BY ProductId");

            database.AddInParameter(command, "@basketId", System.Data.DbType.Int32, basketId);

            //BUILD A LIST OF DISCOUNTED PRODUCTS IN THE BASKET
            List <DiscountedBasketProduct> discountedBasketProducts = new List <DiscountedBasketProduct>();

            using (IDataReader dr = database.ExecuteReader(command))
            {
                while (dr.Read())
                {
                    discountedBasketProducts.Add(new DiscountedBasketProduct(dr.GetInt32(0), dr.GetDecimal(1), dr.GetInt32(2)));
                }
                dr.Close();
            }

            //RETURN THE DISCOUNTED PRODUCTS
            return(discountedBasketProducts.ToArray());
        }
        private void SaveCustomViewState()
        {
            UrlEncodedDictionary customViewState = new UrlEncodedDictionary();

            customViewState["ShowEditGrid"]    = _ShowEditGrid.ToString();
            customViewState["EnableScrolling"] = _EnableScrolling.ToString();
            if (_SelectedCategoryIds.Count > 0)
            {
                customViewState["SC"] = AlwaysConvert.ToList(",", _SelectedCategoryIds.ToArray());
            }
            else
            {
                customViewState["SC"] = string.Empty;
            }
            if (_SelectedFields.Count > 0)
            {
                customViewState["SF"] = string.Join(",", _SelectedFields.ToArray());
            }
            else
            {
                customViewState["SF"] = string.Empty;
            }
            VS.Value = EncryptionHelper.EncryptAES(customViewState.ToString());
        }
Esempio n. 6
0
        /// <summary>
        /// Gets the parent item for the given basket item.
        /// </summary>
        /// <param name="item">Item for which to find the parent.</param>
        /// <param name="recurse">If true, this method gets the top level parent for this item.  If false, only the immediate parent is returned.</param>
        /// <param name="itemPath">List to track the current item path, to prevent recursive loops.</param>
        /// <returns>Returns the BasketItem instance for the parent item.  If the current item has no parent, the current item is returned.</returns>
        private static BasketItem InternalGetParentItem(BasketItem item, bool recurse, List <int> itemPath)
        {
            // IF PARENT ITEM INDICATED, LOOK FOR IT IN THE BASKET
            int parentItemId = item.ParentItemId;
            int basketItemId = item.BasketItemId;

            itemPath.Insert(0, basketItemId);
            if (item.IsChildItem)
            {
                Basket basket = item.Basket;
                if (basket != null)
                {
                    foreach (BasketItem otherItem in basket.Items)
                    {
                        int otherItemId = otherItem.BasketItemId;
                        if (otherItemId == parentItemId)
                        {
                            // CHECK TO MAKE SURE WE ARE NOT IN A RECURSIVE LOOP
                            if (itemPath.Contains(otherItemId))
                            {
                                Logger.Error("Circular parent reference in basket.  Path: " + AlwaysConvert.ToList(",", itemPath.ToArray()));
                                throw new CircularParentReference("Circular parent reference in basket.  Path: " + AlwaysConvert.ToList(",", itemPath.ToArray()));
                            }

                            if (recurse)
                            {
                                return(InternalGetParentItem(otherItem, recurse, itemPath));
                            }
                            // NON-RECURSIVE, ADD THIS ITEM TO THE PATH AND RETURN
                            itemPath.Insert(0, otherItem.BasketItemId);
                            return(otherItem);
                        }
                    }
                }
            }

            // NO PARENT OR NO PARENT FOUND, ENSURE PARENT ID IS CORRECTLY SET
            item.ParentItemId = basketItemId;
            return(item);
        }
 public static ProductCalculator LoadForProduct(int productId, short quantity, string optionList, List <int> kitList)
 {
     return(LoadForProduct(productId, quantity, optionList, AlwaysConvert.ToList(",", kitList), Token.Instance.UserId, false));
 }
        public void Page_Init(object sender, EventArgs e)
        {
            if (_Order == null)
            {
                OrderId = AbleCommerce.Code.PageHelper.GetOrderId();
            }
            if (_OrderShipment == null)
            {
                OrderShipmentId = AlwaysConvert.ToInt(Request.QueryString["OrderShipmentId"]);
            }
            if (_Order == null)
            {
                Response.Redirect("~/Admin/Orders/Default.aspx");
            }
            _ProductId = AlwaysConvert.ToInt(Request.QueryString["ProductId"]);
            _Product   = ProductDataSource.Load(_ProductId);


            if (_Product == null)
            {
                if (_OrderShipment == null)
                {
                    Response.Redirect("~/Admin/Orders/Edit/FindProduct.aspx?OrderNumber=" + _Order.OrderNumber.ToString());
                }
                else
                {
                    Response.Redirect("~/Admin/Orders/Shipments/FindProduct.aspx?OrderShipmentId=" + _OrderShipmentId.ToString());
                }
            }

            if (_OrderShipment == null)
            {
                BackButton.NavigateUrl = "~/Admin/Orders/Edit/EditOrderItems.aspx?OrderNumber=" + _Order.OrderNumber.ToString();
            }
            else
            {
                BackButton.NavigateUrl = "~/Admin/Orders/Shipments/EditShipment.aspx?OrderShipmentId=" + _OrderShipmentId.ToString();
            }

            // update instruction text
            GiftCertMessage.Visible     = _Product.IsGiftCertificate;
            DigitalGoodsMessage.Visible = _Product.IsDigitalGood;
            SubscriptionMessage.Visible = _Product.IsSubscription;

            //SET NAME AND PRICE
            Name.Text             = _Product.Name;
            HiddenProductId.Value = _Product.Id.ToString();
            //BUILD PRODUCT ATTRIBUTES
            _SelectedOptions = AbleCommerce.Code.ProductHelper.BuildProductOptions(_Product, phOptions, true);
            //BUILD PRODUCT CHOICES
            AbleCommerce.Code.ProductHelper.BuildProductChoices(_Product, phOptions);
            //BUILD KIT OPTIONS
            _SelectedKitProducts = AbleCommerce.Code.ProductHelper.BuildKitOptions(_Product, phOptions);
            //SET PRICE
            string            optionList = ProductVariantDataSource.GetOptionList(_Product.Id, _SelectedOptions, true);
            ProductCalculator pcalc      = ProductCalculator.LoadForProduct(_Product.Id, 1, optionList, AlwaysConvert.ToList(",", _SelectedKitProducts), _Order.UserId);

            Price.Text = string.Format("{0:F2}", pcalc.Price);
            // IF ALL OPTIONS HAVE A VALUE SELECTED, SHOW THE BASKET CONTROLS
            SaveButton.Visible = (_SelectedOptions.Count >= _Product.ProductOptions.Count);
            //BackButton.NavigateUrl += "?OrderNumber=" + _Order.OrderNumber.ToString();


            //CHECK IF SHIPMENTS NEED TO BE DISPLAYED
            trShipment.Visible = (_OrderShipment == null && _Product.Shippable != Shippable.No);
            if (trShipment.Visible)
            {
                //BIND SHIPMENT LIST
                foreach (OrderShipment shipment in _Order.Shipments)
                {
                    string address = string.Format("{0} {1} {2} {3}", shipment.ShipToFirstName, shipment.ShipToLastName, shipment.ShipToAddress1, shipment.ShipToCity);
                    if (address.Length > 50)
                    {
                        address = address.Substring(0, 47) + "...";
                    }
                    string name = "Shipment #" + shipment.ShipmentNumber + " to " + address;
                    ShipmentsList.Items.Add(new ListItem(name, shipment.Id.ToString()));
                }

                if (_Order.Shipments != null && _Order.Shipments.Count == 1)
                {
                    // IF THERE IS JUST ONLY ONE SHIPMENT THEN SELECT IT
                    ShipmentsList.SelectedIndex = 2;
                }
            }

            // if a new shipment option is selected then initialize the related fields
            DisplayOrderShipmentFields(ShipmentsList.SelectedValue == "-1"); ShipFrom.DataSource = AbleContext.Current.Store.Warehouses;
            ShipFrom.DataBind();
            if (AddressList.Items.Count <= 1)
            {
                BindShippingAddresses(this.AddressList);
            }
        }
        protected IList <OrderItem> GetOrderItems()
        {
            //GET THE PRODUCT ID
            int     productId = AlwaysConvert.ToInt(HiddenProductId.Value);
            Product product   = ProductDataSource.Load(productId);

            if (product == null)
            {
                return(null);
            }
            //GET THE QUANTITY
            short tempQuantity = AlwaysConvert.ToInt16(Quantity.Text);

            if (tempQuantity < 1)
            {
                return(null);
            }
            if (tempQuantity > System.Int16.MaxValue)
            {
                tempQuantity = System.Int16.MaxValue;
            }

            //RECALCULATE SELECTED KIT OPTIONS
            GetSelectedKitOptions(product);
            // DETERMINE THE OPTION LIST
            string optionList = ProductVariantDataSource.GetOptionList(productId, _SelectedOptions, false);
            //CREATE THE BASKET ITEM WITH GIVEN OPTIONS

            IList <OrderItem> orderItems = OrderItemDataSource.CreateForProduct(productId, tempQuantity, optionList, AlwaysConvert.ToList(",", _SelectedKitProducts));

            if (orderItems.Count > 0)
            {
                // COLLECT ANY ADDITIONAL INPUTS FOR BASE ITEM
                AbleCommerce.Code.ProductHelper.CollectProductTemplateInput(orderItems[0], phOptions);

                // UPADATE THE PRICE OF BASE ITEM IF NEEDED ( KIT PRICE WILL NOT BE MODIFIED)
                if (orderItems[0].Price != AlwaysConvert.ToDecimal(Price.Text) && (product.KitStatus != KitStatus.Master))
                {
                    orderItems[0].Price = AlwaysConvert.ToDecimal(Price.Text);
                }
            }
            return(orderItems);
        }
        public static TaxRuleCollection LoadForTaxCodes(int[] taxCodeIds, TaxAddress taxAddress, User user)
        {
            //IF WE DO NOT HAVE VALID TAX CODES THERE ARE NO RULES
            if ((taxCodeIds == null) || (taxCodeIds.Length == 0))
            {
                return(new TaxRuleCollection());
            }
            TaxRuleCollection potentialTaxRules = new TaxRuleCollection();

            //FIRST DETERMINE THE ZONE(S) FOR THE Tax Address
            ShipZoneCollection shipmentZoneCollection = taxAddress.ShipZones;

            //BUILD A LIST OF ZONEIDS FOR QUERY CRITERIA
            StringBuilder selectQuery = new StringBuilder();

            selectQuery.Append("SELECT DISTINCT " + TaxRule.GetColumnNames("TR"));
            selectQuery.Append(" FROM (ac_TaxRules TR INNER JOIN ac_TaxRuleTaxCodes TRTC ON TR.TaxRuleId = TRTC.TaxRuleId)");
            selectQuery.Append(" LEFT JOIN ac_TaxRuleShipZones TRSZ ON TR.TaxRuleId = TRSZ.TaxRuleId");
            selectQuery.Append(" WHERE StoreId = @storeId ");
            if (taxCodeIds.Length == 1)
            {
                selectQuery.Append(" AND TRTC.TaxCodeId = " + taxCodeIds[0].ToString());
            }
            else
            {
                selectQuery.Append(" AND TRTC.TaxCodeId IN (" + AlwaysConvert.ToList(",", taxCodeIds) + ")");
            }

            //PROCESS SHIPZONE EXCLUSION
            selectQuery.Append(" AND (TRSZ.ShipZoneId IS NULL");
            for (int i = 0; i < shipmentZoneCollection.Count; i++)
            {
                selectQuery.Append(" OR TRSZ.ShipZoneId = @shipZoneId" + i.ToString());
            }
            selectQuery.Append(") ORDER BY TR.Priority");

            Database  database      = Token.Instance.Database;
            DbCommand selectCommand = database.GetSqlStringCommand(selectQuery.ToString());

            database.AddInParameter(selectCommand, "@storeId", System.Data.DbType.Int32, Token.Instance.StoreId);
            //ADD IN NUMBERED ZONE PARAMETERS
            for (int i = 0; i < shipmentZoneCollection.Count; i++)
            {
                database.AddInParameter(selectCommand, "@shipZoneId" + i.ToString(), System.Data.DbType.Int32, shipmentZoneCollection[i].ShipZoneId);
            }
            //EXECUTE THE COMMAND
            using (IDataReader dr = database.ExecuteReader(selectCommand))
            {
                while (dr.Read())
                {
                    TaxRule taxRule = new TaxRule();
                    TaxRule.LoadDataReader(taxRule, dr);
                    potentialTaxRules.Add(taxRule);
                }
                dr.Close();
            }

            //PROCESS GROUP EXCLUSIONS
            TaxRuleCollection potentialTaxRulesWithGroupFilter = new TaxRuleCollection();

            foreach (TaxRule taxRule in potentialTaxRules)
            {
                if (taxRule.AppliesToUser(user))
                {
                    potentialTaxRulesWithGroupFilter.Add(taxRule);
                }
            }

            //RETURN POTENTIAL TAXES
            return(potentialTaxRulesWithGroupFilter);
        }
Esempio n. 11
0
 protected void Page_PreRender(object sender, EventArgs e)
 {
     if (_Product != null)
     {
         if (!_Product.UseVariablePrice)
         {
             // UPDATE THE INCLUDED KITPRODUCTS (Included-Hidden and Included-Shown)
             string kitList = string.Empty;
             if (_SelectedKitProducts == null || _SelectedKitProducts.Count == 0)
             {
                 UpdateIncludedKitOptions();
                 kitList = AlwaysConvert.ToList(",", _SelectedKitProducts.ToArray());
             }
             ProductCalculator pcalc = ProductCalculator.LoadForProduct(_Product.Id, 1, _OptionList, kitList, 0);
             //IF REQUIRED MAKE ADJUSTMENTS TO DISPLAYED PRICE TO INCLUDE VAT
             decimal basePriceWithVAT = TaxHelper.GetShopPrice(_Product.Price, (_Product.TaxCode != null ? _Product.TaxCode.Id : 0));
             decimal priceWithVAT     = TaxHelper.GetShopPrice(pcalc.Price, (_Product.TaxCode != null ? _Product.TaxCode.Id : 0));
             decimal msrpWithVAT      = TaxHelper.GetShopPrice(_Product.MSRP, (_Product.TaxCode != null ? _Product.TaxCode.Id : 0));
             if (!_Product.HidePrice)
             {
                 //PRICE IS VISIBLE, NO POPUP
                 phPricePopup.Visible = false;
                 //SHOW RETAIL PRICE IF INDICATED
                 if (_ShowRetailPrice && msrpWithVAT > 0 && !_Product.UseVariablePrice)
                 {
                     RetailPrice1.Text = string.Format(_RetailPriceFormat, msrpWithVAT.LSCurrencyFormat("lc"));
                 }
                 else
                 {
                     RetailPrice1.Text = string.Empty;
                 }
                 //SHOW THE PRICE
                 if (pcalc.AppliedSpecial != null && pcalc.AppliedSpecial.EndDate != DateTime.MinValue)
                 {
                     // SHOW THE BASE PRICE AND SPECIAL PRICE
                     RetailPrice1.Text = string.Format(_BasePriceFormat, basePriceWithVAT.LSCurrencyFormat("lc"));
                     Price.Text        = string.Format(_SpecialPriceFormat, priceWithVAT.LSCurrencyFormat("lc"), pcalc.AppliedSpecial.EndDate);
                 }
                 else
                 {
                     Price.Text = string.Format(_PriceFormat, priceWithVAT.LSCurrencyFormat("lc"));
                 }
             }
             else
             {
                 // HIDDEN PRICE, USE POPUP
                 Price.Visible    = false;
                 ProductName.Text = _Product.Name;
                 // THESE VARIABLES WILL TRACK SAVINGS OFF LISTED OR REGULAR PRICE
                 decimal amountSaved  = 0;
                 decimal percentSaved = 0;
                 // DETERMINE IF A SALE OR SPECIAL PRICE IS APPLIED
                 bool salePriceEffective = (pcalc.AppliedSpecial != null && pcalc.AppliedSpecial.EndDate != DateTime.MinValue);
                 // DETERMINE IF MSRP IS AVAILABLE FOR DISPLAY
                 if (_ShowRetailPrice && msrpWithVAT > 0 && !salePriceEffective)
                 {
                     trRetailPrice.Visible       = true;
                     HiddenRetailPriceLabel.Text = PopupRetailPriceLabel;
                     HiddenRetailPrice.Text      = string.Format(PopupRetailPriceFormat, msrpWithVAT.LSCurrencyFormat("lc"));
                     // CALCULATE AMOUNT SAVED OVER MSRP
                     amountSaved  = (msrpWithVAT - priceWithVAT);
                     percentSaved = ((decimal)(amountSaved / msrpWithVAT)) * 100;
                 }
                 else
                 {
                     trRetailPrice.Visible = false;
                 }
                 // CHECK IF A SALE PRICE IS APPLIED
                 if (salePriceEffective)
                 {
                     // SPECIAL APPLIED, SHOW THE PRODUCT BASE PRICE AND THE SPECIAL PRICE
                     trSpecialPrice.Visible = true;
                     HiddenPriceLabel.Text  = PopupBasePriceLabel;
                     HiddenPrice.Text       = string.Format(PopupBasePriceFormat, basePriceWithVAT.LSCurrencyFormat("lc"));
                     SpecialPriceLabel.Text = PopupSpecialPriceLabel;
                     SpecialPrice.Text      = string.Format(PopupSpecialPriceFormat, priceWithVAT.LSCurrencyFormat("lc"), pcalc.AppliedSpecial.EndDate);
                     // CALCULATE AMOUNT SAVED WITH SALE PRICE
                     amountSaved  = (basePriceWithVAT - priceWithVAT);
                     percentSaved = ((decimal)(amountSaved / basePriceWithVAT)) * 100;
                 }
                 else
                 {
                     // NO SPECIAL, SO JUST SHOW THE CALCULATED PRICE
                     HiddenPriceLabel.Text = PopupPriceLabel;
                     HiddenPrice.Text      = string.Format(PopupPriceFormat, priceWithVAT.LSCurrencyFormat("lc"));
                 }
                 // SEE IF WE HAVE AN AMOUNT SAVED VALUE
                 if (amountSaved > 0)
                 {
                     trAmountSaved.Visible = true;
                     AmountSavedLabel.Text = PopupAmountSavedLabel;
                     AmountSaved.Text      = string.Format(PopupAmountSavedFormat, amountSaved.LSCurrencyFormat("lc"), percentSaved);
                 }
                 else
                 {
                     trAmountSaved.Visible = false;
                 }
                 //DO NOT GIVE ADD BUTTON FOR KITTED PRODUCTS
                 //AddToCartButton.Visible = (_Product.KitStatus != KitStatus.Master);
             }
         }
         else
         {
             //DO NOT DISPLAY THIS CONTROL IF THE PRODUCT HAS VARIABLE PRICE
             this.Controls.Clear();
             Label lbl = new Label();
             lbl.Text = "Variable";
             this.Controls.Add(lbl);
         }
     }
     else
     {
         //DO NOT DISPLAY THIS CONTROL IF THE PRODUCT IS UNAVAILABLE
         this.Controls.Clear();
     }
     SaveCustomViewState();
 }
Esempio n. 12
0
        protected void Page_PreRender(object sender, EventArgs e)
        {
            if (_Product != null)
            {
                if (!_Product.UseVariablePrice || _Product.IsSubscription)
                {
                    if (_showQuoteOnZeroPrice && !(_Product.VolumeDiscounts.Any() && _Product.VolumeDiscounts[0].Levels.Any()))
                    {
                        if (_Product.Price == 0)
                        {
                            Price.Text = "Request a quote";
                            return;
                        }
                    }

                    if (_hideZeroPrice)
                    {
                        if (_Product.Price == 0 && _Product.ProductOptions.Count > 0)
                        {
                            this.Visible = false;
                            return;
                        }
                    }
                    // UPDATE THE INCLUDED KITPRODUCTS (Included-Hidden and Included-Shown)
                    if (_SelectedKitProducts.Count == 0 && this.EnableDefaultKitProducts)
                    {
                        UpdateIncludedKitOptions();
                    }
                    ProductCalculator pcalc = ProductCalculator.LoadForProduct(_Product.Id, 1, _OptionList, AlwaysConvert.ToList(",", _SelectedKitProducts), AbleContext.Current.UserId, true, this.CalculateOneTimePrice);

                    //IF REQUIRED MAKE ADJUSTMENTS TO DISPLAYED PRICE TO INCLUDE VAT
                    decimal basePriceWithVAT = TaxHelper.GetShopPrice(_Product.Price, (_Product.TaxCode != null) ? _Product.TaxCode.Id : 0);
                    decimal priceWithVAT     = pcalc.PriceWithTax;
                    decimal msrpWithVAT      = TaxHelper.GetShopPrice(_Product.MSRP, (_Product.TaxCode != null) ? _Product.TaxCode.Id : 0);
                    if (!_Product.HidePrice)
                    {
                        //PRICE IS VISIBLE, NO POPUP
                        phPricePopup.Visible = false;
                        //SHOW RETAIL PRICE IF INDICATED
                        if (_ShowRetailPrice && msrpWithVAT > 0 && !_Product.UseVariablePrice)
                        {
                            RetailPrice1.Text = string.Format(_RetailPriceFormat, msrpWithVAT.LSCurrencyFormat("ulc"));
                        }
                        else
                        {
                            RetailPrice1.Text = string.Empty;
                        }
                        //SHOW THE PRICE
                        if (pcalc.AppliedSpecial != null)
                        {
                            // SHOW THE BASE PRICE AND SPECIAL PRICE
                            RetailPrice1.Text = string.Format(_BasePriceFormat, basePriceWithVAT.LSCurrencyFormat("ulc"));
                            if (pcalc.AppliedSpecial.EndDate != DateTime.MinValue)
                            {
                                Price.Text = string.Format(_SpecialPriceFormat, priceWithVAT.LSCurrencyFormat("ulc"), pcalc.AppliedSpecial.EndDate);
                            }
                            else
                            {
                                Price.Text = string.Format(_SpecialPriceFormat2, priceWithVAT.LSCurrencyFormat("ulc"), null);
                            }
                        }
                        else
                        {
                            Price.Text = string.Format(_PriceFormat, priceWithVAT.LSCurrencyFormat("ulc"));
                        }
                    }
                    else
                    {
                        // HIDDEN PRICE, USE POPUP
                        Price.Visible    = false;
                        ProductName.Text = _Product.Name;
                        // THESE VARIABLES WILL TRACK SAVINGS OFF LISTED OR REGULAR PRICE
                        decimal amountSaved  = 0;
                        decimal percentSaved = 0;
                        // DETERMINE IF A SALE OR SPECIAL PRICE IS APPLIED
                        bool salePriceEffective = (pcalc.AppliedSpecial != null);
                        // DETERMINE IF MSRP IS AVAILABLE FOR DISPLAY
                        if (_ShowRetailPrice && msrpWithVAT > 0 && !salePriceEffective)
                        {
                            trRetailPrice.Visible       = true;
                            HiddenRetailPriceLabel.Text = PopupRetailPriceLabel;
                            HiddenRetailPrice.Text      = string.Format(PopupRetailPriceFormat, msrpWithVAT.LSCurrencyFormat("ulc"));
                            // CALCULATE AMOUNT SAVED OVER MSRP
                            amountSaved  = (msrpWithVAT - priceWithVAT);
                            percentSaved = ((decimal)(amountSaved / msrpWithVAT)) * 100;
                        }
                        else
                        {
                            trRetailPrice.Visible = false;
                        }
                        // CHECK IF A SALE PRICE IS APPLIED
                        if (salePriceEffective)
                        {
                            // SPECIAL APPLIED, SHOW THE PRODUCT BASE PRICE AND THE SPECIAL PRICE
                            trSpecialPrice.Visible = true;
                            HiddenPriceLabel.Text  = PopupBasePriceLabel;
                            HiddenPrice.Text       = string.Format(PopupBasePriceFormat, basePriceWithVAT.LSCurrencyFormat("ulc"));
                            SpecialPriceLabel.Text = PopupSpecialPriceLabel;
                            if (pcalc.AppliedSpecial.EndDate != DateTime.MinValue)
                            {
                                SpecialPrice.Text = string.Format(PopupSpecialPriceFormat, priceWithVAT.LSCurrencyFormat("ulc"), pcalc.AppliedSpecial.EndDate);
                            }
                            else
                            {
                                SpecialPrice.Text = string.Format(PopupSpecialPriceFormat2, priceWithVAT.LSCurrencyFormat("ulc"), null);
                            }
                            // CALCULATE AMOUNT SAVED WITH SALE PRICE
                            amountSaved  = (basePriceWithVAT - priceWithVAT);
                            percentSaved = ((decimal)(amountSaved / basePriceWithVAT)) * 100;
                        }
                        else
                        {
                            // NO SPECIAL, SO JUST SHOW THE CALCULATED PRICE
                            HiddenPriceLabel.Text = PopupPriceLabel;
                            HiddenPrice.Text      = string.Format(PopupPriceFormat, priceWithVAT.LSCurrencyFormat("ulc"));
                        }
                        // SEE IF WE HAVE AN AMOUNT SAVED VALUE
                        if (amountSaved > 0)
                        {
                            trAmountSaved.Visible = true;
                            AmountSavedLabel.Text = PopupAmountSavedLabel;
                            AmountSaved.Text      = string.Format(PopupAmountSavedFormat, amountSaved.LSCurrencyFormat("ulc"), percentSaved);
                        }
                        else
                        {
                            trAmountSaved.Visible = false;
                        }
                    }
                }
                else
                {
                    //DO NOT DISPLAY THIS CONTROL IF THE PRODUCT HAS VARIABLE PRICE
                    this.Controls.Clear();
                }
            }
            else
            {
                //DO NOT DISPLAY THIS CONTROL IF THE PRODUCT IS UNAVAILABLE
                this.Controls.Clear();
            }
            SaveCustomViewState();
        }
        protected void AddProductPrice_PreRender(object sender, EventArgs e)
        {
            int     productId = AlwaysConvert.ToInt(AddProductId.Value);
            Product product   = ProductDataSource.Load(productId);

            if (product != null)
            {
                //GET THE SELECTED KIT OPTIONS
                GetSelectedKitOptions(product);
                //SET THE CURRENT CALCULATED PRICE
                string            optionList            = ProductVariantDataSource.GetOptionList(productId, _SelectedOptions, true);
                bool              calculateOneTimePrice = AlwaysConvert.ToBool(OptionalSubscription.SelectedValue, false);
                ProductCalculator pcalc = ProductCalculator.LoadForProduct(productId, 1, optionList, AlwaysConvert.ToList(",", _SelectedKitProducts), _UserId, false, calculateOneTimePrice);
                AddProductPrice.Text = string.Format("{0:F2}", pcalc.Price);

                if (product.IsSubscription)
                {
                    if (product.SubscriptionPlan.IsRecurring)
                    {
                        if (!calculateOneTimePrice)
                        {
                            short frequency = product.SubscriptionPlan.PaymentFrequencyType == PaymentFrequencyType.Optional ? AlwaysConvert.ToInt16(AutoDeliveryInterval.SelectedValue) : product.SubscriptionPlan.PaymentFrequency;
                            SubscriptionMessage.Text    = ProductHelper.GetRecurringPaymentMessage(product.Price, 0, product.SubscriptionPlan, frequency);
                            SubscriptionMessage.Visible = true;
                        }
                        else
                        {
                            SubscriptionMessage.Visible = false;
                        }
                    }
                    else
                    {
                        trSubscriptionRow.Visible = product.SubscriptionPlan.IsOptional;
                    }
                }
                else
                {
                    trSubscriptionRow.Visible = false;
                }

                if (product.UseVariablePrice && !product.IsSubscription && !product.IsKit)
                {
                    AddProductVariablePrice.Text    = string.Format("{0:F2}", pcalc.Price);
                    AddProductVariablePrice.Visible = true;
                    string varPriceText = string.Empty;
                    if (product.MinimumPrice > 0)
                    {
                        if (product.MaximumPrice > 0)
                        {
                            varPriceText = string.Format("(between {0} and {1})", product.MinimumPrice.LSCurrencyFormat("lcf"), product.MaximumPrice.LSCurrencyFormat("lcf"));
                        }
                        else
                        {
                            varPriceText = string.Format("(at least {0})", product.MinimumPrice.LSCurrencyFormat("lcf"));
                        }
                    }
                    else if (product.MaximumPrice > 0)
                    {
                        varPriceText = string.Format("({0} maximum)", product.MaximumPrice.LSCurrencyFormat("lcf"));
                    }
                    phVariablePrice.Controls.Add(new LiteralControl(varPriceText));
                }
                AddProductPrice.Visible = !AddProductVariablePrice.Visible;
                if ((AddProductPrice.Visible && _Basket.UserId == AbleContext.Current.UserId) || (product.IsKit))
                {
                    AddProductPrice.Enabled = false;
                }
            }
        }
        protected BasketItem CreateBasketItem()
        {
            //GET THE PRODUCT ID
            int     productId = AlwaysConvert.ToInt(AddProductId.Value);
            Product product   = ProductDataSource.Load(productId);

            if (product == null)
            {
                return(null);
            }
            //GET THE QUANTITY
            short tempQuantity = AlwaysConvert.ToInt16(AddProductQuantity.Text);

            if (tempQuantity < 1)
            {
                return(null);
            }
            //RECALCULATE SELECTED KIT OPTIONS
            GetSelectedKitOptions(product);
            // DETERMINE THE OPTION LIST
            string optionList = ProductVariantDataSource.GetOptionList(productId, _SelectedOptions, false);

            //CREATE THE BASKET ITEM WITH GIVEN OPTIONS
            bool       calculateOneTimePrice = AlwaysConvert.ToBool(OptionalSubscription.SelectedValue, false);
            BasketItem basketItem            = BasketItemDataSource.CreateForProduct(productId, tempQuantity, optionList, AlwaysConvert.ToList(",", _SelectedKitProducts), _UserId, calculateOneTimePrice);

            if (basketItem != null)
            {
                //BASKET ID
                basketItem.BasketId = _Basket.Id;

                // PRODUCT PRICE FOR VARIABLE PRICE PRODUCT
                if (product.UseVariablePrice && !product.IsSubscription && !product.IsKit)
                {
                    basketItem.Price = AlwaysConvert.ToDecimal(AddProductVariablePrice.Text);
                }
                else
                {
                    basketItem.Price = AlwaysConvert.ToDecimal(AddProductPrice.Text);
                }

                if (product.IsSubscription)
                {
                    if (product.SubscriptionPlan.IsOptional)
                    {
                        basketItem.IsSubscription = !calculateOneTimePrice;
                    }
                    else
                    {
                        basketItem.IsSubscription = true;
                    }

                    if (basketItem.IsSubscription && product.SubscriptionPlan.IsRecurring)
                    {
                        basketItem.Frequency     = product.SubscriptionPlan.PaymentFrequencyType == PaymentFrequencyType.Optional ? AlwaysConvert.ToInt16(AutoDeliveryInterval.SelectedValue) : product.SubscriptionPlan.PaymentFrequency;
                        basketItem.FrequencyUnit = product.SubscriptionPlan.PaymentFrequencyUnit;
                    }
                    else if (basketItem.IsSubscription)
                    {
                        basketItem.Frequency     = product.SubscriptionPlan.PaymentFrequency;
                        basketItem.FrequencyUnit = product.SubscriptionPlan.PaymentFrequencyUnit;
                    }
                }


                // COLLECT ANY ADDITIONAL INPUTS
                AbleCommerce.Code.ProductHelper.CollectProductTemplateInput(basketItem, this);
            }
            return(basketItem);
        }
Esempio n. 15
0
 /// <summary>
 /// Calculates variant
 /// </summary>
 /// <returns><b>true</b> if calculation successful, <b>false</b> otherwise</returns>
 public bool CalculateVariant()
 {
     _Calculated = false;
     int[] choiceIds = this.GetOptionChoices(OptionCountBehavior.ActualCount);
     if (choiceIds != null && choiceIds.Length > 0)
     {
         //INITIALIZE THE CALCULATED VALUES
         _CalculatedPrice  = 0;
         _CalculatedWeight = 0;
         //BUILD CRITERIA TO LOAD CORRECT OPTIONS
         string criteria;
         if (choiceIds.Length == 1)
         {
             criteria = "OptionChoiceId = " + choiceIds[0].ToString();
         }
         else
         {
             string idList = AlwaysConvert.ToList(",", choiceIds);
             criteria = "OptionChoiceId IN (" + idList + ")";
         }
         //RECALCULATE ALL ITEMS
         OptionChoiceCollection choices = OptionChoiceDataSource.LoadForCriteria(criteria);
         OptionChoice           choice;
         List <string>          names = new List <string>();
         StringBuilder          sku   = new StringBuilder();
         sku.Append(this.Product.Sku);
         //LOOP ALL CHOICES INDICATED FOR THIS VARIANT AND CALCULATE THE MODIFIERS
         foreach (int optionChoiceId in choiceIds)
         {
             int index = choices.IndexOf(optionChoiceId);
             if (index > -1)
             {
                 choice = choices[index];
                 names.Add(choice.Name);
                 _CalculatedPrice  += choice.PriceModifier;
                 _CalculatedWeight += choice.WeightModifier;
                 sku.Append(choice.SkuModifier);
             }
         }
         //SET THE CALCULATED VALUES
         _CalculatedName = String.Join(", ", names.ToArray());
         _CalculatedSku  = sku.ToString();
         if (this.VariantName == string.Empty)
         {
             this.VariantName = _CalculatedName;
         }
         if (this.Price == 0)
         {
             this.Price = _CalculatedPrice;
         }
         if (this.Weight == 0)
         {
             this.Weight = _CalculatedWeight;
         }
         if (this.Sku == string.Empty)
         {
             this.Sku = _CalculatedSku;
         }
         _Calculated = true;
     }
     return(_Calculated);
 }
Esempio n. 16
0
 public override string ToString()
 {
     return(AlwaysConvert.ToList(",", this));
 }
Esempio n. 17
0
        protected BasketItem GetBasketItem(string optionList, GridViewCommandEventArgs e)
        {
            //GET THE QUANTITY
            GridViewRow row          = (GridViewRow)((Control)e.CommandSource).Parent.Parent;
            int         tempQuantity = GetControlValue(row, "Quantity", 1);

            if (tempQuantity < 1)
            {
                return(null);
            }
            if (tempQuantity > System.Int16.MaxValue)
            {
                tempQuantity = System.Int16.MaxValue;
            }

            //CREATE THE BASKET ITEM WITH GIVEN OPTIONS
            BasketItem basketItem = BasketItemDataSource.CreateForProduct(_ProductId, (short)tempQuantity, optionList, AlwaysConvert.ToList(",", _SelectedKitProducts));

            if (basketItem != null)
            {
                basketItem.Basket = AbleContext.Current.User.Basket;

                //ADD IN VARIABLE PRICE
                //if (_Product.UseVariablePrice) basketItem.Price = AlwaysConvert.ToDecimal(VariablePrice.Text);
                // COLLECT ANY ADDITIONAL INPUTS
                AbleCommerce.Code.ProductHelper.CollectProductTemplateInput(basketItem, this);
            }
            return(basketItem);
        }
        /// <summary>
        /// Get all basket items that are descendant products of the category and are eligible for discount
        /// </summary>
        /// <param name="categoryId"></param>
        /// <param name="basket"></param>
        /// <param name="productsToExclude"></param>
        /// <returns></returns>
        private static BasketItemCollection GetCategoryItems(int categoryId, Basket basket, List <int> productsToExclude)
        {
            //BUILD CRITERIA FOR PRODUCTS TO EXCLUDE FROM QUERY
            string excludedProducts = string.Empty;

            if (productsToExclude.Count > 0)
            {
                if (productsToExclude.Count == 1)
                {
                    excludedProducts = " AND BI.ProductId <> " + productsToExclude[0].ToString();
                }
                else
                {
                    excludedProducts = " AND BI.ProductId NOT IN (" + AlwaysConvert.ToList(",", productsToExclude.ToArray()) + ")";
                }
            }

            //FIND ALL PRODUCTS THAT ARE A DESCENDANT OF THE CATEGORY
            StringBuilder categorySql = new StringBuilder();

            categorySql.Append("SELECT DISTINCT BI.BasketItemId");
            categorySql.Append(" FROM (ac_BasketItems BI INNER JOIN ac_CatalogNodes CN ON BI.ProductId = CN.CatalogNodeId");
            categorySql.Append(" INNER JOIN ac_CategoryParents CP ON CN.CategoryId = CP.CategoryId)");
            categorySql.Append(" WHERE BI.BasketId = @basketId");
            categorySql.Append(" AND CN.CatalogNodeTypeId = 1");
            categorySql.Append(" AND CP.ParentId = @categoryId");
            categorySql.Append(excludedProducts);

            //EXECUTE THE QUERY
            Database  database = Token.Instance.Database;
            DbCommand command  = database.GetSqlStringCommand(categorySql.ToString());

            database.AddInParameter(command, "@basketId", System.Data.DbType.Int32, basket.BasketId);
            database.AddInParameter(command, "@categoryId", System.Data.DbType.Int32, categoryId);
            //BUILD LIST OF BASKET ITEM IDS
            List <int> basketItemIds = new List <int>();

            using (IDataReader dr = database.ExecuteReader(command))
            {
                while (dr.Read())
                {
                    basketItemIds.Add(dr.GetInt32(0));
                }
                dr.Close();
            }

            //BUILD THE COLLECTION OF BASKET ITEMS
            BasketItemCollection items = new BasketItemCollection();

            foreach (int id in basketItemIds)
            {
                int index = basket.Items.IndexOf(id);
                if (index > -1)
                {
                    items.Add(basket.Items[index]);
                }
            }

            //RETURN THE BASKET ITEMS THAT ARE DESCENDANTS OF THIS CATEGORY
            return(items);
        }
Esempio n. 19
0
        private void SendEmail(bool all, bool perUser)
        {
            List <int> selectedIds = new List <int>();

            if (all)
            {
                if (perUser)
                {
                    int subscriptionPlanId             = AlwaysConvert.ToInt(SubscriptionPlan.SelectedValue);
                    IList <Subscription> subscriptions = SubscriptionDataSource.Search(subscriptionPlanId, OrderNumber.Text, string.Empty, FirstName.Text, LastName.Text, Email.Text, ExpirationStart.SelectedDate, ExpirationEnd.SelectedDate, (BitFieldState)Enum.Parse(typeof(BitFieldState), ActiveOnly.SelectedValue));
                    foreach (Subscription subscription in subscriptions)
                    {
                        int userId = subscription.User.Id;
                        if (!selectedIds.Contains(userId))
                        {
                            selectedIds.Add(userId);
                        }
                    }
                }
                else
                {
                    int subscriptionPlanId             = AlwaysConvert.ToInt(SubscriptionPlan.SelectedValue);
                    IList <Subscription> subscriptions = SubscriptionDataSource.Search(subscriptionPlanId, OrderNumber.Text, string.Empty, FirstName.Text, LastName.Text, Email.Text, ExpirationStart.SelectedDate, ExpirationEnd.SelectedDate, (BitFieldState)Enum.Parse(typeof(BitFieldState), ActiveOnly.SelectedValue));
                    foreach (Subscription subscription in subscriptions)
                    {
                        selectedIds.Add(subscription.Id);
                    }
                }
            }
            else
            {
                if (perUser)
                {
                    List <DataKey> selectedItems = GetSelectedItems();
                    foreach (DataKey item in selectedItems)
                    {
                        if (item.Values.Count > 1)
                        {
                            int userId = AlwaysConvert.ToInt(item.Values[1].ToString());
                            if (!selectedIds.Contains(userId))
                            {
                                selectedIds.Add(userId);
                            }
                        }
                    }
                }
                else
                {
                    List <DataKey> selectedItems = GetSelectedItems();
                    foreach (DataKey item in selectedItems)
                    {
                        int subscriptionId = AlwaysConvert.ToInt(item.Value.ToString());
                        selectedIds.Add(subscriptionId);
                    }
                }
            }

            if (selectedIds.Count < 1)
            {
                return;
            }
            Session["SendMail_IdList"] = (perUser ? "UserId:" : "SubscriptionId:") + AlwaysConvert.ToList(",", selectedIds);
            Response.Redirect("../Users/SendMail.aspx?ReturnUrl=" + Convert.ToBase64String(System.Text.Encoding.UTF8.GetBytes("~/Admin/People/Subscriptions/Default.aspx")));
        }
        /// <summary>
        /// Gets a dictionary of potential discounts for the basket.
        /// </summary>
        /// <param name="basket">Basket to check for potential discounts</param>
        /// <param name="productsToExclude">Products that should not be considered for discounts.</param>
        /// <param name="groupingMode">Grouping mode in use</param>
        /// <returns>A dictionary of potential discounts for the order.</returns>
        private static Dictionary <int, List <PotentialDiscount> > GetPotentialDiscounts(Basket basket, List <int> productsToExclude, GroupingMode groupingMode)
        {
            //INITIALIZE THE RETURN VALUE
            Dictionary <int, List <PotentialDiscount> > potentialDiscounts = new Dictionary <int, List <PotentialDiscount> >();

            //KEEP TRACK OF PRODUCTS TO EXCLUDE FROM GLOBAL DISCOUNTS
            List <int> excludeGlobal = new List <int>();

            //BUILD CRITERIA FOR PRODUCTS TO EXCLUDE FROM QUERY
            string excludedProducts = string.Empty;

            if (productsToExclude.Count > 0)
            {
                if (productsToExclude.Count == 1)
                {
                    excludedProducts = " AND ProductId <> " + productsToExclude[0].ToString();
                }
                else
                {
                    excludedProducts = " AND ProductId NOT IN (" + AlwaysConvert.ToList(",", productsToExclude.ToArray()) + ")";
                }
                //ALSO EXCLUDE THESE PRODUCTS FROM GLOBAL DISCOUNTS
                excludeGlobal.AddRange(productsToExclude);
            }

            //FIND ALL DISCOUNTS THAT ARE ASSOCIATED WITH PRODUCTS IN THE BASKET
            StringBuilder categorySql = new StringBuilder();

            categorySql.Append("SELECT DISTINCT CP.ParentId, CP.ParentLevel, CVD.VolumeDiscountId");
            if (groupingMode == GroupingMode.Product)
            {
                categorySql.Append(", CN.CatalogNodeId");
            }
            categorySql.Append(" FROM (ac_BasketItems BI INNER JOIN ac_CatalogNodes CN ON BI.ProductId = CN.CatalogNodeId");
            categorySql.Append(" INNER JOIN ac_CategoryParents CP ON CN.CategoryId = CP.CategoryId");
            categorySql.Append(" INNER JOIN ac_CategoryVolumeDiscounts CVD ON CP.ParentId = CVD.CategoryId)");
            categorySql.Append(" WHERE BI.BasketId = @basketId ");
            categorySql.Append(" AND CN.CatalogNodeTypeId = 1");
            categorySql.Append(excludedProducts);
            //ORDER FROM THE MOST SPECIFIC CATEGORY TO THE LEAST (PARENTLEVEL)
            categorySql.Append(" ORDER BY CP.ParentLevel DESC");
            if (groupingMode == GroupingMode.Product)
            {
                categorySql.Append(", CN.CatalogNodeId ASC");
            }

            //CREATE THE COMMAND
            Database  database = Token.Instance.Database;
            DbCommand command  = database.GetSqlStringCommand(categorySql.ToString());

            database.AddInParameter(command, "@basketId", System.Data.DbType.Int32, basket.BasketId);
            DataSet allDiscounts = database.ExecuteDataSet(command);

            //LOOP ALL DISCOUNTS, BUILD LIST OF POTENTIAL DISCOUNTS THAT COULD APPLY TO USER
            User user = basket.User;

            foreach (DataRow row in allDiscounts.Tables[0].Rows)
            {
                //GET THE DISCOUNTED OBJECT (EITHER PRODUCT OR CATEGORY LEVEL)
                int key;
                if (groupingMode == GroupingMode.Product)
                {
                    key = (int)row[3];
                }
                else
                {
                    key = Convert.ToInt32((byte)row[1]);
                }

                //GET THE LEVEL OF THE CATEGORY (DETERMINES PRECEDENCE)
                int categoryLevel = Convert.ToInt32((byte)row[1]);

                //FIND THE LIST OF POTENTIAL DISCOUNTS FOR THIS KEY
                if (!potentialDiscounts.ContainsKey(key))
                {
                    potentialDiscounts[key] = new List <PotentialDiscount>();
                }
                List <PotentialDiscount> discountGroup = potentialDiscounts[key];

                //DECIDE WHETHER THIS DISCOUNT HAS ENOUGH PRECDENCE TO CHECK
                bool checkDiscount = true;
                if (discountGroup.Count > 0)
                {
                    //THE CURRENT ROW COULD HAVE THE SAME LEVEL AS THE DISCOUNTS ALREADY FOUND
                    if (categoryLevel < discountGroup[0].CategoryLevel)
                    {
                        checkDiscount = false;
                    }
                    //WE DO NOT HAVE TO CHECK FOR LEVEL BEING GREATER, BECAUSE
                    //THE QUERY INCLUDES PARENT LEVEL IN THE ORDERBY CLAUSE
                }

                if (checkDiscount)
                {
                    //THIS COULD BE A VALID DISCOUNT
                    int volumeDiscountId = (int)row[2];
                    //CHECK FOR USER EXCLUSIONS
                    VolumeDiscount v = VolumeDiscountDataSource.Load(volumeDiscountId);
                    if ((v != null) && (v.IsValidForUser(user)))
                    {
                        //THE DISCOUNT IS VALID FOR THIS USER
                        //ADD TO THE LIST OF POTENTIALS
                        PotentialDiscount pd = new PotentialDiscount();
                        pd.CategoryId       = (int)row[0];
                        pd.CategoryLevel    = categoryLevel;
                        pd.VolumeDiscountId = volumeDiscountId;
                        if (groupingMode == GroupingMode.Product)
                        {
                            pd.ProductId = key;
                            //SINCE THERE IS A CATEGORY DISCOUNT, WE DO
                            //NOT WANT TO USE ANY GLOBAL DISCOUNTS FOR THIS PRODUCT
                            excludeGlobal.Add(key);
                        }
                        discountGroup.Add(pd);
                    }
                }
            }

            List <int> globalDiscountProducts = new List <int>();

            if (groupingMode == GroupingMode.Product)
            {
                //CHECK WHETHER ANY PRODUCTS REMAIN IN ORDER THAT ARE ELIGIBLE
                //FOR GLOBAL DISCOUNTS
                foreach (BasketItem item in basket.Items)
                {
                    //MAKE SURE THIS IS A PRODUCT AND IS NOT EXCLUDED FROM GLOBAL DISCOUNT
                    if ((item.ProductId > 0) && (excludeGlobal.IndexOf(item.ProductId) < 0))
                    {
                        //ADD THIS PRODUCT TO THE GLOBAL DISCOUNT LIST (IF NOT ALREADY THERE)
                        if (globalDiscountProducts.IndexOf(item.ProductId) < 0)
                        {
                            globalDiscountProducts.Add(item.ProductId);
                        }
                    }
                }
            }

            //ARE WE CALCULATING DISCOUNTS USING CATEGORY GROUPING MODE?
            //OR ARE THERE ANY PRODUCTS THAT COULD HAVE GLOBAL DISCOUNTS?
            if (groupingMode == GroupingMode.Category || globalDiscountProducts.Count > 0)
            {
                //FIND ANY GLOBAL DISCOUNTS
                VolumeDiscountCollection globalDiscounts = VolumeDiscountDataSource.LoadGlobal();
                if (globalDiscounts.Count > 0)
                {
                    if (groupingMode == GroupingMode.Product)
                    {
                        foreach (int productId in globalDiscountProducts)
                        {
                            potentialDiscounts[productId] = new List <PotentialDiscount>();
                            List <PotentialDiscount> discountGroup = potentialDiscounts[productId];
                            foreach (VolumeDiscount v in globalDiscounts)
                            {
                                //VERIFY USER RESTRICTION ON GLOBAL DISCOUNT
                                if (v.IsValidForUser(user))
                                {
                                    PotentialDiscount pd = new PotentialDiscount();
                                    pd.CategoryId       = 0;
                                    pd.CategoryLevel    = 0;
                                    pd.VolumeDiscountId = v.VolumeDiscountId;
                                    pd.ProductId        = productId;
                                    discountGroup.Add(pd);
                                }
                            }
                        }
                    }
                    else
                    {
                        potentialDiscounts[0] = new List <PotentialDiscount>();
                        List <PotentialDiscount> discountGroup = potentialDiscounts[0];
                        foreach (VolumeDiscount v in globalDiscounts)
                        {
                            //VERIFY USER RESTRICTION ON GLOBAL DISCOUNT
                            if (v.IsValidForUser(user))
                            {
                                PotentialDiscount pd = new PotentialDiscount();
                                pd.CategoryId       = 0;
                                pd.CategoryLevel    = 0;
                                pd.VolumeDiscountId = v.VolumeDiscountId;
                                pd.ProductId        = 0;
                                discountGroup.Add(pd);
                            }
                        }
                    }
                }
            }

            //REMOVE ANY ENTRIES FROM THE LIST THAT HAVE NO DISCOUNTS
            List <int> emptyKeys = new List <int>();

            foreach (int key in potentialDiscounts.Keys)
            {
                if (potentialDiscounts[key].Count == 0)
                {
                    emptyKeys.Add(key);
                }
            }
            foreach (int key in emptyKeys)
            {
                potentialDiscounts.Remove(key);
            }

            //RETURN POTENTIAL DISCOUNTS FOR BASKET
            return(potentialDiscounts);
        }
        protected void Price_PreRender(object sender, EventArgs e)
        {
            int     productId = AlwaysConvert.ToInt(HiddenProductId.Value);
            Product product   = ProductDataSource.Load(productId);

            if (product != null)
            {
                //GET THE SELECTED KIT OPTIONS
                GetSelectedKitOptions(product);
            }
            //SET THE CURRENT CALCULATED PRICE
            string            optionList = ProductVariantDataSource.GetOptionList(productId, _SelectedOptions, true);
            ProductCalculator pcalc      = ProductCalculator.LoadForProduct(productId, 1, optionList, AlwaysConvert.ToList(",", _SelectedKitProducts));

            Price.Text = string.Format("{0:F2}", pcalc.Price);

            if (product.UseVariablePrice)
            {
                string varPriceText = string.Empty;
                if (product.MinimumPrice > 0)
                {
                    if (product.MaximumPrice > 0)
                    {
                        varPriceText = string.Format("(between {0} and {1})", product.MinimumPrice.LSCurrencyFormat("lcf"), product.MaximumPrice.LSCurrencyFormat("lcf"));
                    }
                    else
                    {
                        varPriceText = string.Format("(at least {0})", product.MinimumPrice.LSCurrencyFormat("lcf"));
                    }
                }
                else if (product.MaximumPrice > 0)
                {
                    varPriceText = string.Format("({0} maximum)", product.MaximumPrice.LSCurrencyFormat("lcf"));
                }
                phVariablePrice.Controls.Add(new LiteralControl(varPriceText));
            }

            // CHANGING PRODUCT PRICE OPTION SHOULD NOT AVAILABLE FOR KIT PRODUCTS
            Price.Enabled = (product.KitStatus != KitStatus.Master);

            InventoryAlertUpdate();
        }