2010-02-17 3 views
2

Я пытаюсь получить jquery для выполнения некоторых атак ui для меня при использовании GWT. У меня есть уведомления, которые я добавляю на страницу, которая при нажатии должна исчезнуть. Поскольку может быть несколько уведомлений одного типа (предупреждение, ошибка и т. Д.), Я пытаюсь динамически добавлять имя стиля только тогда, когда их щелкают через GWT, а затем активируют jquery для этого имени класса.Получение JQuery для работы над именем класса, динамически добавленным GWT

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

Любые идеи?

public abstract class AbstractNotificationWidget extends Composite implements ClickHandler, HasClickHandlers { 

    protected abstract String getUniqueId(); 

    @Override 
    public HandlerRegistration addClickHandler(ClickHandler handler) { 
    return addDomHandler(handler, ClickEvent.getType()); 
    } 

    @Override 
    public void onClick(ClickEvent event) { 
    doClick(getUniqueId()); 
    } 

    protected static native void doClick(String name) /*-{ 
    $wnd.$("#" + name).click(function() { 
     $wnd.$(this).slideUp("slow"); 
     $wnd.$("div", this).fadeOut("slow"); 
     }); 
    }-*/; 

} 

Я тогда подклассы, которые расширяют класс выше

public class ErrorNotificationWidget extends AbstractNotificationWidget { 

    private final String uniqueId; 

    public ErrorNotificationWidget (String title, String message) { 
    uniqueId = DOM.createUniqueId(); 

    initWidget(uiBinder.createAndBindUi(this)); 

    this.getElement().setId(uniqueId); 

    this.addClickHandler(this); 
    } 
    @Override 
    protected String getUniqueId() { 
    return this.uniqueId; 
    } 

Эти подклассы используют UiBinder, чтобы определить, каким образом они должны быть сделаны. Затем эти виджеты добавляются в панель, которая будет отображаться.

+0

Не могли бы вы предоставить еще несколько исходных кодов - часть, которую вы опубликовали, недостаточно точна, чтобы понять, что происходит не так. И вы можете захотеть изменить 'styleName.equals' на' styleName.contains';) Кроме того, было бы проще просто использовать 'FocusPanel' как ваш' mainWidget', чем обрабатывать регистрацию 'ClickHandler' самостоятельно. И вы можете захотеть чтобы переключиться на именование виджетах уведомлений (я предполагаю, что их будет несколько) на DOM.createUniqueId() - вы не сокрываете сразу все виджеты;) –

+0

Спасибо за комментарий. Это не окончательный код, так что есть определенная очистка, но идея содержит хороший. Метод DOM.createUniqueId(), вероятно, тоже хорошая идея, но если виджет закрывается при первом щелчке, это не имеет значения. Я не уверен, какой еще код я мог бы разместить. У меня есть подклассы, которые расширяют этот и добавляют свои собственные стили, чтобы они выглядели как ошибка или предупреждение. Я отредактирую свое сообщение с самой последней версией кода с вашими предложениями. – Josh

+0

Я добавил еще код. Я начал добавлять уникальный идентификатор, когда экземпляр уведомления был создан, но для него все еще требуется 2 клика. Я должен упустить что-то очевидное. – Josh

ответ

1

Что именно вы пытаетесь достичь? Скрыть виджет на основе применяемых стилей или его идентификатора? (В текущей версии, кажется, вы смешиваете одно с другим)

Если ClickEvent стреляет поститься (который может быть проверен путем добавления тайм-аут перед ним), вы можете попробовать окружив его DeferredCommand.

Другая возможность заключается в том, что JQuery является crapping вверх;) У меня были некоторые странные проблемы при использовании функции обратного вызова в JQuery/Mootools - причина в том, что эти рамки расширения/изменения function() (между прочим) - однако, JSNI материал выполнен из «чистого» iframe, где нет изменений, сделанных jQuery (вот почему вы должны ссылаться на основное окно через $wnd). Вы можете проверить, если это проблема здесь, определяя, например, функция тестирования в вашем хост HTML страницы, а затем передать его в качестве функции обратного вызова в методе void doClick(String name):

