国产av日韩一区二区三区精品,成人性爱视频在线观看,国产,欧美,日韩,一区,www.成色av久久成人,2222eeee成人天堂

目錄
使用JavaScript生成關(guān)鍵幀
步驟1:計算起始和結(jié)束狀態(tài)
步驟2:生成關(guān)鍵幀
步驟3:啟用CSS動畫
構(gòu)建可展開部分
性能檢查
最終考慮
首頁 web前端 css教學(xué) 表演者可擴展動畫:即時建立關(guān)鍵框架

表演者可擴展動畫:即時建立關(guān)鍵框架

Apr 08, 2025 am 10:51 AM

Performant Expandable Animations: Building Keyframes on the Fly

CSS動畫技術(shù)日益成熟,為開發(fā)者提供了更強大的工具。特別是CSS動畫,已經(jīng)成為解決大多數(shù)動畫用例的基礎(chǔ)。然而,有些動畫需要更精細的處理。

眾所周知,動畫應(yīng)在合成層運行(此處不再贅述,如有興趣,請參考相關(guān)文獻)。這意味著動畫的變換或不透明度屬性不會觸發(fā)佈局或繪製層。而動畫高度和寬度等屬性則會觸發(fā)這些層,迫使瀏覽器重新計算樣式,這是需要避免的。

此外,即使是動畫變換屬性,如果要實現(xiàn)真正的60 FPS動畫,可能也需要藉助JavaScript,例如使用FLIP技術(shù)來實現(xiàn)更流暢的動畫!

然而,使用變換屬性進行可展開動畫的問題在於,縮放函數(shù)與動畫高度/寬度屬性並不完全相同。它會對內(nèi)容產(chǎn)生傾斜效果,因為所有元素都會被拉伸(向上縮放)或擠壓(向下縮放)。

因此,我的常用解決方案(可能仍然是,原因?qū)⒃卺崦嬖敿氄f明)是Brandon Smith文章中的方法3 。這種方法仍然對高度進行過渡,但使用JavaScript計算內(nèi)容大小,並使用requestAnimationFrame強制進行過渡。在OutSystems,我們實際上使用此方法為OutSystems UI手風(fēng)琴模式構(gòu)建動畫。

使用JavaScript生成關(guān)鍵幀

最近,我偶然發(fā)現(xiàn)了Paul Lewis的另一篇精彩文章,詳細介紹了一種新的展開和折疊動畫解決方案,這促使我撰寫本文並推廣這種技術(shù)。

用他的話說,主要思想是生成動態(tài)關(guān)鍵幀,逐步……

[…] 從0到100,併計算元素及其內(nèi)容所需的縮放值。然後,這些值可以簡化為一個字符串,並將其作為樣式元素注入頁面。

要實現(xiàn)這一點,主要有三個步驟。

步驟1:計算起始和結(jié)束狀態(tài)

我們需要計算兩種狀態(tài)的正確縮放值。這意味著我們對將作為起始狀態(tài)代理的元素使用getBoundingClientRect() ,並將其除以結(jié)束狀態(tài)的值。它應(yīng)該類似於:

 function calculateStartScale () {
  const start= startElement.getBoundingClientRect();
  const end= endElement.getBoundingClientRect();
  return {
    x: start.width / end.width,
    y: start.height / end.height
  };
}

步驟2:生成關(guān)鍵幀

現(xiàn)在,我們需要運行一個for循環(huán),使用所需的幀數(shù)作為長度。 (為了確保動畫流暢,它不應(yīng)該少於60幀。)然後,在每次迭代中,我們使用緩動函數(shù)計算正確的緩動值:

 function ease (v, pow=4) {
  return 1 - Math.pow(1 - v, pow);
}

let easedStep = ease(i / frame);

使用該值,我們將使用以下數(shù)學(xué)公式獲得元素在當(dāng)前步驟的縮放比例:

 const xScale = x (1 - x) * easedStep;
const yScale = y (1 - y) * easedStep;

然後我們將步驟添加到動畫字符串中:

 animation = `${step}% {
  transform: scale(${xScale}, ${yScale});
}`;

為了避免內(nèi)容被拉伸/傾斜,我們應(yīng)該對其進行反向動畫,使用反向值:

 const invXScale = 1 / xScale;
const invYScale = 1 / yScale;

inverseAnimation = `${step}% {
  transform: scale(${invXScale}, ${invYScale});
}`;

最後,我們可以返回已完成的動畫,或直接將它們注入新創(chuàng)建的樣式標(biāo)籤中。

