protected override void OnPreRender(EventArgs e)
    {
        #region Dynamic load CSS and JS files

        string crlf = ""; // "\r\n";

        System.Text.StringBuilder sb = new System.Text.StringBuilder();
        sb.Append("<script type=\"text/javascript\">\r\n");
        //Google Chrome & Safari Ajax Bug
        bool isInAjaxPostBack = AjaxHelper.IsInAjaxPostBack(this.Page);
        if (!isInAjaxPostBack)
        {
            sb.Append("//<![CDATA[\r\n");
        }

        // JS function executed after the JS library is loaded
        sb.Append("function " + this.InitFunctionName2 + "()" + crlf);
        sb.Append("{" + crlf);
        sb.Append("var loadData={" + crlf);
        sb.Append("popupPictureTrimmerClientId:\"" + JSHelper.EncodeString(this.popupPictureTrimmer1.ClientID) + "\"" + crlf);
        sb.Append(",btnEditClientId:\"" + JSHelper.EncodeString(this.btnEdit.ClientID) + "\"" + crlf);
        sb.Append(",btnRemoveClientId:\"" + JSHelper.EncodeString(this.btnRemove.ClientID) + "\"" + crlf);
        sb.Append(",btnBrowseDisabledClientId:\"" + JSHelper.EncodeString(this.btnBrowseDisabled.ClientID) + "\"" + crlf);
        sb.Append(",btnCancelUploadClientId:\"" + JSHelper.EncodeString(this.btnCancelUpload.ClientID) + "\"" + crlf);
        sb.Append(",btnBrowseClientId:\"" + JSHelper.EncodeString(this.btnBrowse.ClientID) + "\"" + crlf);
        sb.Append(",hfActClientId:\"" + JSHelper.EncodeString(this.hfAct.ClientID) + "\"" + crlf);
        sb.Append(",ddlConfigurationsClientId:\"" + JSHelper.EncodeString(this.ddlConfigurations.ClientID) + "\"" + crlf);
        sb.Append(",hlPictureImageEditId:\"" + JSHelper.EncodeString(this.hlPictureImageEdit.ClientID) + "\"" + crlf);        

        sb.Append(",uploadUrl:\"" + JSHelper.EncodeString(this.UploadUrl) + "\"" + crlf);
        sb.Append(",uploadMonitorUrl:\"" + JSHelper.EncodeString(this.UploadMonitorUrl) + "\"" + crlf);
        sb.Append(",btnPostBack_PostBackEventReference:\"" + JSHelper.EncodeString(this.Page.ClientScript.GetPostBackEventReference(this.btnPostBack, "")) + "\"" + crlf);
        sb.Append(",imageEditPopupSize_width:" + this.ImageEditPopupSize.Width.ToString(System.Globalization.CultureInfo.InvariantCulture) + crlf);
        sb.Append(",imageEditPopupSize_height:" + this.ImageEditPopupSize.Height.ToString(System.Globalization.CultureInfo.InvariantCulture) + crlf);
        sb.Append(",autoOpenImageEditPopup:" + JSHelper.EncodeBool(this._AutoOpenImageEditPopup) + crlf);
        sb.Append(",autoDisableImageEdit:" + JSHelper.EncodeBool(this._AutoDisableImageEdit) + crlf);
        sb.Append(",buttonSize_width:" + this.ButtonSize.Width.ToString(System.Globalization.CultureInfo.InvariantCulture) + crlf);
        sb.Append(",buttonSize_height:" + this.ButtonSize.Height.ToString(System.Globalization.CultureInfo.InvariantCulture) + crlf);
        sb.Append(",enableEdit:" + JSHelper.EncodeBool(this._EnableEdit) + crlf);
        sb.Append(",enableRemove:" + JSHelper.EncodeBool(this._EnableRemove) + crlf);
        sb.Append(",enableCancelUpload:" + JSHelper.EncodeBool(this._EnableCancelUpload) + crlf);
        sb.Append(",dup:" + JSHelper.EncodeBool(this._DebugUploadProblems) + crlf);
        sb.Append(",statusMessage_Wait:\"" + JSHelper.EncodeString(this.StatusMessage_Wait) + "\"" + crlf);
        sb.Append("};" + crlf);
        sb.Append("var control = CodeCarvings.Wcs.Piczard.Upload.SimpleImageUpload.loadControl(\"" + JSHelper.EncodeString(this.ClientID) + "\", loadData);");
        sb.Append("}" + crlf);

        // Dynamic load JS / CSS (required for Ajax)
        sb.Append("function " + this.InitFunctionName + "()" + crlf);
        sb.Append("{" + crlf);
        sb.Append("if (typeof(window.__ccpz_siu_lt) === \"undefined\")" + crlf);
        sb.Append("{" + crlf);
        // The variable (window.__ccpz_siu_lt) (configured in simpleImageUpload.js) is undefined...
        sb.Append(JSHelper.GetLoadScript(this.ResolveUrl("simpleImageUpload.js?v=5"), this.InitFunctionName + "_load_js", this.InitFunctionName2 + "();") + crlf);
        sb.Append("}" + crlf);
        sb.Append("else" + crlf);
        sb.Append("{" + crlf);
        sb.Append(this.InitFunctionName2 + "();" + crlf);
        sb.Append("}" + crlf);
        sb.Append("}" + crlf);

        if (!isInAjaxPostBack)
        {
            sb.Append("\r\n//]]>\r\n");
        }
        sb.Append("</script>");

        string scriptToRegister = sb.ToString();
        if (!AjaxHelper.RegisterClientScriptBlockInAjaxPostBack(this.Page, "CCPZ_SIU_DAI_" + this.ClientID, scriptToRegister, false))
        {
            this.litScript.Text = scriptToRegister;
        }
        else
        {
            this.litScript.Text = "";
        }

        // Setup the initialization function
        if (this.Visible)
        {
            this.popupPictureTrimmer1.OnClientControlLoadFunction = this.InitFunctionName;
        }

        #endregion

        // Hide design-time elements
        this.phDesignTimeStart.Visible = false;
        this.phDesignTimeEnd.Visible = false;

        // Update the layout
        this.btnEdit.Visible = this.EnableEdit;
        this.btnEdit.Width = this.ButtonSize.Width;
        this.btnEdit.Height = this.ButtonSize.Height;

        this.btnRemove.Visible = this.EnableRemove;
        this.btnRemove.Width = this.ButtonSize.Width;
        this.btnRemove.Height = this.ButtonSize.Height;

        this.btnBrowse.Width = this.ButtonSize.Width;
        this.btnBrowseDisabled.Width = this.ButtonSize.Width;

        this.btnBrowse.Height = this.ButtonSize.Height;
        this.btnBrowseDisabled.Height = this.ButtonSize.Height;

        this.btnCancelUpload.OnClientClick = "CodeCarvings.Wcs.Piczard.Upload.SimpleImageUpload.cancelUpload(\"" + JSHelper.EncodeString(this.ClientID) + "\"); return false;";

        this.btnCancelUpload.Width = this.ButtonSize.Width;
        this.btnCancelUpload.Height = this.ButtonSize.Height;

        this.phEditCommands.Visible = this.EnableEdit || this.EnableRemove;

        this.phUploadCommands.Visible = this.EnableUpload;
        this.btnCancelUpload.Visible = this.EnableCancelUpload;

        // Update the texts
        this.litStatusMessage.Text = this.GetCurrentStatusMessage();

        this.btnEdit.Text = this.Text_EditButton;
        this.btnRemove.Text = this.Text_RemoveButton;
        this.btnBrowse.Text = this.Text_BrowseButton;
        this.btnBrowseDisabled.Text = this.Text_BrowseButton;
        this.btnCancelUpload.Text = this.Text_CancelUploadButton;

        if (this.HasImage)
        {
            if (!File.Exists(this.PreviewImageFilePath))
            {
                // The preview file does not exists -> create it
                this._UpdatePreview = true;
            }

            if (this._UpdatePreview)
            {
                // Get the processing job (Default resolution = 96DPI)
                ImageProcessingJob job = this.GetImageProcessingJob();
                job.OutputResolution = CommonData.DefaultResolution;

                // Add the preview filter constraint
                if (this.PreviewFilter != null)
                {
                    job.Filters.Add(this.PreviewFilter);
                }

                // Save the preview image
                this.imgPreview.ImageUrl = null;
                if (File.Exists(this.TemporarySourceImageFilePath))
                {
                    // Jpeg images does not allow transparent images - Apply the right back color!
                    FormatEncoderParams format = new JpegFormatEncoderParams();
                    using (System.Drawing.Image previewImage = job.GetProcessedImage(this.TemporarySourceImageFilePath, format))
                    {
                        ImageArchiver.SaveImageToFileSystem(previewImage, this.PreviewImageFilePath, format);

                        // Force the reload of the preview
                        this.imgPreview.ImageUrl = this.PreviewImageUrl;
                        this.imgPreview.Width = Unit.Pixel(previewImage.Size.Width);
                        this.imgPreview.Height = Unit.Pixel(previewImage.Size.Height);
                    }
                }
            }
        }

        if (string.IsNullOrEmpty(this.imgPreview.ImageUrl))
        {
            // Set a dummy image (for xhtml compliance)
            this.imgPreview.ImageUrl = this.ResolveUrl("blank.gif");
            this.imgPreview.Width = Unit.Pixel(1);
            this.imgPreview.Height = Unit.Pixel(1);
        }

        this.imgPreview.BorderColor = this._PreviewBorderColor;
        this.imgPreview.BorderStyle = this._PreviewBorderStyle;
        this.imgPreview.BorderWidth = this._PreviewBorderWidth;

        if (this._CropConstraint == null)
        {
            // Crop disabled
            this.popupPictureTrimmer1.ShowZoomPanel = false;
        }

        // Update the configuration UI
        this.litSelectConfiguration.Text = this.Text_ConfigurationLabel;
        this.ddlConfigurations.Items.Clear();
        string[] configurations = this.Configurations;
        if (configurations != null)
        {
            for (int i = 0; i < configurations.Length; i++)
            {
                this.ddlConfigurations.Items.Add(new ListItem(configurations[i], i.ToString(System.Globalization.CultureInfo.InvariantCulture)));
            }
            this.ddlConfigurations.SelectedIndex = this.SelectedConfigurationIndex.Value;
        }
        this.ddlConfigurations.Attributes["onchange"] = "CodeCarvings.Wcs.Piczard.Upload.SimpleImageUpload.onConfigurationChange(\"" + JSHelper.EncodeString(this.ClientID) + "\");";

        // Hide the SELECT element to mantain compliance with XHTML specs (SELECT cannot be emtpy...)
        if (this.ddlConfigurations.Items.Count > 0)
        {
            this.ddlConfigurations.Visible = true;
        }
        else
        {
            this.ddlConfigurations.Visible = false;
        }

        if (!string.IsNullOrEmpty(this._CssClass))
        {
            string[] classes = this._CssClass.Split(new char[] { ' ' }, StringSplitOptions.RemoveEmptyEntries);
            if (Array.IndexOf<string>(classes, "ccpz_fobr") >= 0)
            {
                this.popupPictureTrimmer1.CssClass = string.IsNullOrEmpty(this.popupPictureTrimmer1.CssClass) ? "ccpz_fobr" : this.popupPictureTrimmer1.CssClass + " ccpz_fobr";
            }
        }

        base.OnPreRender(e);
    }
    protected void SaveImage()
    {
        string savedImageFileName = "";
        FormatEncoderParams formatEncoderParams = null;

        object source = null;

        switch (this.ddlSourceType.SelectedIndex)
        {
        case 0:
            // File system
            source = this.imgLoaded.ImageUrl;
            break;

        case 1:
            // Byte array
            source = System.IO.File.ReadAllBytes(Server.MapPath(this.imgLoaded.ImageUrl));
            break;

        case 2:
            // Stream
            source = System.IO.File.OpenRead(Server.MapPath(this.imgLoaded.ImageUrl));
            // Note: The stream will be automatically closed/disposed by the LoadedImage class
            break;
        }
        using (LoadedImage loadedImage = ImageArchiver.LoadImage(source))
        {
            switch (this.ddlImageFormat.SelectedValue)
            {
            case "Auto":
                formatEncoderParams = ImageArchiver.GetDefaultFormatEncoderParams();
                break;

            case "JPEG":
                formatEncoderParams = new JpegFormatEncoderParams(int.Parse(this.txtJpegQuality.Text));
                break;

            case "GIF":
                GifFormatEncoderParams gifFormatEncoderParams = new GifFormatEncoderParams();
                formatEncoderParams = gifFormatEncoderParams;
                gifFormatEncoderParams.QuantizeImage = this.cbGifQuantize.Checked;
                if (this.cbGifQuantize.Checked)
                {
                    gifFormatEncoderParams.MaxColors = int.Parse(this.ddlGifMaxColors.SelectedValue);
                }
                break;

            case "PNG":
                PngFormatEncoderParams pngformatEncoderParams = new PngFormatEncoderParams();
                formatEncoderParams = pngformatEncoderParams;
                pngformatEncoderParams.ConvertToIndexed = this.cbPngConvertToIndex.Checked;
                if (this.cbPngConvertToIndex.Checked)
                {
                    pngformatEncoderParams.MaxColors = int.Parse(this.ddlPngMaxColors.SelectedValue);
                }
                break;
            }

            savedImageFileName = "~/repository/output/Ex_A_103" + formatEncoderParams.FileExtension;

            // IMPORTANT NOTE:  Apply a Noop (No Operation) filter to prevent a known GDI+ problem with transparent images
            // Example: http://forums.asp.net/t/1235100.aspx
            switch (this.ddlOutputType.SelectedIndex)
            {
            case 0:
                // File system
                new NoopFilter().SaveProcessedImageToFileSystem(loadedImage.Image, savedImageFileName, formatEncoderParams);
                break;

            case 1:
                // Byte array
                byte[] imageBytes = new NoopFilter().SaveProcessedImageToByteArray(loadedImage.Image, formatEncoderParams);
                System.IO.File.WriteAllBytes(Server.MapPath(savedImageFileName), imageBytes);
                break;

            case 2:
                // Stream
                using (System.IO.Stream stream = System.IO.File.OpenWrite(Server.MapPath(savedImageFileName)))
                {
                    new NoopFilter().SaveProcessedImageToStream(loadedImage.Image, stream, formatEncoderParams);
                }
                break;
            }
        }

        // Update the displayed image (add a timestamp parameter to the query URL to ensure that the image is reloaded by the browser)
        this.imgSaved.ImageUrl       = savedImageFileName + "?timestamp=" + DateTime.UtcNow.Ticks.ToString();
        this.phOutputPreview.Visible = true;

        // Display extension and size of both files
        this.litLoadedImageFileDetails.Text = System.IO.Path.GetExtension(this.imgLoaded.ImageUrl).ToUpper() + " file (" + (new System.IO.FileInfo(Server.MapPath(this.imgLoaded.ImageUrl))).Length.ToString() + " bytes)";
        this.litSavedImageFileDetails.Text  = System.IO.Path.GetExtension(savedImageFileName).ToUpper() + " file (" + (new System.IO.FileInfo(Server.MapPath(savedImageFileName))).Length.ToString() + " bytes)";
    }
    protected void SaveImage()
    {
        string savedImageFileName = "";
        FormatEncoderParams formatEncoderParams = null;

        object source = null;
        switch (this.ddlSourceType.SelectedIndex)
        {
            case 0:
                // File system
                source = this.imgLoaded.ImageUrl;
                break;
            case 1:
                // Byte array
                source = System.IO.File.ReadAllBytes(Server.MapPath(this.imgLoaded.ImageUrl));
                break;
            case 2:
                // Stream
                source = System.IO.File.OpenRead(Server.MapPath(this.imgLoaded.ImageUrl));
                // Note: The stream will be automatically closed/disposed by the LoadedImage class
                break;
        }
        using (LoadedImage loadedImage = ImageArchiver.LoadImage(source))
        {           
            switch(this.ddlImageFormat.SelectedValue)
            {
                case "Auto":
                    formatEncoderParams = ImageArchiver.GetDefaultFormatEncoderParams();
                    break;
                case "JPEG":
                    formatEncoderParams = new JpegFormatEncoderParams(int.Parse(this.txtJpegQuality.Text));
                    break;
                case "GIF":
                    GifFormatEncoderParams gifFormatEncoderParams = new GifFormatEncoderParams();
                    formatEncoderParams = gifFormatEncoderParams;
                    gifFormatEncoderParams.QuantizeImage = this.cbGifQuantize.Checked;
                    if (this.cbGifQuantize.Checked)
                    {
                        gifFormatEncoderParams.MaxColors = int.Parse(this.ddlGifMaxColors.SelectedValue);
                    }
                    break;
                case "PNG":
                    PngFormatEncoderParams pngformatEncoderParams = new PngFormatEncoderParams();
                    formatEncoderParams = pngformatEncoderParams;
                    pngformatEncoderParams.ConvertToIndexed = this.cbPngConvertToIndex.Checked;
                    if (this.cbPngConvertToIndex.Checked)
                    {
                        pngformatEncoderParams.MaxColors = int.Parse(this.ddlPngMaxColors.SelectedValue);
                    }
                    break;
            }

            savedImageFileName = "~/repository/output/Ex_A_103" + formatEncoderParams.FileExtension;

            // IMPORTANT NOTE:  Apply a Noop (No Operation) filter to prevent a known GDI+ problem with transparent images
            // Example: http://forums.asp.net/t/1235100.aspx
            switch (this.ddlOutputType.SelectedIndex)
            {
                case 0:
                    // File system
                    new NoopFilter().SaveProcessedImageToFileSystem(loadedImage.Image, savedImageFileName, formatEncoderParams);
                    break;
                case 1:
                    // Byte array
                    byte[] imageBytes = new NoopFilter().SaveProcessedImageToByteArray(loadedImage.Image, formatEncoderParams);
                    System.IO.File.WriteAllBytes(Server.MapPath(savedImageFileName), imageBytes);
                    break;
                case 2:
                    // Stream
                    using (System.IO.Stream stream = System.IO.File.OpenWrite(Server.MapPath(savedImageFileName)))
                    {
                        new NoopFilter().SaveProcessedImageToStream(loadedImage.Image, stream, formatEncoderParams);
                    }
                    break;
            }
        }

        // Update the displayed image (add a timestamp parameter to the query URL to ensure that the image is reloaded by the browser)
        this.imgSaved.ImageUrl = savedImageFileName + "?timestamp=" + DateTime.UtcNow.Ticks.ToString();
        this.phOutputPreview.Visible = true;

        // Display extension and size of both files
        this.litLoadedImageFileDetails.Text = System.IO.Path.GetExtension(this.imgLoaded.ImageUrl).ToUpper() + " file (" + (new System.IO.FileInfo(Server.MapPath(this.imgLoaded.ImageUrl))).Length.ToString() + " bytes)";
        this.litSavedImageFileDetails.Text = System.IO.Path.GetExtension(savedImageFileName).ToUpper() + " file (" + (new System.IO.FileInfo(Server.MapPath(savedImageFileName))).Length.ToString() + " bytes)";
    }