protected static native void doClick(String name) /*-{ 
    $wnd.$("." + name).click($wnd.jqueryTest); // BTW, why '"." + '? 
}-*/; 

И мое первоначальное предложение остается в силе - используйте FocusPanel в качестве вашего основного виджета - стараюсь правильно реализовать HasClickHandlers (и аналогичные интерфейсы) - это PITA из моего опыта и может привести к странным ошибкам и/или утечкам памяти.

+0

Я хочу создать множество уведомлений и уметь их закрывать по отдельности. Если я дам им все то же имя класса DOM, jquery закроет все из них. Когда вы вызываете addStyleName (имя) в gwt, он добавляет имя в класс DOM этого элемента. «.» + имя так jquery тянет имя (.gwt-12-whatever) вместо ".name". Я ценю предложение использовать FocusPanel, но я не могу этого сделать. Мне нужно, чтобы это был композит. Кроме того, я не верю, что это скорость больше, так как даже когда я создаю имя при инициализации, прежде чем его щелкнуть, мне все равно придется дважды щелкнуть. – Josh

+0

Вы неправильно поняли меня о «FocusPanel» - я хотел, чтобы вы использовали его в качестве своей основной/основной панели в своем шаблоне UiBinder (привязанный к конкретному виджету уведомлений). Тогда вы просто можете просто вызвать 'focusPanel.addClickHandler (что угодно)' (вместо того, чтобы внедрять 'HasClickHandlers' самостоятельно и т. Д.). О именах стилей - вместо поиска элемента по его именам стиля он должен быть быстрее (и меньше подвержен ошибкам) ​​сделать это с помощью id - поскольку в DOM не должно быть элемента с одним и тем же идентификатором дважды (это почему я рекомендовал использовать 'DOM.createUniqueId'). –

+0

Как добавить id через gwt? Я знаю только функцию addStyleName(), которая добавляет к классу DOM. – Josh

0

Добавьте класс к элементу, который вы хотите закрыть на щелчок, т.е.

<div class="close-on-click">Content</div> 

Ваш Javascript может автоматически связать функцию для любого из существующих или динамически создаваемых элементов, которые соответствуют селектору:

$('.close-on-click').live('click', function() { 
    $(this).remove(); 
}); 
+0

Это, по сути, то, что я пытаюсь сделать, за исключением того, что я не могу жестко закодировать «close-on-click» в ui.xml, потому что тогда каждый экземпляр этого виджета получит одно и то же имя класса и закрывается, когда любой из их щелкнули. Спасибо за ответ, хотя. – Josh

+0

Если ссылка находится внутри элемента, который вы хотите закрыть, попробуйте следующее: $ ('a.close'). Live ('click', function() { $ (this) .parents ('. Class-to -close: first '). remove(); }); – aceofspades

0

Ваш код требует двух щелчков мыши, потому что вы устанавливаете событие привязки Jquery click при первом щелчке (через метод onclick), и поэтому последний реагирует на второй щелчок.Изменение кода в чем-то вроде этого:

protected static native void doClick(String name) /*-{  
     var $_this = $("#" + name); 
     $_this.slideUp("slow");  
     $wnd.$("div", $_this).fadeOut("slow");  
}-*/; 

FYI, вы можете использовать GwtQuery (GWT клон JQuery) и код не должен выглядеть так:

import static com.google.gwt.query.client.GQuery.$; 

public abstract class AbstractNotificationWidget extends Composite implements ClickHandler, HasClickHandlers {  

@Override 
public HandlerRegistration addClickHandler(ClickHandler handler) {  
    return addDomHandler(handler, ClickEvent.getType()); 
}  

@Override 

public void onClick(ClickEvent event) {  
    $(this).slideUp(Speed.SLOW); 
    $("div", getElement()).fadeOut(Speed.SLOW); 
}  

} 

нет необходимости использовать UniqueID

Смежные вопросы