开始使用Bryntum Grid,React和RXJS
#javascript #react #rxjs #ui

如果您有一个带有大量数据的Web应用程序,则需要找到一种以简洁而有条理的方式显示该信息的方法,这就是电网可以提供帮助的地方。网格是用户界面的关键组成部分,可将大量数据制成,并使用户易于与它们进行交互。许多人选择使用诸如Bryntum Grid之类的预制软件包,因为它们具有高功能并加快编码过程。

Bryntum Grid是Web应用程序的有效且高性能的表组件。它具有各种功能,包括重新排列行和列的能力,或修改单个单元格,搜索和过滤数据以及滚动浏览网格部分。使用渲染器功能,标准CS和用Syntactically Awesome Style Sheets (Sass)构建的主题设置网格的视觉外观。

Bryntum Grid使用各种技术,包括虚拟表示,可重复使用的网格元素以及CSS优化,以实现可视化和导航效率。您可以通过强大的API来修改代码库的任何部分。此外,除JSON之外,自定义数据格式是一种选项,这是所有数据默认情况下加载的方式。它提供了广泛的自定义选择,包括预制或自定义主题。

在本文中,您将学习如何使用React,Bryntum Grid和Reactive Extensions for JavaScript (RxJS)构建应用程序。您将利用React钩子和RXJ进行状态管理,并构建具有内置功能的交互式网格。

实施该应用程序

在开始之前,您需要Node.js版本14或在操作系统(OS)上安装新的。您还需要一个代码编辑器。在这里,Visual Studio (VS) Code将由于其广泛的功能而被使用。

此外,您还需要对React的基本理解。有关更多信息,请查看official React documentationBryntum React guide

本教程的所有代码都可以在此GitHub repo中找到。

设置小bryntum网格

在本教程中,如果您使用的是Create React App script,您将学习如何开始。您可以通过注册私人NPM注册表来获得Bryntum的免费试用版,该注册表在下一节中进行了更详细的介绍。

访问私人NPM注册表

要设置Bryntum Grid,您需要在登录后通过终端访问私有注册表。bryntum的软件包保存在个人的bryntum注册表中。在您的终端中运行以下命令以找到注册表:

npm config set "@bryntum:registry=https://npm.bryntum.com"

然后,使用您的身份验证信息,您需要登录。

请注意:具体细节因您是使用许可版本还是试用版本的不同。

对于试用版,请使用以下命令登录:

 npm login --registry=https://npm.bryntum.com 

然后输入您的用户名( ie user..yourdomain.com),密码( ie 试用)和电子邮件( IE user@yourdomain.com) 。

请注意:在您的用户名中,请确保将“@”登录更改为“ ..”。

如果您想在审判时间结束后继续使用Bryntum,则需要从Bryntum website购买许可证。之后,您需要使用您的客户信息将其连接回Bryntum私人注册表。

