Вызов функции Javascript из Silverlight

Я пытаюсь вызвать функцию javascript (в нашем коде) из элемента управления silverlight. Я пытаюсь вызвать функцию через:

HtmlPage.Window.Invoke("showPopup", new string[] { "http://www.example.com" });

и я получаю сообщение об ошибке "Не удалось вызвать: showPopup"

я могу позвонить HtmlPage.Window.Invoke("alert", new string[]{"test"}); без проблем, но не моя собственная функция.

Я также могу открыть соответствующую страницу в инструментах разработчика IE и вручную вызвать showPopup("http://www.example.com") и работает как положено.

Таким образом, функция js работает, и двоичный файл Silverlight может найти другие функции js. Что мне здесь не хватает?

Дополнительные примечания:

  • Вызов функции происходит в обработчике события нажатия кнопки, поэтому это происходит после загрузки страницы (и сценария)

6 ответов

Решение

Ага! Я понял. Наше приложение использует iframe, поэтому визуализированный HTML выглядит примерно так

<html>
<head></head>
<body>
Stuff
<iframe>
    <html>
        <head></head>
        <body>Other Stuff</body>
    </html>
</iframe>
<body>
</html>

И рассматриваемый элемент управления Silverlight находится в iframe. Проблема заключалась в том, что файл, содержащий showPopup функция была указана во внешнем <head> (почему я мог вызвать функцию с помощью панели инструментов IE), но не внутренний <head>, Добавление ссылки на файл в iframe <head> решил проблему.

Вроде антиклиматик, но спасибо за помощь.

Реальная ссылка на скрипт снова из iframe - не самый эффективный способ ссылки на код, содержащийся в родительском объекте. Если ваша функция называется "showPopup", вы можете вставить ее в свой iframe:

<script type="text/javascript">
    var showPopup = parent.showPopup;
</script>

И вуаля. Объяснение этому заключается в том, что все "глобальные" функции и объекты являются частью этого "глобального пространства имен"... которое является объектом "окна". Поэтому, если вы пытаетесь получить доступ к "глобальным" функциям от потомка, вам нужно либо вызвать функцию у родителя (например, parent.showPopup('....')), либо объявить для нее локальный псевдоним (который является что мы делаем в приведенном выше примере).

Ура!

Является ли функция showPopup javascript на той же странице html или aspx, что и элемент управления Silverlight? Обычно вы получите ошибку "Failed to Invoke ...", если функция javascript не существует:

HtmlPage.Window.Invoke("functionThatDoesNotExist", new [] { "Testing" });

Какой браузер вы используете, когда вы получаете эту проблему?

Вы используете последнюю версию Silverlight?

Используете ли вы ScriptableType в любом месте?

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

Вот как я это делаю. Но я создаю silverlight без визуальной студии. У меня есть только сырой HTML, XAML и JS (JavaScript). Обратите внимание на MouseLeftButtonUp и его значение "LandOnSpace"

        <Canvas x:Name="btnLandOnSpace" Background="LightGreen" MouseLeftButtonUp="LandOnSpace"
            Cursor="Hand" Canvas.Top ="0"  Width="70" Height="50"> 
            <TextBlock Text="LandOnSpace"  />
            </Canvas>

function LandOnSpace(sender, e) {  //on server
if (!ShipAnimateActive && !blnWaitingOnServer) {
    blnWaitingOnServer = true;
    RunServerFunction("/sqgame/getJSLLandOnSpace");
        ShowWaitingBox();
        };
else {
    alert('Waiting on server.');
};

}

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

У меня была такая же проблема в VS 2010 с SL 4. Я создал несколько методов и поместил их в один файл JS. Однако этот файл не был добавлен в раздел заголовка файла ASPX. Добавление его решило проблему. Разница в том, что, хотя у меня не было отдельной секции заголовка в iframe, у меня была проблема, и она была решена.

Другие вопросы по тегам