3

簡単なログインページ/ダイアログを実装する方法の例はありますか?私はdojoボイラープレートでそれをやろうとしています(私の前の質問をチェックしてください:Dojo MVCのレイアウト実装)。これまでのところ、ダイアログボックスを表示することができました。しかし、私は自分のデータを取得できるようにしたいので、クリックイベントで、たとえば(彼のコンテンツを含む)アラートボックスを作成したいと思います。

私の見解:

<form action="Login" method="post" validate="true" id="loginForm">
  <table width="258">
    &nbsp;
    <tr>
      <td><label>Login</label></td>
      <td><input class="cell" type="text" trim="true" dojoType="dijit.form.TextBox" value="" name="login" id="userId"/></td>
    </tr>
    <tr>
      <td><label>Password</label></td>
      <td><input class="cell" type="password" trim="true" dojoType="dijit.form.TextBox" value="" name="password" id="password"/></td>
    </tr>
    <tr><td colspan="2">&nbsp;</td></tr>
    <tr>
      <td colspan="2" align="center">
      <table border="0" cellspacing="0" cellpadding="0">
          <tr>
            <td align="center" valign="top"><button dojoType="dijit.form.Button" type="submit" id="LoginButton" onClick="connect">Ok</button></td>
            &nbsp;
            <td align="left" valign="top"><button dojoType="dijit.form.Button" type="submit" onclick="document.Login.reset()" id="Cancel">Cancel</button></td>
            &nbsp;
            <td><button dojoType="dijit.form.Button" type="submit" onclick="showDialog();" id="resetPassword"> Show Dialog </button></td>
          </tr>
     </table>
     &nbsp;
     </td>
    </tr>
  </table>
</form>

私のウィジェットモジュール/クラス

define([
    "dojo/_base/declare",
    "dijit/_Widget",
    "dijit/_TemplatedMixin",
    "dijit/_WidgetsInTemplateMixin",
    "dojo/text!app/views/Login/Login.html",
    "dijit/Dialog",
    "dijit/form/Button",
    "dijit/form/TextBox"
], function(
    declare,
    _Widget,
    _TemplatedMixin, 
    _WidgetsInTemplateMixin,
    template,
    Dialog
){
    return declare([_Widget, _TemplatedMixin, _WidgetsInTemplateMixin, Dialog], {

        templateString: template
    });
});

ここで、HTMLをチェックすると、要素ID LoginButtonは、この場合は「接続」関数を呼び出す必要があります。これは、(アラートボックスに)ユーザー名とパスワードの現在の入力を表示する必要があります。

関数はどこに置きますか?すこし...

    connect : function(){
    alert("username :" + dom.byId("userId").value() 
+ "  Password: " + dom.byId("password").value());
    }

編集:新しいコード

define([
    "dojo/_base/declare",
    "dijit/_Widget",
    "dojo/dom",
    "dijit/_TemplatedMixin",
    "dijit/_WidgetsInTemplateMixin",
    "dojo/text!app/views/Login/Login.html",
    "dijit/Dialog",
    "dijit/form/Button",
    "dijit/form/TextBox"
], function(
    declare,
    dom,
    _Widget,
    _TemplatedMixin, 
    _WidgetsInTemplateMixin,
    template,
    Dialog
){
    return declare("login", [_Widget, _TemplatedMixin, _WidgetsInTemplateMixin, Dialog], {

        templateString: template,

        postCreate: function() {
           this.inherited(arguments);
           // make reference to widget from the node attachment
           this.submitButton = dijit.getEnclosingWidget(this.submitButtonNode);
           // override its onSubmit
           this.submitButton.onClick = function(){
             alert("username :" + dom.byId("userId").value() 
                 + "  Password: " + dom.byId("password").value());
           };
        },
        // and a sample on how to implement widget-in-template stateful get/setter pattern
        // e.g. if submitbutton label should change on some event, call as such:
        // dijit.byId('loginForm').set("submitLabel", "Sendin login, please wait");
        _setSubmitLabelAttr : function(value) {
            return this.submitButton.set("label", value);
        },
        _getSubmitLabelAttr : function() {
            return this.submitButton.get("label");
        },
    });
});

私のmain.js:

define([ 'dojo/has', 'require', 'dojo/_base/sniff'], function (has, require) {
    var app = {};

    if (has('host-browser')) {

        require([ './views/Login', 'dojo/domReady!' ], function (Login) {
            app.login = new Login().placeAt(document.body);

            app.login.startup();

            // And now…
            app.login.show();
        });
    }
    else {
        console.log('Hello from the server!');
    }
});
4

3 に答える 3

7

ソリューションを追加したい:http://jsfiddle.net/phusick/tG8Sg/

jsFiddleの制約のために少しねじれていますが、主な原則はコーディングで採用しているものと同じです。

まず、ログインプロセス(またはその他のフォーム処理)がダイアログ内にカプセル化され、を介して偶数を出力すると考えられる残りのアプリケーションと通信しますdojo/Evented。仕組みは次のとおりです。

