Search in sources :

Example 1 with PermissionListener

use of org.odk.collect.permissions.PermissionListener in project collect by opendatakit.

the class ODKView method setDataForFields.

/**
 * Saves answers for the widgets in this view. Called when the widgets are in an intent group.
 */
public void setDataForFields(Bundle bundle) throws JavaRosaException {
    FormController formController = Collect.getInstance().getFormController();
    if (formController == null) {
        return;
    }
    if (bundle != null) {
        Set<String> keys = bundle.keySet();
        for (String key : keys) {
            Object answer = bundle.get(key);
            if (answer == null) {
                continue;
            }
            for (QuestionWidget questionWidget : widgets) {
                FormEntryPrompt prompt = questionWidget.getFormEntryPrompt();
                TreeReference treeReference = (TreeReference) prompt.getFormElement().getBind().getReference();
                if (treeReference.getNameLast().equals(key)) {
                    switch(prompt.getDataType()) {
                        case Constants.DATATYPE_TEXT:
                            formController.saveAnswer(prompt.getIndex(), ExternalAppsUtils.asStringData(answer));
                            ((StringWidget) questionWidget).setDisplayValueFromModel();
                            questionWidget.showAnswerContainer();
                            break;
                        case Constants.DATATYPE_INTEGER:
                            formController.saveAnswer(prompt.getIndex(), ExternalAppsUtils.asIntegerData(answer));
                            ((StringWidget) questionWidget).setDisplayValueFromModel();
                            questionWidget.showAnswerContainer();
                            break;
                        case Constants.DATATYPE_DECIMAL:
                            formController.saveAnswer(prompt.getIndex(), ExternalAppsUtils.asDecimalData(answer));
                            ((StringWidget) questionWidget).setDisplayValueFromModel();
                            questionWidget.showAnswerContainer();
                            break;
                        case Constants.DATATYPE_BINARY:
                            try {
                                Uri uri;
                                if (answer instanceof Uri) {
                                    uri = (Uri) answer;
                                } else if (answer instanceof String) {
                                    uri = Uri.parse(bundle.getString(key));
                                } else {
                                    throw new RuntimeException("The value for " + key + " must be a URI but it is " + answer);
                                }
                                permissionsProvider.requestReadUriPermission((Activity) getContext(), uri, getContext().getContentResolver(), new PermissionListener() {

                                    @Override
                                    public void granted() {
                                        File destFile = FileUtils.createDestinationMediaFile(formController.getInstanceFile().getParent(), ContentUriHelper.getFileExtensionFromUri(uri));
                                        // TODO might be better to use QuestionMediaManager in the future
                                        FileUtils.saveAnswerFileFromUri(uri, destFile, getContext());
                                        ((WidgetDataReceiver) questionWidget).setData(destFile);
                                        questionWidget.showAnswerContainer();
                                    }

                                    @Override
                                    public void denied() {
                                    }
                                });
                            } catch (Exception | Error e) {
                                Timber.w(e);
                            }
                            break;
                        default:
                            throw new RuntimeException(getContext().getString(R.string.ext_assign_value_error, treeReference.toString(false)));
                    }
                    break;
                }
            }
        }
    }
}
Also used : FormController(org.odk.collect.android.javarosawrapper.FormController) PermissionListener(org.odk.collect.permissions.PermissionListener) FormEntryPrompt(org.javarosa.form.api.FormEntryPrompt) Uri(android.net.Uri) ExternalParamsException(org.odk.collect.android.exception.ExternalParamsException) ActivityNotFoundException(android.content.ActivityNotFoundException) PlaybackFailedException(org.odk.collect.audioclips.PlaybackFailedException) JavaRosaException(org.odk.collect.android.exception.JavaRosaException) TreeReference(org.javarosa.core.model.instance.TreeReference) StringWidget(org.odk.collect.android.widgets.StringWidget) QuestionWidget(org.odk.collect.android.widgets.QuestionWidget) File(java.io.File)

