最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

Flutter進階之實現(xiàn)動畫效果(七)

 更新時間:2018年08月21日 08:40:03   作者:何小有  
這篇文章主要為大家詳細介紹了Flutter進階之實現(xiàn)動畫效果的第七篇,具有一定的參考價值,感興趣的小伙伴們可以參考一下

我們假設(shè)一種情況,如果應(yīng)用程序使用條形圖顯示給定年份的產(chǎn)品類別的銷售額,用戶可以選擇另一年,然后該應(yīng)用程序?qū)赢嫷皆撃甑臈l形圖。如果產(chǎn)品類別在兩年內(nèi)是相同的,或者恰好是相同的,除了在其中一個圖表中右側(cè)顯示的其他類別,我們可以使用我們現(xiàn)有的代碼。但如果公司在2016年有A,B,C和X類產(chǎn)品,但是在2017年中斷了B并推出了D?

動畫效果可以做得非常好看,但仍然會讓用戶感到困惑。為什么?因為它不保留語義。它將表示產(chǎn)品類別B的圖形元素轉(zhuǎn)換為代表類別C的一個圖形元素,而將C的圖形元素轉(zhuǎn)換到其他地方。正因為2016 B恰好是在2017 C后來出現(xiàn)的同一位置,并不意味著前者應(yīng)該變成后者。相反,2016年B應(yīng)該消失,2016年C應(yīng)該向左移動到2017年,而2017年D應(yīng)該出現(xiàn)在右邊。我們可以使用傳統(tǒng)的合并排序列表實現(xiàn)這種混合。

我們可以分別給每一個條形以不同的顏色,然后使用顏色來區(qū)分銷售的產(chǎn)品,一種顏色代表一個產(chǎn)品,當(dāng)一種顏色消失時,說明該產(chǎn)品已經(jīng)下架,反之,則說明新產(chǎn)品已經(jīng)上架。

通過語義對應(yīng)的組件進行復(fù)合值之間的線性插值(lerp),當(dāng)組件形成排序列表時,合并算法可以將這些組件放在側(cè)面上,使用不可見組件來處理單面合并。我們所需要的是使Bar實例以線性順序相互比較。然后我們可以將它們合并。

// ...
class BarChart {
 // ...
 factory BarChart.random(Size size, Random random) {
 const barWidthFraction = 0.75;
 final ranks = selectRanks(random, ColorPalette.primary.length);
 final barCount = ranks.length;
 final barDistance = size.width / (1+barCount);
 final barWidth = barDistance * barWidthFraction;
 final startX = barDistance - barWidth/2;
 final bars = new List.generate(
  barCount,
  (i)=> new Bar(
  ranks[i],
  startX + i * barDistance,
  barWidth,
  random.nextDouble() * size.height,
  ColorPalette.primary[ranks[i]],
  ),
 );
 return new BarChart(bars);
 }

 static List<int> selectRanks(Random random, int cap) {
 final ranks = <int>[];
 var rank = 0;
 while(true) {
  // 模擬產(chǎn)品的上架下架
  if(random.nextDouble() < 0.2) rank++;
  if(cap <= rank) break;
  ranks.add(rank);
  rank++;
 }
 return ranks;
 }

 static BarChart lerp(BarChart begin, BarChart end, double t) {
 final bars = <Bar>[];
 final bMax = begin.bars.length;
 final eMax = end.bars.length;
 var b = 0;
 var e = 0;
 while (b + e < bMax + eMax) {
  /*
  這里的條件判斷中包含兩種情況
  b < bMax && e == eMax:
  當(dāng)新圖表條形數(shù)減少時
  b < bMax && begin.bars[b] < end.bars[e]:
  當(dāng)新圖表不包含舊圖表的顏色條形時
  滿足一種情況,處理舊圖表中多余的條形,即向左側(cè)方清除舊條形
  */
  if(b < bMax && (e == eMax || begin.bars[b] < end.bars[e])) {
  bars.add(Bar.lerp(begin.bars[b], begin.bars[b].collapsed, t));
  b++;
  /*
  這里的條件判斷中包含兩種情況
  e < eMax && b == bMax:
  當(dāng)新圖表條形數(shù)增加時
  e < eMax && end.bars[e] < begin.bars[b]:
  當(dāng)新圖表包含舊圖表沒有的顏色條形時
  滿足一種情況,處理舊圖表中沒有的條形,即向右側(cè)方繪制新條形
  */
  } else if(e < eMax && (b == bMax || end.bars[e] < begin.bars[b])) {
  bars.add(Bar.lerp(end.bars[e].collapsed, end.bars[e], t));
  e++;
  // 當(dāng)新圖表與舊圖表有同一個顏色條形時,原地變形
  } else {
  bars.add(Bar.lerp(begin.bars[b], end.bars[e], t));
  b++;
  e++;
  }
 }
 return new BarChart(bars);
 }
}