var loginDialog = new LoginDialog({ controller: loginController});
loginDialog.startup();
loginDialog.show();

loginDialog.on("cancel", function() {
    console.log("Login cancelled.");        
});

loginDialog.on("error", function() { 
    console.log("Login error.");
});

loginDialog.on("success", function() { 
    console.log("Login success.");
    console.log(JSON.stringify(this.form.get("value")));
});

jsFiddleでわかるように、コンストラクター内でアセンブルする2つのテンプレートdialog-templatelogin-form-templateLoginDialogがあります。その理由は、通常、dijit/form/Form標準の検証やデータのシリアル化を超えた魔法を実行するためのクラスラッピングもあるためですdijit/form/Formが、ログインは簡単で、jsFiddleの単一ファイルでは混乱するため、それを取り除きました。フォームをダイアログから分離することの利点は、同じフォーム(つまり、View)を、他の場所(たとえば、)のすべてのフォームアドホックコードと一緒に使用できることですContentPane。フォームは、ユーザーとの間でデータを表示および収集するためだけにあり、モデル、つまりWebサービスと直接通信するべきではありません。コントローラーがあります。その目的のために:

var LoginController = declare(null, {

    constructor: function(kwArgs) {
        lang.mixin(this, kwArgs);
    },

    login: function(data) {
        // simulate calling web service for authentication
        var def = new Deferred();
        setTimeout(lang.hitch(this, function() {
            def.resolve(data.username == this.username && data.password == this.password);                
        }), 1000);
        return def;
    }
});

のインスタンスを作成しますLoginController

// provide username & password in the constructor
// since we do not have web service here to authenticate against    
var loginController = new LoginController({username: "user", password: "user"});

LoginDialog上でまだ見たように、それをコンストラクターに渡します。

var loginDialog = new LoginDialog({ controller: loginController});

最後にLoginDialogクラス:

var LoginDialog = declare([Dialog, Evented], {

    READY: 0,
    BUSY: 1,

    title: "Login Dialog",
    message: "",
    busyLabel: "Working...",

    // Binding property values to DOM nodes in templates
    // see: http://www.enterprisedojo.com/2010/10/02/lessons-in-widgetry-binding-property-values-to-dom-nodes-in-templates/
    attributeMap: lang.delegate(dijit._Widget.prototype.attributeMap, {
        message: {
            node: "messageNode",
            type: "innerHTML"               
        }            
    }),

    constructor: function(/*Object*/ kwArgs) {
        lang.mixin(this, kwArgs);            
        var dialogTemplate = dom.byId("dialog-template").textContent; 
        var formTemplate = dom.byId("login-form-template").textContent;
        var template = lang.replace(dialogTemplate, {
            form: formTemplate                
        });

        var contentWidget = new (declare(
            [_Widget, _TemplatedMixin, _WidgetsInTemplateMixin],
            {
                templateString: template                   
            }
        )); 
        contentWidget.startup();
        var content = this.content = contentWidget;
        this.form = content.form;
        // shortcuts
        this.submitButton = content.submitButton;
        this.cancelButton = content.cancelButton;
        this.messageNode = content.messageNode;
    },

    postCreate: function() {
        this.inherited(arguments);

        this.readyState= this.READY;
        this.okLabel = this.submitButton.get("label");

        this.connect(this.submitButton, "onClick", "onSubmit");
        this.connect(this.cancelButton, "onClick", "onCancel");

        this.watch("readyState", lang.hitch(this, "_onReadyStateChange"));

        this.form.watch("state", lang.hitch(this, "_onValidStateChange"));
        this._onValidStateChange();
    },

    onSubmit: function() {
        this.set("readyState", this.BUSY);
        this.set("message", ""); 
        var data = this.form.get("value");

        // ask the controller to login
        var auth = this.controller.login(data);

        Deferred.when(auth, lang.hitch(this, function(loginSuccess) {
            if (loginSuccess === true) {
                this.onLoginSuccess();
                return;                    
            }
            this.onLoginError();
        }));
    },

    onLoginSuccess: function() {
        this.set("readyState", this.READY);            
        this.emit("success");
    },

    onLoginError: function() {
        this.set("readyState", this.READY);
        this.set("message", "Please try again."); 
        this.emit("error");         
    },

    onCancel: function() {
       this.emit("cancel");     
    },

    _onValidStateChange: function() {
        this.submitButton.set("disabled", !!this.form.get("state").length);
    },

    _onReadyStateChange: function() {
        var isBusy = this.get("readyState") == this.BUSY;
        this.submitButton.set("label", isBusy ? this.busyLabel : this.okLabel);
        this.submitButton.set("disabled", isBusy);
    }            
});

前述のjsFiddleのテンプレートを参照してください。それらは通常required経由で別々のファイルにあるはずです。jsFiddleに合うようにdojo/text!それらを入れました。<script type="text/template">

于 2012-06-13T14:29:56.313 に答える
1

ウィジェットをテンプレート化するときに、テンプレート化されたウィジェットの解析を利用する必要があります。以下のhttp://dojotoolkit.org/documentation/tutorials/1.6/templated/から引用して、イベントを単純なdomnodeにアタッチする方法を説明します。

