Versions Compared

Key

  • This line was added.
  • This line was removed.
  • Formatting was changed.

List Of Components

Component

InputType

Description

Textbox

text

Component used to render textbox

Textarea

textarea

Component used to render textarea

Checkbox

checkbox

Component used to render checkbox

Select

select

Component used to render dropdown with single select

MultiSelect

nestedselect

Component used to render dropdown with multi select

Topic Selector

topicselector

Component used to render topic selector

Timer

timer

Component used to render time

Keywords

keywords

Component used to render input tags

Framework

framework

Component used to render dropdown with framework values

FrameworkCategorySelect

frameworkCategorySelect

Component used to render dropdown with framework categories.

Field Configuration Properties

Code Block
breakoutModefull-width
languagejson
{
    "code": string, // property to match the backend schema ("name", "description", etc...)
    "name": string, // name of the field ("Name", "Board", "Medium", "License", "Copyright Year", etc)
    "label": string, // title of the field 
    "

description

placeholder": string, // placeholder text to 

specify

appear 

description

within 

about

the field

and to


show

 

as

 

tooltip

  

"

placeholder

description": string, // 

placeholder

to 

text

specify 

to

description 

appear within

about the field and to show as tooltip
    "

required

default": 

boolean

string, // 

to

specify 

if the field is mandatory or not (currently, not used.)

default value
    

"dataType": string, // to specify the datatype of the field outcome ("list", "number", "text")
    "inputType": string, // to map the field type and the component ("text", "textarea", "select", "nestedselect", etc)
    "

visible

editable": boolean, // to 

hide

enable or 

show

disable the field
    

"

editable

required": boolean, // to

enable

 specify if the field is mandatory or not 

disable

(currently, 

the

not 

field

used.)
    "

renderingHints

visible": 

json

boolean, // to 

specify

hide 

any

or 

additional

show 

configuration ex:({"class": "sb-g-col-lg-1 required"})

the field 
    "depends": array, // array of "code" to specify that this field is dependant on other fields
    "range": array, // Array or array of objects of inputs to fields such as "select", "nestedselect", "multiselect"
    "options": array/function/map, // to specify the inputs to fields such as "select", "nestedselect", "multiselect", "framework", "frameworkCategorySelect"
    "renderingHints": json, // to specify any additional configuration ex:({"class": "sb-g-col-lg-1 required"})
    "validations": array // Array of objects to specity the validations of a field. Each validation object takes properties such as "type", "message", "value", "criteria"
    "output": string, // this field is specific to framework terms and it's associations. The field will decide the property for the field outcome ex:("name", "label", "identifier")
    "sourceCategory": string, // this field is specific to framework categories to map the category and association ex: (to map "subjectIds" with "subject" or to map "targetMediumIds" with "medium")
    "terms": array, // Array or array of object of inputs to fields related to framework and it's categories

"validations": array // Array of objects to specity the validations of a field. Each validation object takes properties such as "type", "message", "value",


"criteria"

}

Sample Configuration for name field:

wide
Code Block
breakoutMode
languagejson
{
    "code": "name",
    "dataTypename": "textName",
    "descriptionlabel": "Name of the contentTitle",
    "editableplaceholder": true"Title",
    "inputTypedescription": "text",Name of    "label": "Title"the content",
    "namedataType": "Nametext",
    "placeholderinputType": "Titletext",
    "renderingHintseditable": {
        "class": "sb-g-col-lg-1 required"
    }true,
    "required": true, // currently not used to check if the field is mandatory. //
    "visible": true,
    "renderingHints": {
        "class": "sb-g-col-lg-1 required"
    },
    "validations": [
        {
            "type": "maxmaxLength",
            "value": "120", // maximum number of characters
            "message": "Input is Exceeded"
        },
        {
            "type": "required", // 
            "message": "Title is required"
        }
    ]
},


Custom invocation when a field’s value changes:

Code Block
breakoutModelanguagewidetypescript
nameFORMCONTROL.valueChanges.pipe(
    tap((value) => {
alert()
      // custom logic
    })
);

Custom invocation when a dependant field values changes:

