@@ -32,59 +32,203 @@ Here is a complete code snippet that demonstrates how to achieve this conversion
3232``` csharp
3333using System ;
3434using System .Diagnostics ;
35+ using System .Windows .Media ;
3536using System .Windows .Media .Imaging ;
3637using Telerik .Windows .Documents .Fixed .FormatProviders .Pdf ;
3738using Telerik .Windows .Documents .Fixed .Model ;
39+ using Telerik .Windows .Documents .Fixed .Model .ColorSpaces ;
40+ using Telerik .Windows .Documents .Fixed .Model .Common ;
3841using Telerik .Windows .Documents .Fixed .Model .Graphics ;
3942using Telerik .Windows .Documents .Fixed .Model .Objects ;
4043using Telerik .Windows .Documents .Fixed .Model .Text ;
4144
42- namespace PDFToBlackAndWhite
45+ namespace _1675661GrayScalePDF
4346{
44- class Program
47+ internal class Program
4548 {
4649 static void Main (string [] args )
4750 {
48- // Load your original PDF report
49- PdfFormatProvider provider = new PdfFormatProvider ();
50- RadFixedDocument document = provider .Import (System .IO .File .ReadAllBytes (" yourOriginalReport.pdf" ));
51+ var reportProcessor = new Telerik .Reporting .Processing .ReportProcessor ();
52+ var deviceInfo = new System .Collections .Hashtable ();
53+ var reportSource = new Telerik .Reporting .UriReportSource ();
54+ reportSource .Uri = " ConditionalReport.trdp" ;
5155
52- // Convert each element's color to grayscale
53- foreach (RadFixedPage page in document .Pages )
56+ Telerik .Reporting .Processing .RenderingResult result = reportProcessor .RenderReport (" PDF" , reportSource , deviceInfo );
57+
58+ if (! result .HasErrors )
5459 {
55- foreach (ContentElementBase element in page .Content )
60+ string fileName = result .DocumentName + " ." + result .Extension ;
61+ string path = System .IO .Path .GetTempPath ();
62+ string filePath = System .IO .Path .Combine (path , fileName );
63+
64+ using (System .IO .FileStream fs = new System .IO .FileStream (filePath , System .IO .FileMode .Create ))
5665 {
57- MakeGrayscale ( element );
66+ fs . Write ( result . DocumentBytes , 0 , result . DocumentBytes . Length );
5867 }
59- }
6068
61- // Export the modified document as a new PDF file
62- string resultFile = " grayscaleReport.pdf" ;
63- System .IO .File .WriteAllBytes (resultFile , provider .Export (document ));
64- Process .Start (new ProcessStartInfo (resultFile ) { UseShellExecute = true });
65- }
69+ Process .Start (new ProcessStartInfo () { FileName = filePath , UseShellExecute = true });
70+
71+ PdfFormatProvider provider = new PdfFormatProvider ();
72+ RadFixedDocument document = provider .Import (System .IO .File .ReadAllBytes (filePath ));
73+
74+ foreach (RadFixedPage page in document .Pages )
75+ {
76+ foreach (ContentElementBase element in page .Content )
77+ {
78+ MakeGrayscale (element );
79+ }
80+ }
81+
82+ string resultFile = " grayscale.pdf" ;
6683
84+ if (System .IO .File .Exists (resultFile ))
85+ {
86+ System .IO .File .Delete (resultFile );
87+ }
88+
89+ System .IO .File .WriteAllBytes (resultFile , provider .Export (document , TimeSpan .FromSeconds (10 )));
90+ Process .Start (resultFile );
91+
92+ }
93+ }
6794 private static void MakeGrayscale (ContentElementBase element )
6895 {
69- if (element is TextFragment text )
96+ TextFragment text = element as TextFragment ;
97+
98+ if (text != null )
7099 {
71100 text .Stroke = MakeGrayscale (text .Stroke );
72101 text .Fill = MakeGrayscale (text .Fill );
73102 }
74103
104+
75105 if (element is Path path )
76106 {
77107 path .Stroke = MakeGrayscale (path .Stroke );
78108 path .Fill = MakeGrayscale (path .Fill );
79109 }
80110
81- if (element is Image image )
111+ Image image = element as Image ;
112+
113+ if (image != null )
82114 {
83- // Convert the image to grayscale - Implementation depends on your specific requirements
115+ BitmapSource originalImage = image .ImageSource .GetBitmapSource ();
116+ BitmapSource grayscaleImage = MakeGrayscale (originalImage );
117+ image .ImageSource = new Telerik .Windows .Documents .Fixed .Model .Resources .ImageSource (grayscaleImage );
84118 }
85119 }
86120
87- // Implement the MakeGrayscale method for ColorBase, Path, and Image as per your requirements
121+ private static BitmapSource MakeGrayscale (BitmapSource source )
122+ {
123+ byte ? [,] intensities = GetPixelsIntensity (source );
124+ BitmapSource grayscaleSource = CreateImageFromGrayPixels (intensities );
125+
126+ return grayscaleSource ;
127+ }
128+
129+ private static ColorBase MakeGrayscale (ColorBase color )
130+ {
131+ RgbColor rgb = (RgbColor )color ;
132+
133+ byte gray = GetGrayIntensity (rgb .R , rgb .G , rgb .G );
134+
135+ return new RgbColor (rgb .A , gray , gray , gray );
136+ }
137+
138+ private static BitmapSource CreateImageFromGrayPixels (byte ?[,] pixels )
139+ {
140+ double dpi = 96 ;
141+ int height = pixels .GetLength (0 );
142+ int width = pixels .GetLength (1 );
143+ byte [] pixelData = new byte [width * height ];
144+
145+ for (int y = 0 ; y < height ; ++ y )
146+ {
147+ int yIndex = y * width ;
148+ for (int x = 0 ; x < width ; ++ x )
149+ {
150+ pixelData [x + yIndex ] = pixels [y , x ] ?? 255 ;
151+ }
152+ }
153+
154+ BitmapSource bmpSource = BitmapSource .Create (width , height , dpi , dpi , PixelFormats .Gray8 , null , pixelData , width );
155+
156+ return bmpSource ;
157+ }
158+
159+ private static byte ?[,] GetPixelsIntensity (BitmapSource bitmapSource )
160+ {
161+ int width = bitmapSource .PixelWidth ;
162+ int height = bitmapSource .PixelHeight ;
163+ byte ? [,] intensities = new byte ?[height , width ];
164+ int [] pixels = GetPixels (bitmapSource );
165+ int pixelIndex = 0 ;
166+
167+ for (int i = 0 ; i < height ; i ++ )
168+ {
169+ for (int j = 0 ; j < width ; j ++ )
170+ {
171+ byte a , r , g , b ;
172+ GetComponentsFromPixel (pixels [pixelIndex ++ ], out a , out r , out g , out b );
173+ byte ? intensity ;
174+ if (a == 0 )
175+ {
176+ intensity = null ;
177+ }
178+ else
179+ {
180+ intensity = (byte )((a / 255 . 0 ) * GetGrayIntensity (r , g , b ));
181+ intensity = intensity .Value < 255 ? ((byte )(intensity .Value + 1 )) : intensity .Value ;
182+ }
183+
184+ intensities [i , j ] = intensity ;
185+ }
186+ }
187+
188+ return intensities ;
189+ }
190+
191+ private static void GetComponentsFromPixel (int pixel , out byte a , out byte r , out byte g , out byte b )
192+ {
193+ b = (byte )(pixel & 0x FF );
194+ g = (byte )((pixel >> 8 ) & 0x FF );
195+ r = (byte )((pixel >> 16 ) & 0x FF );
196+ a = (byte )((pixel >> 24 ) & 0x FF );
197+ }
198+
199+ private static int [] GetPixels (BitmapSource source )
200+ {
201+ int [] pixels = new int [source .PixelWidth * source .PixelHeight ];
202+ if (source .Format == PixelFormats .Bgr32 || source .Format == PixelFormats .Bgra32 || source .Format == PixelFormats .Pbgra32 )
203+ {
204+ checked
205+ {
206+ source .CopyPixels (pixels , source .PixelWidth * 4 , 0 );
207+ }
208+ }
209+ else if (source .Format == PixelFormats .Indexed8 )
210+ {
211+ byte [] indices = new byte [source .PixelWidth * source .PixelHeight ];
212+ source .CopyPixels (indices , source .PixelWidth , 0 );
213+ for (int i = 0 ; i < indices .Length ; ++ i )
214+ {
215+ Color c = source .Palette .Colors [indices [i ]];
216+ pixels [i ] = (c .A << 24 ) | (c .R << 16 ) | (c .G << 8 ) | (c .B << 0 );
217+ }
218+ }
219+ else
220+ {
221+ FormatConvertedBitmap converted = new FormatConvertedBitmap (source , PixelFormats .Bgra32 , null , 0 );
222+ converted .CopyPixels (pixels , source .PixelWidth * 4 , 0 );
223+ }
224+
225+ return pixels ;
226+ }
227+
228+ private static byte GetGrayIntensity (byte r , byte g , byte b )
229+ {
230+ return (byte )(0 . 2126 * r + 0 . 7152 * g + 0 . 0722 * b );
231+ }
88232 }
89233}
90234```
0 commit comments