draupnir4all-web

git clone git://archive.git.mtrnord.blog/MTRNord/draupnir4all-web.git
Log | Files | Refs | README | LICENSE

chart-configs.ts (8474B)


      1 import type { Data, Layout } from "plotly.js"
      2 import { HeatmapDay } from "./heatmap"
      3 
      4 // Helper function to generate heatmap data
      5 export const generateHeatmapData = (intensity = 1, seed = 42): HeatmapDay[] => {
      6     const today = new Date()
      7     const data = []
      8 
      9     // Generate data for the past year (52 weeks)
     10     for (let i = 0; i < 364; i++) {
     11         const date = new Date(today)
     12         date.setDate(today.getDate() - i)
     13 
     14         // Use a simple algorithm to generate semi-random but consistent data
     15         const dayOfYear = Math.floor((date.getTime() - new Date(date.getFullYear(), 0, 0).getTime()) / 86400000)
     16         const value = Math.floor(Math.sin(dayOfYear * 0.1 + seed) * Math.cos(date.getMonth() * 0.3 + seed) * 10 * intensity)
     17 
     18         data.push({
     19             date: date.toISOString().split("T")[0] as string,
     20             count: Math.max(0, value),
     21         })
     22     }
     23 
     24     // Sort by date (oldest first)
     25     return data.reverse()
     26 }
     27 
     28 export interface RoomActivityData {
     29     name: string
     30     reports: number
     31     bans: number
     32 }
     33 
     34 // Room Activity Chart Config
     35 export const getRoomActivityConfig = (roomData: RoomActivityData[]): {
     36     data: Data[],
     37     layout: Partial<Layout>
     38 } => {
     39     return {
     40         data: [
     41             {
     42                 y: roomData.map((item) => item.name),
     43                 x: roomData.map((item) => item.reports),
     44                 name: "Reports",
     45                 type: "bar",
     46                 orientation: "h",
     47                 marker: {
     48                     color: "#9333ea",
     49                 },
     50             },
     51             {
     52                 y: roomData.map((item) => item.name),
     53                 x: roomData.map((item) => item.bans),
     54                 name: "Bans",
     55                 type: "bar",
     56                 orientation: "h",
     57                 marker: {
     58                     color: "#dc2626",
     59                 },
     60             },
     61         ],
     62         layout: {
     63             paper_bgcolor: "rgba(0,0,0,0)",
     64             plot_bgcolor: "rgba(0,0,0,0)",
     65             font: {
     66                 color: "#9ca3af",
     67             },
     68             margin: {
     69                 l: 10, // Increased left margin for room names
     70                 r: 10,
     71                 t: 10,
     72                 b: 10,
     73                 pad: 10,
     74             },
     75             barmode: "stack",
     76             legend: {
     77                 orientation: "h",
     78                 xanchor: "center",
     79                 x: 0.5,
     80                 y: -0.2,
     81             },
     82             xaxis: {
     83                 gridcolor: "#1f2937",
     84                 zerolinecolor: "#1f2937",
     85                 automargin: true,
     86             },
     87             yaxis: {
     88                 gridcolor: "#1f2937",
     89                 automargin: true,
     90             },
     91             height: 280,
     92             autosize: true,
     93         },
     94     }
     95 }
     96 
     97 export interface ReportTypeData {
     98     id: number;
     99     label: string;
    100     value: number;
    101     color: string;
    102 }
    103 
    104 // Report Types Pie Chart Config
    105 export const getReportTypesConfig = (reportData: ReportTypeData[]): {
    106     data: Data[],
    107     layout: Partial<Layout>
    108 } => {
    109     return {
    110         data: [
    111             {
    112                 values: reportData.map((item) => item.value),
    113                 labels: reportData.map((item) => item.label),
    114                 type: "pie",
    115                 hole: 0.5,
    116                 marker: {
    117                     colors: reportData.map((item) => item.color),
    118                 },
    119                 textinfo: "label+percent",
    120                 textposition: "outside",
    121                 insidetextorientation: "radial",
    122                 hoverinfo: "label+value+percent",
    123                 hoverlabel: {
    124                     bgcolor: "#374151",
    125                     bordercolor: "#374151",
    126                     font: {
    127                         size: 12,
    128                         family: "Inter, sans-serif",
    129                         color: "#ffffff"
    130                     },
    131                 },
    132                 // Add slice animation on hover
    133                 pull: Array(reportData.length).fill(0),
    134                 hovertemplate: "<b>%{label}</b><br>Count: %{value}<br>Percentage: %{percent}<extra></extra>",
    135             },
    136         ],
    137         layout: {
    138             paper_bgcolor: "rgba(0,0,0,0)",
    139             plot_bgcolor: "rgba(0,0,0,0)",
    140             font: {
    141                 color: "#9ca3af",
    142             },
    143             margin: {
    144                 l: 30,
    145                 r: 30,
    146                 t: 30,
    147                 b: 30,
    148                 pad: 10,
    149             },
    150             showlegend: false,
    151             height: 280,
    152             autosize: true,
    153             annotations: [
    154                 {
    155                     font: {
    156                         size: 12,
    157                         color: "#9ca3af",
    158                     },
    159                     showarrow: false,
    160                     text: "Report Types",
    161                     x: 0.5,
    162                     y: 0.5,
    163                 },
    164             ],
    165             // Add hover animations
    166             hovermode: "closest",
    167             updatemenus: [
    168                 {
    169                     type: "dropdown",
    170                     showactive: false,
    171                     visible: false, // Hidden menu that enables hover effects
    172                 },
    173             ],
    174         },
    175     }
    176 }
    177 
    178 export interface MonthlyActivityData {
    179     month: string
    180     year: number
    181     reports: number
    182     bans: number
    183 }
    184 
    185 // Monthly Activity Bar Chart Config
    186 export const getMonthlyActivityConfig = (monthlyData: MonthlyActivityData[]): {
    187     data: Data[],
    188     layout: Partial<Layout>
    189 } => {
    190     return {
    191         data: [
    192             {
    193                 x: monthlyData.map((item) => `${item.month} ${item.year}`),
    194                 y: monthlyData.map((item) => item.reports),
    195                 name: "Reports",
    196                 type: "bar",
    197                 marker: {
    198                     color: "#9333ea",
    199                 },
    200             },
    201             {
    202                 x: monthlyData.map((item) => `${item.month} ${item.year}`),
    203                 y: monthlyData.map((item) => item.bans),
    204                 name: "Bans",
    205                 type: "bar",
    206                 marker: {
    207                     color: "#dc2626",
    208                 },
    209             },
    210         ],
    211         layout: {
    212             paper_bgcolor: "rgba(0,0,0,0)",
    213             plot_bgcolor: "rgba(0,0,0,0)",
    214             font: {
    215                 color: "#9ca3af",
    216             },
    217             margin: {
    218                 l: 40,
    219                 r: 10,
    220                 t: 10,
    221                 b: 40,
    222                 pad: 10,
    223             },
    224             barmode: "group",
    225             legend: {
    226                 orientation: "h",
    227                 xanchor: "center",
    228                 x: 0.5,
    229                 y: -0.2,
    230             },
    231             xaxis: {
    232                 gridcolor: "#1f2937",
    233                 tickfont: {
    234                     size: 10,
    235                 },
    236                 automargin: true,
    237             },
    238             yaxis: {
    239                 gridcolor: "#1f2937",
    240                 zerolinecolor: "#1f2937",
    241                 automargin: true,
    242             },
    243             height: 280,
    244             autosize: true,
    245         },
    246     }
    247 }
    248 
    249 export interface BannedServerData {
    250     label: string
    251     value: number
    252     secondaryLabel: string
    253 }
    254 
    255 // Banned Servers Horizontal Bar Chart Config
    256 export const getBannedServersConfig = (serversData: BannedServerData[]): {
    257     data: Data[],
    258     layout: Partial<Layout>
    259 } => {
    260     return {
    261         data: [
    262             {
    263                 y: serversData.map((item) => item.label),
    264                 x: serversData.map((item) => item.value),
    265                 type: "bar",
    266                 orientation: "h",
    267                 marker: {
    268                     color: "#dc2626",
    269                 },
    270                 text: serversData.map((item) => item.secondaryLabel),
    271                 textposition: "auto",
    272                 hoverinfo: "x+text",
    273             },
    274         ],
    275         layout: {
    276             paper_bgcolor: "rgba(0,0,0,0)",
    277             plot_bgcolor: "rgba(0,0,0,0)",
    278             font: {
    279                 color: "#9ca3af",
    280             },
    281             margin: {
    282                 l: 10,
    283                 r: 10,
    284                 t: 10,
    285                 b: 40,
    286                 pad: 10,
    287             },
    288             xaxis: {
    289                 gridcolor: "#1f2937",
    290                 zerolinecolor: "#1f2937",
    291                 automargin: true,
    292             },
    293             yaxis: {
    294                 gridcolor: "#1f2937",
    295                 zerolinecolor: "#1f2937",
    296                 automargin: true,
    297             },
    298             height: 220,
    299             autosize: true,
    300         },
    301     }
    302 }