2010-04-13 8 views
6

Wie konzentrieren Sie sich auf eine Komponente mit Apache Wicket? Die Suche führt zu sehr wenig Information, hauptsächlich zum Setzen des Standardfeldes. Ich möchte kein Standardfeld festlegen, sondern den Fokus festlegen, wenn beispielsweise ein bestimmter Radio-Button ausgewählt ist.Setzen Sie den Fokus auf eine Komponente mit Apache Wicket?

Antwort

8

Sobald Sie Ihr Verhalten zum Festlegen des Fokus erstellen, sollten Sie in der Lage sein, es bei jedem Ereignis der Komponente hinzuzufügen, stellen Sie nur sicher, dass die Komponente Teil von AjaxRequestTarget ist. Ich sehe nicht, warum dies nicht funktionieren würde ...

myRadioButton.add(new AjaxEventBehavior("onchange") { 
@Override 
protected void onEvent(AjaxRequestTarget target) { 
    myOtherComponent.add(new DefaultFocusBehavior()); 
     target.addComponent(myForm); 
} 
}); 

Hier ist ein Link, der zeigt, wie die Standardfokusverhalten erstellen, wenn Sie nicht bereits haben: http://javathoughts.capesugarbird.com/2009/01/wicket-and-default-focus-behavior.html

+0

Ich würde Ihnen vorschlagen, den Code in der Antwort (Beibehaltung des ursprünglichen Bezugs, natürlich) zu kopieren, so dass es nicht auf externe Ressourcen abhängt. – tetsuo

+0

Problem mit dieser Lösung ist, dass, sobald Sie es jedes Mal wenn es angefügt wurde (AjaxRequestTarget # addComponent) es konzentriert (oder zumindest Fokus Javascript ist) mit AjaxRequestTarget # FocusComponent ist One-Shot-Fokus, so ist es besser geeignet für Verhalten in angefordert Frage ("Optionsfeld ist ausgewählt") –

3

Wenn Sie nur wollen Javascript setFocus durch und wollen nicht ein Formular oder eine Komponente neu zu laden, können Sie den folgenden Code verwenden:

import org.apache.wicket.Component; 

public class JavascriptUtils { 
    private JavascriptUtils() { 

    } 

    public static String getFocusScript(Component component) { 
     return "document.getElementById('" + component.getMarkupId() + "').focus();"; 
    } 
} 

und dann in jeder Ajax-Methode können Sie verwenden:

target.appendJavascript(JavascriptUtils.getFocusScript(componentToFocus)); 
0

Gibt es eine Möglichkeit, das gleiche ohne JavaScript zu erreichen?

(ich bin der Umsetzung ein Formular mit einem Feedback-Panels, die nur kommt, wenn Javascript ausgeschaltet ist, so dass es nicht sinnvoll wäre, da auf JavaScript angewiesen ..., -)

ich nur finden konnte, Antworten, die JS verwenden. focs() ... vielleicht bietet Wicket 1.5 eine Methode Component.setFocus() ...

+3

Es gibt keine Möglichkeit, den Fokus auf ein HTML-Element zu setzen, ohne JavaScript zu verwenden. HTML hat kein Tag oder Attribut, das dies (noch) ermöglichen würde. Wenn Wicket jemals eine Component.setFocus() -Methode implementiert, würde es trotzdem einige JavaScript generieren, um es zu aktivieren. – Marcelo

+1

Sie können das einfache HTML-Attribut "Autofokus" verwenden. Sie können es direkt zum ersten Eingabe-Tag der HTML-Datei hinzufügen oder hinzufügen wie "component.add (new AttributeAppender (" autofocus "," "));" Überprüfe meine kurze Antwort. – BlondCode

0

Wenn Sie zufällig eine Ajax-Taste verwenden, können Sie einfach target.focusComponent(myComponent); in der onSubmit Methode der Schaltfläche aufrufen .

16

Ich empfehle die Verwendung der nativen org.apache.wicket.ajax.AjaxRequestTarget#focusComponent(). Zum Beispiel:

/** 
* Sets the focus in the browser to the given component. The markup id must be set. If    
* the component is null the focus will not be set to any component. 
* 
* @param component 
*   The component to get the focus or null. 
*/ 
org.apache.wicket.ajax.AjaxRequestTarget#focusComponent(Component component) 
+0

Hör zu, was Martin-G sagt ;-) – Jesse

0

Für ein Pop-up wie modalWindow meine Abhilfe Lösung war das Attribut „Autofokus“ auf dem ersten Eingangs-Tag zu verwenden. Eine einfache Lösung ist es, es direkt zum HTML hinzuzufügen.

<input ..... autofocus> 

Eine andere Lösung ist es auf die modalWindow selbst hinzuzufügen:

@Override 
public void show(AjaxRequestTarget target) { 
    super.show(target); 
    setUpFocus(); 
} 

protected void setUpFocus() { 
    DeepChildFirstVisitor visitor = new DeepChildFirstVisitor() { 

     @Override 
     public void component(Component component, IVisit<Void> iVisit) { 
      if (isAutofocusable(component)) { 
       component.add(new AttributeAppender("autofocus", "")); 
       iVisit.stop(); 
      } 
     } 

     @Override 
     public boolean preCheck(Component component) { 
      return false; 
     } 
    }; 
    this.visitChildren(FormComponent.class, visitor); 
} 

    protected boolean isAutofocusable(Component component) { 
     if (component instanceof TextArea || 
       component instanceof DropDownChoice || 
//    component instanceof RadioChoice || 
       component instanceof AjaxCheckBox || 
       component instanceof AjaxButton || 
       component instanceof TextField) { 
      return true; 
     } 
     return false; 
    } 

RadioChoice wird kommentiert, weil diese Lösung nicht auf, dass die Arbeit. Für RadioChoice würde ich empfehlen, ein FocusedRadioChoice zu implementieren:

public class FocusedRadioChoice<T> extends RadioChoice<T> { 
//constructors... 
    @Override 
    protected IValueMap getAdditionalAttributes(int index, T choice) { 
     super.getAdditionalAttributes(0, choice); 
     AttributeMap am = new AttributeMap(); 
     am.put("autofocus", ""); 
     return am; 
    } 
} 
Verwandte Themen