2013-01-22 14 views
18

Pracuję nad aplikacją na Androida, która musi drukować na drukarce. Zdecydowałem się na korzystanie z Google Cloud Print, ponieważ wydawało się łatwe do skonfigurowania. Początkowo postępowałem zgodnie z instrukcjami znalezionymi pod here dla integracji z Androidem. To działa tak, jak w przypadku drukowania do wybranej drukarki. Jednak proces ten jest nieco skomplikowany dla użytkownika. W moim przypadku proces wygląda następująco:Używanie interfejsu Google Cloud Print z Androidem

  1. Użytkownik wybiera przycisk drukowania, który został wyświetlony obok niektórych informacji.
  2. Zostanie wyświetlone okno dialogowe z podglądem tego, co zostanie wydrukowane. W pasku akcji znajduje się przycisk z napisem "Drukuj". To rozpoczyna proces.
  3. Wyświetlane jest nowe działanie z listą drukarek podłączonych do konta Google tego użytkownika. Użytkownik musi wybrać jeden.
  4. Zostanie wyświetlona nowa strona z opisem zadania drukowania.
  5. Użytkownik musi wybrać "Drukuj" w prawym górnym rogu.
  6. Zadanie drukowania zostaje uruchomione, a drukarka wydrukuje zdjęcie.

Niestety, mój klient nie chce tego procesu. Chcą, aby użytkownik kliknął "Drukuj" w kroku drugim, a następnie wydrukował zdjęcie (kroki 1, 2 i 6). W związku z tym nie mogę korzystać z intencji dostarczonej przez Google, muszę korzystać z rzeczywistego interfejsu API. Wymaga to ode mnie uzyskania tokena uwierzytelniania Google, pobrania żądanej drukarki i przesłania zadania drukowania w ten sposób. Wykonuję następujące czynności:

  1. Skorzystaj z usług Google Play, aby pobrać token OAuth dla konta Gmail użytkownika.
  2. Uzyskaj listę drukarek za pomocą wywołania funkcji API/search.
  3. Prześlij zadanie drukowania za pomocą wywołania funkcji API/submit.

Mam pierwsze dwa wykończone. Mam problem z faktycznym drukowaniem obrazu. Zamiast drukować obraz, drukowane są bajtowe dane obrazu (zakodowane w Base64). Oto kod, jak Ja was posyłam się wniosek:

ContentResolver contentResolver = context.getContentResolver(); 
try { 
    InputStream is = contentResolver.openInputStream(uri); 
    ByteArrayOutputStream baos = new ByteArrayOutputStream(); 

    byte[] buffer = new byte[4096]; 
    int n = is.read(buffer); 
    while (n >= 0) { 
      baos.write(buffer, 0, n); 
      n = is.read(buffer); 
    } 
    is.close(); 
    baos.flush(); 

    content = Base64.encodeToString(baos.toByteArray(), Base64.DEFAULT); 
} catch (FileNotFoundException e) { 
    Log.d(TAG, "File not found: " + uri.toString(), e); 
} catch (IOException e) { 
    e.printStackTrace(); 
} 

Ten kod pobiera plik (zmienna „uri” jest URI tego pliku) i zamienia ją w Base64 zakodowany ciąg. Jest to ta sama metoda, którą użyto w narzędziu PrintDialogActivity, dostępnym na stronie Google Cloud Print (z powyższymi linkami). Poniżej jak wyślę że up:

O ile wiem, tak właśnie powinno być. Otrzymuję odpowiedź {"success": true} podczas drukowania. Ale, jak wspomniałem powyżej, wypisuje rzeczywisty ciąg danych Base64. Każda pomoc będzie doceniona.

EDYCJA: Używając tego, co powiedziałem poniżej, udało mi się to naprawić.Zamiast używać powyższy kod, użyłem następujących czynności:

public void submitPrintJobWithFile(String printerId, String title, String token, String filePath, String contentType){ 
    File file = new File(filePath); 
    // Method that gets the correct headers 
    List<Header> headers = getHeaders(contentType, token); 
    // Method that gets the correct post parameters 
    String url = CLOUDPRINT_URL + PATH_SUBMIT; 
    List<NameValuePair> postParams = getParams(title, contentType); 
    String params = "access_token=" + token + "&cookies=false" + "&printerid=" + printerId; 
    url += params; 
    response = sendMultipartData(url, file, postParams, headers); 
} 

private String sendMultipartData(String url, File file, List<NameValuePair> fields, List<Header> headers){ 
    HttpPost post = new HttpPost(url); 
    MultipartEntity entity = new MultipartEntity(); 
    for(NameValuePair pair : fields){ 
     String name = pair.getName(); 
     String value = pair.getValue(); 
     try{ 
      entity.addPart(name, new StringBody(value)); 
     }catch (UnsupportedEncodingException e){ 
      Log.d(TAG, "Error turning pair (name=" + name + ", value=" + value + ") into StringBody."); 
    } 
    entity.addPart("content", new FileBody(file)); 
    post.setEntity(entity); 
    // Finish HttpClient request here... 
} 
+0

Czy możesz podać kilka próbek swojej pracy na temat pierwszych dwóch kroków? – Skiba

+0

Chcę zrobić to samo, ale bez kroku 3 Chcę wyświetlić drukarki, które są podłączone do tej samej sieci lokalnej i obsługują wyszukiwanie drukarki za pomocą jego adresu IP. –

+0

Witaj @ ariets może udostępnić krok u, którego należy przestrzegać, aby wypełnić 1 & 2 – SaravanaRaja

Odpowiedz

2

Wygląda na to trzeba użyć wieloczęściowy kodowanie, przykład tutaj:

http://blog.tacticalnuclearstrike.com/2010/01/using-multipartentity-in-android-applications/

FTA:

pliki potrzebne są apache-mime4j, httpclient, httpcore and httpmime. Wszystkie są projektami open source zbudowanymi przez fundację Apache.

Pobierz 4 pliki i dodaj je do swojego projektu, wtedy powinieneś być w stanie użyć następującego kodu, aby opublikować ciągi i pliki na stronach.

HttpClient httpclient = new DefaultHttpClient(); 
HttpPost httppost = new HttpPost("http://www.tumblr.com/api/write"); 

try { 
    MultipartEntity entity = new MultipartEntity(); 

    entity.addPart("type", new StringBody("photo")); 
    entity.addPart("data", new FileBody(image)); 
    httppost.setEntity(entity); 
    HttpResponse response = httpclient.execute(httppost); 
} catch (ClientProtocolException e) { 
} catch (IOException e) { 
} 

Zmienny obraz w tym przypadku jest to plik, który zawiera obraz rejestrowany przez kamerę w telefonie.

+1

To w rzeczywistości zadziałało. Dzięki. – ariets

1

Patrząc na metodzie Python Sample Code SubmitJob wydaje się, że tylko typs PDF musi być zakodowany w base64.

+0

Ach, masz rację. Nie wiem, jak to przegapiłem. Dam ci to. – ariets

+0

Pamiętaj, że to nie zadziałało. – ariets

0

Odpowiedzi na pytanie z niewielką aktualizacją. Od października 2013 r. W wersji 4.4 i bibliotece pomocy dostępne są metody obsługi drukowania. Zapoznaj się z poniższą dokumentacją, aby dowiedzieć się, jak to zrobić poprawnie: