Как указать и добавить пользовательский принтер в приложение для Android?
Я создаю приложение для Android. Часть желаемой функциональности приложения заключается в том, что пользователь может выбрать специальный принтер (давайте просто назовем его Transfer Printer), который передаст готовый к печати документ процессу, выполняющемуся на внешнем сервере.
Какие шаги необходимо предпринять, чтобы добавить пользовательский принтер в список принтеров на панели печати Android, доступный из опции «Печать» в меню «Переполнение»?
Желательно использовать существующую функциональность панели печати Android, а не, например, дополнительную опцию «Поделиться» в Селекторе приложений из-за соображений взаимодействия с пользователем; пользователь не будет интуитивно понятным нажимать кнопку «Поделиться», а не «Печать» для достижения желаемой функциональности.
Предыдущие исследованияЕстьсуществующий аналогичный вопрос который вызвал небольшой интерес, так как он был опубликован некоторое время назад. Аскер определил класс PrintManager как ведущего, но я считаю, чтоPrintService Класс, скорее всего, будет более плодотворным:
Служба печати отвечает за обнаружение принтеров, добавление обнаруженных принтеров, удаление добавленных принтеров и обновление добавленных принтеров.
На этой же странице подробно описаны Декларация и Конфигурация службы печати. Я сделал так, как показано ниже.
Попытка казниДекларация и КонфигурацияВ AndroidManifest.xml:
...
<application
... >
...
<service
android:name=".TransferPrintService"
android:permission="android.permission.BIND_PRINT_SERVICE"
android:enabled="true"
android:exported="false">
<intent-filter>
<action android:name="android.printservice.PrintService" />
</intent-filter>
<meta-data
android:name="android.printservice"
android:resource="@xml/transfer_print_service" />
</service>
</application>
Мета-данныеМне неясно, где именно должны быть указаны метаданные. Из раздела SERVICE_META_DATA страницы PrintService:
Эти метаданные должны ссылаться на ресурс XML, содержащий тег службы печати.
В res / xml / Transfer_print_service.xml:
<print-service
android:label="TransferPrintService"
android:vendor="Company Ltd." />
TransferPrintService ClassЭто создает пользовательский PrinterDiscoverySession. Моя цель на этом этапе - просто заставить принтер появиться на панели печати и работать оттуда.
public class TransferPrintService extends PrintService {
public TransferPrintService() {
}
@Override
public void onPrintJobQueued(PrintJob printJob) {
printJob.start();
printJob.complete();
}
@Override
public PrinterDiscoverySession onCreatePrinterDiscoverySession() {
return new TransferPrinterDiscoverySession(this);
}
@Override
public void onRequestCancelPrintJob(PrintJob printJob) {
}
}
Служба запускается в BroadcastReceiver с намерением ACTION_BOOT_COMPLETED.
TransferPrinterDiscoverySession ClassЭто на самом деле создает пользовательский принтер.
public class TransferPrinterDiscoverySession extends PrinterDiscoverySession {
private transferPrintService printService;
private static final String PRINTER = "Transfer Printer";
public transferPrinterDiscoverySession(TransferPrintService printService) {
this.printService = printService;
}
@Override
public void onStartPrinterDiscovery(List<PrinterId> printerList) {
PrinterId id = printService.generatePrinterId(PRINTER);
PrinterInfo.Builder builder =
new PrinterInfo.Builder(id, PRINTER, PrinterInfo.STATUS_IDLE);
PrinterInfo info = builder.build();
List<PrinterInfo> infos = new ArrayList<>();
infos.add(info);
addPrinters(infos);
}
@Override
public void onStopPrinterDiscovery() {
}
@Override
public void onValidatePrinters(List<PrinterId> printerIds) {
}
@Override
public void onStartPrinterStateTracking(PrinterId printerId) {
PrinterInfo.Builder builder = new PrinterInfo.Builder(printerId,
PRINTER, PrinterInfo.STATUS_IDLE);
PrinterCapabilitiesInfo.Builder capBuilder =
new PrinterCapabilitiesInfo.Builder(printerId);
capBuilder.addMediaSize(PrintAttributes.MediaSize.ISO_A4, true);
capBuilder.addResolution(new PrintAttributes.Resolution(
"Default", "Default", 360, 360), true);
capBuilder.setColorModes(PrintAttributes.COLOR_MODE_COLOR
+ PrintAttributes.COLOR_MODE_MONOCHROME,
PrintAttributes.COLOR_MODE_COLOR);
capBuilder.setMinMargins(PrintAttributes.Margins.NO_MARGINS);
PrinterCapabilitiesInfo caps = capBuilder.build();
builder.setCapabilities(caps);
PrinterInfo info = builder.build();
List<PrinterInfo> infos = new ArrayList<PrinterInfo>();
infos.add(info);
addPrinters(infos);
}
@Override
public void onStopPrinterStateTracking(PrinterId printerId) {
}
@Override
public void onDestroy() {
}
}
Основные проблемыЭто не создает дополнительную опцию принтера.Правильное ли расположение документов? В частности, имея<print-service>
тег в отдельном документе XML под res? Попытка разместить тег в любом месте документа AndroidManfiest.xml приводит к ошибкам IDE.Как мне позвонить в TransferPrintService? Например, предположим, что я в Chrome, я открываю меню Overflow и выбираю Print ... Какой PrintService вызывается? Как мне убедиться, что это мое?Я здесь на неправильном пути?