步驟3:啟用CSS動畫

在CSS方面,我們需要在正確的元素上啟用動畫:

 .element--expanded {
  animation-name: animation;
  animation-duration: 300ms;
  animation-timing-function: step-end;
}

.element-contents--expanded {
  animation-name: inverseAnimation ;
  animation-duration: 300ms;
  animation-timing-function: step-end;
}

您可以在Codepen上查看Paul Lewis文章中的菜單示例(由Chris提供)。

構(gòu)建可展開部分

掌握了這些基本概念後,我想檢查一下是否可以將此技術(shù)應(yīng)用於不同的用例,例如可展開部分。

在這種情況下,我們只需要動畫高度,特別是在計算縮放比例的函數(shù)中。我們從節(jié)標(biāo)題獲取Y值,作為折疊狀態(tài),並獲取整個節(jié)來表示展開狀態(tài):

 _calculateScales () {
      var collapsed = this._sectionItemTitle.getBoundingClientRect();
      var expanded = this._section.getBoundingClientRect();

      // create css variable with collapsed height, to apply on the wrapper
      this._sectionWrapper.style.setProperty('--title-height', collapsed.height 'px');

      this._collapsed = {
        y: collapsed.height / expanded.height
      }
    }

由於我們希望展開的部分具有絕對定位(為了避免它在折疊狀態(tài)下佔用空間),我們使用折疊高度為其設(shè)置CSS變量,並將其應(yīng)用於包裝器。這將是唯一具有相對定位的元素。

接下來是創(chuàng)建關(guān)鍵幀的函數(shù): _createEaseAnimations() 。這與上面解釋的內(nèi)容差別不大。對於這個用例,我們實際上需要創(chuàng)建四個動畫:

  1. 展開包裝器的動畫
  2. 內(nèi)容的反向展開動畫
  3. 折疊包裝器的動畫
  4. 內(nèi)容的反向折疊動畫

我們遵循與之前相同的方法,運行長度為60的for循環(huán)(以獲得平滑的60 FPS動畫),並基於緩動步驟創(chuàng)建關(guān)鍵幀百分比。然後,我們將它推送到最終的動畫字符串:

 outerAnimation.push(`
  ${percentage}% {
    transform: scaleY(${yScale});
  }`);

innerAnimation.push(`
  ${percentage}% {
    transform: scaleY(${invScaleY});
  }`);

我們首先創(chuàng)建一個樣式標(biāo)籤來保存完成的動畫。由於這是作為一個構(gòu)造函數(shù)構(gòu)建的,為了能夠輕鬆添加多個模式,我們希望所有這些生成的動畫都在同一個樣式表中。因此,首先,我們驗證元素是否存在。如果不存在,我們創(chuàng)建它並添加一個有意義的類名。否則,您最終會為每個可展開的部分獲得一個樣式表,這不是理想的。

 var sectionEase = document.querySelector('.section-animations');
 if (!sectionEase) {
  sectionEase = document.createElement('style');
  sectionEase.classList.add('section-animations');
 }

說到這一點,您可能已經(jīng)在想,“嗯,如果我們有多個可展開的部分,它們是否仍然使用相同名稱的動畫,並且其內(nèi)容可能具有錯誤的值?”

你完全正確!因此,為了防止這種情況,我們還生成動態(tài)動畫名稱。很酷,對吧?

當(dāng)進行querySelectorAll('.section')查詢以向名稱添加唯一元素時,我們使用傳遞給構(gòu)造函數(shù)的索引:

 var sectionExpandAnimationName = "sectionExpandAnimation" index;
var sectionExpandContentsAnimationName = "sectionExpandContentsAnimation" index;

然後我們使用此名稱在當(dāng)前可展開部分設(shè)置CSS變量。由於此變量僅在此範(fàn)圍內(nèi),我們只需要在CSS中將動畫設(shè)置為新的變量,每個模式將獲得其各自的animation-name值。

 .section.is--expanded {
  animation-name: var(--sectionExpandAnimation);
}

.is--expanded .section-item {
  animation-name: var(--sectionExpandContentsAnimation);
}

.section.is--collapsed {
  animation-name: var(--sectionCollapseAnimation);
}

.is--collapsed .section-item {
  animation-name: var(--sectionCollapseContentsAnimation);
}

腳本的其餘部分與添加事件監(jiān)聽器、切換折疊/展開狀態(tài)的函數(shù)以及一些輔助功能改進有關(guān)。

