2
votes

In a page when we will click the component Presentation tab we can see the component and template listed there.On clicking of Insert button just below that, it will open another window "Insert component presentation" there also we will have Insert and close button.So now what i need to do While inserting i need to check whether the combination of selected Component and Template is already present there on page or not. If yes then it should prevent inserting the same with a popup like "this combination is already present, select other componet". Any idea how can i proceed. How can i trigger a Javascript on the Insert button?

EDIT:

When i am subscrbing it to Page i am getting erro.My code :

using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.UI;
using System.Text;
using Tridion.ContentManager.Extensibility.Events;
using Tridion.ContentManager.Extensibility;
using Tridion.ContentManager.ContentManagement;
using System.IO;
using System.Windows.Forms;




namespace MyEventHandlers
{
[TcmExtension("MyEventHandlerExtension")]

public class MyEventHandler : TcmExtension 
{
    public MyEventHandler()
{
  Subscribe();
}

public void Subscribe()
{
    EventSystem.Subscribe<Page, SaveEventArgs>(SaveBtnInitiated, EventPhases.Initiated);

}

private void SaveBtnInitiated(Page subject, SaveEventArgs args, EventPhases phase)
{

    try
    {
        List<string> allcplist = new List<string>();
        List<string> allcplist = new List<string>();
        foreach (ComponentPresentation cp in subject.ComponentPresentations)
        {
            allcplist.Add(cp.Component.Id + "," + cp.ComponentTemplate.Id);   
        }
        List<string> uniquecplist = allcplist.Distinct().ToList();
        if (allcplist.Count != uniquecplist.Count)
        {
            subject.Checkin(false);
            throw new Exception("Page has duplicate component presentation");

    }
    catch(Exception)
    {

    }
} 
3
Why do you check-in the page? When you run this handler on the initiated phase throwing an exception will cancel the operation. Besides that you cancel the exception by catching it and not doing anything. - Arjen Stobbe
I removed check-in and used save . and its working . thank u arjen - SDLBeginner

3 Answers

4
votes

You can implement this in an event handler that is subscribed to the Page Save event and the Initiated phase. When there is a duplicate Component Presentation you can cancel the Save by throwing an exception. The message will be shown in the Message Center in the TCM Explorer.

2
votes

Why are you subscribing to the Component? I think it should be the Page. Then you can walk through the ComponentPresentations property.

Code to go through the Component Presentations and throw an exception when duplicate presentations are found:

foreach (var cpA in subject.ComponentPresentations)
{
    if (subject.ComponentPresentations.Where(cpB => ComponentPresentationsAreEqual(cpA, cpB)).ToList().Count() > 2)
    {
        throw new DuplicateComponentPresentationsEmbeddedOnPageException();
    }
}

And the function to include cpB in the list when it is equal to cpA:

function ComponentPresentationsAreEqual(ComponentPresentation cpA, ComponentPresentation cpB)
{
    return cpA.Component.Id == cpB.Component.Id && cpA.ComponentTemplate.Id == cpB.ComponentTemplate.Id;
}
0
votes

I got my Result with this code Thanks to @Arjen Stobbe

using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.UI;
using System.Text;
using Tridion.ContentManager.Extensibility.Events;
using Tridion.ContentManager.Extensibility;
using Tridion.ContentManager.ContentManagement;
using System.IO;
using System.Windows.Forms;




namespace MyEventHandlers
{
[TcmExtension("MyEventHandlerExtension")]

public class MyEventHandler : TcmExtension 
{
    public MyEventHandler()
{
  Subscribe();
}

public void Subscribe()
{
    EventSystem.Subscribe<Page, SaveEventArgs>(SaveBtnInitiated, EventPhases.Initiated);

}

private void SaveBtnInitiated(Page subject, SaveEventArgs args, EventPhases phase)
{

    try
    {
        List<string> allcplist = new List<string>();
        List<string> allcplist = new List<string>();
        foreach (ComponentPresentation cp in subject.ComponentPresentations)
        {
            allcplist.Add(cp.Component.Id + "," + cp.ComponentTemplate.Id);   
        }
        List<string> uniquecplist = allcplist.Distinct().ToList();
        if (allcplist.Count != uniquecplist.Count)
        {
            subject.Save(false);
            throw new Exception("Page has duplicate component presentation");

    }
    catch(Exception)
    {

    }
} 

But i am not deleting the duplicate CP present on the page. Do i need to add,

for each()

inside

if (allcplist.Count != uniquecplist.Count)
{
}