This is a migrated thread and some comments may be shown as answers.

Content menus shared across RichTextBoxes?

6 Answers 154 Views
RichTextBox
This is a migrated thread and some comments may be shown as answers.
Joel
Top achievements
Rank 1
Joel asked on 27 May 2011, 01:54 PM
Hi,


I've encountered a weird behavior.  I am trying to hide certain parts (table and font formatting) of a RadRichTextBox's content menu using the "Use ContextMenuBuilder class" approach of this example: http://www.telerik.com/help/wpf/radrichtextbox-features-context-menu.html

This is the class I created to hide certain parts of the context menu:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Telerik.Windows.Documents.UI.Extensibility;
using Telerik.Windows.Documents.UI;
using Telerik.Windows.Controls.RichTextBoxUI.Menus;
using Telerik.Windows.Documents.Model;
using Telerik.Windows.Controls;
 
 
class CustomMenuBuilder : ContextMenuContentBuilder
{
    private RadRichTextBox radRichTextBox;
 
    public CustomMenuBuilder(RadRichTextBox radRichTextBox)
        : base(radRichTextBox)
    {
        this.radRichTextBox = radRichTextBox;
    }
 
    protected override ContextMenuGroup CreateTableCommands()
    {
        ContextMenuGroup g = new ContextMenuGroup();
        return g;
    }
 
    protected override ContextMenuGroup CreateHyperlinkCommands(bool forExistingHyperlink)
    {
        ContextMenuGroup g = new ContextMenuGroup();
        return g;
    }
 
    protected override ContextMenuGroup CreateTextEditCommands()
    {
        ContextMenuGroup g = new ContextMenuGroup();
        return g;
    }
}


And I then set my RichTextBox to use that new Context menu in another class:

((Telerik.Windows.Controls.RichTextBoxUI.ContextMenu)rtb1.ContextMenu).ContentBuilder = new CustomMenuBuilder(rtb1);

This works perfectly if you only have 1 RichTextBox you want to do this on.  The problem appears if you want to do this on many RichTextBoxes:

((Telerik.Windows.Controls.RichTextBoxUI.ContextMenu)rtb1.ContextMenu).ContentBuilder = new CustomMenuBuilder(rtb1);
((Telerik.Windows.Controls.RichTextBoxUI.ContextMenu)rtb2.ContextMenu).ContentBuilder = new CustomMenuBuilder(rtb2);
((Telerik.Windows.Controls.RichTextBoxUI.ContextMenu)rtb3.ContextMenu).ContentBuilder = new CustomMenuBuilder(rtb3);

Now, if you right click and paste in rtb1 or rtb2, the text appears in rtb3 (the last RichTextBox for which we assigned the menu).  It seems that the 3 menus are pointing to the same instance even though they are all new CustomMenuBuilder  objects.  Any way of hiding context menu sections and having each menu related to the right RichTextBox?

Thanks,

-- Joel

6 Answers, 1 is accepted

Sort by
0
Iva Toteva
Telerik team
answered on 31 May 2011, 08:12 AM
Hi Joel,

You are right, by default all rich text boxes share one and the same context menu and the code in your snippet is setting three different content menu builders to one and the same context menu, used by all rich text boxes.
You can change this behavior by creating new context menus for each rich text box and then setting the ContentMenuBuilder of each one. Please refer to the code-snippet below.

rtb1.ContextMenu = new Telerik.Windows.Controls.RichTextBoxUI.ContextMenu() { ContentBuilder = new CustomMenuBuilder(rtb1) };
rtb2.ContextMenu = new Telerik.Windows.Controls.RichTextBoxUI.ContextMenu() { ContentBuilder = new CustomMenuBuilder(rtb2) };
rtb3.ContextMenu = new Telerik.Windows.Controls.RichTextBoxUI.ContextMenu() { ContentBuilder = new CustomMenuBuilder(rtb3) };

I hope this helps.


Regards,
Iva
the Telerik team
Do you want to have your say when we set our development plans? Do you want to know when a feature you care about is added or when a bug fixed? Explore the Telerik Public Issue Tracking system and vote to affect the priority of the items
0
Joel
Top achievements
Rank 1
answered on 31 May 2011, 01:48 PM
That worked.  Thanks!

-- Joel
0
Robert
Top achievements
Rank 1
answered on 23 Jun 2012, 01:12 AM
I have noticed exactly the same behaviour with my project. It is as if all of the loaded RadRichTextBoxes are referncing the same RTB at the same time (only for certain scenarios).

I use the RadDocking Control, where the document host has multiple panes loaded. Each pane then contains a RadRichTextBox.
I would set some ContextMenu items from one RichTextBox and noticed that they were also appearing in the Context Menus of the other RichTextBoxes.

I also have a RadRibbionMenu above the RadDocking control that contains various buttons which perform specific actions on the selected document. I find at times, when I try to perform an action on the given selected pane that is hosting a RichTextBox, it ends up being applied to one of the other host pane RichTextBoxes. This often happens when the panes have been located side by side rather than grouped with tabs.
I guess changing the layout of the docking panes alters the panes some how.

Rob


0
Iva Toteva
Telerik team
answered on 26 Jun 2012, 09:54 AM
Hello Rob,

By default only one instance of RadContextMenu is created and used for all RadRichTextBox instances in the application. If you would like to change this behavior, you can mark your custom context menu with the following attribute:

[PartCreationPolicy(CreationPolicy.NonShared)]
[CustomContextMenu]
public class NonSharedContextMenu : ContextMenu
{
}

This ensures that MEF will instantiate different context menus for all rich text boxes in the application.

Please, let us know if that does not solve the problem.

Greetings,
Iva Toteva
the Telerik team

Explore the entire Telerik portfolio by downloading the Ultimate Collection trial package. Get it now >>

0
Robert
Top achievements
Rank 1
answered on 04 Jul 2012, 09:27 AM
Hi,

Thanks for getting back to me. I'm not using a custom ContextMenu. I add a new Menu Item when the ContextMenu_Showing event is triggered.

private void ContextMenu_Showing(object sender, ContextMenuEventArgs e)
{
//Add menu item to data context
RadMenuItem addPriceMenuItem = new RadMenuItem()
{
Header = "Set Price",
Icon = new System.Windows.Controls.Image() { Source = new BitmapImage(new Uri("Icons/Spec-Editor-Menu/sterling_pound_currency_50.png", UriKind.Relative))},
Tag = products[products.Count - 1]
};
addPriceMenuItem.Click += this.SetPriceMenuItem_Click;
ContextMenuGroup customContextMenuGroup = new ContextMenuGroup();
customContextMenuGroup.Add(addPriceMenuItem);
e.ContextMenuGroupCollection.Add(customContextMenuGroup);
}


0
Accepted
Robert
Top achievements
Rank 1
answered on 04 Jul 2012, 09:34 AM
Ok this is easily solved.
When each RadRichTextBox loads I just create a new ContextMenu for each instance.

//**** RadRichTextBox Context Menu *****
private void ContextMenuSubscribe()
{
    this.radRichTextBox.ContextMenu = new Telerik.Windows.Controls.RichTextBoxUI.ContextMenu();
    ContextMenu contextMenu = (ContextMenu)this.radRichTextBox.ContextMenu;
    contextMenu.Showing += this.ContextMenu_Showing;
}

Tags
RichTextBox
Asked by
Joel
Top achievements
Rank 1
Answers by
Iva Toteva
Telerik team
Joel
Top achievements
Rank 1
Robert
Top achievements
Rank 1
Share this question
or