Как проверить, загружен или нет элемент управления веб-ресурсами в Dynamics CRM 2016

#crm #dynamics-crm-2016

#crm #dynamics-crm-2016

Вопрос:

Для доступа к элементу управления Webresource из другого элемента управления webresoucre используется следующий javascript ,

   var webResource = $(window.parent.Xrm.Page.getControl(webResourceName).getObject().contentWindow.window.document.getElementById(dropDownName));
  

Но иногда он работает правильно, иногда он возвращает нулевое значение.

Таким образом, можно проверить, загружен ли веб-ресурс или нет.

Ответ №1:

У вас есть несколько вариантов.

Есть ли код запуска вашего веб-ресурса

Мой любимый подход — пойти в другом направлении: на вашем веб-ресурсе добавьте код для запуска выполнения в родительской форме CRM. Вы можете использовать готовый метод jQuery или один из многих подходов, о которых вы можете прочитать здесь, чтобы не использовать jQuery. Если вы используете jQuery, ваш веб-ресурс может иметь что-то вроде этого:

 $.ready(function() {
    window.parent.Xrm.Page.getAttribute('name').setValue('test'); // or whatever your webresource needs to do
});
  

Идея заключается в том, что веб-ресурс запускает некоторую логику, когда он готов, чтобы вы могли избежать проблем с обнаружением завершения загрузки веб-ресурса.

Используйте метод загрузки jQuery

Я не могу вспомнить, пробовал ли я это на самом деле, но вы должны иметь возможность использовать метод загрузки jQuery. В скрипте на форме CRM сделайте что-то вроде этого:

 $('iframe#WebResource_xyz').on('load', function() {
    // Here, the 'this' object will refer to the iframe object

    this.contentWindow.document.getElementById(dropDownName); // you might have to tweak this slightly, didn't test it
});
  

Определить, когда веб-ресурс готов

Этот подход делает то, о чем вы просите, и это то, что я использовал до того, как jQuery был доступен в формах из коробки (включая его для будущих читателей, которые могут использовать более старую версию CRM, где jQuery был недоступен). Он ожидает завершения загрузки веб-ресурса, а затем вызывает обратный вызов. Добавьте эту функцию в скрипт, который загружается в вашу форму CRM:

 // Waits for web resource to be ready and then invokes the callback.
// webResourceId: the id of either a web resource or an iframe on the form
// urlCheck: this string will be checked for in the iframe's url to make 
//           sure it is on the right page. can be any part of the url, 
//           doesn't have to be the whole thing.
// callback: Called once the iframe is ready. The context of the callback 
//           method will be set to the iframe's window, so the callback can 
//           use "this" to refer to the iframe window.
function waitForWebResourceReady(webResourceId, urlCheck, callback) {
    var tryCount = arguments[3] || 0;
    var control = Xrm.Page.getControl(webResourceId);

    if (!control ||
        !control.getObject() ||
        !control.getObject().contentWindow ||
        !control.getObject().contentWindow.location ||
        !control.getObject().contentWindow.location.href ||
        control.getObject().contentWindow.location.href.indexOf(urlCheck) < 0 ||
        control.getObject().readyState !== 'complete') {
        if (tryCount > 50) {
            console.log("waitForWebResourceReady: "   
                "Failed to reach ready state on "   webResourceId);
            return;
        }

        console.log("waitForWebResourceReady: "   webResourceId   " not ready yet");
        window.setTimeout(function () {
            waitForWebResourceReady(webResourceId, urlCheck, callback,   tryCount);
        }, 20);
        return;
    }

    console.log("waitForWebResourceReady: "   webResourceId   " is ready");
    callback.call(control.getObject().contentWindow);
}
  

а затем используйте его следующим образом:

 waitForWebResourceReady('WebResource_xyz', 'mycontrol.html', function () {
    // In this context, 'this' will refer to the window object of the webresource
    var dropdown = this.document.getElementById(dropDownName);
    // ....
});
  

Комментарии:

1. В версии 9, похоже, они удалили свойство readyState из корневого объекта (GetObject()), но вы все равно можете получить его из GetObject().contentDocument.readyState .