Example 2 with PermissionListener

use of org.odk.collect.permissions.PermissionListener in project collect by opendatakit.

the class BackgroundAudioPermissionDialogFragment method onOKClicked.

private void onOKClicked(FragmentActivity activity) {
    permissionsProvider.requestRecordAudioPermission(activity, new PermissionListener() {

        @Override
        public void granted() {
            try {
                viewModel.grantAudioPermission();
            } catch (IllegalStateException e) {
                Timber.e(e);
                Toast.makeText(activity, "Could not start recording. Please reopen form.", Toast.LENGTH_LONG).show();
                activity.finish();
            }
        }

        @Override
        public void denied() {
            activity.finish();
        }
    });
}
Also used : PermissionListener(org.odk.collect.permissions.PermissionListener)

Example 3 with PermissionListener

use of org.odk.collect.permissions.PermissionListener in project collect by opendatakit.

the class InternalRecordingRequester method requestRecording.

@Override
public void requestRecording(FormEntryPrompt prompt) {
    permissionsProvider.requestRecordAudioPermission(activity, new PermissionListener() {

        @Override
        public void granted() {
            String quality = FormEntryPromptUtils.getBindAttribute(prompt, "quality");
            if (quality != null && quality.equals("voice-only")) {
                audioRecorder.start(prompt.getIndex(), Output.AMR);
            } else if (quality != null && quality.equals("low")) {
                audioRecorder.start(prompt.getIndex(), Output.AAC_LOW);
            } else {
                audioRecorder.start(prompt.getIndex(), Output.AAC);
            }
        }

        @Override
        public void denied() {
        }
    });
    formEntryViewModel.logFormEvent(AnalyticsEvents.AUDIO_RECORDING_INTERNAL);
}
Also used : PermissionListener(org.odk.collect.permissions.PermissionListener)

Example 4 with PermissionListener

use of org.odk.collect.permissions.PermissionListener in project collect by opendatakit.

the class FormEntryActivity method loadingComplete.

/**
 * Given a {@link FormLoaderTask} which has created a {@link FormController} for either a new or
 * existing instance, shows that instance to the user. Either launches {@link FormHierarchyActivity}
 * if an existing instance is being edited or builds the view for the current question(s) if a
 * new instance is being created.
 * <p>
 * May do some or all of these depending on current state:
 * - Ensures phone state permissions are given if this form needs them
 * - Cleans up {@link #formLoaderTask}
 * - Sets the global form controller and database manager for search()/pulldata()
 * - Restores the last-used language
 * - Handles activity results that may have come in while the form was loading
 * - Alerts the user of a recovery from savepoint
 * - Verifies whether an instance folder exists and creates one if not
 * - Initializes background location capture (only if the instance being loaded is a new one)
 */
