presentation-api ionic7 capacitor5 Solution (Android Only)

Development purpose

During point of sale (POS) development,

it was necessary to print on-screen receipts for customers (secondary screen).

There are usually Android products that are sold back(1st screen) and forth(2nd screen).

My device was an IMIN dual product.

It is easy to develop using PRESENTATION-API,

but unfortunately, it was difficult to find data for IONIC. (I don’t think there is one at the moment)

 

I’ve been looking for modules for a long time,

but I couldn’t find any new modules.

I am writing this because I think there are people who are having a hard time like me.

It works well, but it’s not clean code. Use only if you are really in a hurry.

Version Problem


There were no modules that I could use yet,
so I was looking for a way and found a solution.
It is not a standard method,
but it is useful for those who are in a hurry until the next version is released.

The modules currently supported by ionic are as follows.

01. https://github.com/TheeMachine/presentation-capacitor

Supports capacitor 4 and lower versions. Capacitor 5 is not supported.

02. https://github.com/fraunhoferfokus/cordova-plugin-presentation

It’s too old version to use.

 

Solution


Since Java supports presentation API, I tried coding using it in combination.

I’ve never used Java before,

so I thought about it after watching a basic video.

Since I didn’t have time,

I just made it so that it could be linked.

My idea was to create IONIC and then add PRESENTATION-API to the source file of Android Studio.


STEP 1. Make a Java Class (SecondaryDisplay.java)

01. APP > JAVA > COM.BLABLA.POS <-- YOUR DIRECTORY
02. ADD CLASS: NEW > Java Class > SecondaryDisplay
package com.brandkor.poscashier;

import android.app.Presentation;
import android.content.Context;
import android.os.Bundle;
import android.view.Display;

public class SecondaryDisplay extends Presentation {
  public SecondaryDisplay(Context outerContext, Display display) {
    super(outerContext, display);
  }

  @Override
  protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.secondary_display);
  }
}

STEP 2. Make a Layout (secondary_display.xml)

01. APP > res > layout
02. ADD CLASS: NEW > layout Resource file

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
  xmlns:tools="http://schemas.android.com/tools"
  xmlns:app="http://schemas.android.com/apk/res-auto"
  android:layout_width="match_parent"
  android:layout_height="match_parent"
  tools:context=".SecondaryDisplay"
  android:background="#fef1ed">

  <ImageView
    android:id="@+id/imageView"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:layout_centerInParent="true"
    android:src="@drawable/customer_display" <--- Your Image (Copy res/drawable/customer_display.jpg)
    />
</RelativeLayout>


STEP3. MainActivity.java

package com.brandkor.poscashier;

import android.content.Context;
import android.content.SharedPreferences;
import android.hardware.display.DisplayManager;
import android.os.Bundle;
import android.os.Handler;
import android.util.Log;
import android.view.Display;

import androidx.annotation.Nullable;

import com.getcapacitor.BridgeActivity;

import java.util.Timer;
import java.util.TimerTask;

public class MainActivity extends BridgeActivity {
 public DisplayManager displayManager = null;
 public Display[] presentationDisplays = null;

 private Handler mHandler = new Handler();

 SecondaryDisplay secondaryDisplay = null;

 @Override
 protected void onCreate(@Nullable Bundle savedInstanceState) {
  super.onCreate(savedInstanceState);
  displayManager = (DisplayManager)getSystemService(Context.DISPLAY_SERVICE);
  if (displayManager!= null) {
   // dual monitor only
   presentationDisplays = displayManager.getDisplays(DisplayManager.DISPLAY_CATEGORY_PRESENTATION);
   if (presentationDisplays.length > 0) {
   secondaryDisplay = new SecondaryDisplay(MainActivity.this, presentationDisplays[0]);
   secondaryDisplay.show();
   Timer timer = new Timer();
   timer.scheduleAtFixedRate(new TimerTask() {
   @Override
   public void run() {
   mHandler.post(new Runnable() {
   public void run() {
   String key = "storageCustomerDisplayFlag";
   SharedPreferences preferences = getSharedPreferences("CapacitorStorage", MODE_PRIVATE);
   String value = preferences.getString(key, "0");
   if (value == "") {
   value = "0";
   }
   if (Integer.parseInt(value) == 1) {
   secondaryDisplay.dismiss();
   } else {
   secondaryDisplay.show();
   }
  }
  });
  }
  }, 0, 1000);
  }
  }
 }
}
// End Source

I didn’t know how to communicate between IONIC and JAVA,

so I used a timer to periodically exchange data.

Data exchange was sent and received through SharedPreferences.

When accessing with JAVA, getSharedPreferences(“CapacitorStorage“, MODE_PRIVATE);

You need to write . The sauce is very simple. SharedPreferences values ​​are read periodically using a timer.

When it is a specific flag, the screen is lowered to DISMISS, and when it is a specific flag, it is SHOW again.

The meaning of DISMISS is that the existing IONIC pop-up can be displayed on the 2ND SCREEN.

This is because dual monitors are usually mirrored.

Now in IONIC

await Preferences.set({ key: env.EnumStorageKey.closedBusiness, value: `${this.mCashup.day}`, });

Just change the flag like this.

Leave a Comment