Editor’s Note: This edition brings you Formily based drag-and-drop form designer gameplay and explores the possibilities of form designers in the visual age.

background

Forms are the most common form of interaction in console-like Web applications. Users fill in information in the form and click Submit to complete data creation or modification operations.

In the beginning, the front-end developer implements each field in the form one by one by writing or declaring it according to the business model and specific requirements, and releases it after passing the test. Gradually, developers began to abstract some common methods into a form library reuse, improve the development efficiency. With the increase of business complexity and the continuous evolution of requirements, the requirements for form presentation and flexibility are also constantly improving. The existing form library can only solve part of the problems, and developers still need to spend a lot of energy on updating form fields or developing new forms.

Is there a way for developers to build forms quickly, with little or no developer intervention to update forms later?

This is where the form designer comes in. The form designer provides a visual interface that allows non-professional developers to build business-required forms in a wySIWYG drag-and-drop manner.

Form designer styles

Many open source form designer implementations are similar in their UI, and the structure of the designer is similar to the layout of the design software. Form designers typically have three columns left, middle, and right:

  • On the left is a list of controls that list the form controls supported by the designer.

  • The middle part is the canvas, and the control on the left can be directly dragged to the canvas, and supports control order adjustment, copy and other operations.

  • On the right is the field configuration area. If you select a field on the canvas, all the properties of the field are displayed on the right. You can configure the field title, description, and verification rule here.

The principle of analytic

The output of the form designer is a JSON Schema describing the form fields, which is stored directly to the back end after the form design is complete. After the form is published, the front end renders the form according to JSON Schema. The information for all the fields in the form is stored in the Schema, so every update to the form changes the contents of the Schema without the traditional compilation process. The form designer not only frees developers from frequent changes in response to business changes, but also greatly increases the productivity of non-professional developers and reduces communication costs.

JSON Schema is the language for communication between form designers and form rendering components. To understand the heart of a form designer, you first need to understand schemas. In actual projects, JSON schemas are usually complex and are not expanded here. The topic of this article is the implementation principle of form designer. The main concern is how to provide a visual interface that enables users to quickly generate schemas. The detailed Schema format will be introduced in the following articles.

	interface Schema {
		fields: Record<FieldKey, FieldSchema>;
	}
	​
	interface FieldSchema {
		title: string;
		type: 'string' | 'object' | 'array' | 'number' | 'boolean';
		component: string;
		componentProps: {
			[name: string]: any;
		};
	}
Copy the code

As we all know, forms are composed of multiple input controls. Input controls can be in various forms, such as text, number, radio, and multiple. In addition to describing the input type of the field, the Schema also describes the behavior of the control, such as whether the input length is limited and whether it is mandatory. With these descriptions, the form rendering component can render the form according to the Schema as expected. In the type definition above:

  • Component indicates what input component the field is rendered with.

  • ComponentProps Represents props passed to a component to control the behavior of the component.

  • Type indicates the type of data that the component accepts and expects to return.

  • FieldKey is the unique identifier of the field in the form and is not visible from the user side.

  • Title represents the label corresponding to the field in the form, and its value is readable by the user.

The task of the form designer is to start from scratch, or take an existing JSON Schema as input, add, delete, and update the fields in the Schema, and finally output the Schema. If we look at the form designer as a whole, its functionality can be represented as follows:

Further, we can break down the diagram to the control level, take the configuration of a field as input, and re-print the configuration of that field after updating it.

As a whole, a form is a combination of the actions of each control, resulting in a complete JSON Schema.

To enable the modification of form fields, we provide field configuration areas in the form designer, where users can visually define field properties without worrying about the specific format of the Schema. The form designer is responsible for converting configuration values to a Schema and converting the Schema to configuration values to display the configured page form.

Note: The configuration area is actually a form, and each type of control has its own specific configuration form.

To accomplish this, each control needs to implement two methods: toConfig and toSchema. A formula is used to represent the relationship between the two methods and the Schema, where configValue is used to echo the configuration form.

	FieldSchema => toConfig => configValue => toSchema => FieldSchema
Copy the code

With that out of the way, let’s return to the UI rendering of the form designer.

On the left is a list of controls supported by the designer. Based on the analysis above, each control needs to provide implementations of the control name, configuration form, toConfig, and toSchema interfaces. The middle canvas displays the controls in the Schema and handles user click and drag events. When the user clicks on a field in the canvas, the configuration area on the right needs to find the corresponding configuration form and render it.

conclusion

The above is the most core architecture implementation of the form designer, and there are some details that need to be considered in the implementation, such as the definition and resolution of the form Schema, which will be elaborated in the subsequent articles step by step. Please continue to pay attention to it.

The form designer for the all-image cloud low-code platform is implemented based on Formily. We admire Formily for its flexible scalability and business-specific features. We thank the Formily team for their contributions and hope we can contribute code to Formily in the future.

The author

Duan Guowei, Wang Xi