散點圖

此示例總共包含超過 1000 行程式碼(此處無法嵌入太多程式碼)。因此,所有程式碼都可以在 http://blockbuilder.org/SumNeuron/956772481d4e625eec9a59fdb9fbe5b2 上訪問 (或者在 https://bl.ocks.org/SumNeuron/956772481d4e625eec9a59fdb9fbe5b2 上託管 。請注意,bl.ocks.org 使用 iframe,因此要檢視調整大小,你需要單擊開啟的按鈕(iframe 的右下角)。由於存在大量程式碼,因此它已被分解為多個檔案,相關的程式碼段將通過檔名和行號引用。請仔細閱讀此示例。

什麼使圖表?

任何完整的圖表都有幾個核心元件; 這些包括:

  • 標題
  • 軸標籤
  • 資料

根據圖表可能還包括其他方面 - 例如圖表圖例。但是,許多這些元素可以通過工具提示來規避。出於這個原因,有互動式圖表特定元素 - 例如在資料之間切換的按鈕。

由於我們的圖表內容將是互動式的,因此圖表本身是動態的 - 例如,當視窗大小改變時調整大小。SVG 是可擴充套件的,因此你可以只保留當前透檢視來縮放圖表。但是,根據設定的透檢視,即使圖表仍有足夠的空間(例如,如果寬度大於高度),圖表可能會變得太小而無法讀取。因此,最好只重繪剩餘大小的圖表。

此示例將介紹如何動態計算按鈕,標題,軸,軸標籤的位置,以及處理不同資料量的資料集

建立

組態

由於我們的目標是重用程式碼,因此我們應該建立一個配置檔案來包含圖表各方面的全域性選項。這種配置檔案的一個例子是 charts_configuration.json

如果我們檢視這個檔案,我們可以看到我已經包含了幾個元素,這些元素在製作圖表時應該已經有了明確的用途:

  • files(儲存我們的圖表資料所在的字串)
  • document_state(當前為我們的圖表選擇了哪個按鈕)
  • chart_ids(我們將製作的圖表的 html ID)
  • svg(svg 的選項,例如大小)
  • plot_attributes
    • 標題(設定各種字型屬性)
    • 工具提示(設定各種工具提示樣式屬性)
    • 軸(設定各種字型屬性)
    • 按鈕(設定各種字型和樣式屬性)
  • 地塊
    • 散射(設定散點圖的各個方面,例如點半徑)
  • 顏色(要使用的特定調色盤)

助手功能

除了設定這些全域性方面,我們還需要定義一些輔助函式。這些可以在 helpers.js 下找到

  • ajax_json(同步或非同步載入 json 檔案)
  • keys(返回給定物件的鍵 - 相當於 d3.keys()
  • parseNumber(一般編號解析,以防我們不知道是什麼型別或數字)
  • typeofNumber(返回數字型別)

index.html

最後我們應該設定我們的 html 檔案。出於此示例的目的,我們將圖表放在 section 標記中,其中 id 與配置檔案中提供的 id 匹配(第 37 行)。由於百分比只有在可以從其父成員計算時才有效,我們還包括一些基本樣式(第 19-35 行)

製作散點圖

讓我們開啟 make_scatter_chart.js。現在讓我們密切注意第 2 行,其中預定了許多最重要的變數:

  • svg - d3 選擇圖表的 svg
  • chart_group - d3 選擇將放置資料的 svg 內的組
  • canvas - 為方便起見,svg 提取的核心方面
  • 利潤 - 我們需要考慮的利潤率
  • maxi_draw_space 是我們可以繪製資料的最大 x 和 y 值
  • doc_state - 如果我們使用按鈕(在本例中我們是),文件的當前狀態

你可能已經注意到我們沒有在 html 中包含 svg。因此,在我們對圖表做任何事情之前,我們需要新增 svg toindex.html(如果它還不存在)。這是通過函式 make_chart_svg 在檔案 make_svg.js 中實現的。看看 make_svg.js,我們看到我們在 svg 寬度和高度的圖表配置中使用輔助函式 parseNumber。如果數字是浮點數,它會使 svg 的寬度和高度與其截面的寬度和高度成比例。如果數字是整數,它只會將其設定為整數。

第 6 - 11 行測試 - 實際上 - 如果這是第一次呼叫,則設定 chart_group(如果是第一次呼叫,則設定文件狀態)。

第 14-15 行通過點選的按鈕提取當前選擇的資料; 第 16 行 data_extent。雖然 d3 具有提取資料範圍的功能,但我更傾向於將資料範圍儲存在此變數中。

第 27-38 行包含通過製作邊距,按鈕,標題和軸來設定圖表的魔法。這些都是動態確定的,可能看起來有點複雜,所以我們將依次檢視每個。

make_margins(在 make_margins.js 中)

我們可以看到邊距物件考慮了圖表左側,右側,頂部和底部的一些空間(分別為 x.left,x.right,y.top,y.bottom),標題,按鈕和軸。

我們還看到軸邊距在第 21 行更新。

我們為什麼要做這個?除非我們指定刻度數,刻度標籤刻度尺寸和刻度標籤字型大小,否則我們無法計算軸所需的大小。即使這樣,我們仍然需要猜測刻度標籤和刻度線之間的空間。因此,使用我們的資料製作一些虛擬軸更容易,檢視相應的 svg 元素有多大,然後返回大小。

實際上我們只需要 y 軸的寬度和 x 軸的高度,這是儲存在 axes.y 和 axes.x 中的。

設定預設邊距後,我們計算 max_drawing_space(make_margins.js 中的第 29-34 行)

make_buttons(在 make_buttons.js 中)

該函式為所有按鈕建立一個組,然後為每個按鈕建立一個組,該組又儲存一個圓和文字元素。第 37-55 行計算按鈕的位置。它通過檢視每個按鈕長度的文字是否長於允許我們繪製的空間(第 75 行)來實現此目的。如果是這樣,它會將按鈕放下一行並更新邊距。

make_title(在 make_title.js 中)

make_title 類似於 make_buttons,因為它會自動將圖表的標題分成多行,如果需要則可以連字元。它有點 hacky,因為它沒有 TeX 的連字方案的複雜性,但它足夠好。如果我們需要更多的行,則更新邊距。

通過設定按鈕,標題和邊距,我們可以製作軸。

make_axes(在 make_axes.js 中)

make_axes 的邏輯反映了用於計算虛擬軸所需空間的邏輯。然而,在這裡,它增加了軸之間變化的過渡。

最後是我們的散點圖

完成所有這些設定後,我們終於可以製作散點圖了。由於我們的資料集可能有不同的點數,我們需要考慮到這一點並相應地利用 d3 的進入和退出事件。獲取現有點的數量在第 40 行中完成。如果我們有更多資料,或者將額外元素轉換到角落,然後在有太多資料的情況下刪除它們,則第 45-59 行中的 if 語句會新增更多圓元素。

一旦我們知道我們有正確數量的元素,我們就可以將所有剩餘元素轉換到正確的位置(第 64 行)

最後,我們在第 67 行和第 68 行新增工具提示。工具提示功能在 make_tooltip.js