protected OgexValue toValue( DataStructure ds ) {
        OgexValue result = new OgexValue();
        
        String s = ds.getProperty("curve", "linear");
        Curve curve = Curve.lookup(s);
        result.setCurve(curve);
        
        OgexKey[] keys;
        switch( curve ) {
            case Linear:
                keys = new OgexKey[1];
                break;
            case Bezier:
                keys = new OgexKey[3];
                break;
            case Tcb:
                keys = new OgexKey[4];
                break;
            default:
                throw new RuntimeException("Unhandled curve type:" + curve + ", from:" + ds.location());
        }
        
        int index = 0;
        for( BaseStructure child : ds ) {
            if( StructTypes.KEY.equals(child.getType()) ) {
                if( index >= keys.length ) {
                    throw new RuntimeException("Too many Key structures found in Value, from:" + ds.location());
                }
                keys[index++] = toKey((DataStructure)child);    
            } else {
                log.warn("Unhandled structure type:" + child.getType() + ", from:" + child.location());
            }
        }
        if( index < keys.length ) {
            throw new RuntimeException("Missing Key structure for Value structure with curve:" + curve + ", from:" + ds.location());
        }
        result.setKeys(keys);        
        
        return result;
    }