class BarChartTween extends Tween<BarChart> {
 BarChartTween(BarChart begin, BarChart end) : super(begin: begin, end: end);

 @override
 BarChart lerp(double t) => BarChart.lerp(begin, end, t);
}

class Bar {
 Bar(this.rank, this.x, this.width, this.height, this.color);
 final int rank;
 final double x;
 final double width;
 final double height;
 final Color color;

 Bar get collapsed => new Bar(rank, x, 0.0, 0.0, color);

 /*
 bool operator <(
 Duration other
 )
 如果此Duration的值小于other值,則返回true
 bool operator <(Duration other) => this._duration < other._duration;
 */
 bool operator <(Bar other) => rank < other.rank;

 static Bar lerp(Bar begin, Bar end, double t) {
 assert(begin.rank == end.rank);
 return new Bar(
  begin.rank,
  lerpDouble(begin.x, end.x, t),
  lerpDouble(begin.width, end.width, t),
  lerpDouble(begin.height, end.height, t),
  Color.lerp(begin.color, end.color, t)
 );
 }
}

class BarTween extends Tween<Bar> {
 BarTween(Bar begin, Bar end) : super(begin: begin, end: end) {
 assert(begin.rank == end.rank);
 }

 @override
 Bar lerp(double t) => Bar.lerp(begin, end, t);
}
// ...

具體來說,我們將以整數(shù)rank屬性的形式為每個條形分配一個排序鍵。然后可以方便地使用rank來從調(diào)色板中分配每個條形的顏色,從而使我們能夠跟蹤動畫演示中各個條形圖的移動。

隨機條形圖現(xiàn)在將基于隨機選擇的行列。

但這不是最有效的解決方案,我們正在BarChart.lerp中重復(fù)執(zhí)行合并算法,對于t的每個值都執(zhí)行一次。為了解決這個問題,我們將實現(xiàn)前面一篇文章中提到的想法,以便在BarChartTween中存儲可重用的信息。

// ...
class BarChartTween extends Tween<BarChart> {
 final _tweens = <BarTween>[];

 BarChartTween(BarChart begin, BarChart end) : super(begin: begin, end: end) {
 final bMax = begin.bars.length;
 final eMax = end.bars.length;
 var b = 0;
 var e = 0;
 while (b + e < bMax + eMax) {
 if(b < bMax && (e == eMax || begin.bars[b] < end.bars[e])) {
 _tweens.add(new BarTween(begin.bars[b], begin.bars[b].collapsed));
 b++;
 } else if(e < eMax && (b == bMax || end.bars[e] < begin.bars[b])) {
 _tweens.add(new BarTween(end.bars[e].collapsed, end.bars[e]));
 e++;
 } else {
 _tweens.add(new BarTween(begin.bars[b], end.bars[e]));
 b++;
 e++;
 }
 }
 }

 @override
 BarChart lerp(double t) => new BarChart(
 new List.generate(
 _tweens.length,
 (i) => _tweens[i].lerp(t))
 );
}
// ...

然后我們就可以刪除靜態(tài)的BarChart.lerp方法了。

以上就是本文的全部內(nèi)容,希望對大家的學(xué)習(xí)有所幫助,也希望大家多多支持腳本之家。

