从动态选择用户图库中的图像的代码,然后将图像显示在传递给函数的3d模型的表面上。 以下是主要活动中的函数调用:
@Override
public void onSurfaceCreated(GL10 gl, EGLConfig config) {
GLES20.glClearColor(0.1f, 0.1f, 0.1f, 1.0f);
// Prepare the rendering objects. This involves reading shaders, so may throw an IOException.
try {
// Create the texture and pass it to ARCore session to be filled during update().
backgroundRenderer.createOnGlThread(/*context=*/ this);
augmentedImageRenderer.createOnGlThread(/*context=*/ this);
} catch (IOException e) {
Log.e(TAG, "Failed to read an asset file", e);
}
}
在AugmentedImageRenderer文件中,该函数定义如下:
public void createOnGlThread(Context context) throws IOException {
corkboardObj.createOnGlThread(
context, "models/Test3.obj", "models/wood.png");
// imageFrameUpperLeft.setMaterialProperties(0.0f, 3.5f, 1.0f, 6.0f);
corkboardObj.setBlendMode(BlendMode.SourceAlpha);
paper.createOnGlThread(context, "models/PaperTest1.obj", "models/basketball.jpg");
}
函数draw(...)定义了如何将3d模型放置在真实世界空间中:
public void draw(
float[] viewMatrix,
float[] projectionMatrix,
AugmentedImage augmentedImage,
Anchor centerAnchor,
float[] colorCorrectionRgba) {
float[] tintColor =
convertHexToColor(TINT_COLORS_HEX[augmentedImage.getIndex() % TINT_COLORS_HEX.length]);
Pose[] localBoundaryPoses = {
Pose.makeTranslation(
-0.5f * augmentedImage.getExtentX(),
0.0f,
-0.5f * augmentedImage.getExtentZ()), // upper left
Pose.makeTranslation(
0.5f * augmentedImage.getExtentX(),
0.02f,
-0.5f * augmentedImage.getExtentZ()), // upper right
Pose.makeTranslation(
0.5f * augmentedImage.getExtentX(),
0.0f,
0.5f * augmentedImage.getExtentZ()), // lower right
Pose.makeTranslation(
-0.5f * augmentedImage.getExtentX(),
0.0f,
0.5f * augmentedImage.getExtentZ()) // lower left
};
Pose anchorPose = centerAnchor.getPose();
Pose[] worldBoundaryPoses = new Pose[4];
for (int i = 0; i < 4; ++i) {
worldBoundaryPoses[i] = anchorPose.compose(localBoundaryPoses[i]);
}
float scaleFactor = 1.0f;
float[] modelMatrix = new float[16];
worldBoundaryPoses[0].toMatrix(modelMatrix, 0);
corkboardObj.updateModelMatrix(modelMatrix, scaleFactor);
corkboardObj.draw(viewMatrix, projectionMatrix, colorCorrectionRgba, tintColor);
if (showPaper) {
worldBoundaryPoses[1].toMatrix(modelMatrix, 0);
paper.updateModelMatrix(modelMatrix, 0.05f);
paper.draw(viewMatrix, projectionMatrix, colorCorrectionRgba, tintColor);
}
}
添加了一段代码,让用户在触摸事件的主要活动中从照片库中进行选择:
@Override
public boolean onTouchEvent(MotionEvent event) {
//augmentedImageRenderer.drawPaper();
AlertDialog.Builder pictureDialog = new AlertDialog.Builder(this);
pictureDialog.setTitle("Select Action:");
String[] pictureDialogItems = {
"Select photo from gallery",
"Capture photo from camera" };
pictureDialog.setItems(pictureDialogItems, new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
switch (which){
case 0:
choosePhotoFromGallary();
break;
case 1:
takePhotoFromCamera();
break;
}
}
});
pictureDialog.show();
return super.onTouchEvent(event);
}
functions called when user action captured:
public void choosePhotoFromGallary(){
Intent galleryIntent = new Intent(Intent.ACTION_PICK,
MediaStore.Images.Media.EXTERNAL_CONTENT_URI);
startActivityForResult(galleryIntent, GALLERY);
}
private void takePhotoFromCamera() {
Intent cameraIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
startActivityForResult(cameraIntent, CAMERA);
}
@Override
public void onSurfaceChanged(GL10 gl, int width, int height) {
displayRotationHelper.onSurfaceChanged(width, height);
GLES20.glViewport(0, 0, width, height);
}
//activity result for receiveing data
@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (resultCode == this.RESULT_CANCELED) {
return;
}
if (requestCode == GALLERY) {
if (data != null) {
Uri contentURI = data.getData();
try {
Bitmap bitmap = MediaStore.Images.Media.getBitmap(this.getContentResolver(), contentURI);
String path = saveImage(bitmap);
augmentedImageRenderer.drawPaper();
} catch (IOException e) {
e.printStackTrace();
}
}
} else if (requestCode == CAMERA) {
Bitmap thumbnail = (Bitmap) data.getExtras().get("data");
saveImage(thumbnail);
}
}
我的问题是:
public void createOnGlThread(Context context)
在代码中,它只识别要传递的本机路径(例如models / XXX.jpg),它适用于app文件夹内的路径。该代码不适用于从电话传入的absoulute路径(例如resources / media / photo / XXX.jpg)抛出错误。外部读写权限已添加到清单文件中。