国产 无码 综合区,色欲AV无码国产永久播放,无码天堂亚洲国产AV,国产日韩欧美女同一区二区

flutter自定義系列之簡單的K線圖繪制

這篇具有很好參考價值的文章主要介紹了flutter自定義系列之簡單的K線圖繪制。希望對大家有所幫助。如果存在錯誤或未考慮完全的地方,請大家不吝賜教,您也可以點擊"舉報違法"按鈕提交疑問。

上篇文章講了flutter自定義的相關(guān)流程,

今天繼續(xù)練習(xí)下flutter的自定義K線:

我們可以通過自定義Painter來實現(xiàn)一個簡單的K線圖界面:

  1. 創(chuàng)建一個自定義的Painter,用于繪制K線圖:
import 'dart:ui';

import 'package:flutter/material.dart';

class KLinePainter extends CustomPainter {
  final List<dynamic> data;
  final double itemWidth;
  final double scaleFactor;

  KLinePainter({required this.data, required this.itemWidth, required this.scaleFactor});

  @override
  void paint(Canvas canvas, Size size) {
    // 設(shè)置畫筆
    final linePaint = Paint()
      ..color = Colors.grey
      ..strokeWidth = 0.5;

    final textPainter = TextPainter(textDirection: TextDirection.ltr, textAlign: TextAlign.left);

    // 計算價格范圍和最大成交量
    num highestPrice = double.minPositive;
    num lowestPrice = double.maxFinite;
    num highestVolume = double.minPositive;

    for (var item in data) {
      if (item['high'] > highestPrice) {
        highestPrice = item['high'];
      }
      if (item['low'] < lowestPrice) {
        lowestPrice = item['low'];
      }
      if (item['vol'] > highestVolume) {
        highestVolume = item['vol'];
      }
    }

    // 計算價格和成交量的縮放比例
    double priceScale = (size.height - 20) / (highestPrice - lowestPrice);
    double volumeScale = size.height * 0.2 / highestVolume;

    // 繪制K線圖
    for (int i = 0; i < data.length; i++) {
      var item = data[i];

      double open = (item['open'] - lowestPrice) * priceScale;
      double close = (item['close'] - lowestPrice) * priceScale;
      double high = (item['high'] - lowestPrice) * priceScale;
      double low = (item['low'] - lowestPrice) * priceScale;
      double vol = item['vol'] * volumeScale;

      // 設(shè)置畫筆顏色
      linePaint.color = close >= open ? Colors.green : Colors.red;

      // 繪制實體
      double halfWidth = itemWidth * scaleFactor / 2;
      double centerX = i * itemWidth * scaleFactor + halfWidth;
      canvas.drawRect(
        Rect.fromCenter(
          center: Offset(centerX, size.height - (open + close) / 2 - 10),
          width: itemWidth * scaleFactor,
          height: (open - close).abs(),
        ),
        linePaint,
      );

      // 繪制上下影線
      canvas.drawLine(Offset(centerX, size.height - high - 10), Offset(centerX, size.height - low - 10), linePaint);
    }
  }

  @override
  bool shouldRepaint(CustomPainter oldDelegate) {
    return true;
  }
}
  1. 創(chuàng)建一個StatefulWidget,用于處理縮放和滾動:
class KLineChart extends StatefulWidget {
  final List<dynamic> data;

  KLineChart({required this.data});

  @override
  _KLineChartState createState() => _KLineChartState();
}

class _KLineChartState extends State<KLineChart> {
  double _scaleFactor = 1.0;
  double _itemWidth = 10.0;
  late double _baseScaleFactor;

  @override
  void initState() {
    super.initState();
    _baseScaleFactor = _scaleFactor;
  }

  @override
  Widget build(BuildContext context) {
    return GestureDetector(
      onScaleStart: (details) {
        _baseScaleFactor = _scaleFactor;
      },
      onScaleUpdate: (details) {
        setState(() {
          // 修改這里,減小縮放速度
          _scaleFactor = _baseScaleFactor * (1.0 + (details.scale - 1.0) / 2);
        });
      },
      child: SingleChildScrollView(
        scrollDirection: Axis.horizontal,
        child: CustomPaint(
          size: Size(widget.data.length * _itemWidth * _scaleFactor, MediaQuery.of(context).size.height),
          painter: KLinePainter(data: widget.data, itemWidth: _itemWidth, scaleFactor: _scaleFactor),
        ),
      ),
    );
  }
}
  1. 在需要使用K線圖的地方,調(diào)用KLineChart組件并傳入K線數(shù)據(jù):
List<dynamic> kLineData = [
  // 你的K線數(shù)據(jù)
];

KLineChart(data: kLineData);

這樣,你就可以實現(xiàn)一個簡單的可左右滑動、放大縮小的K線界面。

這里我們看看實現(xiàn)的效果:
我先模擬了一些K線數(shù)據(jù):

List<dynamic> generateKLineData(int count) {
  List<dynamic> data = [];
  Random random = Random();
  double open = 100.0;
  double close, high, low;
  num volume;

  for (int i = 0; i < count; i++) {
    close = open + random.nextDouble() * 20 - 10;
    high = max(open, close) + random.nextDouble() * 5;
    low = min(open, close) - random.nextDouble() * 5;
    volume = random.nextInt(10000) + 1000;

    data.add({
      'open': open,
      'close': close,
      'high': high,
      'low': low,
      'vol': volume,
    });

    open = close;
  }

  return data;
}

之后直接引用:

SliverToBoxAdapter(
  child: SizedBox(
    height: 300.w,
    child: KLineChart(data: generateKLineData(100)),
  ),
)

運行后如下效果:

flutter自定義系列之簡單的K線圖繪制

可左右滑動,可伸縮,僅包含基本功能,真正的需要分時圖,各種的指標(biāo),甚至是自定義的指標(biāo)繪制等等,你可以根據(jù)需求進(jìn)一步完善和優(yōu)化。

技術(shù)人日拱一卒,共勉!文章來源地址http://www.zghlxwxcb.cn/news/detail-479989.html

到了這里,關(guān)于flutter自定義系列之簡單的K線圖繪制的文章就介紹完了。如果您還想了解更多內(nèi)容,請在右上角搜索TOY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持TOY模板網(wǎng)!

本文來自互聯(lián)網(wǎng)用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務(wù),不擁有所有權(quán),不承擔(dān)相關(guān)法律責(zé)任。如若轉(zhuǎn)載,請注明出處: 如若內(nèi)容造成侵權(quán)/違法違規(guī)/事實不符,請點擊違法舉報進(jìn)行投訴反饋,一經(jīng)查實,立即刪除!

領(lǐng)支付寶紅包贊助服務(wù)器費用

