Пример #1
0
        public void ChangePicture(string bookFolderPath, GeckoElement img, PalasoImage imageInfo, IProgress progress)
        {
            var imageFileName = ProcessAndCopyImage(imageInfo, bookFolderPath);

            img.SetAttribute("src", imageFileName);
            UpdateMetdataAttributesOnImgElement(img, imageInfo);
        }
Пример #2
0
        public static void CopyImageMetadataToWholeBook(string folderPath, HtmlDom dom, Metadata metadata, IProgress progress)
        {
            progress.WriteStatus("Starting...");

            //First update the images themselves

            int completed   = 0;
            var imgElements = GetImagePaths(folderPath);

            foreach (string path in imgElements)
            {
                progress.ProgressIndicator.PercentCompleted = (int)(100.0 * (float)completed / imgElements.Count());
                progress.WriteStatus("Copying to " + Path.GetFileName(path));
                using (var image = PalasoImage.FromFile(path))
                {
                    image.Metadata = metadata;
                    image.SaveUpdatedMetadataIfItMakesSense();
                }
                ++completed;
            }

            //Now update the html attributes which echo some of it, and is used by javascript to overlay displays related to
            //whether the info is there or missing or whatever.

            foreach (XmlElement img in dom.SafeSelectNodes("//img"))
            {
                UpdateImgMetdataAttributesToMatchImage(folderPath, img, progress, metadata);
            }
        }
Пример #3
0
        private bool ShouldSaveAsJpeg(PalasoImage imageInfo)
        {
            /*
             * Note, each guid is VERY SIMILAR. The difference is only in the last 2 digits of the 1st group.
             * Undefined  B96B3CA9
             *      MemoryBMP  B96B3CAA
             *      BMP    B96B3CAB
             *      EMF    B96B3CAC
             *      WMF    B96B3CAD
             *      JPEG    B96B3CAE
             *      PNG    B96B3CAF
             *      GIF    B96B3CB0
             *      TIFF    B96B3CB1
             *      EXIF    B96B3CB2
             *      Icon    B96B3CB5
             */
            if (ImageFormat.Jpeg.Guid == imageInfo.Image.RawFormat.Guid)
            {
                return(true);
            }

            if (ImageFormat.Jpeg.Equals(imageInfo.Image.PixelFormat))           //review
            {
                return(true);
            }

            if (string.IsNullOrEmpty(imageInfo.FileName))
            {
                return(false);
            }

            return(new [] { "jpg", "jpeg" }.Contains(Path.GetExtension(imageInfo.FileName).ToLower()));
        }
Пример #4
0
        //Up through Bloom 3.0, we would make white areas transparent when importing images, in order to make them
        //look good against the colored background of a book cover.
        //This caused problems with some PDF viewers, so in Bloom 3.1, we switched to only making them transparent at runtime.
        //This method allows us to undo that transparency-making.
        public static void RemoveTransparencyOfImagesInFolder(string folderPath, IProgress progress)
        {
            var imageFiles = Directory.GetFiles(folderPath, "*.png");
            int completed  = 0;

            foreach (string path in imageFiles)
            {
                if (Path.GetFileName(path).ToLowerInvariant() == "placeholder.png")
                {
                    return;
                }

                progress.ProgressIndicator.PercentCompleted = (int)(100.0 * (float)completed / (float)imageFiles.Length);
                using (var pi = PalasoImage.FromFileRobustly(path))
                {
                    // If the image isn't jpeg, and we can't be sure it's already opaque, change the
                    // image to be opaque.  As explained above, some PDF viewers don't handle transparent
                    // images very well.
                    if (!AppearsToBeJpeg(pi) && !IsIndexedAndOpaque(pi.Image))
                    {
                        RemoveTransparency(pi, path, progress);
                    }
                }
                completed++;
            }
        }
Пример #5
0
 public void Locked_NewOne_False()
 {
     using (var pi = new PalasoImage())
     {
         Assert.IsFalse(pi.MetadataLocked);
     }
 }
Пример #6
0
        private static string GetImageFileName(string bookFolderPath, PalasoImage imageInfo, bool isJpeg)
        {
            string s;

            if (string.IsNullOrEmpty(imageInfo.FileName) || imageInfo.FileName.StartsWith("tmp"))
            {
                // Some images, like from a scanner or camera, won't have a name yet.  Some will need a number
                // in order to differentiate from what is already there. We don't try and be smart somehow and
                // know when to just replace the existing one with the same name... some other process will have
                // to remove unused images.

                s = "image";
                int    i         = 0;
                string suffix    = "";
                string extension = isJpeg ? ".jpg" : ".png";

                while (File.Exists(Path.Combine(bookFolderPath, s + suffix + extension)))
                {
                    ++i;
                    suffix = i.ToString();
                }

                return(s + suffix + extension);
            }
            else
            {
                var extension = isJpeg ? ".jpg" : ".png";
                return(Path.GetFileNameWithoutExtension(imageInfo.FileName) + extension);
            }
        }
        public static Image MakePngBackgroundTransparent(PalasoImage originalImage)
        {
            // If the image is indexed and opaque, convert the palette to have a transparent background.  This produces
            // a much smaller image file than the process of redrawing the image with a transparent conversion.  That
            // process always produces a 32-bit RGBA format image.  Changing the palette should also be faster than
            // redrawing in a new size and format.
            // libgdiplus on Linux doesn't handle Alpha (transparency) information for indexed format images.
            if (SIL.PlatformUtilities.Platform.IsWindows && ImageUtils.IsIndexedAndOpaque(originalImage.Image))
            {
                var revisedBitmap = originalImage.Image.Clone() as Image;
                revisedBitmap.Palette = GivePaletteTransparentBackground(revisedBitmap);
                return(revisedBitmap);
            }
            //impose a maximum size because in BL-2871 "Opposites" had about 6k x 6k and we got an ArgumentException
            //from the new BitMap()
            var destinationWidth  = Math.Min(1000, originalImage.Image.Width);
            var destinationHeight = (int)((float)originalImage.Image.Height * ((float)destinationWidth / (float)originalImage.Image.Width));
            var processedBitmap   = new Bitmap(destinationWidth, destinationHeight);

            using (var g = Graphics.FromImage(processedBitmap))
            {
                var destRect = new Rectangle(0, 0, destinationWidth, destinationHeight);
                lock (ConvertWhiteToTransparent)
                {
                    g.DrawImage(originalImage.Image, destRect, 0, 0, originalImage.Image.Width, originalImage.Image.Height,
                                GraphicsUnit.Pixel, ConvertWhiteToTransparent);
                }
            }
            return(processedBitmap);
        }
Пример #8
0
        private PalasoImage MakeSampleTifImage(string path)
        {
            var x = new Bitmap(kSampleImageDimension, kSampleImageDimension);

            x.Save(path, ImageFormat.Tiff);
            return(PalasoImage.FromFileRobustly(path));
        }
Пример #9
0
        public void Image_CreatedWithImageOnly_GivesSameImage()
        {
            Bitmap bitmap = new Bitmap(10, 10);
            var    pi     = new PalasoImage(bitmap);

            Assert.AreEqual(bitmap, pi.Image);
        }
Пример #10
0
 public void FileName_CreatedWithImageOnly_Null()
 {
     using (var pi = PalasoImage.FromImage(new Bitmap(10, 10)))
     {
         Assert.IsNull(pi.FileName);
     }
 }
Пример #11
0
        private PalasoImage MakeSamplePngImage(string path)
        {
            var x = new Bitmap(kSampleImageDimension, kSampleImageDimension);

            x.Save(path, ImageFormat.Png);
            x.Dispose();
            return(PalasoImage.FromFile(path));
        }
Пример #12
0
        private PalasoImage MakeSampleJpegImage(string path)
        {
            var x = new Bitmap(kSampleImageDimension, kSampleImageDimension);

            x.Save(path, ImageFormat.Jpeg);
            //nb: even if we reload the image from the file, the rawformat will be memory bitmap, not jpg as we'd wish
            return(PalasoImage.FromFileRobustly(path));
        }
Пример #13
0
        public void ShouldChangeFormatToJpeg_OneColor_False()
        {
            var    path     = FileLocationUtilities.GetFileDistributedWithApplication(_pathToTestImages, "bird.png");
            string jpegPath = Path.Combine(Path.GetTempPath(), Path.GetTempFileName() + ".jpg");

            Assert.IsFalse(ImageUtils.TryChangeFormatToJpegIfHelpful(PalasoImage.FromFile(path), jpegPath));
            Assert.IsFalse(File.Exists(jpegPath));
        }
Пример #14
0
 public void SetImage(PalasoImage image)
 {
     _previousImage = image;
     if (ImageChanged != null)
     {
         ImageChanged.Invoke(this, null);
     }
 }
Пример #15
0
        /// <summary>
        /// Creates a thumbnail of just the cover image (no title, language name, etc.)
        /// </summary>
        /// <returns>Returns true if successful; false otherwise. </returns>
        internal static bool CreateThumbnailOfCoverImage(Book.Book book, HtmlThumbNailer.ThumbnailOptions options, Action <Image> callback = null)
        {
            var imageSrc = book.GetCoverImagePath();

            if (!IsCoverImageSrcValid(imageSrc, options))
            {
                Debug.WriteLine(book.StoragePageFolder + " does not have a cover image.");
                return(false);
            }
            var size         = Math.Max(options.Width, options.Height);
            var destFilePath = Path.Combine(book.StoragePageFolder, options.FileName);
            // Writing a transparent image to a file, then reading it in again appears to be the only
            // way to get the thumbnail image to draw with the book's cover color background reliably.
            var transparentImageFile = Path.Combine(Path.GetTempPath(), "Bloom", "Transparent", Path.GetFileName(imageSrc));

            Directory.CreateDirectory(Path.GetDirectoryName(transparentImageFile));
            try
            {
                if (RuntimeImageProcessor.MakePngBackgroundTransparent(imageSrc, transparentImageFile))
                {
                    imageSrc = transparentImageFile;
                }
                using (var coverImage = PalasoImage.FromFile(imageSrc))
                {
                    if (imageSrc == transparentImageFile)
                    {
                        coverImage.Image = MakeImageOpaque(coverImage.Image, book.GetCoverColor());
                    }
                    var shouldAddDashedBorder = options.BorderStyle == HtmlThumbNailer.ThumbnailOptions.BorderStyles.Dashed;
                    coverImage.Image = options.CenterImageUsingTransparentPadding ?
                                       ImageUtils.CenterImageIfNecessary(new Size(size, size), coverImage.Image, shouldAddDashedBorder) :
                                       ImageUtils.ResizeImageIfNecessary(new Size(size, size), coverImage.Image, shouldAddDashedBorder);
                    switch (Path.GetExtension(destFilePath).ToLowerInvariant())
                    {
                    case ".jpg":
                    case ".jpeg":
                        ImageUtils.SaveAsTopQualityJpeg(coverImage.Image, destFilePath);
                        break;

                    default:
                        PalasoImage.SaveImageRobustly(coverImage, destFilePath);
                        break;
                    }
                    if (callback != null)
                    {
                        callback(coverImage.Image.Clone() as Image);                            // don't leave GC to chance
                    }
                }
            }
            finally
            {
                if (File.Exists(transparentImageFile))
                {
                    SIL.IO.RobustFile.Delete(transparentImageFile);
                }
            }
            return(true);
        }
Пример #16
0
 public void FromFile_HugeJPEG_DoesNotCrash()
 {
     //nb: trying to reproduce a problem that came up in bloom with this very image, but
     //i never did get this to crash here
     PalasoImage.FromFile(@"C:\Users\John\Desktop\hugetestimage.jpg");
     PalasoImage.FromFile(@"C:\Users\John\Desktop\hugetestimage.jpg");
     PalasoImage.FromFile(@"C:\Users\John\Desktop\hugetestimage.jpg");
     PalasoImage.FromFile(@"C:\Users\John\Desktop\hugetestimage.jpg");
 }
Пример #17
0
 public void Image_FromFile_GivesImage()
 {
     using (Bitmap bitmap = new Bitmap(10, 10))
         using (var temp = TempFile.CreateAndGetPathButDontMakeTheFile())
         {
             bitmap.Save(temp.Path);
             var pi = PalasoImage.FromFile(temp.Path);
             Assert.AreEqual(10, pi.Image.Width);
         }
 }
Пример #18
0
 private static void RemoveTransparency(PalasoImage original, string path, IProgress progress)
 {
     progress.WriteStatus("RemovingTransparency from image: " + Path.GetFileName(path));
     using (var b = new Bitmap(original.Image.Width, original.Image.Height))
     {
         DrawImageWithWhiteBackground(original.Image, b);
         original.Image = b;
         PalasoImage.SaveImageRobustly(original, path);                 // BL-4148: this method preserves existing metadata
     }
 }