@Override
public void loadingComplete(FormLoaderTask task, FormDef formDef, String warningMsg) {
    DialogFragmentUtils.dismissDialog(FormLoadingDialogFragment.class, getSupportFragmentManager());
    final FormController formController = task.getFormController();
    if (formController != null) {
        if (readPhoneStatePermissionRequestNeeded) {
            permissionsProvider.requestReadPhoneStatePermission(this, true, new PermissionListener() {

                @Override
                public void granted() {
                    readPhoneStatePermissionRequestNeeded = false;
                    loadForm();
                }

                @Override
                public void denied() {
                    finish();
                }
            });
        } else {
            formLoaderTask.setFormLoaderListener(null);
            FormLoaderTask t = formLoaderTask;
            formLoaderTask = null;
            t.cancel(true);
            t.destroy();
            Collect.getInstance().setFormController(formController);
            backgroundLocationViewModel.formFinishedLoading();
            Collect.getInstance().setExternalDataManager(task.getExternalDataManager());
            // Set the language if one has already been set in the past
            String[] languageTest = formController.getLanguages();
            if (languageTest != null) {
                String defaultLanguage = formController.getLanguage();
                Form form = formsRepository.getOneByPath(formPath);
                if (form != null) {
                    String newLanguage = form.getLanguage();
                    try {
                        formController.setLanguage(newLanguage);
                    } catch (Exception e) {
                        // if somehow we end up with a bad language, set it to the default
                        Timber.i("Ended up with a bad language. %s", newLanguage);
                        formController.setLanguage(defaultLanguage);
                    }
                }
            }
            boolean pendingActivityResult = task.hasPendingActivityResult();
            if (pendingActivityResult) {
                Timber.w("Calling onActivityResult from loadingComplete");
                formControllerAvailable(formController);
                onScreenRefresh();
                onActivityResult(task.getRequestCode(), task.getResultCode(), task.getIntent());
                return;
            }
            // it can be a normal flow for a pending activity result to restore from a savepoint
            // (the call flow handled by the above if statement). For all other use cases, the
            // user should be notified, as it means they wandered off doing other things then
            // returned to ODK Collect and chose Edit Saved Form, but that the savepoint for
            // that form is newer than the last saved version of their form data.
            boolean hasUsedSavepoint = task.hasUsedSavepoint();
            if (hasUsedSavepoint) {
                runOnUiThread(() -> showLongToast(this, R.string.savepoint_used));
            }
            if (formController.getInstanceFile() == null) {
                FormInstanceFileCreator formInstanceFileCreator = new FormInstanceFileCreator(storagePathProvider, System::currentTimeMillis);
                File instanceFile = formInstanceFileCreator.createInstanceFile(formPath);
                if (instanceFile != null) {
                    formController.setInstanceFile(instanceFile);
                } else {
                    showFormLoadErrorAndExit(getString(R.string.loading_form_failed));
                }
                formControllerAvailable(formController);
                identityPromptViewModel.requiresIdentityToContinue().observe(this, requiresIdentity -> {
                    if (!requiresIdentity) {
                        formController.getAuditEventLogger().logEvent(AuditEvent.AuditEventType.FORM_START, true, System.currentTimeMillis());
                        startFormEntry(formController, warningMsg);
                    }
                });
            } else {
                Intent reqIntent = getIntent();
                boolean showFirst = reqIntent.getBooleanExtra("start", false);
                if (!showFirst) {
                    // we've just loaded a saved form, so start in the hierarchy view
                    String formMode = reqIntent.getStringExtra(ApplicationConstants.BundleKeys.FORM_MODE);
                    if (formMode == null || ApplicationConstants.FormModes.EDIT_SAVED.equalsIgnoreCase(formMode)) {
                        formControllerAvailable(formController);
                        identityPromptViewModel.requiresIdentityToContinue().observe(this, requiresIdentity -> {
                            if (!requiresIdentity) {
                                if (!allowMovingBackwards) {
                                    // we aren't allowed to jump around the form so attempt to
                                    // go directly to the question we were on last time the
                                    // form was saved.
                                    // TODO: revisit the fallback. If for some reason the index
                                    // wasn't saved, we can now jump around which doesn't seem right.
                                    FormIndex formIndex = SaveFormIndexTask.loadFormIndexFromFile();
                                    if (formIndex != null) {
                                        formController.jumpToIndex(formIndex);
                                        onScreenRefresh();
                                        return;
                                    }
                                }
                                formController.getAuditEventLogger().logEvent(AuditEvent.AuditEventType.FORM_RESUME, true, System.currentTimeMillis());
                                formController.getAuditEventLogger().logEvent(AuditEvent.AuditEventType.HIERARCHY, true, System.currentTimeMillis());
                                startActivityForResult(new Intent(this, FormHierarchyActivity.class), RequestCodes.HIERARCHY_ACTIVITY);
                            }
                        });
                        formSaveViewModel.editingForm();
                    } else {
                        if (ApplicationConstants.FormModes.VIEW_SENT.equalsIgnoreCase(formMode)) {
                            startActivity(new Intent(this, ViewOnlyFormHierarchyActivity.class));
                        }
                        finish();
                    }
                } else {
                    formControllerAvailable(formController);
                    identityPromptViewModel.requiresIdentityToContinue().observe(this, requiresIdentity -> {
                        if (!requiresIdentity) {
                            formController.getAuditEventLogger().logEvent(AuditEvent.AuditEventType.FORM_RESUME, true, System.currentTimeMillis());
                            startFormEntry(formController, warningMsg);
                        }
                    });
                }
            }
        }
    } else {
        Timber.e("FormController is null");
        showLongToast(this, R.string.loading_form_failed);
        finish();
    }
}
Also used : FormController(org.odk.collect.android.javarosawrapper.FormController) PermissionListener(org.odk.collect.permissions.PermissionListener) FormInstanceFileCreator(org.odk.collect.android.formentry.loading.FormInstanceFileCreator) Form(org.odk.collect.forms.Form) Intent(android.content.Intent) RepeatsInFieldListException(org.odk.collect.android.javarosawrapper.RepeatsInFieldListException) JavaRosaException(org.odk.collect.android.exception.JavaRosaException) FormLoaderTask(org.odk.collect.android.tasks.FormLoaderTask) FormIndex(org.javarosa.core.model.FormIndex) File(java.io.File)

