Javascript и Drupal

Прислано: Khurgin

пн, 21/07/2008 - 13:33

Я новичок в drupal, но по этому вопросу облазил всё что мог.
Может быть вы сможете мне подсказать, буду очень благодарен.

Ситуация:
Пишу модуль к drupal 6. Drupal стоит поверх денвера. Модуль выводит на страницу в блок content html код.
Вывод находится в функции: function mymodule_block($op='list', $delta=0).
В ней генерится html код, записывается в переменную $block_content и выдается через
$block['content'] = $block_content;
return $block;
Пока я не начал использовать javascript всё выводилось нормально.
Потом я решил добавить в выод таблицу с прокруткой, для чего применил javascript.
Отдельно от друпала скрипт рабоает.

Но в друпале нет.

Часть скрипта, что пишется в я смог добавить в на свою страницу, где используется с помощью
drupal_add_js("myGrid.js");

Но вот вызов javascript функции из сделать не получается. Drupal просто игнорирует тег и вместо вызова функции, которая должна выводить таблицу - просто пишет "0".

Более того, если этот скрипт вызова просто добавить на страницу через админку, то выпадает ошибка
Parse error: syntax error, unexpected '<' in Z:\home\drupal\www\includes\common.inc(1537) : eval()'d code on line 2

Скрипт вызова функции:

var currencies = ["ARS","ATS","AUD","BBD","BEF","BGL","BMD","BRL","BSD","CAD",
"CHF","CLP","CNY","CYP","CZK","DEM","DKK","DZD","EGP","ESP",
"EUR","FIM","FJD","FRF","GBP","GRD","HKD","HUF","IDR","IEP",
"ILS","INR","ISK","ITL","JMD","JOD","JPY","KRW","LBP","LUF",
"MXN","MYR","NLG","NOK","NZD","PHP","PKR","PLN","PTE","ROL",
"RUR","SAR","SDD","SEK","SGD","SKK","THB","TRL","TTD","TWD",
"USD","VEB","XAG","XAU","XCD","XDR","XPD","XPT","ZAR","ZMK"];
var data =
{
nCol:6,
nRow:10,
nCellWidth:70,
nCellHeight:20
};
data.colHeaders = currencies;
data.rowHeaders = currencies;
data.values = new Array();
for ( var i = 0; i < currencies.length; i++ )
{
data.values.push(new Array());
for ( var j = 0; j < currencies.length; j++ )
{
if ( i == j )
data.values[i].push('-');
else
data.values[i].push(Math.round(10000*Math.random() / Math.random())/10000);
}
}
new Grid('theGrid', data);

В админке друпала для страницы, где находится мой модуль я выбрал Input format "PHP code".

Вопрос:
Подскажите пожалуйста в чём может быть проблема и как вообще правильно работать с javascript при написании модулей.

Комментарии


Настройки просмотра комментариев

Выберите нужный метод показа комментариев и нажмите "Применить"
Опубликовано gorr в пн, 21/07/2008 - 15:08.

http://api.drupal.ru/api/function/drupal_add_js/6


Опубликовано Khurgin в пн, 21/07/2008 - 16:26.

Да, я пытался использовать эту функцию, но у меня не получилось. Буду очень признателен более развернутому ответу и примерам применения.


Опубликовано Химический Али в пн, 21/07/2008 - 18:27.

проводили аналогии с другими модулями, использующими свои js?


Опубликовано Vergilius в пн, 21/07/2008 - 22:13.

Что ты как то путанно описал. Но насколько я понял, у тебя есть скрипт, который написан в отдельном файле. Однако Jquery ты не пользуешься, и функцию вызова прописываешь прямо в HTML коде. Тогда ты должен использовать ‘inline’ в вызове. Вот так:

drupal_add_js( 'moy_funcia()','inline');

Ну или даже весь скрипт, что ты привел:

drupal_add_js('var currencies = ["ARS","ATS","AUD","BBD","BEF","BGL","BMD","BRL","BSD","CAD",
"CHF","CLP","CNY","CYP","CZK","DEM","DKK","DZD","EGP","ESP",
"EUR","FIM","FJD","FRF","GBP","GRD","HKD","HUF","IDR","IEP",
"ILS","INR","ISK","ITL","JMD","JOD","JPY","KRW","LBP","LUF",
"MXN","MYR","NLG","NOK","NZD","PHP","PKR","PLN","PTE","ROL",
"RUR","SAR","SDD","SEK","SGD","SKK","THB","TRL","TTD","TWD",
"USD","VEB","XAG","XAU","XCD","XDR","XPD","XPT","ZAR","ZMK"];
var data =
{
nCol:6,
nRow:10,
nCellWidth:70,
nCellHeight:20
};
data.colHeaders = currencies;
data.rowHeaders = currencies;
data.values = new Array();
for ( var i = 0; i < currencies.length; i++ )
{
data.values.push(new Array());
for ( var j = 0; j < currencies.length; j++ )
{
if ( i == j )
data.values[i].push('-');
else
data.values[i].push(Math.round(10000*Math.random() / Math.random())/10000);
}
}
new Grid("theGrid", data); 
','inline');