Пример #19
0
 public void FromFile_DoesNotLockFile()
 {
     using (Bitmap bitmap = new Bitmap(10, 10))
         using (var temp = TempFile.CreateAndGetPathButDontMakeTheFile())
         {
             bitmap.Save(temp.Path);
             PalasoImage.FromFile(temp.Path);
             Assert.DoesNotThrow(() => File.Delete(temp.Path));
         }
 }
Пример #20
0
        private void OnEditImageMetdata(DomEventArgs ge)
        {
            var imageElement = GetImageNode(ge);

            if (imageElement == null)
            {
                return;
            }
            string fileName = imageElement.GetAttribute("src").Replace("%20", " ");

            var path = Path.Combine(_model.CurrentBook.FolderPath, fileName);

            using (var imageInfo = PalasoImage.FromFile(path))
            {
                bool looksOfficial = imageInfo.Metadata != null && !string.IsNullOrEmpty(imageInfo.Metadata.CollectionUri);
                if (looksOfficial)
                {
                    MessageBox.Show(imageInfo.Metadata.GetSummaryParagraph("en"));
                    return;
                }
                Logger.WriteEvent("Showing Metadata Editor For Image");
                using (var dlg = new Palaso.UI.WindowsForms.ClearShare.WinFormsUI.MetadataEditorDialog(imageInfo.Metadata))
                {
                    if (DialogResult.OK == dlg.ShowDialog())
                    {
                        imageInfo.Metadata = dlg.Metadata;
                        imageInfo.SaveUpdatedMetadataIfItMakesSense();
                        imageInfo.Metadata.StoreAsExemplar(Metadata.FileCategory.Image);
                        //update so any overlays on the image are brough up to data
                        var editor = new PageEditingModel();
                        editor.UpdateMetdataAttributesOnImgElement(imageElement, imageInfo);

                        var answer = MessageBox.Show(LocalizationManager.GetString("EditTab.copyImageIPMetdataQuestion", "Copy this information to all other pictures in this book?", "get this after you edit the metadata of an image"), LocalizationManager.GetString("EditTab.titleOfCopyIPToWholeBooksDialog", "Picture Intellectual Property Information"), MessageBoxButtons.YesNo);
                        if (answer == DialogResult.Yes)
                        {
                            Cursor = Cursors.WaitCursor;
                            try
                            {
                                _model.CopyImageMetadataToWholeBook(dlg.Metadata);
                                // There might be more than one image on this page. Update overlays.
                                _model.RefreshDisplayOfCurrentPage();
                            }
                            catch (Exception e)
                            {
                                ErrorReport.NotifyUserOfProblem(e, "There was a problem copying the metadata to all the images.");
                            }
                            Cursor = Cursors.Default;
                        }
                    }
                }
            }

            //_model.SaveNow();
            //doesn't work: _browser1.WebBrowser.Reload();
        }
Пример #21
0
        public void Locked_LoadedButImageHasNoMetadata_False()
        {
            var png = new Bitmap(10, 10);

            using (var temp = new TempFile(false))
            {
                png.Save(temp.Path);
                var pi = PalasoImage.FromFile(temp.Path);
                Assert.IsFalse(pi.MetadataLocked);
            }
        }
Пример #22
0
        public static void UpdateMetadataAttributesOnImage(GeckoElement img, PalasoImage imageInfo)
        {
            //see also Book.UpdateMetadataAttributesOnImage(), which does the same thing but on the document itself, not the browser dom
            img.SetAttribute("data-copyright",
                             String.IsNullOrEmpty(imageInfo.Metadata.CopyrightNotice) ? "" : imageInfo.Metadata.CopyrightNotice);

            img.SetAttribute("data-creator", String.IsNullOrEmpty(imageInfo.Metadata.Creator) ? "" : imageInfo.Metadata.Creator);


            img.SetAttribute("data-license", imageInfo.Metadata.License == null ? "" : imageInfo.Metadata.License.ToString());
        }
Пример #23
0
        public void ShowToolboxWith_PreExisting_EnsureRawFormatUnchanged()
        {
            Application.EnableVisualStyles();
            PalasoImage i = PalasoImage.FromImage(TestImages.logo);

            using (var dlg = new ImageToolboxDialog(i, ""))
            {
                dlg.ShowDialog();
                Assert.AreEqual(ImageFormat.Jpeg.Guid, dlg.ImageInfo.Image.RawFormat.Guid);
            }
        }