相關(guān)文章

  • Android中使用HttpURLConnection實現(xiàn)GET POST JSON數(shù)據(jù)與下載圖片

    Android中使用HttpURLConnection實現(xiàn)GET POST JSON數(shù)據(jù)與下載圖片

    這篇文章主要介紹了Android中使用HttpURLConnection實現(xiàn)GET POST JSON數(shù)據(jù)與下載圖片,需要的朋友可以參考下
    2016-01-01
  • Android 使用Vibrator服務(wù)實現(xiàn)點擊按鈕帶有震動效果

    Android 使用Vibrator服務(wù)實現(xiàn)點擊按鈕帶有震動效果

    這篇文章主要介紹了Android 使用Vibrator服務(wù)實現(xiàn)點擊按鈕帶有震動效果,,本文通過實例圖文相結(jié)合給大家介紹的非常詳細,對大家的學(xué)習(xí)火鍋工作具有一定的參考借鑒價值,需要的朋友可以參考下
    2020-06-06
  • Android listview ExpandableListView實現(xiàn)多選,單選,全選,edittext實現(xiàn)批量輸入的實例代碼

    Android listview ExpandableListView實現(xiàn)多選,單選,全選,edittext實現(xiàn)批量輸入

    這篇文章主要介紹了Android listview ExpandableListView實現(xiàn)多選,單選,全選,edittext實現(xiàn)批量輸入的實例代碼,非常不錯,具有參考借鑒價值,需要的朋友可以參考下
    2017-01-01
  • Android RecyclerView多類型布局卡片解決方案

    Android RecyclerView多類型布局卡片解決方案

    這篇文章主要介紹了Android RecyclerView多類型布局卡片解決方案,小編覺得挺不錯的,現(xiàn)在分享給大家,也給大家做個參考。一起跟隨小編過來看看吧
    2019-03-03
  • Android實現(xiàn)游戲中的漸隱和漸現(xiàn)動畫效果

    Android實現(xiàn)游戲中的漸隱和漸現(xiàn)動畫效果

    本文給大家分享android中實現(xiàn)游戲中的漸隱漸現(xiàn)的動畫效果,在游戲開發(fā)中經(jīng)常會遇到,對android漸隱漸現(xiàn)效果感興趣的朋友可以參考下本教程
    2016-09-09
  • Android中RecyclerView的item寬高問題詳解

    Android中RecyclerView的item寬高問題詳解

    RecyclerView出現(xiàn)已經(jīng)有一段時間了,相信大家肯定不陌生了,下面這篇文章主要給大家介紹了關(guān)于Android中RecyclerView的item寬高問題的相關(guān)資料,文中通過示例代碼介紹的非常詳細,需要的朋友可以參考借鑒,下面來一起看看吧。
    2017-08-08
  • 拯救強迫癥Android Builder模式

    拯救強迫癥Android Builder模式

    這篇文章主要為大家介紹了拯救強迫癥Android Builder模式的使用示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進步,早日升職加薪
    2023-02-02
  • android編程之XML文件解析方法詳解(附源碼)

    android編程之XML文件解析方法詳解(附源碼)

    這篇文章主要介紹了android編程之XML文件解析方法,結(jié)合實例形式較為詳細的分析了Android解析XML文件的sax、pull及Dom三種方法,具有一定參考借鑒價值,需要的朋友可以參考下
    2015-11-11
  • Flutter 仿微信支付界面

    Flutter 仿微信支付界面

    網(wǎng)傳微信支付頁面的第三方鏈接一個格子需要廣告費1一個億,微信支付頁非常適合做功能導(dǎo)航,本篇使用 ListView和 GridView 模仿了微信支付的頁面,同時介紹了如何裝飾一個組件的背景和邊緣樣式。
    2021-05-05
  • Android自定義字母導(dǎo)航欄

    Android自定義字母導(dǎo)航欄

    這篇文章主要為大家詳細介紹了Android自定義字母導(dǎo)航欄,文中示例代碼介紹的非常詳細,具有一定的參考價值,感興趣的小伙伴們可以參考一下
    2019-12-12

最新評論

东明县| 阜城县| 望都县| 寿光市| 石城县| 北碚区| 水城县| 于田县| 霸州市| 健康| 八宿县| 伊通| 克什克腾旗| 澄迈县| 吉林市| 横山县| 揭东县| 平度市| 陆川县| 调兵山市| 吉木乃县| 筠连县| 高密市| 馆陶县| 通许县| 深水埗区| 乐至县| 霍州市| 崇礼县| 英山县| 棋牌| 通许县| 都江堰市| 体育| 武冈市| 大埔区| 淮安市| 浪卡子县| 黑龙江省| 克什克腾旗| 清苑县|