Jsonforms in angular without material

is it possible to create jsonforms without material in angular 9

Hi @howdyAnkit,

technically, yes. You need to consume an older version of JSON Forms core (@jsonforms/core) and the Angular bindings (@jsonforms/angular) which were built against Angular 9. Then instead of using @jsonforms/angular-material you need to write your own renderer set either with Vanilla JS or with a UI framework of your choice.

However you will need to use a pretty old version of JSON Forms for which you will then need to write a new renderer set. Probably you would be better off converting your Angular app to a later version if that is possible for you.

is there are any examples out there ive chefked with angular 2 but we are using angular 10

ohh you mean that ill have to downgrade my angular app for that?

Hi @howdyAnkit,

We currently build against Angular 12 and are compatible with Angular 12, 13 and 14. If you use Angular 9 or 10 then you need to use an older version of JSON Forms which is compatible with Angular 9 and/or 10. Alternatively you can update your app to Angular 12 or later and therefore use the latest version of JSON Forms.

In any case, you will need to write your own renderer set as we only offer Angular Material. You can take a look at the Angular Material code base, replicate it and exchange the Angular Material specific parts with the framework you would like to use.

Hi @sdirix

Thankyou so much for replying and getting back this was helpfull in analyzing future things for us. though as i’ve started digging and integrating jsonform in our code base could you please let me know what version of material, flex-layout would be compatible for us i went through the release doc and for Angular 10 i found out jsonform@2.5.1 could be better for us but after few mins of installing things am getting json-schema-ref-parser error stating could not resolve

/node_modules/json-schema-ref-parser/lib/resolvers/http.js

module not found and similarly for https.

few more errrors with jsonforms/angular-material it seems

Warning in project-dir depends on @jsonforms/angular-material.commonJS or Amd dependencies can cause optimization bailouts

could you recommend material, flex-layout and other dependencies version which should be compatible for us with Angular 10?

i am using this versions below mentioned

angular/flex-layout : 9.0.0-beta.29
angular/material:^10.1.3
jsonforms/angular: ^2.5.1
jsonforms/angular-material: ^2.5.1
jsonforms/core: ^2.5.1

Hi @howdyAnkit,

I think the latest compatible version of JSON Forms for Angular 10 is 3.0.0-alpha.1. I would recommend using that version over 2.5.1 as the json-schema-ref-parser was removed for 3.0.0 so it can’t break your build.

3.0.0-alpha.1 is build against

    "@angular/animations": "^9.0.0",
    "@angular/cdk": "^9.0.0",
    "@angular/common": "^9.0.0",
    "@angular/compiler": "^9.0.0",
    "@angular/compiler-cli": "^9.0.0",
    "@angular/core": "^9.0.0",
    "@angular/flex-layout": "^9.0.0-beta.29",
    "@angular/forms": "^9.0.0",
    "@angular/material": "^9.0.0",
    "@angular/platform-browser": "^9.0.0",
    "@angular/platform-browser-dynamic": "^9.0.0",
    "@angular/router": "^9.0.0",

but should actually work against Angular 9, 10 and 11.

Hi Sidrix,

I tried creating this mentioned form(List With Detail Example - JSON Forms) and was not able to get same results. when i keep my data filled with mentioned values i cant see the ui getting rendered and many other errors in the chrome console. so i kept the data schema as empty and after that i was able to render the empty ui with no tabs on left. but anyhow after clicking the plus button i wasnt able to add a new form to the left list and even form wasn’t getting rendered on right.

Could you let me know what fixes i can check.

Thanks,
Ankit Pal

Hi @howdyAnkit,

I’m missing too much information. Which version of JSON Forms are you now using with which version of Angular? Can you please post the JSON Schema, UI Schema and data you are using? If possible, please try to reproduce the issue with the Angular seed and/or upload a reproducible example so we can take a look.

Hi @sdirix Thanks for the reply I was able to get it working with custom renderer with examples mentioned here (GitHub - eclipsesource/jsonforms: Customizable JSON Schema-based forms with React, Angular and Vue support out of the box.)

also I was checking the Angular seed master custom select as mentioned over here (jsonforms-angular-seed/custom.autocomplete.ts at master · eclipsesource/jsonforms-angular-seed · GitHub)

with the below schema

data = {
toppings: "DE"
}

