Changing Configuration at Runtime

You might want to change the configuration used to display your documents at runtime. Depending on how you've shown the document this can easily be achieved.

Changing the configuration of the PdfActivity.

In order to change the configuration of the PdfActivity you just call PdfActivity#setConfiguration which will take care of saving the state and recreating the activity with the new configuration.

Copy
DynamicConfigurationActivity.kt
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
class DynamicConfigurationActivity : PdfActivity() {

    override fun onPrepareOptionsMenu(menu: Menu): Boolean {
        super.onPrepareOptionsMenu(menu)
        menuInflater.inflate(R.menu.dynamic_configuration_menu, menu)
        return true
    }

    override fun onOptionsItemSelected(item: MenuItem): Boolean {
        var handled = false
        when (item.itemId) {
            R.id.toggle_scroll_direction -> {
                handled = true
                // Create configuration builder with configuration pre-filled from the current configuration.
                val newConfiguration = PdfActivityConfiguration.Builder(configuration)
                    .scrollDirection(
                        if (configuration.configuration.scrollDirection == PageScrollDirection.HORIZONTAL)
                            PageScrollDirection.VERTICAL
                        else
                            PageScrollDirection.HORIZONTAL)
                    .build()
                // Set configuration on the activity. This will recreate the activity similar to changing orientation or language.
                configuration = newConfiguration
            }
        }
        return handled || super.onOptionsItemSelected(item)
    }
}
Copy
DynamicConfigurationActivity.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
public class DynamicConfigurationActivity extends PdfActivity {

    @Override public boolean onPrepareOptionsMenu(Menu menu) {
        super.onPrepareOptionsMenu(menu);
        getMenuInflater().inflate(R.menu.dynamic_configuration_menu, menu);
        return true;
    }

    @Override public boolean onOptionsItemSelected(@NonNull MenuItem item) {
        boolean handled = false;
        PdfActivityConfiguration configuration = getConfiguration();
        switch (item.getItemId()) {
            case R.id.toggle_scroll_direction: {
                handled = true;
                // Create configuration builder with configuration pre-filled from the current configuration.
                PdfActivityConfiguration newConfiguration = new PdfActivityConfiguration.Builder(getConfiguration())
                        .scrollDirection(
                                configuration.getConfiguration().getScrollDirection() == PageScrollDirection.HORIZONTAL ?
                                        PageScrollDirection.VERTICAL :
                                        PageScrollDirection.HORIZONTAL)
                        .build();
                // Set configuration on the activity. This will recreate the activity similar to changing orientation or language.
                setConfiguration(newConfiguration);
                break;
            }
        }
        return handled || super.onOptionsItemSelected(item);
    }
}

Changing the configuration of the PdfFragment

In order to change the configuration of the PdfFragment you need to:

  1. Save the state of your current fragment using PdfFragment#getState.
  2. Create a new fragment with the desired configuration using PdfFragment#newInstance.
  3. Replace the original fragment with the new one.
  4. Restore the state using PdfFragment#setState.
Copy
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
/** The currently displayed PdfFragment. **/
private var fragment: PdfFragment? = null
    set(fragment) {
        // Remove previous fragment.
        this.fragment?.let {
            it.removeDocumentListener(this)
        }
        field = fragment
        if (fragment != null) {
            // Replace old fragment with a new one.
            supportFragmentManager
                .beginTransaction()
                .replace(R.id.fragmentContainer, fragment)
                .commit()
            // Register the activity to be notified when the document is loaded.
            fragment.addDocumentListener(this)
        }
    }

/** Switches between horizontal and vertical scrolling. */
private fun toggleScrollDirection() {
    val currentFragment = fragment
    val currentDocument = fragment?.document
    if (currentFragment == null || currentDocument == null || currentFragment.configuration == null) return

    val scrollDirection = currentFragment.configuration.scrollDirection

    // Copy existing configuration to a new configuration builder.
    val configurationBuilder = PdfConfiguration.Builder(currentFragment.configuration)

    // Toggle scroll direction.
    configurationBuilder.scrollDirection(
        if (scrollDirection == PageScrollDirection.HORIZONTAL)
            PageScrollDirection.VERTICAL
        else
            PageScrollDirection.HORIZONTAL)

    // Save old fragment state.
    val state = currentFragment.state
    // Create fragment with already loaded document and the new configuration.
    val newFragment = PdfFragment.newInstance(currentDocument, configurationBuilder.build())
    fragment = newFragment
    // Restore fragment state.
    newFragment.state = state
}
Copy
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
/** The currently displayed PdfFragment. **/
private PdfFragment fragment;

/** Replaces the currently displayed fragment. */
private void setFragment(@NonNull PdfFragment fragment) {
    // Remove previous fragment.
    if (this.fragment != null) {
        this.fragment.removeDocumentListener(this);
    }
    this.fragment = fragment;

    // Replace old fragment with a new one.
    getSupportFragmentManager()
            .beginTransaction()
            .replace(R.id.fragmentContainer, fragment)
            .commit();

    // Register the activity to be notified when the document is loaded.
    fragment.addDocumentListener(this);
}

/** Switches between horizontal and vertical scrolling. */
private void toggleScrollDirection() {
    if (fragment == null || fragment.getDocument() == null || fragment.getConfiguration() == null) return;

    PageScrollDirection scrollDirection = fragment.getConfiguration().getScrollDirection();

    // Copy existing configuration to a new configuration builder.
    PdfConfiguration.Builder configurationBuilder = new PdfConfiguration.Builder(fragment.getConfiguration());

    // Toggle scroll direction.
    configurationBuilder.scrollDirection(
            scrollDirection == PageScrollDirection.HORIZONTAL ?
                PageScrollDirection.VERTICAL :
                PageScrollDirection.HORIZONTAL);

    // Save old fragment state.
    Bundle state = fragment.getState();
    // Create fragment with already loaded document and the new configuration.
    PdfFragment newFragment = PdfFragment.newInstance(fragment.getDocument(), configurationBuilder.build());
    setFragment(newFragment);
    // Restore fragment state.
    newFragment.setState(state);
}

For more details you can check out the DynamicConfigurationExample and CustomFragmentDynamicConfigurationExample in the catalog app.