lukefx
2/26/2014 - 2:52 PM

Use any json api as datasource for a combobox in Editor component ArcGIS Flex API

Use any json api as datasource for a combobox in Editor component ArcGIS Flex API

// usage example, save the user id of github inside a feature and show the login name inside a combobox

var endpoint:String = "https://api.github.com/orgs/tirug/public_members";

var field:FieldInspector = new FieldInspector();
field.featureLayer = featureLayer;
field.fieldName = "user_id"; // feature field
field.label = "Username";
field.visible = true;

var renderer:ClassFactory = new ClassFactory(CustomDataSourceComboRenderer);	
renderer.properties = { labelField: "login", valueField: "id", endpoint: endpoint };
field.renderer = renderer;
field.rendererIsEditor = true;

editor.attributeInspector.fieldInspectors = [ field ]
package ch.lugano.gisweb.controllers.edit {
	
	import com.esri.ags.components.supportClasses.IFieldRenderer;
	import com.esri.ags.skins.fieldClasses.DropDownListField;
	import com.esri.ags.utils.JSONUtil;
	
	import flash.events.Event;
	
	import mx.collections.ArrayCollection;
	import mx.collections.IList;
	import mx.events.PropertyChangeEvent;
	import mx.events.PropertyChangeEventKind;
	import mx.rpc.events.FaultEvent;
	import mx.rpc.events.ResultEvent;
	import mx.rpc.http.HTTPService;
	
	import spark.events.DropDownEvent;
	
	public class CustomDataSourceComboRenderer extends DropDownListField implements IFieldRenderer {
		
		private var _endpoint:String;
		
		[Bindable]
		public var m_data:*;
		
		public function CustomDataSourceComboRenderer() {	
			super();			
		}
		
		private function loadData():void {
		
			var service:HTTPService = new HTTPService();
			service.url = encodeURI(endpoint);
			var header:Object = new Object();
			header["Content-Type"] = "application/json; charset=utf-8";
			service.headers = header;
			service.resultFormat = "object";
			service.addEventListener(ResultEvent.RESULT, parse);
			service.addEventListener(FaultEvent.FAULT, onFault);
			service.send();
		
		}
		
		public function parse(event:ResultEvent):void {

			dataProvider = new ArrayCollection(JSONUtil.decode(event.result.toString()) as Array);
			addEventListener(DropDownEvent.CLOSE,this.closeHandler);
			this.refreshSelectedItem();
						
		}
		
		private function closeHandler(event:Event) : void {
			var pce:PropertyChangeEvent = null;
			var newData:Object = null;
			if(selectedItem is String) {
				newData = selectedItem;
			}
			else {
				newData = selectedItem[this.valueField];
			}
			if(this.m_data != newData) {
				pce = new PropertyChangeEvent(PropertyChangeEvent.PROPERTY_CHANGE, true, false, PropertyChangeEventKind.UPDATE, "data", this.m_data, newData, this);
				dispatchEvent(pce);
				this.m_data = newData;
			}
			
		}
		
		private function refreshSelectedItem() : void {
			var i:* = 0;
			var item:Object = null;
			var list:IList = dataProvider;
			if(list) {
				i = 0;
				while(i < list.length) {
					item = list.getItemAt(i);
					if(item == this.m_data) {
						selectedIndex = i;
						break;
					}
					if((item.hasOwnProperty(this.valueField)) && (item[this.valueField] === this.m_data)) {
						selectedIndex = i;
						break;
					}
					i++;
				}
				
			}
			
		}
				
		public function onFault(event:FaultEvent):void {
			trace(event.message);
		}
		
		private function comboBox_labelFunc(item:Object):String {
			return item[this.fieldLabel];
		}
		
		public function get endpoint():String {
			return _endpoint;
		}
		
		public function set endpoint(value:String):void {
			_endpoint = value;
			loadData();
		}
		
		override public function get data() : Object {
			return this.m_data;
		}
		
		override public function set data(value:Object) : void {
			if(this.m_data != value) {
				this.m_data = value;
			}
		}
		
	}
	
}