2015-05-12 14 views
6

Tôi muốn tạo hiệu ứng một phiên dịch với chuyển đổi trên sự kiện nhấp bằng cách thêm lớp vào div trong js. Các thuộc tính biến đổi và chuyển đổi được thêm vào trong tệp css.Quá trình chuyển đổi không hoạt động mà không truy vấn thuộc tính chiều rộng

var widget = document.getElementById('widget');  
widget.style.display = 'block'; 
document.getElementById('widget2').clientWidth; //comment this line out and it wont work 
widget.className = 'visible'; 

Nó chỉ hoạt động nếu tôi truy vấn thuộc tính chiều rộng của bất kỳ phần tử trong dom trước khi thêm lớp.

đây là một jsfiddle: https://jsfiddle.net/5z9fLsr5/2/

bất cứ ai có thể giải thích tại sao điều này không hoạt động?

+1

Vì bạn đã sửa đổi thuộc tính 'display'" cùng một lúc ": https://jsfiddle.net/5z9fLsr5/3/ – Passerby

+0

bạn có thể sử dụng độ mờ thay vì hiển thị: https://jsfiddle.net/5z9fLsr5/4/ – Pete

Trả lời

2

Đó là vì bạn bắt đầu quá trình chuyển đổi và sửa đổi thuộc tính display "cùng một lúc". Thay đổi display sẽ hủy hoại bất kỳ chuyển tiếp (cần dẫn nguồn, thừa nhận), vì vậy nó sẽ là một ý tưởng tốt để cô lập các display thay đổi và quá cảnh thực tế:

https://jsfiddle.net/5z9fLsr5/3/

document.getElementById('showWidget').addEventListener('click', function(e) { 
 
    e.preventDefault(); 
 
    var widget = document.getElementById('widget');  
 
    widget.style.display = 'block'; 
 
    //document.getElementById('widget2').clientWidth; 
 
    window.setTimeout(function(){ 
 
     widget.className = 'visible'; 
 
    },0); 
 
});
#widget { 
 
    width: 200px; 
 
    height: 80px; 
 
    background: black; 
 
    position: absolute; 
 
    transition: transform 500ms; 
 
    transform: translateX(-200px); 
 
    display: none; 
 
} 
 
#widget.visible { 
 
    transform: translateX(200px); 
 
} 
 

 

 

 
#widget2 { 
 
    position: absolute; 
 
    right: 0 
 
}
<a href="#" id="showWidget">show</a> 
 
<div id="widget"></div> 
 
<div id="widget2">xxx</div>

Truy vấn clientWidth dường để "tạm dừng" việc thực hiện trong một thời gian, vì vậy nó hoạt động quá.

+0

đã không nhận ra rằng màn hình hiển thị prop có tác động như vậy trên hình ảnh động của tôi. Thx cho phản hồi nhanh của bạn. Tôi cũng nghĩ về một số kiểu bố cục kích hoạt bằng cách truy vấn chiều rộng – yacon

+0

@yacon Bởi vì 'display' không phải là" transitable ", nên bất kỳ sự chuyển đổi nào liên quan đến' display' (ngay cả khi bạn định nghĩa 'transition-property' để loại trừ nó) sẽ thất bại . – Passerby

0

Sự cố ở đây là cài đặt ban đầu của display: none. Đối với trình quản lý bố cục của trình duyệt, điều này cho thấy rằng bố cục nên được thực hiện như thể phần tử được đề cập không nằm trong DOM (nó vẫn là, nhớ bạn). Điều này có nghĩa là kiểu CSS transform: translateX(-200px); sẽ không được áp dụng.

Việc làm này:

widget.style.display = 'block'; 
widget.className = 'visible'; 

gây nên cả hai thay đổi về cơ bản cùng một lúc - bố trí được chỉ tái thực hiện sau khi cả hai câu lệnh đã được thực hiện. Chèn document.getElementById('widget2').clientWidth; (clientHeight cũng hoạt động) sẽ kích hoạt trình quản lý bố cục để sơn lại, do đó hãy đăng ký transform: translateX(-200px).

Như những người khác đã đề cập trước tôi, giải pháp là sử dụng một trong hai opacity thay vì display (điều này sẽ là sự lựa chọn của tôi), hoặc sử dụng setTimeout với một sự chậm trễ từ 0 (xem Why is setTimeout(fn, 0) sometimes useful?).

Các vấn đề liên quan