How to make TextBlock inside of Rich Text Box Non-removable?

private void AddVCard()
        {
            FlowDocument flowDocument = rich.Document;
            Paragraph dp = new Paragraph(); 
            Run fnRun = new Run() {Foreground = System.Windows.Media.Brushes.Black };
            Run companyRun = new Run() {Foreground = System.Windows.Media.Brushes.Black };
            Run telRun = new Run() {Foreground = System.Windows.Media.Brushes.Black };
            Run emailRun = new Run() { Foreground = System.Windows.Media.Brushes.Black };
            Run adrRun = new Run() {Foreground = System.Windows.Media.Brushes.Black };
            
            InlineUIContainer fnTb = new InlineUIContainer(new TextBlock() {  Tag = "fn", Text = "First Name:", Foreground = System.Windows.Media.Brushes.Green });
            InlineUIContainer ctbh = new InlineUIContainer(new TextBlock() {  Tag = "company", Text = "Company:", Foreground = System.Windows.Media.Brushes.Green });
            InlineUIContainer teltb = new InlineUIContainer(new TextBlock() { Tag = "tel", Text = "Phone/Tel No:", Foreground = System.Windows.Media.Brushes.Green });
            InlineUIContainer emailtb = new InlineUIContainer(new TextBlock() {  Tag = "email", Text = "Email:", Foreground = System.Windows.Media.Brushes.Green });
            InlineUIContainer adrtb = new InlineUIContainer(new TextBlock() {  Tag = "adr", Text = "Address:", Foreground = System.Windows.Media.Brushes.Green });
            fnTb.Unloaded += InlineUIContainer_Unloaded_1;
            ctbh.Unloaded += InlineUIContainer_Unloaded_2;
            teltb.Unloaded += InlineUIContainer_Unloaded_3;
            emailtb.Unloaded += InlineUIContainer_Unloaded_4;
            adrtb.Unloaded += InlineUIContainer_Unloaded_5;
            dp.Inlines.Add(fnTb);
            //np.Inlines.Add(fnTb);

            dp.Inlines.Add(fnRun);
            dp.Inlines.Add(new LineBreak());

            dp.Inlines.Add(ctbh);
            //np.Inlines.Add(ctbh);

            dp.Inlines.Add(companyRun);
            dp.Inlines.Add(new LineBreak());

            dp.Inlines.Add(teltb);
            //np.Inlines.Add(teltb);

            dp.Inlines.Add(telRun);
            dp.Inlines.Add(new LineBreak());

            dp.Inlines.Add(emailtb);
            //np.Inlines.Add(emailtb);

            dp.Inlines.Add(emailRun);
            dp.Inlines.Add(new LineBreak());

            dp.Inlines.Add(adrtb);
            //np.Inlines.Add(adrtb);

            dp.Inlines.Add(adrRun);

            vcardRuns["fn"] = fnRun;
            vcardRuns["company"] = companyRun;
            vcardRuns["tel"] = telRun;
            vcardRuns["email"] = emailRun;
            vcardRuns["adr"] = adrRun;

            // Get the FlowDocument of the RichTextBox
            

            // Add the dynamicParagraph to the Blocks collection
            flowDocument.Blocks.Add(dp);
        }

        private void InlineUIContainer_Unloaded_1(object sender, RoutedEventArgs e)
        {
            (sender as InlineUIContainer).Unloaded -= new RoutedEventHandler(InlineUIContainer_Unloaded_1);

            TextBlock tb = new TextBlock();
            tb.Text = "Full Name:";
            tb.Foreground = System.Windows.Media.Brushes.Green; 

            TextPointer tp = rich.CaretPosition.GetInsertionPosition(LogicalDirection.Forward);
            //rich.CaretPosition = rich.CaretPosition.GetPositionAtOffset(tb.Text.Length+1);
            InlineUIContainer iuic = new InlineUIContainer(tb, tp);
            iuic.Unloaded += new RoutedEventHandler(InlineUIContainer_Unloaded_1);
        }

        private void InlineUIContainer_Unloaded_2(object sender, RoutedEventArgs e)
        {
            (sender as InlineUIContainer).Unloaded -= new RoutedEventHandler(InlineUIContainer_Unloaded_2);

            TextBlock tb = new TextBlock();
            tb.Text = "Company:";
            tb.Foreground = System.Windows.Media.Brushes.Green;

            TextPointer tp = rich.CaretPosition.GetInsertionPosition(LogicalDirection.Forward);
            //rich.CaretPosition = rich.CaretPosition.GetPositionAtOffset(tb.Text.Length+1);
            InlineUIContainer iuic = new InlineUIContainer(tb, tp);
            iuic.Unloaded += new RoutedEventHandler(InlineUIContainer_Unloaded_2);
        }

        private void InlineUIContainer_Unloaded_3(object sender, RoutedEventArgs e)
        {
            (sender as InlineUIContainer).Unloaded -= new RoutedEventHandler(InlineUIContainer_Unloaded_3);

            TextBlock tb = new TextBlock();
            tb.Text = "Phone/Tel:";
            tb.Foreground = System.Windows.Media.Brushes.Green;

            TextPointer tp = rich.CaretPosition.GetInsertionPosition(LogicalDirection.Forward);
            //rich.CaretPosition = rich.CaretPosition.GetPositionAtOffset(tb.Text.Length+1);
            InlineUIContainer iuic = new InlineUIContainer(tb, tp);
            iuic.Unloaded += new RoutedEventHandler(InlineUIContainer_Unloaded_3);
        }

        private void InlineUIContainer_Unloaded_4(object sender, RoutedEventArgs e)
        {
            (sender as InlineUIContainer).Unloaded -= new RoutedEventHandler(InlineUIContainer_Unloaded_4);

            TextBlock tb = new TextBlock();
            tb.Text = "Email:";
            tb.Foreground = System.Windows.Media.Brushes.Green;

            TextPointer tp = rich.CaretPosition.GetInsertionPosition(LogicalDirection.Forward);
            //rich.CaretPosition = rich.CaretPosition.GetPositionAtOffset(tb.Text.Length+1);
            InlineUIContainer iuic = new InlineUIContainer(tb, tp);
            iuic.Unloaded += new RoutedEventHandler(InlineUIContainer_Unloaded_4);
        }

        private void InlineUIContainer_Unloaded_5(object sender, RoutedEventArgs e)
        {
            (sender as InlineUIContainer).Unloaded -= new RoutedEventHandler(InlineUIContainer_Unloaded_5);

            TextBlock tb = new TextBlock();
            tb.Text = "Address:";
            tb.Foreground = System.Windows.Media.Brushes.Green;

            TextPointer tp = rich.CaretPosition.GetInsertionPosition(LogicalDirection.Forward);
            //rich.CaretPosition = rich.CaretPosition.GetPositionAtOffset(tb.Text.Length+1);
            InlineUIContainer iuic = new InlineUIContainer(tb, tp);
            iuic.Unloaded += new RoutedEventHandler(InlineUIContainer_Unloaded_5);
        }
}

(code updated)
I have the following code in which im adding text blocks to dynamic paragraph inlines but the user is able to entirely remove the textblocks just like any other text.

I dont want the user to remove the TextBlock and i want to stay fixed just there.

Update: I tried following Read-only run element post but Im unable to move the caret to the corresponding run and I think if this is done properly then the issue should most likely be resolved.

  • Does Read-only Run elements in a WPF RichTextBox? answer your question?

    – 

  • TextBlock has an IsEnabled property. I wonder whether setting it to false would freeze it?

    – 




  • @OlivierJacot-Descombes Nope it doesn’t do anything

    – 

  • @dbc It actually works but when i type, the editable Runs values are not set im not understanding where i have to place the caret after replacing the text blocks after it gets unloaded in the event so that its placed in the right Run

    – 

  • @Rushaan – then I’d suggest you edit your question and update it with the code you adapted from Read-only Run elements in a WPF RichTextBox? that shows what you tried and how it isn’t quite working — i.e. an updated minimal reproducible example.

    – 




Leave a Comment