А вообще советую пользоваться Jquery. Не надо ни одной строчки кода в html писать. Все делается через скриптовый файл.


Опубликовано Khurgin в вт, 22/07/2008 - 10:00.

Vergilius, попробовал сделать как ты предлагал, но не смотря на параметр inline скрипт добавился просто в head ко всем остальным и вызова функции не произошло.

У меня модуль генерит html в строковой переменной $blockcontent и мне нужно добавить в неё сгенерированный javascript' ом new Grid('theGrid', data);
Как это сделать? Спасибо заранее!


Опубликовано Khurgin в вт, 22/07/2008 - 10:01.

Химический Али, среди стандартных модулей drupal похожего не нашёл. Посоветуешь что посмотреть? Спасибо!


Опубликовано gorr в вт, 22/07/2008 - 10:08.

А в коде страницы проверял, твой код присутствует?


Опубликовано gorr в вт, 22/07/2008 - 10:13.

Если нет, то в шаблоне страницы может пропущена строчка:

<?php print $scripts ?>

или вот такая:
<?php print $closure ?> 

в конце странички обычно вставляют.


Опубликовано Khurgin в вт, 22/07/2008 - 13:04.

gorr, в модуле я пишу:
.......
$block_content .= ''[tbody]
[tr]
[td]';
drupal_add_js(" ... ", "inline");

$block_content .= '[/td]
.....

В получаемом коде оказывается просто:
[tr] [td][/td]
И вместо того, чтобы быть вызванным между тегами td - текст скрипта тобавляется в head ко всем остальным скриптам.

<?php print $scripts ?> в шаблоне есть


Опубликовано Vergilius в вт, 22/07/2008 - 14:00.

Уверен, что твой код работает? Проверял в тестовом файле?

Если да, то попробуй сделать так:

drupal_add_js( 'moy_funcia()','inline', ‘gridobj’);

То есть тут ты добавляешь скрипт в переменную ‘gridobj’ (лю6ое название можно). До6авлять скриптов можно сколько хочешь, они будут располагаться в том порядке, каком ты их добавлял. Скрипты не выводятся через обычный drupal_get_js (то есть в head не будет), а вызывается функцией:

drupal_get_js('gridobj');

Эту функцию нужно вставить на странице, где тебе нужно. Например, говоришь, у тебя есть строковая переменная $blockcontent. Так вот в ее определении вставь drupal_get_js(' gridobj '); там где тебе нужно:

“... $blockcontent определение….”.drupal_get_js('gridobj').”….$blockcontent определение.....”

И все таки советую пользоваться Jquery. Ведь порой javascript нужно вставлять во многих местах, и это не удобно. А с jquery все твои скрипты будут в одном файле.


Опубликовано Khurgin в вт, 22/07/2008 - 18:33.

Vergilius, спасибо огромное!!! Заработало!!!
А насчёт jquery в друпале - что посоветуешь посмотреть на эту тему?


Опубликовано Vergilius в вт, 22/07/2008 - 18:59.

Не-не, ты что. Если у тебя все вставилось, есть теги , но скрипт не выполняется, то это дело уже в твоем скрипте, а не в Drupal. Javascript – client-side язык, то есть он интерпретируется броузером пользователя, а не движком сайта.

Проверь, чтобы у тебя в хеде был файл с определениями функций, чтобы вызов функции стоял там где нужно. У тебя, например, я не вижу определения функции grid, что она вообще делает? Иногда бывает, что нужно интерпретировать скрипт только после полной загрузки страницы. Следовательно нужно использовать событие onload.

Чтобы проверить, что скрипт ра6отает вставь в свой $blockcontent следующий скрипт.

drupal_add_js( 'document.write(“SCRIPT_RABOTAET”) ','inline', ‘gridobj’);

......

“... $blockcontent определение….”. drupal_get_js(' gridobj ').”….$blockcontent определение.....”;

Если он заработает, то это лишнее доказательство ошибки в твоем скрипте, а не друпала.


Опубликовано Vergilius в вт, 22/07/2008 - 19:00.

Пока писал ответ - ты уже все решил ;)


Опубликовано Vergilius в вт, 22/07/2008 - 19:06.

Насчет jquery я посоветую:

http://docs.jquery.com/

Но это если ты знаешь английский. Наверняка есть доки на русском. Через Google посмотри. В любом случае Jquery очень советую. Сам я относительно недавно познакомился с этой библиотекой, сразу понял, что это офигенно удобно. Как CSS файл, только javascript пишется. До этого писал как и ты, прямо в HTML.


Опубликовано Ареч в чт, 24/07/2008 - 12:59.

Vergilius, чего-то я никак не найду, как инжектить код jQuery в странички, сгенерённые Друпалом? Там же вроде нужно ещё jquery.js подключать или drupal.js... Их надо самому вставлять или есть какая-то автоматизация?


Опубликовано Vergilius в пт, 25/07/2008 - 19:33.