<div 
  data-dojo-attach-point="focusNode"
  data-dojo-attach-event="ondijitclick:_onClick"
  role="menuitem" tabindex="-1">
    <span data-dojo-attach-point="containerNode"></span>
</div>

テンプレートにウィジェットがあるので、子ウィジェットへの参照を作成し、これらの参照を介してそれらのプロパティを設定します。

<td align="center" valign="top">
  <button 
     id="LoginButton"  type="submit" 
     dojoType="dijit.form.Button"
     dojoAttachPoint="submitButtonNode">
        Ok
   </button>
</td>

dijit / dojox/dojoフォルダーの「兄弟」になるようにフォルダーを作成します。これを「app」と呼びます。そして、ウィジェットの宣言に続いて、app / widget/MyWidget.jsというファイルを下に置きます。

define([
    "dojo/_base/declare",
"dijit/_Widget",
"dijit/_TemplatedMixin",
"dijit/_WidgetsInTemplateMixin",
"dojo/text!app/views/Login/Login.html",
"dijit/Dialog",
"dijit/form/Button",
"dijit/form/TextBox"

], function(
    declare,
 _Widget,
_TemplatedMixin, 
_WidgetsInTemplateMixin,
template,
Dialog

){
    return declare("app.widget.MyWidget", [_Widget, _TemplatedMixin, _WidgetsInTemplateMixin, Dialog], {

        templateString: template
        postCreate: function() {
           this.inherited(arguments);
           // make reference to widget from the node attachment
           this.submitButton = dijit.getEnclosingWidget(dojo.query(".dijitButton")[0], this.domNode);
                 // or simply dijit.byId('LoginButton');
           // override its onSubmit
           this.submitButton.onClick = function(){
             alert("username :" + dom.byId("userId").value() 
                 + "  Password: " + dom.byId("password").value());
           };
        },
        // and a sample on how to implement widget-in-template stateful get/setter pattern
        // e.g. if submitbutton label should change on some event, call as such:
        // dijit.byId('loginForm').set("submitLabel", "Sendin login, please wait");
        _setSubmitLabelAttr : function(value) {
            return this.submitButton.set("label", value);
        },
        _getSubmitLabelAttr : function() {
            return this.submitButton.get("label");
        }
    });
});

そして、ファイルが配置されたら、次のようにhtmlを記述します。

<head>
   <script src=...dojo...></script>
   <script>
      dojo.require([ 
        "dojo/parser", 
        "app/widget/MyWidget",
        "dojo/domReady!" ] , function(parser) {

          parser.parse();

      });
   </script>
</head>
<body>
   <form dojoType="app.widget.MyWidget"></div>
</body>

これは次のようになります。

  • dojotoolkit(dojo / dojo.js)をロードします
  • サブスペース「widget」を持つ「app」という名前空間を作成します
  • ボディのレンダリング(単純なフォームのDOMノード)
  • スクリプトをondomreadyで呼び出すには、app.widget.MyWidget
  • MyWidgetには依存関係が必要です
  • parser.parseは、<form dojoType="mywidget">
于 2012-06-11T18:21:58.783 に答える
1

mschrの助けを借りて。私はこの特定の解決策に出くわしました。

define([
"dojo/_base/declare",
"dojo/dom",
"dijit/_Widget",
"dijit/_TemplatedMixin",
"dijit/_WidgetsInTemplateMixin",
"dojo/text!app/views/Login/Login.html",
"dijit/Dialog",
"dijit/form/Button",
"dijit/form/TextBox"

], function(
    declare,
    dom,
 _Widget,
_TemplatedMixin, 
_WidgetsInTemplateMixin,
template,
Dialog
){
    return declare([_Widget, _TemplatedMixin, _WidgetsInTemplateMixin, Dialog], {

        templateString: template,

        postCreate: function() {
           this.inherited(arguments);
           // make reference to widget from the node attachment
           //this.submitButton = this.getChildren()[ButtonIndex];
           // override its onSubmit
             /*alert("username :" + dom.byId("userId").value() 
                 + "  Password: " + dom.byId("password").value());*/
            dojo.connect(this.loginButton, 'onclick', this._login);
        },
        // and a sample on how to implement widget-in-template stateful get/setter pattern
        // e.g. if submitbutton label should change on some event, call as such:
        // dijit.byId('loginForm').set("submitLabel", "Sendin login, please wait");
        _login : function() {
            var value = dom.byId("userId").value;

            if(value)
                alert("username: " + value);
        },
        // and a sample on how to implement widget-in-template stateful get/setter pattern
        // e.g. if submitbutton label should change on some event, call as such:
        // dijit.byId('loginForm').set("submitLabel", "Sendin login, please wait");
        _setSubmitLabelAttr : function(value) {
            return this.submitButton.set("label", value);
        },
        _getSubmitLabelAttr : function() {
            return this.submitButton.get("label");
        },
    });
});
于 2012-06-12T16:31:04.540 に答える