2016-07-07 57 views
0

我有一個Angular2組件,它更新了我註釋並允許用戶編輯的導入的HTML文件。爲此,我正在使用純HTML5直接更新DOM。單擊一個類應該被添加到單擊的DOM元素。在瀏覽器中(FF和Chrome在Linux上)它會暫時添加 - 這意味着如果我立即打印節點,我會看到該類,但是在我退出該功能並打印之後,我不會。檢查元素顯示元素被更新爲< .... class>,當元素被點擊時沒有值。 這是工作時,我沒有Angular實現它。 我嘗試了直接的DOM操作(使用classList.add和x.className = y),angular的Renderer,並通過NgZone運行代碼,並且都具有相同的效果。有人能告訴我爲什麼會發生這種情況,我能做些什麼來解決這個問題? 注意:這是(應該是)一個簡單的內部工具 - 在這一點上,我需要一個快速修復(儘管額外的建議也是受歡迎的)。 (即還沒有完全執行代碼的幾個無關緊要的部分被省略。)DOM更改在我的Angular2組件中不按順序執行

import { Component, OnInit, NgZone } from "@angular/core"; 
import { Http, Headers, RequestOptions } from "@angular/http"; 

@Component({ 
    selector: "editor", 
    templateUrl: `editor/starterDemo.html` 
}) 
export class EditorComponent implements OnInit { 

    ngOnInit() { 
     this.fixImagePaths(); 
     this.annotate(); 
    } 

    constructor(public http: Http, public zone: NgZone) { } 
    // constructor(public http: Http, public renderer: Renderer) { } 

    fixImagePaths =() => { 
     const els = document.querySelectorAll('img'); 
     for (let i: number = 0, el: any; (el = els[i]); i++) { 
      el.src = 'editor/' + el.getAttribute('src'); 
     } 

    } 

    annotate =() => { 
     document.body.addEventListener('dragover', this.drag_over); 
     document.body.addEventListener('click', this.selectNone); 
     document.body.addEventListener('keydown', this.keyDown); 

     const els = document.querySelectorAll('img, .box'); 
     for (let i: number = 0, el: any; (el = els[i]); i++) { 
      el.draggable = true; 
      el.addEventListener('dragstart', this.drag_start); 
      el.addEventListener('click', this.selectItem); 
     } 
    } 

    selectItem = (event) => { 
     console.log("select item!"); 
     this.selectNone(); 
//  this.zone.run(() => { 
      event.target.closest('[draggable]').classList.add('dragme'); 
//  }); 
     //  this.renderer.setElementClass(event.target.closest('[draggable]').nativeElement, 'dragme', true); 
     //  console.log(event.target.closest('[draggable]')); 
     //  console.log(event.target.closest('[draggable]').classList); 
     //  console.log(event.target.closest('[draggable]').classList.contains('dragme')); 
     console.log(this.selected()); 
     return false; 
    } 

    selectNone =() => { 
     this.selected() && this.selected().classList.remove('dragme'); 
    } 

    selected =(): any => document.getElementsByClassName('dragme')[0]; 
} 

HTML:

<div class='box' 
    style="background-color: white; position: absolute; top: 847px; left: 842px; z-index: 20; height: 118px; width: 351px"></div> 

<img src="Screenshot1.png" 
    style="position: absolute; top: 0px; left: -1px" /> 
<img src="Screenshot2.png" 
    style="position: absolute; top: 913px; left: 0px; z-index: 2"/> 
<img src="Screenshot3.png" 
    style="position: absolute; top: 1768px; left: 0px" /> 

<div style="height: 2000px">&nbsp;</div> 
+0

你能告訴我們相應的HTML嗎? – rinukkusu

+0

我添加了HTML,並且我已經嘗試了x.className = y。 –

回答

0

我只是想出了這個問題(痛苦的時段後)。看起來在linux chrome中,返回false並不足以防止事件傳播,所以click事件在addClass調用之前一次和一次之前運行兩次。由於click事件在開始時有一個selectNone()(清除現有的選定項目),因此它在添加該類之前和之後運行了selectNone()。我添加了event.preventDefault();和event.stopPropagation();給我的事件處理程序。 我希望這可以幫助某人。