Если ты не менял шаблон, то у тебя и так все скрипты выводятся. Друпал собирает их по всем функциям, которые запускает. В одной функции есть код drupal_add_js(‘'misc/jquery.js'’), в другой drupal_add_js(‘misc/drupal.js’), в третьей drupal_add_js(‘misc/ajax.js’), в четвертой drupal_add_js(‘misc/textarea.js’) и так далее. Потом на страницу через функцию drupal_get_js() выводится весь массив:

Таким образом получается, что на разных страницах набор скриптов разный (так как запускаются разные функции).

И ты тоже можешь добавить свой скрипт в какой-ли6о из своих функций. Написал скрипт moy_script.js, поместил его в папку moy_sait/sites/all/misc/ , чтобы не засорять дефолтную папку /misc, иначе трудно сайт будет апгрейдить. Затем в своей функции прописал drupal_add_js(‘sites/all/misc/moy_script.js’) (без слэша перед “sites”). И если эта функция запускается перед тем как вывести какую либо страницу, то твой скрипт появится в о6щем списке. Можно вызвать по-другому. Например, в своей шабоне в head после <?php print $scripts ?> (чтобы jquery.js был ДО твоего скрипта) написать:

drupal_add_js( 'sites/all/misc/moy_script.js','visov','visov_moy_script');
drupal_get_js(‘visov_moy_script’);

Если у тебя по какой то причине в коде странице нет вызова jquery.js то можешь добавить:

drupal_add_js( 'misc/jquery.js','visov','visov_moy_script');
drupal_add_js( 'sites/all/misc/moy_script.js','visov','visov_moy_script');
drupal_get_js(‘visov_moy_script’);

Для работы тебе нужны минимум jquery.js и твой скрипт. Drupal.js , ajax.js и т.д. – это плагины, расширяющие возможности, но можно работать и без них.

Вообщем, делаешь как я сказал, в своем скрипте ‘visov_moy_script’ прописываешь что-нибудь типа:

$(document).ready(function(){ //Говорим броузеру, чтобы запускал нижний скрипт только после загрузки страницы

$("#edit-pass").click(function(){ //Говорим броузеру, что когда кликнут на объект с id "edit-pass" выполнить функцию. Значок # указывает на то, что "edit-pass" - это id объекта.
$("#edit-submit").val("HELLO!!"); // Функция добавляет в value объекта edit-submit (это id клавиши LOG IN) слово "HELLO".
});

$("#edit-name").keyup(function(){ // Говорим броузеру, что когда отпустят клавишу клавиатуры,печатая в объекте с id "edit-name", выполнить функцию.Значок # указывает на то, что "edit-name" - это id объекта.

if($("#edit-name").val()!=""){ // Если объект не пустой, то выполнить нижеследующее условие. Заметь, что когда val() без ничего, то он выводит value объекта, когда val("какой_нибудь_simvol") содержит что-нибудь в скобочках, тогда он наоборот заполняет value объекта.
$("#edit-name").css({ backgroundColor:"red", color:"white" }); // изменить css объекта

}else{
$("#edit-name").css({ backgroundColor:"white", color:"black" }); // в случае, если в edit-name ничего напечатано, то css изменяется к изначальным значениям.
}
});

$("#edit-submit").click(function(event){ // если кликнут по клавиши edit-submit (это id клавиши LOG IN), то выполнить следующую функцию

event.preventDefault(); //говорим браузеру, чтобы он не отсылал нас на другую страницу, когда мы кликнем по клавише.
$("#edit-pass-wrapper").hide(); // спрятать объект с id edit-pass-wrapper
});

}); //окончание $(document).ready(function(){

Потом заходишь на страницу не логинясь, как анонимус (чтобы окошко User login было видно) и проверяешь. Кликнешь по строке ввода password и кнопка “Log in” изменится на “HELLO”; напечатаешь что-нибудь в строке ввода username и задний фон с цветом шрифта изменится, если сотрешь, то все вернется к черно-белому; кликнешь по клавише Log in и строка ввода password исчезнет.

Вообщем вот таким образом и можно выполнять javascript 6ез вмешательства в HTML. Весь javascript в отдельном файле moy_script.


Опубликовано gorr в пт, 25/07/2008 - 18:57.

Vergilius, классно расписал, как по нотам, молодец!


Опубликовано andypost@drupal.org в пт, 25/07/2008 - 20:07.

jquery.js + drupal.js добавляются автоматом при первом обращении к drupal_add_js


Опубликовано Vergilius в сб, 26/07/2008 - 15:09.

Если ты добавляешь их просто, без указания scope, то да. Если ты указываешь scope они не добавятся. Я, например, стер дефолтный drupal_get_js у себя. Вместо него у меня стоит drupal_get_js через scope.


Опубликовано PavelZ в ср, 04/02/2009 - 14:24.

Спасибо, очень полезно.
На счёт русской документации, думаю нет необходимости её искать, пользуюсь переводом Google, помогает здорово.


Опубликовано kyky в ср, 04/02/2009 - 15:05.

Заходите на http://www.visualjquery.com -- отличная шпаргалка


Новое на сайте

Ссылки партнёров