關(guān)於HTML和CSS:需要額外的工作才能使可展開功能正常工作。我們需要一個額外的包裝器作為不進行動畫的相對元素??烧归_的子元素具有絕對位置,因此在折疊時不會佔用空間。

請記住,由於我們需要進行反向動畫,因此我們使其縮放全尺寸以避免內(nèi)容出現(xiàn)傾斜效果。

 .section-item-wrapper {
  min-height: var(--title-height);
  position: relative;
}

.section {
  animation-duration: 300ms;
  animation-timing-function: step-end;
  contain: content;
  left: 0;
  position: absolute;
  top: 0;
  transform-origin: top left;
  will-change: transform;
}

.section-item {
  animation-duration: 300ms;
  animation-timing-function: step-end;
  contain: content;
  transform-origin: top left;
  will-change: transform;  
}

我想強調(diào)animation-timing-function屬性的重要性。它應(yīng)該設(shè)置為linearstep-end以避免每個關(guān)鍵幀之間的緩動。

will-change change屬性——正如您可能知道的那樣——將為變換動畫啟用GPU加速,以獲得更流暢的體驗。使用contains屬性,值為contents ,將幫助瀏覽器獨立於DOM樹的其餘部分處理元素,限制其重新計算佈局、樣式、繪製和大小屬性的區(qū)域。

我們使用visibilityopacity來隱藏內(nèi)容,並在折疊時阻止屏幕閱讀器訪問它。

 .section-item-content {
  opacity: 1;
  transition: opacity 500ms ease;
}

.is--collapsed .section-item-content {
  opacity: 0;
  visibility: hidden;
}

最後,我們有了可展開的部分!以下是完整的代碼和演示供您查看:

性能檢查

每當(dāng)我們處理動畫時,性能都應(yīng)該銘記於心。因此,讓我們使用開發(fā)者工具來檢查所有這些工作在性能方面是否值得。使用Performance選項卡(我使用的是Chrome DevTools),我們可以分析動畫期間的FPS和CPU使用率。

結(jié)果非常好!

使用FPS測量工具更詳細地檢查值,我們可以看到它始終達到60 FPS的標(biāo)記,即使是濫用使用也是如此。

最終考慮

那麼,最終結(jié)論是什麼?這是否取代了所有其他方法?這是“聖杯”解決方案嗎?

在我看來,不是。

但是……這沒關(guān)係!它只是列表中的另一個解決方案。並且,與任何其他方法一樣,應(yīng)該分析它是否是針對用例的最佳方法。

這種技術(shù)肯定有其優(yōu)點。正如Paul Lewis所說,這確實需要大量工作來準(zhǔn)備。但是,另一方面,我們只需要在頁面加載時執(zhí)行一次。在交互過程中,我們僅僅是切換類(在某些情況下,為了輔助功能,還切換屬性)。

然而,這給元素的UI帶來了一些限制。正如您在可展開部分元素中看到的那樣,反向縮放使其更可靠地用於絕對和畫布外元素,例如浮動操作或菜單。由於它使用overflow: hidden ,因此難以設(shè)置邊框樣式。

儘管如此,我認為這種方法潛力巨大。請告訴我您的想法!

以上是表演者可擴展動畫:即時建立關(guān)鍵框架的詳細內(nèi)容。更多資訊請關(guān)注PHP中文網(wǎng)其他相關(guān)文章!

本網(wǎng)站聲明
本文內(nèi)容由網(wǎng)友自願投稿,版權(quán)歸原作者所有。本站不承擔(dān)相應(yīng)的法律責(zé)任。如發(fā)現(xiàn)涉嫌抄襲或侵權(quán)的內(nèi)容,請聯(lián)絡(luò)admin@php.cn

熱AI工具

Undress AI Tool

Undress AI Tool

免費脫衣圖片

Undresser.AI Undress

Undresser.AI Undress

人工智慧驅(qū)動的應(yīng)用程序,用於創(chuàng)建逼真的裸體照片

AI Clothes Remover

AI Clothes Remover

用於從照片中去除衣服的線上人工智慧工具。

Clothoff.io

Clothoff.io

AI脫衣器

Video Face Swap

Video Face Swap

使用我們完全免費的人工智慧換臉工具,輕鬆在任何影片中換臉!

熱工具

記事本++7.3.1

記事本++7.3.1

好用且免費的程式碼編輯器

SublimeText3漢化版

SublimeText3漢化版

中文版,非常好用

禪工作室 13.0.1

禪工作室 13.0.1

強大的PHP整合開發(fā)環(huán)境

Dreamweaver CS6