对于许可版本,请使用前面提到的同一命令(npm login --registry=https://npm.bryntum.com)登录,然后将您的bryntum客户区域电子邮件作为用户名(但请务必用“ ..”替换为“@”),然后输入您的bryntum客户区密码。

创建应用程序

登录后,您需要利用Create React应用程序与Bryntum Grid软件包一起创建React应用程序。在本教程中,您将使用JavaScript进行该项目。在您的终端,
导航到您要设置项目的目录并运行以下内容:

npx create-react-app react-bryntum-grid --template @bryntum/cra-template-javascript-grid

另外,如果您想使用打字稿,请使用以下代码:

npx create-react-app react-bryntum-grid --template @bryntum/cra-template-typescript-grid 

用您首选的应用程序名称替换为react-bryntum-grid

请注意:可以通过创建React应用程序作为依赖项的版本前缀插入Caret(^)。要正确调节升级,您不应将Caret字符用作版本前缀。检查package.json并用以下内容替换依赖性和依赖性依赖性:

试用版:

"dependencies": {
  "@bryntum/grid": "npm:@bryntum/grid-trial@5.1.1",
  "@bryntum/grid-react": "5.1.1",
  "react": "17.0.2",
  "react-dom": "17.0.2",
  "react-scripts": "4.0.3"
},
"devDependencies": {
  "babel-preset-react-app": "npm:@bryntum/babel-preset-react-app@10.0.0",
  "cross-env": "~7.0.2",
  "sass": "~1.42.0"
}

对于许可版本:

"dependencies": {
  "@bryntum/grid": "5.1.1",
  "@bryntum/grid-react": "5.1.1",
  "react": "17.0.2",
  "react-dom": "17.0.2",
  "react-scripts": "4.0.3"
},
"devDependencies": {
  "babel-preset-react-app": "npm:@bryntum/babel-preset-react-app@10.0.0",
  "cross-env": "~7.0.2",
  "sass": "~1.42.0"
}

然后从终端导航到您的项目文件夹,然后使用以下代码安装所有必要的依赖项:

cd react-bryntum-grid
npm install

然后使用以下命令启动应用:

npm start

您应该在上面看到下面的页面,上面有样品网格:

Bryntum starter template

通过功能设置网格

现在,您需要使用必要的列,数据和配置来设置网格。为此,您需要使用RXJS商店中的示例数据和列。您也可以通过拨打API调用来填充数据。

_App.js_文件中,您需要导入useState来处理数据,列和配置。然后继续导入bryntum网格以进行反应。要设置网格,请将参数传递到BryntumGrid元素,即Bryntum组件使用的数据,列和功能:


import React, { useState } from 'react';
import { BryntumGrid } from '@bryntum/grid-react';

function App() {
    const [columns, setColumns] = useState(
        [
        { text : 'Country Name', field : 'countryName', flex : 2 },
        { text : 'Code', field : 'code', flex: 1},
        { text : 'Capital', field : 'capital', flex : 1 },
        { text : 'Continent', field : 'continent', flex : 1 },
        { text : 'Currency', field : 'currency', flex : 1 },
        { text : 'Languages', field : 'languages', flex : 1 }
    ]    );

    const [data, setData] = useState(
 [       
    {
    id        : 1,
    countryName     : 'Brasil',
    code : 'BR',
    capital  : 'Brasília',
    continent   : 'South America',
    currency    : 'BRL',
    languages   : 'Portuguese'
    },
    {
        id      : 2,
        countryName     : 'Bahamas',
        code : 'BS',
        capital  : 'Nassau',
        continent   : 'North America',
        currency    : 'BSD',
        languages   : 'English'
        },
        {
            id      : 3,
            countryName     : 'Botswana',
            code : 'BW',
            capital  : 'Gaborone',
            continent   : 'Africa',
            currency    : 'BWP',
            languages   : 'English, Tswana'
            },
            {
                id      : 4,
                countryName     : 'Colombia',
                code : 'CO',
                capital  : 'Bogotá',
                continent   : 'South America',
                currency    : 'COP',
                languages   : 'Spanish'
                },
                {
                    id      : 5,
                    countryName     : 'Costa Rica',
                    code : 'CRC',
                    capital  : 'Brasília',
                    continent   : 'North America',
                    currency    : 'CR',
                    languages   : 'Spanish'
                    },
                    {
                        id      : 6,
                        countryName     : 'Ecuador',
                        code : 'EC',
                        capital  : 'Quito',
                        continent   : 'South America',
                        currency    : 'USD',
                        languages   : 'Spanish'
                        }]  );
    const [features, setFeatures] = useState({
        cellEdit    : true,
        regionResize : false,
        stripe: true
    });
    return (
            <BryntumGrid data={data}  columns={columns} features={features} />
    );

}

export default App;

确保您导入处理_App.scss_文件中bryntum网格样式的CSS文件,否则您的网格将不使用:


// import bryntum css theme
@import '~@bryntum/grid/grid.stockholm.css';

当前,有一个可用于Bryntum Grid列的渲染器设置功能,该功能是将参数作为输入和输出HTML的函数。为了制备美学上令人愉悦的单元格内容,可以应用任何类型的条件逻辑。

您可以通过在功能对象中添加更多配置来格式化网格,并且有many configurations available

用于管理应用程序状态的RXJS

rxjs是一个软件包,允许在可观察的序列的帮助下创建异步和基于事件的应用程序。简而言之,RXJS软件包使您可以随着时间的推移管理和修改数据。您可以在official documentation中阅读有关RXJ的更多信息。

RXJ的基本特征如下:

  • Observable可观察到的是一个数据源,其中包含可以在应用程序的各个组件之间共享的数据。源可以同步或异步运行,并且可以随着时间的推移提供许多值。
  • Observer一个观察者是一个消耗可观察到的信息的对象。直到可观察到的观察者从可观察到的观察者取消订阅之前,观察者将继续从可观察到的数据中接收数据。
  • Subscription这与观察者有关可观察的信息的观察者有关。观察者只会接收他们订阅的数据。
  • Subjects rxjs受试者可以同时作为观察者和可观察的。值可以向众多观察者广播,从而使每个订阅对象的观察者获取收到的任何数据。

安装RXJS并创建一家商店

要安装RXJ并创建商店,在终端中运行以下命令:

npm install rxjs 

在使用REACT挂钩的RXJS时,组件之间交互的最佳方法是利用可观察的和受试者。

要包含您的商店,您需要在src文件夹中构建数据存储目录和_src/store_

导航到_src/store_并创建将用于网格功能的_DataStore.js_文件。然后,您需要导入主题类并在_DataStore.js_中创建一个变量:

import { Subject } from 'rxjs';

const subject = new Subject();

现在您需要从商店获取数据。数据可以是空的,但是当进行API调用时,它需要包含数据。在本教程中,您将使用虚拟数据。在data-store.js中,在主题之后,添加以下内容:

let   data = [      
    {
    id        : 1,
    countryName     : 'Brasil',
    code : 'BR',
    capital  : 'Brasília',
    continent   : 'South America',
    currency    : 'BRL',
    languages   : 'Portuguese'
    },
    {
        id      : 2,
        countryName     : 'Bahamas',
        code : 'BS',
        capital  : 'Nassau',
        continent   : 'North America',
        currency    : 'BSD',
        languages   : 'English'
        },
        {
            id      : 3,
            countryName     : 'Botswana',
            code : 'BW',
            capital  : 'Gaborone',
            continent   : 'Africa',
            currency    : 'BWP',
            languages   : 'English, Tswana'
            },
            {
                id      : 4,
                countryName     : 'Colombia',
                code : 'CO',
                capital  : 'Bogotá',
                continent   : 'South America',
                currency    : 'COP',
                languages   : 'Spanish'
                },
                {
                    id      : 5,
                    countryName     : 'Costa Rica',
                    code : 'CRC',
                    capital  : 'Brasília',
                    continent   : 'North America',
                    currency    : 'CR',
                    languages   : 'Spanish'
                    },
                    {
                        id      : 6,
                        countryName     : 'Ecuador',
                        code : 'EC',
                        capital  : 'Quito',
                        continent   : 'South America',
                        currency    : 'USD',
                        languages   : 'Spanish'
                        }]

接下来,创建一种用于从商店发送和接收数据的方法:

export const DataStore = {
    sendData: (data) => { subject.next([...data] ); },
    onData: () => subject.asObservable(),
    data,
};

当您要更新数据时,使用sendData()方法。将向sendData()方法提供数据参数,该方法将附加到数据集。

然后,onData()方法返回可观察到的可观察到您订阅以接收最新数据。另外,您导出数据,以便可以用作初始数据。您需要导出商店,以便可以在其他地方导入并使用。

在组件中使用数据

_App.js_文件中,您需要导入DataStore并从商店中获取数据以在useState钩中使用。为此,您只需更新_const [data, setData]_的初始状态:

import React, { useState } from 'react';
import { DataStore } from './store/DataStore';

function App() { 
const [data, setData] = useState(DataStore.data);

}

然后,您需要创建一个useEffect钩并订阅onData方法以聆听任何更改。导入useEffect,以便您可以使用它:

import React  from 'react';

function App() { 


React.useEffect(() => {
        const subscription = dataStore.onData().subscribe(data => {
            setData(data);
        });
        return () => subscription.unsubscribe();  
} , []);

}

最后,您需要在组件卸下以防止应用程序中的内存泄漏时取消订阅。

将数据添加到网格

您需要创建的下一步是一种表格,该表格允许您在网格中添加其他国家数据。因为您在useEffect中订阅了它,所以您在提交表单时会通知您,并实时更新网格。

您可以继续更新_App.js_文件中的代码,以添加用于创建新电网项目的信息表格。制作一个按钮以打开和关闭表单。之后,创建和样式。然后,您需要处理切换和形式状态,如下所示:

const [toggleForm, setToggleForm] = useState(false);
const [formData, setFormData] = useState({
         id: "",
        countryName: "",
        code: "",
        capital: "",
        continent: "",
        currency: "",
        languages: ""

});

 const triggerToggle = () => {
     setToggleForm(!toggleForm);
 }


return (
        <>
            <div className='content-container'>
                <div className='new-content'>
                    <button 
                    className='btn-primary' 
                    onClick={triggerToggle}>Add new
                    </button> 
                </div>

{ toggleForm && <div>
                    <form className='form-container'>
                        <input 
                            type="text" 
                            placeholder="Country Name" 
                            name='countryName'  
                            id='countryName'
                            className='form-input' 
                            onChange={(e) => 
setFormData({...formData, countryName: e.target.value})} 
                                value={formData.countryName}
                        />
                        <input 
                            type="text" 
                            placeholder="Code" 
                            name='code' 
                            id='code' 
                            className='form-input'
                            onChange={(e) => 
                                setFormData({...formData, 
                                code: e.target.value})
                            } 
                            value={formData.code}
                        />
<input 
                            type="text" 
                            placeholder="Capital" 
                            name='capital'
                            id='capital'
                            className='form-input'
                            onChange={(e) =>
                                setFormData({...formData,
                                capital: e.target.value})
                            }
                            value={formData.capital}
                        /> <br />
                        <input 
                            type="text" 
                            placeholder="Continent" 
                            name='continent'
                            id='continent'
                            className='form-input'
                            onChange={(e) =>
                                setFormData({...formData,
                                continent: e.target.value})
                            }
                            value={formData.continent}
                        />
                        <input 
                            type="text" 
                            placeholder="Currency" 
                            name='currency'
                            id='currency'
                            className='form-input'
                            onChange={(e) =>
                                setFormData({...formData,
                                currency: e.target.value})
                            }
                            value={formData.currency}
                        />
                        <input 
                            type="text" 
                            placeholder="Languages" 
                            name='languages'
                            id='languages'
                            className='form-input'
                            onChange={(e) =>
                                setFormData({...formData,
                                languages: e.target.value})
                            }
                            value={formData.languages}
                        />
                        <div>
                            <button className='btn-primary' >Submit</button>
                        </div>
                        <br />
                    </form>
                        </div>}
                <BryntumGrid data={data}  columns={columns}   features={features} />
            </div>
        </>
    );

现在在_App.scss_ file中添加样式:


.content-container {
    width: 100%;
}

.btn-primary {
    display: inline-block;
    font-weight: 400;
    text-align: center;
    border: 1px solid transparent;
    padding: 0.375rem 0.75rem;
    font-size: 1rem;
    line-height: 1.5;
    border-radius: 0.25rem;
    color: #fff;
    background-color: #007bff;
    border-color: #007bff;
    cursor: pointer;
}

.new-content {
    display: flex;
    justify-content: right;
    margin: 10px;
}

.form-container {
    text-align: center;
}

.form-input {
    padding: 0.375rem 0.75rem;
    font-size: 1rem;
    line-height: 1.5;
    color: #495057;
    background-color: #fff;
    background-clip: padding-box;
    border: 1px solid #ced4da;
    border-radius: 0.25rem;
    margin: 5px;
}

在上一个代码中,当您选择添加新按钮时,使用toggleForm显示和隐藏表单。 formData包含表单的详细信息,这些详细信息将其设置为表单输入的onChange。您当前的表格应该看起来像:

Info form

提交表单后,数据将发送到RXJS商店,并重置表格。然后,由于您订阅了商店,_data_将被更新,从而导致网格的播放器,并将新数据添加到表中。

App.js文件中添加提交功能:

const handleSubmit = (e) => {
        e.preventDefault();
        // to increment the id of the new record
        formData.id = data.length + 1;

        // to add the new record to the data array
        dataStore.sendData([...data, formData]);

        // to reset the form
        setFormData({
            id: '',
            countryName: '',
            code: '',
            capital: '',
            continent: '',
            currency: '',
            languages: ''
        });
        // to close the form
        setToggleForm(!toggleForm);

    }

然后更新它:


<button className='btn-primary' onClick={handleSubmit}>Submit</button>

Fill form data

现在提交时列表已更新:

Updated grid

网格功能

Bryntum Grid组件使用的功能,这些功能以Feature为前缀为配置设置和属性值,并且与实例的相关API功能相关联。

默认情况下,网格的许多功能都设置为_true_,但是您可以切换功能以适应您的需求。例如,在_App.js_文件中,以下更新_feature_变量:

const [features, setFeatures] = useState({
     cellEdit     : true,
     regionResize : false,
     stripe: true,
     filter: true,
     rowReorder: true,
     columnReorder: true,
    });

_filter_设置为True时,您可以按这样的列过滤数据:

Filter data

_rowReorder_设置为true还允许排重排。在下图中,最后一行移至第三行:

Row reorder

同样,启用_columnReorder_可以通过拖动标题来移动列:

Column reorder

您可以看到,最后一列是第二列。

Bryntum Grid中有许多功能可根据任何功能的触发来收听事件。 Bryntum Grid docs中提供了完整的功能列表。

结论

在本文中,您学会了如何在React应用程序中使用Bryntum Grid及其配置。您还学会了如何使用RXJ管理应用程序状态。此外,您还学会了如何从RXJS商店获取数据以预填充电网,然后在商店中添加更多数据。

您已经在使用bryntum网格吗?我们很想听听您有关它如何改变您的工作流程的反馈。

Bryntum帮助全世界遵守计划。我们的组件库为各种前端框架提供了各种高质量的高级UI控件。想了解更多吗?在bryntum.com尝试我们的计划和甘特组件。