2016-12-04 54 views
0

我是Javascript开发的初学者,我必须做古典的待办应用程序。它必须是面向对象的,我的程序有两个类:任务和标签。 任务包含一些标签。如何使用局部变量在其他地方写监听器函数?

当用户点击标签时,他可以修改其名称。首先,我写了一个匿名回调函数,它正在监听修改表单提交,并且运行良好。但是,我必须创建一个声明的函数,而不是我现有的侦听器。但是,我需要访问我的对象的某些属性(这是编辑),我完全不知道如何做这样的事情。

这里是我的代码的一小部分:

module.Tag = class Tag { 
     constructor(name = 'untitled', parent = null) { 
      this.name = name; 
      this.parentTask = parent; 
     } 

     //Method which displays the tag name 
     display_name() { 
     return $('<li>').addClass('tag').text(this.name);  
     } 

     //Method which displays the tag 
     display() { 
     let tag_item = this.display_name(); 

     let field = $('<input>').prop('type', 'text').prop('value', this.name); 
     let button = $('<button>').addClass('validationButton').prop('type', 'submit').text('✓'); 
     let removeButton = $('<button>').addClass('removeButton').text('X'); 
     let form = $('<form>').append(field).append(button).append(removeButton); 
     let in_edit = false; 

     tag_item.click((event) => { 
      event.stopPropagation(); 
      event.preventDefault(); 

      let target = $(event.target); 

      if (target.is('li') && !in_edit) { 
      tag_item.empty(); 
      tag_item.append(form); 
      in_edit = true;   
      } 

      if (target.is('button') && target.prop('type') === 'submit') { 
      if(field.val() !== '') { 
       this.name = field.val(); 
       module.StorageManager.storeTasks(); 
      } 

      tag_item.empty(); 
      tag_item.text(this.name); 

      field.val(this.name); 

      in_edit = false; 
      } 

      if (target.is('button') && target.hasClass('removeButton')) { 
      if(confirm('Voulez-vous vraiment supprimer ce tag ?')) { 
       tag_item.remove(); 
       this.removeTagFromParent(); 

       module.StorageManager.storeTasks(); 
      } 
      } 
     }); 

     return tag_item; 
    } 

    //Method which removes the tag from the parent task 
    removeTagFromParent() { 
     this.parentTask.removeTag(this); 
    } 
    }; 

我的听众是在显示方法,它使用Tag.name财产和一些在方法体中创建的变量。我看不到如何在其他地方编写这个函数,而谷歌没有帮助我。

我希望我的问题很清楚,英文不是我的母语。 一些建议?

+0

“*我要创建声明别的地方,而不是我的听众现有的*命名函数” - 为什么?使用可用的代码。 – Bergi

+1

使用闭包。 – Bergi

+0

如果我的教授没有要求我在其他地方执行特定功能,我会这样做。另一个原因是我在我的代码的另一部分有相同的监听器,如果我找到解决问题的方法,我可以避免重复的代码。 – LeGaulois88

回答

2

您可以提取您的anonymouse函数作为另一个类方法。它是一个事件处理程序,所以为了正确访问定义的对象,您必须正确地绑定它。

下面是修改脚本的例子:

module.Tag = class Tag { 
     constructor(name = 'untitled', parent = null) { 
      this.name = name; 
      this.parentTask = parent; 
     } 

     //Method which displays the tag name 
     display_name() { 
     return $('<li>').addClass('tag').text(this.name);  
     } 

     //Method which displays the tag 
     display() { 
     let tag_item = this.display_name(); 

     let field = $('<input>').prop('type', 'text').prop('value', this.name); 
     let button = $('<button>').addClass('validationButton').prop('type', 'submit').text('✓'); 
     let removeButton = $('<button>').addClass('removeButton').text('X'); 
     let form = $('<form>').append(field).append(button).append(removeButton); 
     let in_edit = false; 

     tag_item.click(this.handleClick.bind(this)); // this is where you invoke the function and //bind it to the context of the class 

     return tag_item; 
    } 

    //Method which removes the tag from the parent task 
    removeTagFromParent() { 
     this.parentTask.removeTag(this); 
    } 

    // extracted method defined here: handleClick(event) { let tag_item = this.display_name(); let field = $('').prop('type', 'text').prop('value', this.name); event.stopPropagation(); event.preventDefault(); let target = $(event.target); if (target.is('li') && !in_edit) { tag_item.empty(); tag_item.append(form); in_edit = true; } if (target.is('button') && target.prop('type') === 'submit') { if(field.val() !== '') { this.name = field.val(); module.StorageManager.storeTasks(); } tag_item.empty(); tag_item.text(this.name); field.val(this.name); in_edit = false; } if (target.is('button') && target.hasClass('removeButton')) { if(confirm('Voulez-vous vraiment supprimer ce tag ?')) { tag_item.remove(); this.removeTagFromParent(); module.StorageManager.storeTasks(); } } } 
    };
+0

谢谢你的回答。另一个问题是我不得不在我的Tag类之外编写函数,所以我无法访问'this.name'或'this.display_name()'。 – LeGaulois88

+1

要在类外使用该函数,您需要在其外部提取名称函数体“handclick”。然后,您必须修改该函数以接受参数,以处理标签项目类的范围或直接参数以接受tag_item和字段的值。 – Pineda

+0

非常感谢。它完美的工作! – LeGaulois88

相关问题