Example 5 with PermissionListener

use of org.odk.collect.permissions.PermissionListener in project collect by opendatakit.

the class QRCodeTabsActivity method onCreate.

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    DaggerUtils.getComponent(this).inject(this);
    menuDelegate = new QRCodeMenuDelegate(this, intentLauncher, qrCodeGenerator, appConfigurationGenerator, fileProvider, settingsProvider, scheduler);
    activityResultDelegate = new QRCodeActivityResultDelegate(this, settingsImporter, qrCodeDecoder, currentProjectProvider.getCurrentProject());
    setContentView(R.layout.tabs_layout);
    AppBarUtils.setupAppBarLayout(this, getString(R.string.reconfigure_with_qr_code_settings_title));
    menuDelegate = new QRCodeMenuDelegate(this, intentLauncher, qrCodeGenerator, appConfigurationGenerator, fileProvider, settingsProvider, scheduler);
    permissionsProvider.requestCameraPermission(this, new PermissionListener() {

        @Override
        public void granted() {
            setupViewPager();
        }

        @Override
        public void denied() {
            finish();
        }
    });
}
Also used : PermissionListener(org.odk.collect.permissions.PermissionListener)

Aggregations

PermissionListener (org.odk.collect.permissions.PermissionListener)5 File (java.io.File)2 JavaRosaException (org.odk.collect.android.exception.JavaRosaException)2 FormController (org.odk.collect.android.javarosawrapper.FormController)2 ActivityNotFoundException (android.content.ActivityNotFoundException)1 Intent (android.content.Intent)1 Uri (android.net.Uri)1 FormIndex (org.javarosa.core.model.FormIndex)1 TreeReference (org.javarosa.core.model.instance.TreeReference)1 FormEntryPrompt (org.javarosa.form.api.FormEntryPrompt)1 ExternalParamsException (org.odk.collect.android.exception.ExternalParamsException)1 FormInstanceFileCreator (org.odk.collect.android.formentry.loading.FormInstanceFileCreator)1 RepeatsInFieldListException (org.odk.collect.android.javarosawrapper.RepeatsInFieldListException)1 FormLoaderTask (org.odk.collect.android.tasks.FormLoaderTask)1 QuestionWidget (org.odk.collect.android.widgets.QuestionWidget)1 StringWidget (org.odk.collect.android.widgets.StringWidget)1 PlaybackFailedException (org.odk.collect.audioclips.PlaybackFailedException)1 Form (org.odk.collect.forms.Form)1