schema = {
   type: "object",
   properties : {
     toppings: {
        type: "string",
        enum : [
           "DE",
           "IT",
            "JP",
           "US",
           "RU",
           "Other"
        ]
     }
  }

uischema = {
   type: "VerticalLayout",
   elements: [
       {
          type: "Control",
          scope: "#/properties/toppings"
       }
   ]
}

I was able to bind the data into select also was able to get the enum in options but few things dont worked for me such as selecting another option and submitting I was getting the same prefilled value
for Eg In data json i have DE as prefilled value but when i select another option such as US and submit i was still getting the DE as on submit.

Also when i keep the data as empty it gives error without even bieng touched to select value where as i was expecting the error of not selectd option on submit.

could you please help me fix this

Also yeah i am using jsonforms 2.5.2

Hi @howdyAnkit,

I was able to bind the data into select also was able to get the enum in options but few things dont worked for me such as selecting another option and submitting I was getting the same prefilled value
for Eg In data json i have DE as prefilled value but when i select another option such as US and submit i was still getting the DE as on submit.

These don’t seem to be errors within JSON Forms but how you are using it in your application. You need to listen to the dataChange events which are emitted from the JSON Forms component and then update your view of the data accordingly, e.g.

<jsonforms
    [data]="data"
    [schema]="schema"
    [uischema]="uischema"
    [renderers]="renderers"
    [i18n]="i18n"
    [ajv]="ajv"
    (dataChange)="dataChange($event)"
></jsonforms>
dataChange = (newData => { this.dataToEmit = newData });

The same can be done for the errors which we emit. According to this data you can then enable/disable your submit button and submit the current data.

Thanks @sdirix for the reply i was able to get the data on changes. since i was building a custom component I made a second component which listen to changes on the first component and then assign the value selected in option to the input value for eg like below

this.jsonformsService.$state.subscribe({
 this.temp = state?.jsonforms?.core?.data?.toppings; 
// this reads the value from state from option selected  
});

<input 
  [formControl]="form"
  [(ngModel)] = "temp"  //the above value gets assigned here and i can see it in input 
/>

the above works fine but it’s not getting applied to datachanges scope it comes as empty.
{toppings: ‘IT’, sauces: ‘’ }

whereas sauces key should be the holding the value on change

In my view the datachange is not getting emitted in this above not sure why tried with select aswell is there any thing i am missing? to re-emmit changes happened on another component

Hi @howdyAnkit,

Your custom control needs to adhere to the JSON Forms patterns to work properly. For example changes must be done via the onChange methods, which then goes through the update action of the core reducer and makes sure the form-wide JSON Forms state is updated accordingly and the data events are emitted.

I would like to recommend to look at the existing renderers and implement your cutom renderer in a similar fashion.

Hi @sdirix could you please provide with an example or suggestions how can i achieve this i am unable to proceed with data binding? i’ve tried it various ways but no luck

i am using this custom renderer on your previous suggestions for text
(jsonforms/text.renderer.ts at ede7d61677329c92a5878808ac20277392734676 · eclipsesource/jsonforms · GitHub)

Hi @howdyAnkit,

Without seeing your code I can’t really help you. Did you try to copy the existing renderer, modify it a little bit and register it as a custom renderer?

Thanks @sdirix for replying back i’ve created a small glimpse of my feature what i am trying to achieve in this stackblitz version ( Angular 10 Starter Project (forked) - StackBlitz

I wasnt able to setup the dependencies on this. skipping that

I tried with viewchild decorator aswell to set the input value hoping to get emitted but was unable to do that aswell on ngOninit.

The select-renderer.ts is a custom controller where we select the value and that value get’s emitted with datachanges but since whatever we select in the select-renderer we hear those changes in input-renderer.ts and apply the same value to input-renderer.ts input field. since the value is bieng set in the input-renderer text field what i am expecting is to get the value emmited in datachanges.

Hi @howdyAnkit,

Concrete issue why it’s not working for you:

  • The input renderer change does not go through the onChange of the input renderer. So to fix it you don’t need to update some local state of the input but go through the onChange to properly trigger the form-wide state update and therefore data event.

However even if that fixes the concrete issue, I would not recommend actually doing it like this as this is not a good way of syncing. What you are describing is that the sync mechanism is implemented as part of the UI, by listening to changes within one renderer to data of another and then applying these changes on their on value. This can work if everything goes right, but it’s brittle and error prone.

Conceptual issues:

  • To the outside world the data will be in an inconsistent state for one tick as the first emitted data will only contain the select update
  • Any UI interference will prevent the UI mechanism of working. For example if the input renderer is hidden away via a UI rule or is moved into an optional collapsible part of the UI, the syncing will be broken
  • The form is rendered twice as you go through two state updates in separate renderer passes

A clean solution is to push the update of the dependent field. So the select field could not only update itself via the provided onChange but the other property at the same time. For this you can dispatch an update action on the jsonforms state, e.g.

    this.jsonFormsService.updateCore(
      Actions.update('otherPropertyPath', () => newValue)
    );

The onChange does the same thing, it’s just a pretty facade.

In case you conceptually can’t know or don’t want to know the dependent fields in your renderer, you could also listen to the emitted data changes outside of JSON Forms and adapt the whole data object as you see fit and hand over the modified data again back to JSON Forms. This avoids most of the bad issues and encapsulates the dependent-value updating in a clear step instead of spreading it throughout the UI.