Пример #24
0
 /// <summary>
 /// Check whether the new image file is the same as the one we already have chosen.
 /// (or at least the same pathname in the filesystem)
 /// </summary>
 /// <remarks>
 /// See https://silbloom.myjetbrains.com/youtrack/issue/BL-2776.
 /// If the user goes out of his way to choose the exact same picture file from the
 /// original location again, a copy will still be created with a slightly revised
 /// name.  Cropping a picture also results in a new copy of the file with the
 /// revised name.  We still need a tool to remove unused picture files from a
 /// book's folder.  (ie, BL-2351)
 /// </remarks>
 private bool IsSameFilePath(string bookFolderPath, UrlPathString src, PalasoImage imageInfo)
 {
     if (src != null)
     {
         var path = Path.Combine(bookFolderPath, src.PathOnly.NotEncoded);
         if (path == imageInfo.OriginalFilePath)
         {
             return(true);
         }
     }
     return(false);
 }
Пример #25
0
 public void SetImage(PalasoImage image)
 {
     if (image == null)
     {
         Image = null;
     }
     else
     {
         _originalFormat = image.Image.RawFormat;
         Image           = image;
     }
 }
Пример #26
0
        public void LoadAndSave_DeleteAfter_NothingLocked()
        {
            var png = new Bitmap(10, 10);

            using (var temp = new TempFile(false))
            {
                png.Save(temp.Path);
                var pi = PalasoImage.FromFile(temp.Path);
                pi.Metadata.CopyrightNotice = "Copyright 2011 me";
                Assert.DoesNotThrow(() => pi.Save(temp.Path));
                Assert.DoesNotThrow(() => File.Delete(temp.Path));
            }
        }
Пример #27
0
        private void MakeSamplePngImageWithMetadata(string path)
        {
            var x = new Bitmap(10, 10);

            x.Save(path, ImageFormat.Png);
            x.Dispose();
            using (var img = PalasoImage.FromFile(path))
            {
                img.Metadata.Creator         = "joe";
                img.Metadata.CopyrightNotice = "Copyright 1999 by me";
                img.SaveUpdatedMetadataIfItMakesSense();
            }
        }
Пример #28
0
        protected void MakeSamplePngImageWithMetadata(string path, int width = 10, int height = 10)
        {
            var x = new Bitmap(width, height);

            RobustImageIO.SaveImage(x, path, ImageFormat.Png);
            x.Dispose();
            using (var img = PalasoImage.FromFileRobustly(path))
            {
                img.Metadata.Creator         = "joe";
                img.Metadata.CopyrightNotice = "Copyright 1999 by me";
                RetryUtility.Retry(() => img.SaveUpdatedMetadataIfItMakesSense());
            }
        }
Пример #29
0
 public void FromFileTwiceMaintainsCorrectPath()
 {
     using (var bitmap1 = new Bitmap(10, 10))
         using (var bitmap2 = new Bitmap(10, 10))
             using (var tf1 = TempFile.WithExtension(".png"))
                 using (var tf2 = TempFile.WithExtension(".png"))
                 {
                     bitmap1.Save(tf1.Path);
                     bitmap2.Save(tf2.Path);
                     using (var pi1 = PalasoImage.FromFile(tf1.Path))
                         using (var pi2 = PalasoImage.FromFile(tf2.Path))
                             Assert.AreNotEqual(pi1.OriginalFilePath, pi2.OriginalFilePath);
                 }
 }
Пример #30
0
        protected void MakeSamplePngImageWithMetadata(string path)
        {
            var x = new Bitmap(10, 10);

            x.Save(path, ImageFormat.Png);
            x.Dispose();
            using (var img = PalasoImage.FromFile(path))
            {
                img.Metadata.Creator         = "joe";
                img.Metadata.CopyrightNotice = "Copyright 1999 by me";
                img.Metadata.License         = new CreativeCommonsLicense(true, true, CreativeCommonsLicense.DerivativeRules.NoDerivatives);
                img.SaveUpdatedMetadataIfItMakesSense();
            }
        }
Пример #31
0
 public void SetImage(PalasoImage image)
 {
     if (image == null)
     {
         Image = null;
     }
     else
     {
         _originalFormat = image.Image.RawFormat;
         Image = image;
         CheckForInvalidImage();
     }
 }