Android App Development: Håndtering Extra Kamera Capabilities

I tidligere tutorials vi så på å skrive kode for å få tilgang til den innebygde kameraet, forhåndsvise displayet, og lagre et bilde i en Android-applikasjon. Det er grunnleggende; men moderne smarttelefoner har ofte ganske kompliserte kameraer med en hel rekke funksjoner - blits, hvitbalanse, en rekke sceneinnstillinger, ulike Instagram-stil fotoeffekter, selv ansiktsgjenkjenning (håndteres bare i den nyeste Android utgivelse og ikke dekkes av denne tutorial). Sjekk ut Camera.Parameters API docs for hele Lowdown på de funksjonene du kan være i stand til å spille med. Den Camera.Parameters API kan du også finne ut hvilke funksjoner som støttes av maskinvaren din app skjer for å kjøre på. Når du vet hvilke parametre /funksjoner du har tilgjengelig, de er alle håndteres på en ganske lik måte. Les videre for å finne ut hvordan man skal håndtere dem.

Håndtering Flash

La oss begynne med å se på blitsen, som sannsynligvis er den mest brukte kamerafunksjonen. Vi vil skape en chooseFlash () metode for å sette opp blitsen valg alternativer:

 private void chooseFlash () {endelige Camera.Parameters params = camera.getParameters (); endelig List < String > flashModeList = params.getSupportedFlashModes (); if (flashModeList == null) {//no flash! komme tilbake; } Endelige CharSequence [] flashText = flashModeList.toArray (ny CharSequence [flashModeList.size ()]); AlertDialog.Builder byggmester = new AlertDialog.Builder (denne); builder.setTitle ("Velg flash type"); builder.setSingleChoiceItems (flashText, -1, ny DialogInterface.OnClickListener () {public void onClick (dialog DialogInterface, int hvilken) {params.setFlashMode (flashModeList.get (som)); camera.setParameters (params); dialog.dismiss ( );}}); endelig AlertDialog alert = builder.create (); alert.show ();} 

Før du gjør noe annet, må vi sjekke om det er noen som støttes blitsmodi i det hele tatt, med getSupportedFlashModes (). Hvis listen er tom, er det ingen blits, og vi kommer tilbake uten å gjøre noe.

Hvis det er blitsmodi, ønsker vi at brukeren kan velge én. Her bruker vi en AlertDialog å håndtere det, men du kan bruke et annet alternativ. Vi snur listen over blitsmodi (i streng skjema) i en CharSequence array, å passere inn AlertDialog.Builder, deretter bruke Builder metoder for å angi tittel og å skape en radioknapp valg (setSingleChoiceItems (), du kan også lage boksene eller bruke setItems () for en valgbar liste uten radioknappene).

Når brukeren velger deres foretrukne blitsmodus, bruker vi dialogen er OnClickListener å identifisere indeksen for det valgte elementet, og trekke dette elementet ut av String liste flashModeList å sette parameter. Fordi vi har oversatt flashModeList direkte inn i CharSequence matrise brukes i AlertDialog byggmester, vil indeksen av elementet valgt i AlertDialog være den samme som indeksen for den artikkelen i flashModeList.

Du
samtale camera.setParameters () etter params.setFlashMode () for å gjøre endringen faktisk trer i kraft. Vi deretter avslutte onClick () metoden ved avviser dialog og tilbake til hovedskjermen. Til slutt, etter å ha bygget dialogen, skaper vi og vise det.

Dynamiske oppsett

Det neste spørsmålet er hvordan man skal vise dette til brukeren. Vi kunne bare kjøre den automatisk på app oppstart, men det er ikke spesielt brukervennlig. Vi kan legge til noen XML i den statiske layout, men da det ville bli vist selv om enheten ikke har en flash, noe som er en stor sløsing med plass på skjermen og veldig brukervennlig uvennlig. I stedet kan vi bruke dynamisk layout -. Layout som forvaltes avhengig av hva som skjer i programmet

For å gjøre dette, la oss legge denne koden på slutten av chooseFlash () -metoden, erstatte alert.show ( ) linjen slik at vi bare vise velger flash typen listen hvis knappen klikkes

 LinearLayout lin = (LinearLayout) findViewById (R.id.linearlayout.); Button flashButton = new knappen (denne); flashButton.setText ("Flash"); flashButton.setLayoutParams (nye LayoutParams (LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT)); lin.addView (flashButton); flashButton.setOnClickListener (ny View.OnClickListener () {public void onClick (Vis v) {alert.show ();}}); 

Du må også legge til en ID-verdien til den overordnede LinearLayout i XML:

 < LinearLayout xmlns: android = "http://schemas.android.com/apk/res/android" android: id = "+ id /linearlayout" ... > 

kode griper en referanse til den overordnede LinearLayout, skaper en "Flash" -knappen, og legger det til layout, så viser AlertDialog når du trykker på knappen. Som du kan se her, kan du angi høyden og bredden på en knapp programmatisk ved hjelp setLayoutParams (). (Dette er ViewGroup.LayoutParams.) Et par av konstruktører er tilgjengelig; dette tar bredde og høyde. (Du kan bruke en av undergrupper av LayoutParams å få mer spesifikk når du bygger en layout.) Alle de andre egenskapene til en knapp kan også stilles programmatisk. Du kan for eksempel være lurt å sette på knappen for å vise et bilde i stedet for tekst ved hjelp setBackgroundDrawable () i stedet for setText () (eller bruk en ImageButton og setImageResource () i stedet).

Til slutt, vi hekte dette inn i vår setUpLayout () metode:

 private void setUpLayout () {//... som før chooseFlash ();} 

Compile og kjøre på maskinvaren for å teste det ut.

Scene sette

Det finnes en haug med andre kameraeffekter tilgjengelig i Android, selv om hardware tilgjengelighet selvfølgelig varierer med hvert håndsett. Disse inkluderer zoom, antibanding, scenemodus, fokusmodus, og så videre. Sjekk ut kamera Parameter docs for en full liste. De er alle satt og behandlet på samme måte, skjønt, så la oss ta en rask titt på et annet eksempel, sette scenemodus. Moduser inkluderer Partiet, portait, Landskap, Natt, etc - se getSceneMode () docs for flere muligheter. Den faktiske listen tilgjengelig vil variere med kameratypen

 private void chooseSceneMode () {endelige Camera.Parameters params = camera.getParameters (.); endelig List < String > sceneModeList = params.getSupportedSceneModes (); if (sceneModeList == null) {//ingen scene-modus tilgjengelig! komme tilbake; } Endelige CharSequence [] sceneModeText = sceneModeList.toArray (ny CharSequence [sceneModeList.size ()]); AlertDialog.Builder byggmester = new AlertDialog.Builder (denne); builder.setTitle ("Velg scene mode"); builder.setSingleChoiceItems (sceneModeText, -1, ny DialogInterface.OnClickListener () {public void onClick (dialog DialogInterface, int hvilken) {params.setSceneMode (sceneModeList.get (som)); camera.setParameters (params); dialog.dismiss ( );}}); endelig AlertDialog alert = builder.create (); LinearLayout lin = (LinearLayout) findViewById (R.id.linearlayout); Button sceneModeButton = new knappen (denne); sceneModeButton.setText ("Scene Mode"); sceneModeButton.setLayoutParams (nye LayoutParams (LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT)); lin.addView (sceneModeButton); sceneModeButton.setOnClickListener (ny View.OnClickListener () {public void onClick (Vis v) {alert.show ();}});} 

Som du kan se, er dette i utgangspunktet identisk med chooseFlash (). (Så mye, faktisk, at det ville være en god idé å faktor det ut i en chooseEffect () metoden og passerer i den type effekt du setter som en parameter. Prøv det ut som en nyttig øvelse og se hva andre effekter du kan plugge inn i den.)

Du vil nok også være lurt å se på bedre layout, som for tiden ikke er visuelt tiltalende, og ville få mindre så med flere knapper og effekter lagt til. Du kan for eksempel ønsker å ha en glidende meny, eller arrangere knappene på rad. I fremtidige tutorials, vil vi se nærmere på både statiske og dynamiske oppsett, og på menyer og alternativer som vises bare under visse omstendigheter eller når forespurt av brukeren.