'allow arabic text in pdf table using itext7 (xamarin android)

I have to put my list data in a table in a pdf file. My data has some Arabic words. When my pdf is generated, the Arabic words don't appear. I searched and found that I need itext7.pdfcalligraph so I installed it in my app. I found this code too https://itextpdf.com/en/blog/technical-notes/displaying-text-different-languages-single-pdf-document and tried to do something similar to allow Arabic words in my table but I couldn't figure it out.

This is a trial code before I apply it to my real list:

var path2 = global::Android.OS.Environment.ExternalStorageDirectory.AbsolutePath;
filePath = System.IO.Path.Combine(path2.ToString(), "myfile2.pdf");
stream = new FileStream(filePath, FileMode.Create);
PdfWriter writer = new PdfWriter(stream);
PdfDocument pdf2 = new iText.Kernel.Pdf.PdfDocument(writer);
            
Document document = new Document(pdf2, PageSize.A4);
FontSet set = new FontSet();
set.AddFont("ARIAL.TTF");


document.SetFontProvider(new FontProvider(set));
document.SetProperty(Property.FONT, "Arial");
 
string[] sources = new string[] { "يوم","شهر 2020" };
 iText.Layout.Element.Table table = new iText.Layout.Element.Table(2, false);
 foreach (string source in sources)
                {
                    Paragraph paragraph = new Paragraph();
                    Bidi bidi = new Bidi(source, Bidi.DirectionDefaultLeftToRight);
                    if (bidi.BaseLevel != 0)
                    {
                        paragraph.SetTextAlignment(iText.Layout.Properties.TextAlignment.RIGHT);
                    }

                    paragraph.Add(source);
                    table.AddCell(new Cell(1, 1).SetTextAlignment(iText.Layout.Properties.TextAlignment.CENTER).Add(paragraph));
                }
                document.Add(table);
                document.Close();

I updated my code and added the arial.ttf to my assets folder . i'm getting the following exception:

System.InvalidOperationException: 'FontProvider and FontSet are empty. Cannot resolve font family name (see ElementPropertyContainer#setFontFamily) without initialized FontProvider (see RootElement#setFontProvider).' and I still can't figure it out. any ideas? thanks in advance



Solution 1:[1]

- C #

I have a similar situation for Turkish characters, and I've followed these steps :

  • Create a folder under projects root folder which is : /wwwroot/Fonts
  • Add OpenSans-Regular.ttf under the Fonts folder

Path for font is => ../wwwroot/Fonts/OpenSans-Regular.ttf

  • Create font like below :
public static PdfFont CreateOpenSansRegularFont()
{
    var path = "{Your absolute path for FONT}";
    return PdfFontFactory.CreateFont(path, PdfEncodings.IDENTITY_H, true);
}

and use it like :

paragraph.Add(source)
         .SetFont(FontFactory.CreateOpenSansRegularFont());  //set font in here

table.AddCell(new Cell(1, 1)
     .SetTextAlignment(iText.Layout.Properties.TextAlignment.CENTER)
     .Add(paragraph));

This is how I used font factory for Turkish characters ex: "ü,i,ç,?,ö"

For Xamarin-Android, you could try

string documentsPath = Environment.GetFolderPath(Environment.SpecialFolder.MyDocuments); 
var path = Path.Combine(documentsPath, "Fonts/Arial.ttf");

Solution 2:[2]

Look i fixed it in java,this may help you:

 String font = "your Arabic font";

//the magic is in the next 4 lines:

        PdfFontFactory.register(font);
        FontProgram fontProgram = FontProgramFactory.createFont(font, true);
        PdfFont f = PdfFontFactory.createFont(fontProgram, PdfEncodings.IDENTITY_H);
        LanguageProcessor languageProcessor = new ArabicLigaturizer();

//and look here how i used setBaseDirection & and don't use TextAlignment ,it will work without it

  com.itextpdf.kernel.pdf.PdfDocument tempPdfDoc = new com.itextpdf.kernel.pdf.PdfDocument(new PdfReader(pdfFile.getPath()), TempWriter);
            com.itextpdf.layout.Document TempDoc = new com.itextpdf.layout.Document(tempPdfDoc);
            com.itextpdf.layout.element.Paragraph paragraph0 = new com.itextpdf.layout.element.Paragraph(languageProcessor.process("????????? ???????????--????????? ???????????--????????? ???????????--????????? ???????????"))
                    .setFont(f).setBaseDirection(BaseDirection.RIGHT_TO_LEFT)
                    .setFontSize(15);

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1
Solution 2 Ayman.dev