Dreamweaver CS6

視覺化網(wǎng)頁開發(fā)工具

SublimeText3 Mac版

SublimeText3 Mac版

神級程式碼編輯軟體(SublimeText3)

什麼是'渲染障礙CSS”? 什麼是'渲染障礙CSS”? Jun 24, 2025 am 12:42 AM

CSS會阻塞頁面渲染是因為瀏覽器默認將內(nèi)聯(lián)和外部CSS視為關(guān)鍵資源,尤其是使用引入的樣式表、頭部大量內(nèi)聯(lián)CSS以及未優(yōu)化的媒體查詢樣式。 1.提取關(guān)鍵CSS並內(nèi)嵌至HTML;2.延遲加載非關(guān)鍵CSS通過JavaScript;3.使用media屬性優(yōu)化加載如打印樣式;4.壓縮合併CSS減少請求。建議使用工具提取關(guān)鍵CSS,結(jié)合rel="preload"異步加載,合理使用media延遲加載,避免過度拆分與復(fù)雜腳本控制。

外部與內(nèi)部CSS:最好的方法是什麼? 外部與內(nèi)部CSS:最好的方法是什麼? Jun 20, 2025 am 12:45 AM

thebestapphachforcssdepprodsontheproject'sspefificneeds.forlargerprojects,externalcsSissBetterDuoSmaintoMaintainability andReusability; forsMallerProjectsorsingle-pageApplications,InternaltCsmightBemoresobleable.InternalCsmightBemorese.it.it'sclucialtobalancepopryseceneceenceprodrenceprodrenceNeed

我的CSS必須在較低的情況下嗎? 我的CSS必須在較低的情況下嗎? Jun 19, 2025 am 12:29 AM

否,CSSDOESNOTHAVETOBEINLOWERCASE.CHOMENDENS,使用flowercaseisrecommondendendending:1)一致性和可讀性,2)避免使用促進性技術(shù),3)潛在的Performent FormanceBenefits,以及4)RightCollaboraboraboraboraboraboraboraboraboraboraboraboraboraboraboraboraborationWithInteams。

CSS案例靈敏度:了解重要的 CSS案例靈敏度:了解重要的 Jun 20, 2025 am 12:09 AM

cssismostlycaseminemintiment,buturlsandfontfamilynamesarecase敏感。 1)屬性和valueslikeColor:紅色; prenotcase-sensive.2)urlsmustmustmatchtheserver'server'scase,例如

什麼是AutoPrefixer,它如何工作? 什麼是AutoPrefixer,它如何工作? Jul 02, 2025 am 01:15 AM

Autoprefixer是一個根據(jù)目標(biāo)瀏覽器範(fàn)圍自動為CSS屬性添加廠商前綴的工具。 1.它解決了手動維護前綴易出錯的問題;2.通過PostCSS插件形式工作,解析CSS、分析需加前綴的屬性、依配置生成代碼;3.使用步驟包括安裝插件、設(shè)置browserslist、在構(gòu)建流程中啟用;4.注意事項有不手動加前綴、保持配置更新、非所有屬性都加前綴、建議配合預(yù)處理器使用。

什麼是CSS計數(shù)器? 什麼是CSS計數(shù)器? Jun 19, 2025 am 12:34 AM

csscounterscanautomationallymentermentermentections和lists.1)usecounter-ensettoInitializize,反插入式發(fā)芽,andcounter()orcounters()

CSS:何時重要(何時不)? CSS:何時重要(何時不)? Jun 19, 2025 am 12:27 AM

在CSS中,選擇器和屬性名不區(qū)分大小寫,而值、命名顏色、URL和自定義屬性則區(qū)分大小寫。 1.選擇器和屬性名不區(qū)分大小寫,例如background-color和Background-Color相同。 2.值中的十六進制顏色不區(qū)分大小寫,但命名顏色區(qū)分大小寫,如red有效而Red無效。 3.URL區(qū)分大小寫,可能導(dǎo)致文件加載問題。 4.自定義屬性(變量)區(qū)分大小寫,使用時需注意大小寫一致。

什麼是圓錐級函數(shù)? 什麼是圓錐級函數(shù)? Jul 01, 2025 am 01:16 AM

theconic-Gradient()functionIncsscreatesCircularGradientsThatRotateColorStopSaroundAcentralPoint.1.IsidealForPieCharts,ProgressIndicators,colordichers,colorwheels和decorativeBackgrounds.2.itworksbysbysbysbydefindefingincolordefingincolorstopsatspecificains off.

See all articles