相關(guān)文章

  • Flutter系列文章-Flutter基礎(chǔ)

    Flutter是Google推出的一種新的移動應(yīng)用開發(fā)框架,允許開發(fā)者使用一套代碼庫同時開發(fā)Android和iOS應(yīng)用。它的設(shè)計理念、框架結(jié)構(gòu)、以及對Widget的使用,都讓開發(fā)者能更有效率地創(chuàng)建高質(zhì)量的應(yīng)用。 Flutter的設(shè)計理念是“一切皆為Widget”。這意味著不論是按鈕、字體、顏色、布局

    2024年02月16日
    瀏覽(16)
  • Flutter系列文章-Flutter應(yīng)用優(yōu)化

    當(dāng)涉及到優(yōu)化 Flutter 應(yīng)用時,考慮性能、UI 渲染和內(nèi)存管理是至關(guān)重要的。在本篇文章中,我們將通過實例深入討論這些主題,展示如何通過優(yōu)化技巧改進(jìn)你的 Flutter 應(yīng)用。 1. 使用 const 構(gòu)造函數(shù) 在構(gòu)建小部件時,盡可能使用 const 構(gòu)造函數(shù)來創(chuàng)建靜態(tài)小部件。這將避免在每次

    2024年02月11日
    瀏覽(63)
  • Flutter系列文章-Flutter進(jìn)階2

    這一節(jié)我將再詳細(xì)地為您介紹 Flutter 進(jìn)階主題,包括導(dǎo)航和路由、狀態(tài)管理、異步處理、HTTP請求和Rest API,以及數(shù)據(jù)持久化。讓我們逐個介紹這些主題。 在 Flutter 中,導(dǎo)航和路由是構(gòu)建多頁面應(yīng)用的關(guān)鍵概念。導(dǎo)航是指從一個頁面(或稱為路由)切換到另一個頁面的過程。每

    2024年02月15日
    瀏覽(24)
  • Flutter系列文章-Flutter 插件開發(fā)

    在本篇文章中,我們將學(xué)習(xí)如何開發(fā) Flutter 插件,實現(xiàn) Flutter 與原生平臺的交互。我們將詳細(xì)介紹插件的開發(fā)過程,包括如何創(chuàng)建插件項目、實現(xiàn)方法通信、處理異步任務(wù)等。最后,我們還將演示如何將插件打包并發(fā)布到 Flutter 社區(qū)。 在 Flutter 項目中,你可能需要與原生平臺

    2024年02月11日
    瀏覽(50)
  • Flutter系列文章-Flutter UI進(jìn)階

    Flutter系列文章-Flutter UI進(jìn)階

    在本篇文章中,我們將深入學(xué)習(xí) Flutter UI 的進(jìn)階技巧,涵蓋了布局原理、動畫實現(xiàn)、自定義繪圖和效果、以及 Material 和 Cupertino 組件庫的使用。通過實例演示,你將更加了解如何創(chuàng)建復(fù)雜、令人印象深刻的用戶界面。 Row 和 Column 是常用的布局組件,但靈活地使用它們可以帶來

    2024年02月13日
    瀏覽(58)
  • Flutter系列文章-實戰(zhàn)項目

    Flutter系列文章-實戰(zhàn)項目

    在本篇文章中,我們將通過一個實際的 Flutter 應(yīng)用來綜合運用最近學(xué)到的知識,包括保存到數(shù)據(jù)庫、進(jìn)行 HTTP 請求等。我們將開發(fā)一個簡單的天氣應(yīng)用,可以根據(jù)用戶輸入的城市名獲取該城市的天氣信息,并將用戶查詢的城市列表保存到本地數(shù)據(jù)庫中。 1. 確定項目目標(biāo) 我們

    2024年02月13日
    瀏覽(22)
  • Flutter系列文章-Flutter環(huán)境搭建和Dart基礎(chǔ)

    Flutter系列文章-Flutter環(huán)境搭建和Dart基礎(chǔ)

    Flutter是Google推出的一個開源的、高性能的移動應(yīng)用開發(fā)框架,可以用一套代碼庫開發(fā)Android和iOS應(yīng)用。Dart則是Flutter所使用的編程語言。讓我們來看看如何搭建Flutter開發(fā)環(huán)境,并了解Dart語言的基礎(chǔ)知識。 1. 安裝Flutter SDK 首先,訪問Flutter官網(wǎng)下載Flutter SDK。選擇適合你操作系統(tǒng)

    2024年02月15日
    瀏覽(17)
  • Flutter系列文章-Flutter在實際業(yè)務(wù)中的應(yīng)用

    1. 跨平臺開發(fā): 在移動應(yīng)用開發(fā)中,面對不同的平臺(iOS和Android),我們通常需要編寫兩套不同的代碼。而Flutter通過一套代碼可以構(gòu)建適用于多個平臺的應(yīng)用,大大提高了開發(fā)效率,降低了維護(hù)成本。 2. 混合開發(fā): 在一些已有的原生應(yīng)用中,引入Flutter可以用于開發(fā)某些特

    2024年02月11日
    瀏覽(15)
  • flutter的自定義系列雷達(dá)圖

    flutter的自定義系列雷達(dá)圖

    自定義是flutter進(jìn)階中不可缺少的ui層知識點,這里我們來總結(jié)下: 在Flutter中,自定義繪制通常是通過使用 CustomPaint 和 CustomPainter 來實現(xiàn)的。 創(chuàng)建 CustomPaint 組件 首先,需要創(chuàng)建一個 CustomPaint 組件。 CustomPaint 是一個Widget,它可以作為其他組件的子組件,用于提供自定義繪制

    2024年02月09日
    瀏覽(25)
  • flutter系列之:如何自定義動畫路由

    flutter系列之:如何自定義動畫路由

    目錄 簡介 自定義跳轉(zhuǎn)使用 flutter動畫基礎(chǔ) 實現(xiàn)一個自定義的route 總結(jié) flutter中有默認(rèn)的Route組件,叫做MaterialPageRoute,一般情況下我們在flutter中進(jìn)行跳轉(zhuǎn)的話,只需要向Navigator中傳入一個MaterialPageRoute就可以了。 但是MaterialPageRoute太普通了,如果我們想要做點不同的跳轉(zhuǎn)特效

    2023年04月19日
    瀏覽(19)

覺得文章有用就打賞一下文章作者

支付寶掃一掃打賞

博客贊助

微信掃一掃打賞

請作者喝杯咖啡吧~博客贊助

支付寶掃一掃領(lǐng)取紅包,優(yōu)惠每天領(lǐng)

二維碼1

領(lǐng)取紅包

二維碼2

領(lǐng)紅包