Code Block
breakoutModelanguagewidetypescript
merge(..._.map([DependantFieldControl1, DependantFieldControl2], depend => depend.valueChanges)).pipe(
       tap((value) => {
      // your custom logic
  })
)

Custom validation:

Let’s say we have two fields, maxTime and warningTime and assume that the condition here is warningTime should not be greater than maxTime

Code Block
languagejson
{
    "code": "maxTime",
    "dataType": "text",
    "name": "MaxTimer",
    "default": "3600",
    "renderingHints": {
        "class": "sb-g-col-lg-1 required"
    },
    "description": "MaxTime for the content",
    "inputType": "timer"
}
Code Block
{
    "code": "warningTime",
    "dataType": "list",
    "name": "Warning Time",
    "depends": [
        "maxTime"
    ],
    "inputType": "timer",
    "validations": [
        {
            "type": "compare",
            "criteria": {
                "<": [
                    "maxTime"
                ]
            },
            "message": "warning time should be less than max timer"
        }
    ]
}

We introduced a new type of validations called compare:

Code Block
{
    "type": "compare",
    "criteria": {
        "<": [
            "maxTime"
        ]
    },
    "message": "warning time should be less than max timer"
}

Here, criteria is a map which takes any comparison operator as the key and array of codes as value.

Following is our custom function to compare two fields and handle errors if any. The following function takes two arguments - criteria and AbstractControl.

Code Block
breakoutModelanguagewidetypescript
compareFields(criteria, control: AbstractControl): ValidationErrors | null {
    // your custom code to compare fields based on the criteria
}

Now the function can be passed to Angular by doing Validators.compose as shown below:

Code Block
Validators.compose([compareFields.bind(this, criteria)])

Function compareFields will now be called whenever warningTime field is changes.

Custom Event Listener:

Angular by default provides two methods to listen to any field’s changes.

  1. FormControl.valueChanges

  2. FormControl.statusChanges

The above two methods will be immediately triggered when there is a change in the field.

Let’s assume we have a scenario where we need to make an async API call and make use of the API response, the above two methods will not help us as the API might have a delay.

To tackle this scenario, we will introduce a custom event emitter on the FormControl.

The following interface extends the default Angular FormControl and adds a RxJS Subject event emitter.

Code Block
languagetypescript
export interface CustomFormControl extends FormControl {
  customEventHandler$?: Subject<any>;
}

This will help us emit the event when the API returns a response

Code Block
ObservableAPI..subscribe(
    (APIResponse) => {
        FORMCONTROL.customEventHandler$.next(APIResponse);
    }
  );
}

Any other fields that are dependant on this API response can now listen to this event emitter.

Code Block
languagetypescript
merge(_.map([DependantControl1, DependantControl2], depend => depend.customEventHandler$)).subscribe(
  (response) => {
    ...
  }, error => {
    ...
  }
)


Status
colourYellow
titleIN PROGRESS

Closure function:

A closure function take takes the following objects as its arguments.

wide
Code Block
breakoutMode
control: FormControl // form control of the framework field
depends: [FormControl, FormControl], // array of formcontrols of the fields that the framework field depends on (if any)
formGroup: FormGroup // instance of the entire FormGroup
loading: anonymous function // to notify about the data loading status 
loaded: anonymous function // to notify about the data loaded status 

Sample Closure function:

Let’s say we have a field called framework. On change of framework field, if we have to invoke a logic, it can be achieved as shown below:

During the initialisation of the framework field, we will pass the following function to options property of framework field.

Code Block
breakoutModelanguagewidetypescript
getFramework(control, depends: FormControl[], formGroup: FormGroup, loading, loaded) {
    const response =  control.valueChanges.pipe(
      switchMap((value: any) => {
          return callFrameworkObservable()
      })
    );
    return response;
}

Field Config for framework

wide
Code Block
breakoutMode
languagejson
{
  "code": "framework",
  "visible": true,
  "editable": true,
  "dataType": "text",
  "label": "Course Type",
  "required": true,
  "name": "Framework",
  "inputType": "framework",
  "placeholder": "Select Course Type",
  "output": "identifier",
  "options": getFramework
  "validations": [
    {
        "type": "required",
        "message": "Course Type is required"
    }
  ]
}
To handle delay in APIs,