Charger une liste

Bonjour,

Je souhaite charger ma liste en passant par code et non pas graphiquement.

Voilà un bout de mon code :

var list = this.getField("kpi").getList().getAllItems();

console.log("Size of list : " +list.size());

var object = new ObjectField(ObjectField.TYPE_ENUM,"kpi",this.getFieldValue("kpi"));

var objectField = new ObjectFieldList(object);

var enumItem = new EnumItem("PRO","Value of PRO");
var enumItem1 = new EnumItem("ABO","Value of ABO");

objectField.putItem(enumItem);
objectField.putItem(enumItem1);

this.getField("kpi").setList(objectField);
console.log("Size of list ITEM : " +list.size()); 

for (var i = 0; i < list.size(); i++) {
	console.log(i+" before setValue:"+list.get(i).getValue());
	list.get(i).setValue(list.get(i).getValue());
	console.log(i+" after setValue:"+list.get(i).getValue());
}

Il me semble que cette demande est la même que celle du topic Comment je peux remplir une liste déroulante

Bref, pour charger dynamiquement une liste de valeur veuillez vous reporter à la documentation, en l’occurrence ce sujet est traité ici : https://docs.simplicite.io/documentation/01-core/advanced-code-examples.md#dynamiclist

Faites attention à mettre votre code dans le bon hook : si par exemple cette liste dépend de valeurs du record cela devra se fait dans le postSelect, pas dans le postLoad.

Faites aussi en sorte d’optimiser ce code car, par exemple, si votre code fait des recherches complexes en base, sur une édition en liste les performances ne seront pas optimales.

Ayez bien en tête que ce code s’exécute coté serveur donc avant l’affichage du formulaire, cela ne sera donc pas neutre en termes d’expérience utilisateur.

C’est pour toutes ces raisons que, depuis le début, j’essaie de comprendre votre besoin métier plutôt que répondre bêtement à votre question technique car je suis persuadé que votre approche et/ou votre modélisation n’est pas la bonne… Mais bon vous faites comme vous voulez…

@david j’ai toujours la liste vide, par contre sur le log je vois les valeurs.

Merci de copier-coller votre code car on ne peut pas deviner ce que vous avez écrit…

Indicateur.postLoad = function(){
	    var field = this.getField("kpi");
    	field.setList(new ObjectFieldList(field)); // Empty the configured list

		 
    	var list = field.getList();
		var year = Tool.parseInt(Tool.getCurrentYear(), 2000);
		 for (var i = year; i <= year + 20; i++)
        	list.putItem(new EnumItem(i.toString(), this.getGrant().T("YEAR") + " " + i));
};

L’exemple de la doc marche parfaitement:


Merçi @david c’est régler.

OK
Dans quel hook avez vous implémenté le chargement de votre liste dynamique ?

Je pose la question car si c’est dans le postLoad comme dans l’exemple de la doc je voudrais être sûr que vous avec compris quel est le rôle de ce hook et si c’est bien ça qui répond à votre besoin.

SI c’est dans un autre hook, je vous ai aussi alerté sur les potentiels problèmes de performances ou de comportement non souhaité que ce genre de code peut générer.

Bref, je veux bien voir votre code pour comprendre si ce que vous faites est bien une bonne approche.

@david mon code il ressemble à ça :

Indicateur.postLoad = function(){
	
    var objectField = new ObjectFieldList(this.getField("kpi"));
	var o = this.getGrant().getTmpObject("Indicateur");
		o.resetFilters();
		var rows = o.search(false);
		
		for (var i = 0; i < rows.size(); i++) {
			o.setValues(rows.get(i));
			var v1 = o.getField("nomIndicateur").getValue();
			var enumItem = new EnumItem(rows.get(i),v1);
			objectField.putItem(enumItem);
			this.getField("kpi").setList(objectField);
		}

};

Merci @david pour votre aide

Franchement, là je ne comprends pas votre logique…

Vous construisez une liste de valeur statique (car dans le postLoad) à partir d’une recherche non filtrée sur votre objet Indicateur .

Pourquoi n’avez vous pas simplement paramétré une référence vers l’objet Indicateur ?!?!?

PS: et avec le rendering “popup and select” vous auriez une ergonomie type “liste déroulante” sur votre référence, exemple dans la démo:

J’ai oublié d’ajouter un filtre merci pour votre remarque et cette fois mon code ressemble à ça :

Indicateur.postLoad = function(){
	
    var objectField = new ObjectFieldList(this.getField("kpi"));
	var o = this.getGrant().getTmpObject("Indicateur");
		o.resetFilters();
		o.getField("modaliteCalcul").setFilter("%GLOBAL");
		var rows = o.search(false);
		
		for (var i = 0; i < rows.size(); i++) {
			o.setValues(rows.get(i));
			var v1 = o.getField("nomIndicateur").getValue();
			var enumItem = new EnumItem(rows.get(i),v1);
			objectField.putItem(enumItem);
			this.getField("kpi").setList(objectField);
		}

};

Même avec un filtre statique ça reste pas du tout la bonne logique.

Dans votre cas, si je comprends bien, ça devrait être une référence avec un link mapping comme je vous l’ai suggéré dans une autre réponse.

Dénormaliser un objet en liste de valeur statique n’a pas strictement aucun sens (sauf s’il y a une subtilité qui m’échappe toujours)

Par ailleurs, cette ligne de code var enumItem = new EnumItem(rows.get(i),v1); n’a pas de sens, le 1er argument du constructeur EnumItem doit être un String, je pense que vous vouliez écrire rows.get(i)[0] (ou plutôt o.getRowId() vu que vous avez fait un setValues avant…).

Et en faisant ça vous stockerez en base un row ID donc conceptuellement une référence (i.e. une foreign key) vers un autre objet, mais sans lui donner un type référence… bref pour moi c’est n’importe quoi (ou peut être que vous ne m’avez toujours pas donné les bonnes infos pour comprendre pourquoi vous faites ça).

PS: Autre chose aussi, la ligne this.getField("kpi").setList(objectField); ne devrait pas être dans la boucle mais après la boucle.