-
Notifications
You must be signed in to change notification settings - Fork 591
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Feature request: respect typedef enum names #477
Comments
I've fixed that in commit 5af4255. It's going to take to the name of the infoMap.put(new Info("Spinnaker::GenApi::ENameSpace").enumerate().valueTypes("_ENameSpace")) Thanks for reporting! |
Thanks for addressing this issue quickly. I see names generated correctly in the Java code. infoMap.put(new Info("Spinnaker::GenApi::ENameSpace").cast().pointerTypes("Pointer")); Does it make sense to make it part of the code generated by Parser for "typedef enum" constructs? |
It should already be doing that. Can you give an example that fails? |
Type enum in this example is called
Example typedef enum typedef enum
{
NI,
NA,
WO,
RO,
RW,
_UndefinedAccesMode,
_CycleDetectAccesMode
} EAccessMode; Class (from Spinnaker API) for which generated JNI wrapper code has error in method class SPINNAKER_API EAccessModeClass
{
public:
static bool FromString(const GenICam::gcstring& ValueStr, EAccessMode* pValue);
static void ToString(GenICam::gcstring& ValueStr, EAccessMode* pValue);
static GenICam::gcstring ToString(EAccessMode Value);
}; In the generated JNI code (jniGenICam.cpp)) the error in this line using Spinnaker::GenApi::EAccessModeClass::ToString(*ptr0, val1); Complete generated JNI function code (to provide context for the line with error) JNIEXPORT void JNICALL Java_org_bytedeco_spinnaker_GenICam_EAccessModeClass_ToString__Lorg_bytedeco_spinnaker_GenICam_gcstring_2Lorg_bytedeco_spinnaker_global_GenICam_00024EAccessMode_2(JNIEnv* env, jclass cls, jobject arg0, jobject arg1) {
Spinnaker::GenICam::gcstring* ptr0 = arg0 == NULL ? NULL : (Spinnaker::GenICam::gcstring*)jlong_to_ptr(env->GetLongField(arg0, JavaCPP_addressFID));
if (ptr0 == NULL) {
env->ThrowNew(JavaCPP_getClass(env, 7), "Pointer address of argument 0 is NULL.");
return;
}
jlong position0 = arg0 == NULL ? 0 : env->GetLongField(arg0, JavaCPP_positionFID);
ptr0 += position0;
if (arg1 == NULL) {
env->ThrowNew(JavaCPP_getClass(env, 7), "Enum for argument 1 is NULL.");
return;
}
::Spinnaker::GenApi::EAccessMode val1 = (::Spinnaker::GenApi::EAccessMode)env->GetIntField(arg1, JavaCPP_intValueFID);
jthrowable exc = NULL;
try {
Spinnaker::GenApi::EAccessModeClass::ToString(*ptr0, val1);
} catch (...) {
exc = JavaCPP_handleException(env, 9);
}
if (exc != NULL) {
env->Throw(exc);
}
} |
Also the generated Java wrapper classes for @Namespace("Spinnaker::GenApi") public enum EAccessMode {
NI(0),
NA(1),
WO(2),
RO(3),
RW(4)
_UndefinedAccesMode(5),
_CycleDetectAccesMode(6);/** used internally for AccessMode cycle detection*/
public final int value;
private EAccessMode(int v) { this.value = v; }
private EAccessMode(EAccessMode e) { this.value = e.value; }
public EAccessMode intern() { for (EAccessMode e : values()) if (e.value == value) return e; return this; }
@Override public String toString() { return intern().name(); }
} @Namespace("Spinnaker::GenApi") @Properties(inherit = org.bytedeco.spinnaker.presets.GenICam.class)
public class EAccessModeClass extends Pointer {
static { Loader.load(); }
/** Default native constructor. */
public EAccessModeClass() { super((Pointer)null); allocate(); }
/** Native array allocator. Access with {@link Pointer#position(long)}. */
public EAccessModeClass(long size) { super((Pointer)null); allocateArray(size); }
/** Pointer cast constructor. Invokes {@link Pointer#Pointer(Pointer)}. */
public EAccessModeClass(Pointer p) { super(p); }
private native void allocate();
private native void allocateArray(long size);
@Override public EAccessModeClass position(long position) {
return (EAccessModeClass)super.position(position);
}
@Override public EAccessModeClass getPointer(long i) {
return new EAccessModeClass((Pointer)this).offsetAddress(i);
}
/**
* Converts a string to enum value
*/
public static native @Cast("bool") boolean FromString(@Const @ByRef gcstring ValueStr, EAccessMode pValue);
/**
* Converts a string to an int32_t property
*/
public static native void ToString(@ByRef gcstring ValueStr, EAccessMode pValue);
/**
* Converts a string to an int32_t property
*/
public static native @ByVal gcstring ToString(@ByVal EAccessMode Value);
} |
Ok, thanks, but I mean, what do the presets that you have written look like? |
Below is the You may notice there other code to deal with If you uncomment the line at the end package org.bytedeco.spinnaker.presets;
import org.bytedeco.javacpp.annotation.Platform;
import org.bytedeco.javacpp.annotation.Properties;
import org.bytedeco.javacpp.presets.javacpp;
import org.bytedeco.javacpp.tools.Info;
import org.bytedeco.javacpp.tools.InfoMap;
import org.bytedeco.javacpp.tools.InfoMapper;
/**
* Wrapper for Point Grey Spinnaker library (the C++ API v.2).
*
* @author Jarek Sacha
*/
@Properties(inherit = javacpp.class,
target = "org.bytedeco.spinnaker.GenICam",
global = "org.bytedeco.spinnaker.global.GenICam", value = {
@Platform(value = {"linux-x86_64", "linux-arm64", "windows"},
include = {
"SpinGenApi/GCTypes.h",
"SpinGenApi/GCString.h",
"SpinGenApi/GCStringVector.h",
"SpinGenApi/GCUtilities.h",
"SpinGenApi/GCBase.h",
"SpinGenApi/IBoolean.h",
"SpinGenApi/ICommand.h",
"SpinGenApi/IDeviceInfo.h",
"SpinGenApi/IEnumEntry.h",
"SpinGenApi/IEnumeration.h",
"SpinGenApi/IFloat.h",
"SpinGenApi/IInteger.h",
"SpinGenApi/IRegister.h",
"SpinGenApi/ISelector.h",
"SpinGenApi/Reference.h",
"SpinGenApi/INode.h",
"SpinGenApi/IPort.h",
"SpinGenApi/IString.h",
"SpinGenApi/IValue.h",
"SpinGenApi/Autovector.h",
"SpinGenApi/Base.h",
"SpinGenApi/Container.h",
"SpinGenApi/EnumClasses.h",
"SpinGenApi/Node.h",
"SpinGenApi/NodeMap.h",
"SpinGenApi/Synch.h",
"SpinGenApi/Types.h",
// "SpinGenApi/BooleanNode.h", // INode, ValueNode, IBoolean
// ...
// "SpinGenApi/SpinnakerGenApi.h"
},
link = {"Spinnaker@.2"},
includepath = "/usr/include/spinnaker"),
@Platform(value = "linux-arm",
link = "Spinnaker@.2"),
@Platform(value = "windows",
link = {"Spinnaker_v140"},
includepath = "C:/Program Files/FLIR Systems/Spinnaker/include/"),
@Platform(value = "windows-x86",
linkpath = {"C:/Program Files/FLIR Systems/Spinnaker/lib/vs2015/",
"C:/Program Files (x86)/FLIR Systems/Spinnaker/lib/vs2015/"},
preloadpath = {"C:/Program Files/FLIR Systems/Spinnaker/bin/vs2015/",
"C:/Program Files (x86)/FLIR Systems/Spinnaker/bin/vs2015/"}),
@Platform(value = "windows-x86_64",
linkpath = {"C:/Program Files/FLIR Systems/Spinnaker/lib64/vs2015/"},
preloadpath = {"C:/Program Files/FLIR Systems/Spinnaker/bin64/vs2015/"})})
public class GenICam implements InfoMapper {
public void map(InfoMap infoMap) {
infoMap
.put(new Info().enumerate())
.put(new Info(
// "SPINNAKER_LOCAL",
"SPINNAKER_API",
// GeniCam defs
"GC_W64", "GC_INT64_MAX", "GC_INT64_MIN", "GC_UINT64_MAX", "GC_INT32_MAX", "GC_INT32_MIN",
"GC_UINT32_MAX", "GC_INT8_MAX", "GC_INT8_MIN", "GC_UINT8_MAX",
"GCBASE_API", "GCBASE_RTTI_CLASS_API"
).cppTypes().annotations().cppText(""))
.put(new Info("GENICAM_GCC_VERSION").skip())
// // set to parse GCUtilities.h and skip definition of GENICAM_GCC_VERSION
// .put(new Info("defined (__GNUC__)").define(false))
// set to parse GCUtilities.h definition of __LINE_STR__ and __LOCATION__
.put(new Info("__LINE_STR__").cppText(""))
.put(new Info("__LOCATION__").cppText(""))
// // set to compile GCUtilities.h on windows
.put(new Info("defined(UNDER_RTSS)").define(false))
// GeniCamApi/Types.h
.put(new Info("interface").cppTypes().annotations().cppText(""))
.put(new Info("NO_UNDEFINEDED_REPRESENTATION").define())
// Skip due to problems with the return type "EAccessMode", it should be with namespace "Spinnaker::GenApi::EAccessMode"
// .put(new Info("Spinnaker::GenApi::IBase::GetAccessMode()").skip())
// .put(new Info("Spinnaker::GenApi::IBase").skip())
// "SpinGenApi/Container.h"
// TODO We may just need a stub for node_vector and value_vector so other code compiles
// (rather than disabling individual methods in node_vector and value_vector)
.put(new Info("Spinnaker::GenApi::node_vector::const_iterator").skip())
.put(new Info("Spinnaker::GenApi::node_vector::erase").skip())
.put(new Info("Spinnaker::GenApi::node_vector::begin").skip())
.put(new Info("Spinnaker::GenApi::node_vector::end").skip())
.put(new Info("Spinnaker::GenApi::node_vector::insert").skip())
.put(new Info("Spinnaker::GenApi::value_vector::const_iterator").skip())
.put(new Info("Spinnaker::GenApi::value_vector::erase").skip())
.put(new Info("Spinnaker::GenApi::value_vector::begin").skip())
.put(new Info("Spinnaker::GenApi::value_vector::end").skip())
.put(new Info("Spinnaker::GenApi::value_vector::insert").skip())
.put(new Info("Spinnaker::GenApi::IEnumerationT::const_iterator").skip())
.put(new Info("Spinnaker::GenApi::IEnumerationT::iterator").skip())
.put(new Info("Spinnaker::GenApi::IEnumerationT::erase").skip())
.put(new Info("Spinnaker::GenApi::IEnumerationT::begin").skip())
.put(new Info("Spinnaker::GenApi::IEnumerationT::end").skip())
.put(new Info("Spinnaker::GenApi::IEnumerationT::insert").skip())
// `typedef value_vector FeatureList_t`
.put(new Info("Spinnaker::GenApi::FeatureList_t")
.valueTypes("value_vector")
// .pointerTypes("@Cast(\"Spinnaker::GenApi::FeatureList_t*\") @ByPtrPtr value_vector")
// .pointerTypes("@Cast(\"Spinnaker::GenApi::FeatureList_t&\") value_vector")
)
// `typedef GenICam::gcstring_vector StringList_t`
.put(new Info("Spinnaker::GenApi::StringList_t").cast().pointerTypes("Pointer"))
// `typedef node_vector NodeList_t`
.put(new Info("Spinnaker::GenApi::NodeList_t").cast().pointerTypes("Pointer"))
// "SpinGenApi/ISelector.h"
// Ignore methods that cause JNI compilation issues: "Illegal indirection" (for FeatureList_t&)
.put(new Info("Spinnaker::GenApi::ISelector::GetSelectedFeatures").skip())
.put(new Info("Spinnaker::GenApi::ISelector::GetSelectingFeatures").skip())
// "SpinGenApi/Node.h"
.put(new Info("Spinnaker::GenApi::Node::GetSelectedFeatures").skip())
.put(new Info("Spinnaker::GenApi::Node::GetSelectingFeatures").skip())
.put(new Info("Spinnaker::GenApi::Node::NodeImpl").skip())
// "SpinGenApi/INode.h"
// .put(new Info("Spinnaker::GenApi::INode::asIReference").skip())
;
// // "SpinGenApi/EnumClasses.h"
// // `typedef enum _ENameSpace {...} ENameSpace` etc.
final String[] typedefEnums = {
"EAccessMode",
"ECachingMode",
"EDisplayNotation",
"EEndianess",
"EGenApiSchemaVersion",
"EIncMode",
"EInputDirection",
"EInterfaceType",
"ELinkType",
"ENameSpace",
"ERepresentation",
"ESign",
"ESlope",
"EStandardNameSpace",
"EVisibility",
"EXMLValidation",
"EYesNo"
};
for (String name : typedefEnums) {
String cppName = "Spinnaker::GenApi::" + name;
// String javaName = "_" + name;
// infoMap.put(
// new Info(cppName)
// .enumerate()
// .valueTypes(javaName)
// .pointerTypes("@Cast(\"" + cppName + "*\") @ByPtrPtr " + javaName)
// );
// infoMap.put(new Info(cppName).cast().pointerTypes("Pointer"));
}
}
} |
Strange, I'm not able to reproduce that with a simpler example. There must be something wrong going on with the macros or something somewhere. In any case, you can simplify all that assuming that it works, and I'll check it out when you have something cleaner to look at. Thanks! |
Since there is a workaround with The issue related probably to the fix (I did not see it before). The generated JNI code my not reference
Here is the part of the C++ header defining the
Another place in C++ API referring to virtual void GetChildren(GenApi::NodeList_t & Children, ELinkType LinkType = ctReadingChildren) const = 0; The JNI generated code:
compiler gives error: |
Looks that I closed this issue. It was not intentional. Wrong button. |
Hum, again I'm not able to reproduce in isolation that issue either. Could you try to figure out a minimal example that fails? |
One of the patterns of using C
enum
s is to use them in combination withtypedef
(for instance in Spinnaker API). Consider followingenum
definition.Using "new Info().enumerate()" a Java enum class named
_ENameSpace
is generated:But the usage in the original code (C++) is without underscore:
ENameSpace
. The request is to provide option to make javacpp to create class without "_", usingtypedef
nameENameSpace
.Note: following suggested in the mailing list does not work (will not create enum named
ENameSpace
)Note: a work around to make
_ENameSpace
work is to use:in Java code you then need to use
_ENameSpace
The text was updated successfully, but these errors were encountered: