Você está na página 1de 62

CRIANDO APPS PARA EMPRESAS

COM ANDROID

LUIZTOOLS.COM.BR

0
Código 1: disponível em luiztools.com.br/livro-android-fontes

public class ​MainActivity ​extends ​AppCompatActivity {

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

Código 2: disponível em luiztools.com.br/livro-android-fontes

<​TextView
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"
​android​:text=​"Hello world!" ​/>

Código 3: disponível em luiztools.com.br/livro-android-fontes

public class ​MainActivity ​extends ​AppCompatActivity {

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

Código 4: disponível em luiztools.com.br/livro-android-fontes

<​RelativeLayout ​xmlns:​android​=​"http://schemas.android.com/apk/res/android"
​xmlns:​tools​=​"http://schemas.android.com/tools"
​android​:layout_width=​"match_parent"
​android​:layout_height=​"match_parent"
​android​:paddingLeft=​"@dimen/activity_horizontal_margin"
​android​:paddingRight=​"@dimen/activity_horizontal_margin"
​android​:paddingTop=​"@dimen/activity_vertical_margin"
​android​:paddingBottom=​"@dimen/activity_vertical_margin"
​tools​:context=​".MainActivity"​>

<​TextView
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"
​android​:text=​"Hello World!" ​/>
</​RelativeLayout​>

Código 5: disponível em luiztools.com.br/livro-android-fontes

1
<​Button
​android​:layout_width=​"100dp"
​android​:layout_height=​"50dp"
​android​:text=​"Centro"
​android​:id=​"@+id/btnCentro"
​android​:layout_centerHorizontal=​"true"
​android​:layout_centerVertical=​"true" ​/>

Código 6: disponível em luiztools.com.br/livro-android-fontes

<​Button
​android​:layout_width=​"100dp"
​android​:layout_height=​"50dp"
​android​:text=​"Norte"
​android​:id=​"@+id/btnNorte"
​android​:layout_centerHorizontal=​"true"
​android​:layout_above=​"@+id/btnCentro"​/>

Código 7: disponível em luiztools.com.br/livro-android-fontes

<​Button
​android​:layout_width=​"100dp"
​android​:layout_height=​"50dp"
​android​:text=​"Sul"
​android​:id=​"@+id/btnSul"
​android​:layout_below=​"@+id/btnCentro"
​android​:layout_centerHorizontal=​"true" ​/>

Código 8: disponível em luiztools.com.br/livro-android-fontes

<​Button
​android​:layout_width=​"100dp"
​android​:layout_height=​"50dp"
​android​:text=​"Leste"
​android​:id=​"@+id/btnLeste"
​android​:layout_below=​"@+id/btnNorte"
​android​:layout_toRightOf=​"@+id/btnCentro" ​/>

<​Button
​android​:layout_width=​"100dp"
​android​:layout_height=​"50dp"
​android​:text=​"Oeste"
​android​:id=​"@+id/btnOeste"
​android​:layout_below=​"@+id/btnNorte"
​android​:layout_toLeftOf=​"@+id/btnCentro" ​/>

Código 9: disponível em luiztools.com.br/livro-android-fontes

2
<​LinearLayout ​xmlns:​android​=​"http://schemas.android.com/apk/res/android"
​android​:orientation=​"vertical"
​android​:layout_width=​"match_parent"
​android​:layout_height=​"match_parent"​>

</​LinearLayout​>

Código 10: disponível em luiztools.com.br/livro-android-fontes

<​LinearLayout ​xmlns:​android​=​"http://schemas.android.com/apk/res/android"
​android​:orientation=​"vertical"
​android​:layout_width=​"match_parent"
​android​:layout_height=​"match_parent"​>

<​LinearLayout
​android​:orientation=​"horizontal"
​android​:layout_width=​"match_parent"
​android​:layout_height=​"wrap_content"​></​LinearLayout​>

<​LinearLayout
​android​:orientation=​"horizontal"
​android​:layout_width=​"match_parent"
​android​:layout_height=​"wrap_content"​></​LinearLayout​>

<​LinearLayout
​android​:orientation=​"horizontal"
​android​:layout_width=​"match_parent"
​android​:layout_height=​"wrap_content"​></​LinearLayout​>

</​LinearLayout​>

Código 11: disponível em luiztools.com.br/livro-android-fontes

<​LinearLayout
​android​:orientation=​"horizontal"
​android​:layout_width=​"match_parent"
​android​:layout_height=​"wrap_content"​>

<​TextView
​android​:layout_width=​"150dp"
​android​:layout_height=​"50dp"
​android​:textAppearance=​"?android:attr/textAppearanceLarge"
​android​:text=​"Nome:"
​android​:id=​"@+id/textView" ​/>

<​EditText
​android​:layout_width=​"match_parent"
​android​:layout_height=​"50dp"
​android​:id=​"@+id/editText" ​/>

</​LinearLayout​>

3
Código 12: disponível em luiztools.com.br/livro-android-fontes

<​LinearLayout
​android​:orientation=​"horizontal"
​android​:layout_width=​"match_parent"
​android​:layout_height=​"wrap_content"​>

<​TextView
​android​:layout_width=​"150dp"
​android​:layout_height=​"50dp"
​android​:textAppearance=​"?android:attr/textAppearanceLarge"
​android​:text=​"Endereço:"
​android​:id=​"@+id/textView2" ​/>

<​EditText
​android​:layout_width=​"match_parent"
​android​:layout_height=​"50dp"
​android​:id=​"@+id/editText2" ​/>

</​LinearLayout​>

Código 13: disponível em luiztools.com.br/livro-android-fontes

<​LinearLayout
​android​:orientation=​"horizontal"
​android​:layout_width=​"match_parent"
​android​:layout_height=​"wrap_content"​>

<​Button
​android​:layout_width=​"100dp"
​android​:layout_height=​"50dp"
​android​:text=​"Cancelar"
​android​:id=​"@+id/button"​/>

<​Button
​android​:layout_width=​"100dp"
​android​:layout_height=​"50dp"
​android​:text=​"Salvar"
​android​:id=​"@+id/button2"​/>

</​LinearLayout​>

Código 14: disponível em luiztools.com.br/livro-android-fontes

<​TextView
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"
​android​:textAppearance=​"?android:attr/textAppearanceLarge"
​android​:text=​"Texto Grande"
​android​:id=​"@+id/lblTeste" ​/>

4
Código 15: disponível em luiztools.com.br/livro-android-fontes

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

TextView lblTeste = (TextView)findViewById(R.id.​lblTeste​);


String teste = lblTeste.getText().toString();
lblTeste.setText(​"Outro teste"​);
}

Código 16: disponível em luiztools.com.br/livro-android-fontes

<​EditText
​android​:layout_width=​"match_parent"
​android​:layout_height=​"wrap_content"
​android​:inputType=​"textPersonName"
​android​:text=​""
​android​:id=​"@+id/txtTeste"​/>

Código 17: disponível em luiztools.com.br/livro-android-fontes

EditText​ txtTeste = (​EditText​)findViewById(R.id.​txtTeste​);


String texto = txtTeste.getText().toString();
txtTeste.setText(​"Novo teste"​);

Código 18: disponível em luiztools.com.br/livro-android-fontes

<​EditText
​android​:layout_width=​"match_parent"
​android​:layout_height=​"wrap_content"​>
<​requestFocus ​/>
</​EditText​>

Código 19: disponível em luiztools.com.br/livro-android-fontes

<​Button
​android​:layout_width=​"wrap_content"

5
​android​:layout_height=​"wrap_content"
​android​:text=​"Botão"
​android​:id=​"@+id/btnTeste" ​/>

Código 20: disponível em luiztools.com.br/livro-android-fontes

<​Button
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"
​android​:text=​"Botão"
​android​:id=​"@+id/btnTeste"
​android​:onClick=​"exibirMensagem" ​/>

Código 21: disponível em luiztools.com.br/livro-android-fontes

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

public void ​exibirMensagem(View v){


Toast.​makeText​(​this​, ​"Exemplo!"​, Toast.​LENGTH_LONG​).show();
}

Código 22: disponível em luiztools.com.br/livro-android-fontes

<​ImageButton
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"
​android​:src=​"@drawable/salvar"
​android​:onClick=​"salvar"
​android​:id=​"@+id/btnImagem"​/>

Código 23: disponível em luiztools.com.br/livro-android-fontes

<​Spinner
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"
​android​:id=​"@+id/spinner" ​/>

6
Código 24: disponível em luiztools.com.br/livro-android-fontes

<?​xml version=​"1.0" ​encoding=​"utf-8"​?>


<​resources​>
<​string-array ​name=​"estados"​>
<​item​>RS</​item​>
<​item​>SC</​item​>
<​item​>PR</​item​>
</​string-array​>
</​resources​>

Código 25: disponível em luiztools.com.br/livro-android-fontes

<​Spinner
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"
​android​:id=​"@+id/spinner"
​android​:entries=​"@array/estados"​/>

Código 26: disponível em luiztools.com.br/livro-android-fontes

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

String[] array = {​"RS"​,​"SC"​,​"PR"​};


ArrayAdapter<String> adapter = ​new ​ArrayAdapter<>(​this​,
android.R.layout.​simple_spinner_item​, array);
Spinner spinner = (Spinner)findViewById(R.id.​spinner​);
spinner.setAdapter(adapter);
}

Código 27: disponível em luiztools.com.br/livro-android-fontes

//carrega o spinner em uma variável local


Spinner spinner = (Spinner)findViewById(R.id.​spinner​);
//pega o item selecionado do Spinner em formato texto
String uf = spinner.getSelectedItem().toString();

7
//muda o item selecionado do spinner passando a posição
spinner.setSelection(​1​);

Código 28: disponível em luiztools.com.br/livro-android-fontes

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

String[] array = {​"RS"​,​"SC"​,​"PR"​};


ArrayAdapter<String> adapter = ​new ​ArrayAdapter<>(​this​,
android.R.layout.​simple_spinner_item​, array);
​final ​Spinner spinner = (Spinner)findViewById(R.id.​spinner​);
spinner.setAdapter(adapter);

spinner.setOnItemSelectedListener(​new ​Spinner.OnItemSelectedListener() {
​@Override
​public void ​onItemSelected(AdapterView<?> parent, View view, i​ nt ​position, ​long ​id) {
String uf = ​spinner​.getSelectedItem().toString();
Toast.​makeText​(getBaseContext(), ​"UF selecionado: " ​+ uf,
Toast.​LENGTH_LONG​).show();
}

​@Override
​public void ​onNothingSelected(AdapterView<?> parent) {

}
});
}

Código 29: disponível em luiztools.com.br/livro-android-fontes

public class ​Estado {


​private ​String ​nome​;
​private ​String ​sigla​;

​public ​Estado(String nome, String sigla){


​this​.​nome ​= nome;
​this​.​sigla ​= sigla;
}

​public ​String getNome(){ ​return this​.​nome​; }


​public ​String getSigla(){ ​return this​.​sigla​; }

8
​@Override
​public ​String toString(){ ​return this​.​nome​; }
}

Código 30: disponível em luiztools.com.br/livro-android-fontes

List<Estado> array = ​new ​ArrayList<>();


array.add(​new ​Estado(​"Rio Grande do Sul"​, ​"RS"​));
array.add(​new ​Estado(​"Santa Catarina"​, "​ SC"​));
array.add(​new ​Estado(​"Paraná"​, ​"PR"​));

ArrayAdapter<Estado> adapter = ​new ​ArrayAdapter<>(​this​,


android.R.layout.​simple_spinner_item​, array);
final ​Spinner spinner = (Spinner)findViewById(R.id.​spinner​);
spinner.setAdapter(adapter);

Código 31: disponível em luiztools.com.br/livro-android-fontes

spinner.setOnItemSelectedListener(​new S​ pinner.OnItemSelectedListener() {
​@Override
​public void ​onItemSelected(AdapterView<?> parent, View view, i​ nt ​position, ​long ​id) {
Estado uf = (Estado)​spinner​.getSelectedItem();
Toast.​makeText​(getBaseContext(), ​"UF selecionado: " ​+ uf.getSigla(),
Toast.​LENGTH_LONG​).show();
}

​@Override
​public void ​onNothingSelected(AdapterView<?> parent) {

}
});

Código 32: disponível em luiztools.com.br/livro-android-fontes

<​RadioGroup
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"
​android​:orientation=​"horizontal"
​android​:id=​"@+id/grpSexo"​>
</​RadioGroup​>

9
Código 33: disponível em luiztools.com.br/livro-android-fontes

<​RadioGroup
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"
​android​:orientation=​"horizontal"
​android​:id=​"@+id/grpSexo"​>

<​RadioButton
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"
​android​:text=​"Masculino"
​android​:id=​"@+id/radMasculino"​/>

<​RadioButton
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"
​android​:text=​"Feminino"
​android​:id=​"@+id/radFeminino"​/>

</​RadioGroup​>

Código 34: disponível em luiztools.com.br/livro-android-fontes

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

RadioButton radMasculino = (RadioButton)findViewById(R.id.​radMasculino​);


RadioButton radFeminino = (RadioButton)findViewById(R.id.​radFeminino​);
​if​(radMasculino.isSelected()) {
​//o sexo masculino foi selecionado durante o cadastro
​}
​else if​(radFeminino.isSelected()){
​//o sexo feminino foi selecionado durante o cadastro
​}
}

Código 35: disponível em luiztools.com.br/livro-android-fontes

10
radMasculino​.setOnCheckedChangeListener(​new ​RadioButton.OnCheckedChangeListener() {
​@Override
​public void ​onCheckedChanged(CompoundButton buttonView, ​boolean ​isChecked) {
​//esse método dispara no instante que o radio masculino for selecionado!
​}
});

Código 36: disponível em luiztools.com.br/livro-android-fontes

<​CheckBox
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"
​android​:checked=​"true"
​android​:text=​"Desejo receber informativos"
​android​:id=​"@+id/chkReceberInformativos"​/>

Código 37: disponível em luiztools.com.br/livro-android-fontes

//carrega o widget para uma variável local


CheckBox chkReceberInformativos = (CheckBox)findViewById(R.id.​chkReceberInformativos​);
//obtém a informação se foi selecionado ou não
boolean ​selecionado = chkReceberInformativos.isSelected();
//altera o estado selecionado do checkbox
chkReceberInformativos.setSelected(​true​);

Código 38: disponível em luiztools.com.br/livro-android-fontes

chkReceberInformativos​.setOnClickListener(​new ​CheckBox.OnClickListener() {
​@Override
​public void ​onClick(View v) {
​boolean ​selecionado = ​chkReceberInformativos​.isSelected();
​//método dispara no instante em que o checkbox foi clicado
​}
});

Código 39: disponível em luiztools.com.br/livro-android-fontes

<​ImageView
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"

11
​android​:src=​"@drawable/arsenal"
​android​:id=​"@+id/imageView"​/>

Código 40: disponível em luiztools.com.br/livro-android-fontes

ImageView​ imageView = (​ImageView​)findViewById(R.id.​imageView​);


File storageDir =
Environment.​getExternalStoragePublicDirectory​(Environment.​DIRECTORY_DOWNLOADS​);
String foto = storageDir + File.​pathSeparator ​+ ​"imagem.jpg"​;
Bitmap bitmap = BitmapFactory.​decodeFile​(foto);
imageView.setImageBitmap(bitmap);

Código 41: disponível em luiztools.com.br/livro-android-fontes

ImageView​ imageView = (​ImageView​)findViewById(R.id.​imageView​);


imageView.setImageResource(R.drawable.imagem1);

Código 42: disponível em luiztools.com.br/livro-android-fontes

<​RelativeLayout ​xmlns:​android​=​"http://schemas.android.com/apk/res/android"
​xmlns:​tools​=​"http://schemas.android.com/tools" ​android​:layout_width=​"match_parent"
​android​:layout_height=​"match_parent"
android​:paddingLeft=​"@dimen/activity_horizontal_margin"
​android​:paddingRight=​"@dimen/activity_horizontal_margin"
​android​:paddingTop=​"@dimen/activity_vertical_margin"
​android​:paddingBottom=​"@dimen/activity_vertical_margin"
tools​:context=​".MainActivity"​>

<​EditText
​android​:layout_width=​"fill_parent"
​android​:layout_height=​"45dp"
​android​:maxLength=​"10"
​android​:id=​"@+id/txtPesquisa"
​android​:layout_alignParentTop=​"true"
​android​:layout_alignParentLeft=​"true" /​ >

<​Button
​android​:layout_width=​"80dp"
​android​:layout_height=​"45dp"
​android​:text=​"Buscar"
​android​:onClick=​"btnBuscar_OnClick"
​android​:id=​"@+id/btnBuscar"
​android​:layout_alignParentTop=​"true"

12
​android​:layout_alignParentRight=​"true" ​/>

<​ListView
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"
​android​:id=​"@+id/lstResultados"
​android​:layout_below=​"@+id/txtPesquisa"
​android​:layout_marginTop=​"10dp"​/>
</​RelativeLayout​>

Código 43: disponível em luiztools.com.br/livro-android-fontes

ListView​ ​lstResultados​;
EditText ​txtPesquisa​;
Button ​btnBuscar​;
String[] ​cidades ​= { ​"Porto Alegre"​, ​"Florianópolis"​, ​"Curitiba"​, ​"São Paulo" ​};

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

​txtPesquisa ​= (EditText)findViewById(R.id.​txtPesquisa​);
​btnBuscar ​= (Button)findViewById(R.id.​btnBuscar)​ ;
​lstResultados ​= (​ListView​)findViewById(R.id.​lstResultados​);
}

public void ​btnBuscar_OnClick(View v){


String busca = ​txtPesquisa​.getText().toString();
List<String> encontradas = ​new A ​ rrayList<>();
​for​(String cidade : ​cidades​){
​if​(cidade.contains(busca)) encontradas.add(cidade);
}
ArrayAdapter<String> adapter =
​new ​ArrayAdapter<>(getBaseContext(), android.R.layout.​simple_list_item_1​,
encontradas);
​lstResultados​.setAdapter(adapter);
}

Código 44: disponível em luiztools.com.br/livro-android-fontes

@Override
protected void ​onCreate(Bundle savedInstanceState) {
​super​.onCreate(savedInstanceState);

13
setContentView(R.layout.​activity_main​);

​txtPesquisa ​= (EditText)findViewById(R.id.​txtPesquisa​);
​btnBuscar ​= (Button)findViewById(R.id.​btnBuscar)​ ;
​lstResultados ​= (ListView)findViewById(R.id.​lstResultados​);
​lstResultados​.setOnItemClickListener(​new ​ListView.OnItemClickListener() {
​public void ​onItemClick(AdapterView<?> parent, View view, ​int ​position, ​long ​id) {
String cidade = ​lstResultados​.getItemAtPosition(position).toString();
Toast.​makeText​(getBaseContext(), ​"Item " ​+ cidade, Toast.​LENGTH_LONG​).show();
}
});
}

Código 45: disponível em luiztools.com.br/livro-android-fontes

<?​xml version=​"1.0" ​encoding=​"utf-8"​?>


<​RelativeLayout
​xmlns:​android​=​"http://schemas.android.com/apk/res/android"
​android​:layout_width=​"match_parent"
​android​:layout_height=​"match_parent"
​android​:layout_margin=​"10dp"​>

<​ImageView
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"
​android​:id=​"@+id/imgCidade"
​android​:src=​"@drawable/florianopolis"
​android​:layout_marginRight=​"10dp"
​android​:layout_alignParentTop=​"true"
​android​:layout_alignParentLeft=​"true" /​ >

<​TextView
​android​:​layout_width​=​"wrap_content"
​android​:layout_height=​"wrap_content"
​android​:textAppearance=​"?android:attr/textAppearanceLarge"
​android​:text=​"Florianópolis"
​android​:id=​"@+id/lblCidade"
​android​:layout_alignParentTop=​"true"
​android​:layout_toRightOf=​"@+id/imgCidade" ​/>

<​TextView
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"
​android​:textAppearance=​"?android:attr/textAppearanceLarge"
​android​:text=​"/SC"
​android​:id=​"@+id/lblUF"

14
​android​:layout_alignParentTop=​"true"
​android​:layout_marginLeft=​"10dp"
​android​:layout_toRightOf=​"@+id/lblCidade"​/>

<​TextView
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"
​android​:textAppearance=​"?android:attr/textAppearanceMedium"
​android​:text=​"Capital de Santa Catarina"
​android​:id=​"@+id/lblDescricao"
​android​:textColor=​"@android:color/darker_gray"
​android​:layout_below=​"@+id/lblCidade"
​android​:layout_toRightOf=​"@+id/imgCidade"​/>
</​RelativeLayout​>

Código 46: disponível em luiztools.com.br/livro-android-fontes

public class ​Cidade {

​private ​String ​nome​;


​private ​String ​descricao​;
​private ​String ​uf​;
​private int ​resIdImagem​;

​public ​Cidade(String nome, String descricao, String uf, ​int ​resIdImagem){


​this​.​nome ​= nome;
​this​.​descricao ​= descricao;
​this​.​uf ​= uf;
​this​.​resIdImagem ​= resIdImagem;
}

​public ​String getNome(){ ​return this​.​nome​; }


​public ​String getDescricao(){ ​return this​.​descricao​; }
​public ​String getUf(){ ​return this​.​uf​; }
​public int ​getIdImagem(){ ​return this​.​resIdImagem​; }
}

Código 47: disponível em luiztools.com.br/livro-android-fontes

cidades​ = ​new ​ArrayList<>();


cidades​.add(​new ​Cidade(​"Florianópolis"​, "​ Capital de Santa Catarina"​, ​"SC"​,
R.drawable.​florianopolis​));
cidades​.add(​new ​Cidade(​"Curitiba"​, "​ Capital do Paraná"​, ​"PR"​, R.drawable.​curitiba​));
cidades​.add(​new ​Cidade(​"São Paulo"​, ​"Capital de São Paulo"​, ​"SP"​,R.drawable.​sao_paulo​));

15
cidades​.add(​new ​Cidade(​"Porto Alegre"​, ​"Capital do Rio Grande do Sul"​, ​"RS"​,
R.drawable.​porto_alegre​));

Código 48: disponível em luiztools.com.br/livro-android-fontes

public class ​CidadeAdapter ​extends ​ArrayAdapter<Cidade> {


​private ​List<Cidade> ​items​;

​public ​CidadeAdapter(Context context, ​int t​ extViewResourceId, List<Cidade> items) {


​super​(context, textViewResourceId, items);
​this​.​items ​= items;
}

​@Override
​public ​View getView(​int ​position, View convertView, ViewGroup parent) {
View v = convertView;
​if ​(v == ​null​) {
Context ctx = getContext();
LayoutInflater vi =
(LayoutInflater)ctx.getSystemService(Context.​LAYOUT_INFLATER_SERVICE​);
v = vi.inflate(R.layout.​item_modelo​, n
​ ull​);
}
Cidade cidade = ​items​.get(position);
​if ​(cidade != ​null​) {
((TextView) v.findViewById(R.id.​lblCidade​)).setText(cidade.getNome());
((TextView) v.findViewById(R.id.​lblUF​)).setText(​"/" ​+ cidade.getUf());
((TextView) v.findViewById(R.id.​lblDescricao​)).setText(cidade.getDescricao());

((ImageView)
v.findViewById(R.id.​imgCidade​)).setImageResource(cidade.getIdImagem());
}
​return ​v;
}
}

Código 49: disponível em luiztools.com.br/livro-android-fontes

public void ​btnBuscar_OnClick(View v){


String busca = ​txtPesquisa​.getText().toString();
List<Cidade> encontradas = ​new ​ArrayList<>();
​for​(Cidade cidade : ​cidades​){
​if​(cidade.getNome().contains(busca)) encontradas.add(cidade);
}
CidadeAdapter adapter = ​new ​CidadeAdapter(getBaseContext(), R.layout.​item_modelo​,

16
encontradas);
​lstResultados​.setAdapter(adapter);
}

Código 50: disponível em luiztools.com.br/livro-android-fontes

lstResultados​.setOnItemClickListener(​new L​ istView.OnItemClickListener() {
​public void ​onItemClick(AdapterView<?> parent, View view, ​int ​position, ​long ​id) {
Cidade cidade = (Cidade)​lstResultados​.getItemAtPosition(position);
Toast.​makeText​(getBaseContext(), ​"Item " ​+ cidade.getNome(),
Toast.​LENGTH_LONG​).show();
}
});

Código 51: disponível em luiztools.com.br/livro-android-fontes

<?​xml version=​"1.0" ​encoding=​"utf-8"​?>


<​RelativeLayout ​xmlns:​android​=​"http://schemas.android.com/apk/res/android"
​xmlns:​tools​=​"http://schemas.android.com/tools"
​android​:layout_width=​"match_parent"
​android​:layout_height=​"match_parent"
​android​:paddingBottom=​"@dimen/activity_vertical_margin"
​android​:paddingLeft=​"@dimen/activity_horizontal_margin"
​android​:paddingRight=​"@dimen/activity_horizontal_margin"
​android​:paddingTop=​"@dimen/activity_vertical_margin"
​tools​:context=​"br.com.luiztools.controller.MainActivity"​>

<​ScrollView
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"
​android​:id=​"@+id/scrollView"​>
</​ScrollView​>

</​RelativeLayout​>

Código 52: disponível em luiztools.com.br/livro-android-fontes

<​ScrollView
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"
​android​:id=​"@+id/scrollView"​>

17
<​RelativeLayout
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"​>
</​RelativeLayout​>

</​ScrollView​>

Código 53: disponível em luiztools.com.br/livro-android-fontes

AlertDialog​.Builder builder = ​new ​AlertDialog​.Builder(​this​);


builder.setMessage(​"Mensagem da Janela"​)
.setTitle(​"Título da Janela"​);
AlertDialog​ dialog = builder.create();

Código 54: disponível em luiztools.com.br/livro-android-fontes

AlertDialog​.Builder builder = ​new ​AlertDialog​.Builder(​this​);


builder.setPositiveButton(​"Ok"​, ​new ​DialogInterface.OnClickListener() {
​@Override
​public void ​onClick(DialogInterface dialog, ​int ​which) {
​//usuário clicou em ok
​}
})
.setNegativeButton(​"Cancelar"​, ​new ​DialogInterface.OnClickListener() {
​@Override
​public void ​onClick(DialogInterface dialog, ​int ​which) {
​//usuário clicou em Cancelar
​}
});
AlertDialog​ dialog = builder.create();

Código 55: disponível em luiztools.com.br/livro-android-fontes

AlertDialog​.Builder builder = ​new ​AlertDialog​.Builder(​this​);


builder.setTitle(​"Título da Janela"​)
.setItems(R.array.cores, ​new ​DialogInterface.OnClickListener() {
​@Override
​public void ​onClick(DialogInterface dialog, ​int ​which) {
​//o parâmetro which diz o índice do item escolhido
​}
});
AlertDialog​ dialog = builder.create();

18
Código 56: disponível em luiztools.com.br/livro-android-fontes

<?​xml version=​"1.0" ​encoding=​"utf-8"​?>


<​resources​>
<​string-array ​name=​"cores"​>
<​item​>Azul</​item​>
<​item​>Branco</​item​>
<​item​>Amarelo</​item​>
</​string-array​>
</​resources​>

Código 57: disponível em luiztools.com.br/livro-android-fontes

public class ​FireMissilesDialogFragment ​extends D ​ ialogFragment {


​@Override
​public ​Dialog onCreateDialog(Bundle savedInstanceState){
AlertDialog.Builder builder = ​new ​AlertDialog.Builder(getActivity());
builder.setMessage(​"Fire missles?"​)
.setPositiveButton(​"Fire"​, ​new ​DialogInterface.OnClickListener() {
​@Override
​public void ​onClick(DialogInterface dialog, ​int ​which) {
​//FOGO!
​}
})
.setNegativeButton(​"Cancel"​, ​new ​DialogInterface.OnClickListener() {
​@Override
​public void ​onClick(DialogInterface dialog, ​int ​which) {
​//ABORTAR!
​}
});
​return ​builder.create();
}
}

Código 58: disponível em luiztools.com.br/livro-android-fontes

public void ​pedirConfirmacao(){


DialogFragment fragment = ​new ​FireMissilesDialogFragment();
fragment.show(getFragmentManager(), ​"missiles"​);
}

19
Código 59: disponível em luiztools.com.br/livro-android-fontes

<?​xml version=​"1.0" ​encoding=​"utf-8"​?>


<​LinearLayout ​xmlns:​android​=​"http://schemas.android.com/apk/res/android"
​android​:orientation=​"vertical"
​android​:padding=​"10dp"
​android​:layout_width=​"match_parent"
​android​:layout_height=​"match_parent"​>

<​TextView
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"
​android​:text=​"Digite o nome da nova pasta:" ​/>

<​EditText
​android​:layout_width=​"match_parent"
​android​:layout_height=​"wrap_content"
​android​:id=​"@+id/txtNovaPasta" ​/>
</​LinearLayout​>

Código 60: disponível em luiztools.com.br/livro-android-fontes

public class ​NovaPastaDialog ​extends ​DialogFragment {

​@Override
​public ​Dialog onCreateDialog(Bundle bundle){
AlertDialog.Builder builder = ​new ​AlertDialog.Builder(getActivity());
builder.setTitle(​"Nova Pasta"​)
.setPositiveButton(​"Criar"​, ​new ​DialogInterface.OnClickListener() {
​public void ​onClick(DialogInterface dialog, ​int ​which) {
​//...
​}
});
​return ​builder.create();
}
}

Código 61: disponível em luiztools.com.br/livro-android-fontes

@Override
public ​Dialog onCreateDialog(Bundle bundle){

20
f​ inal ​Activity activity = getActivity();
LayoutInflater inflater = activity.getLayoutInflater();
View v = inflater.inflate(R.layout.​dialog_nova_pasta​, ​null​);

AlertDialog.Builder builder = ​new ​AlertDialog.Builder(activity);


builder.setTitle(​"Nova Pasta"​)
.setView(v)
.setPositiveButton(​"Criar"​, ​new ​DialogInterface.OnClickListener() {
​public void ​onClick(DialogInterface dialog, ​int ​which) {
​//...
​}
});
​return ​builder.create();
}

Código 62: disponível em luiztools.com.br/livro-android-fontes

.setPositiveButton(​"Criar"​, ​new D ​ ialogInterface.OnClickListener() {


​public void ​onClick(DialogInterface dialog, ​int ​which) {
EditText txtNovaPasta = (EditText) ((Dialog)dialog).findViewById(R.id.​txtNovaPasta​);
Toast.​makeText​(​activity​.getBaseContext(), txtNovaPasta.getText().toString(),
Toast.​LENGTH_LONG​).show();
}
});

Código 63: disponível em luiztools.com.br/livro-android-fontes

new ​NovaPastaDialog().show();

Código 64: disponível em luiztools.com.br/livro-android-fontes

<​menu ​xmlns:​android​=​"http://schemas.android.com/apk/res/android"
​xmlns:​app​=​"http://schemas.android.com/apk/res-auto"
​xmlns:​tools​=​"http://schemas.android.com/tools" ​tools​:context=​".MainActivity"​>
<​item ​android​:id=​"@+id/menu_nova_pasta" ​android​:title=​"Nova Pasta"
​android​:orderInCategory=​"100" ​app​:showAsAction=​"never" ​/>
<​item ​android​:id=​"@+id/menu_novo_arquivo" ​android​:title=​"Novo Arquivo"
​android​:orderInCategory=​"200" ​app​:showAsAction=​"never" ​/>
<​item ​android​:id=​"@+id/menu_sair" ​android​:title=​"Sair"
​android​:orderInCategory=​"300" ​app​:showAsAction=​"never" ​/>
</​menu​>

21
Código 65: disponível em luiztools.com.br/livro-android-fontes

@Override
public boolean ​onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.​menu_main,​ menu);
​return true​;
}

Código 66: disponível em luiztools.com.br/livro-android-fontes

@Override
public boolean ​onOptionsItemSelected(MenuItem item) {
​int ​id = item.getItemId();

​if ​(id == R.id.​menu_nova_pasta​) {


​//ação de criar nova pasta
​return true​;
}
​else if​(id == R.id.​menu_novo_arquivo​){
​//ação de criar novo arquivo
​return true​;
}
​else if​(id == R.id.​menu_sair​){
finish();
}

​return super​.onOptionsItemSelected(item);
}

Código 67: disponível em luiztools.com.br/livro-android-fontes

registerForContextMenu​(​lstArvore​);

Código 68: disponível em luiztools.com.br/livro-android-fontes

@Override
public void ​onCreateContextMenu(ContextMenu menu, View v,
ContextMenu.ContextMenuInfo menuInfo) {
​if ​(v.getId() == R.id.​lstArvore​) {

22
getMenuInflater().inflate(R.menu.​menu_context,​ menu);
}
}

Código 69: disponível em luiztools.com.br/livro-android-fontes

@Override
public boolean ​onContextItemSelected(MenuItem item) {
AdapterView.AdapterContextMenuInfo info =
(AdapterView.AdapterContextMenuInfo)item.getMenuInfo();

​int ​id = item.getItemId();


​if​(id == R.id.​menu_ctx_editar​){
​//ação editar
​String itemSelecionado = ​lstArvore​.getItemAtPosition(info.​position​).toString();
Toast.​makeText​(​this​, itemSelecionado, Toast.​LENGTH_LONG​).show();
​return true​;
}
​else if​(id == R.id.​menu_ctx_excluir​){
​//ação excluir
​return true​;
}
​return super​.onContextItemSelected(item);
}

Código 70: disponível em luiztools.com.br/livro-android-fontes

<​activity
​android​:name=​".MainActivity"
​android​:label=​"@string/app_name" ​>
<​intent-filter​>
<​action ​android​:name=​"android.intent.action.MAIN" ​/>
<​category ​android​:name=​"android.intent.category.LAUNCHER" ​/>
</​intent-filter​>
</​activity​>

Código 71: disponível em luiztools.com.br/livro-android-fontes

public class ​MyActivity ​extends ​Activity {

​@Override
​protected void ​onCreate(Bundle savedInstanceState) {

23
​super​.onCreate(savedInstanceState);
setContentView(R.layout.​activity_my​);
}
}

Código 72: disponível em luiztools.com.br/livro-android-fontes

public class ​MyActivity ​extends ​Activity {

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

Código 73: disponível em luiztools.com.br/livro-android-fontes

public final class ​R {


​public static final class ​attr {
}
​public static final class ​dimen {
​public static final int ​activity_horizontal_margin​=​0x7f040000​;
​public static final int ​activity_vertical_margin​=​0x7f040001​;
}
​public static final class ​drawable {
​public static final int ​ic_launcher​=​0x7f020000​;
}
​public static final class ​id {
​public static final int ​action_settings​=​0x7f080005​;
​public static final int ​btnCentro​=​0x7f080000​;
​public static final int ​btnLeste​=​0x7f080003​;
​public static final int ​btnNorte​=​0x7f080001​;
​public static final int ​btnOeste​=​0x7f080004​;
​public static final int ​btnSul​=​0x7f080002​;
}
​public static final class ​layout {
​public static final int ​activity_my​=​0x7f030000​;
}
​public static final class ​menu {
​public static final int ​my​=​0x7f070000​;
}
​public static final class ​string {
​public static final int ​action_settings​=​0x7f050000​;

24
​public static final int ​app_name​=​0x7f050001​;
}
​public static final class ​style {
​public static final int ​AppTheme​=​0x7f060000​;
}
}

Código 74: disponível em luiztools.com.br/livro-android-fontes

EditText​ txtTeste = (​EditText​)findViewById(R.id.​txtTeste​);


String texto = txtTeste.getText().toString();
txtTeste.setText(​"Novo teste"​);

Código 75: disponível em luiztools.com.br/livro-android-fontes

public class ​MyActivity ​extends ​Activity {

EditText ​txtTeste​;

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

​txtTeste ​= (EditText)findViewById(R.id.txtTeste);
}
}

Código 76: disponível em luiztools.com.br/livro-android-fontes

@Override
protected void ​onRestart(){
​super​.onRestart();
​//faz algo ao reiniciar
}

Código 77: disponível em luiztools.com.br/livro-android-fontes

public class ​MyActivity ​extends ​Activity {

25
​@Override
​protected void ​onCreate(Bundle savedInstanceState) {
​super​.onCreate(savedInstanceState);
setContentView(R.layout.​activity_my​);
​//a activity está sendo criada
}​

​@Override
​protected void ​onResume(){
​super​.onResume();
​//a activity se tornou visível
}​

​@Override
​protected void ​onPause(){
​super​.onPause();
​//outra activity está assumindo o foco
}​

​@Override
​protected void ​onStop(){
​super​.onStop();
​//esta activity já não é mais visível
}​

​@Override
​protected void ​onStart(){
​super​.onStart();
​//a activity está sendo inicializada
}​

​@Override
​protected void ​onDestroy(){
​super​.onDestroy();
​//a activity está sendo finalizada
}​
}

Código 78: disponível em luiztools.com.br/livro-android-fontes

@Override
public boolean ​onOptionsItemSelected(MenuItem item){
​int ​id = item.getItemId();
​if​(id == R.id.​action_settings​){
Intent intent = ​new ​Intent(​this​, OutraActivity.​class​);
startActivity(intent);

26
}
​return super​.onOptionsItemSelected(item);
}

Código 79: disponível em luiztools.com.br/livro-android-fontes

Intent​ intent = ​new ​Intent​(​this​, OutraActivity.​class​);


startActivity(intent);

Código 80: disponível em luiztools.com.br/livro-android-fontes

@Override
public boolean ​onOptionsItemSelected(MenuItem item){
​int ​id = item.getItemId();
​if​(id == R.id.​action_settings​){
Intent intent = ​new ​Intent(​this​, OutraActivity.​class​);
startActivity(intent);
}​else​{
finish();
}
​return super​.onOptionsItemSelected(item);
}

Código 81: disponível em luiztools.com.br/livro-android-fontes

Intent​ intent = ​new ​Intent​(​this​, OutraActivity.​class​);


intent.putExtra(​"ItemSelecionado"​, ​1​);
startActivity(intent);

Código 82: disponível em luiztools.com.br/livro-android-fontes

Intent​ intent = getIntent();


int ​itemSelecionado = intent.getIntExtra(​"ItemSelecionado"​, ​0​);

Código 83: disponível em luiztools.com.br/livro-android-fontes

<​LinearLayout ​xmlns:​android​=​"http://schemas.android.com/apk/res/android"
​xmlns:​tools​=​"http://schemas.android.com/tools"

27
​android​:layout_width=​"match_parent"
​android​:layout_height=​"match_parent"
​android​:orientation=​"vertical"
​tools​:context=​".MainActivity"​>

<​TextView
​android​:layout_width=​"fill_parent"
​android​:​layout_height​=​"50dp"
​android​:textAppearance=​"?android:attr/textAppearanceLarge"
​android​:text=​"/"
​android​:id=​"@+id/txtPath"
​android​:textStyle=​"bold"​/>

<​ListView
​android​:layout_width=​"fill_parent"
​android​:layout_height=​"0dp"
​android​:layout_weight=​"8"
​android​:id=​"@+id/lstArvore" ​/>

<​LinearLayout
​android​:layout_width=​"fill_parent"
​android​:layout_height=​"0dp"
​android​:layout_weight=​"2"
​android​:layout_marginTop=​"20dp"
​android​:orientation=​"horizontal"​>

<​Button
​android​:layout_width=​"0dp"
​android​:layout_height=​"fill_parent"
​android​:layout_weight=​"1"
​android​:text=​"Nova Pasta"
​android​:onClick=​"btnNovaPasta_OnClick"
​android​:id=​"@+id/btnNovaPasta" ​/>

<​Button
​android​:layout_width=​"0dp"
​android​:layout_height=​"fill_parent"
​android​:layout_weight=​"1"
​android​:onClick=​"btnNovoArquivo_OnClick"
​android​:text=​"Novo Arquivo"
​android​:id=​"@+id/btnNovoArquivo" ​/>

</​LinearLayout​>
</​LinearLayout​>

Código 84: disponível em luiztools.com.br/livro-android-fontes

28
public class ​MainActivity ​extends A
​ ctionBarActivity {

TextView ​txtPath​;
ListView ​lstArvore​;

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

​txtPath ​= (TextView)findViewById(R.id.​txtPath​);
​lstArvore ​= (ListView)findViewById(R.id.​lstArvore​);
}

​public void ​btnNovoArquivo_OnClick(View v){


​//clique no botão de novo arquivo
}​

​public void ​btnNovaPasta_OnClick(View v){


​//clique no botão de nova pasta
}​
}

Código 85: disponível em luiztools.com.br/livro-android-fontes

void ​atualizarArvore(){
String raiz = Environment.​getExternalStorageDirectory​().getPath();
String path = ​txtPath​.getText().toString();
File file = ​new ​File (raiz + path);
String[] tree = file.list();

​if​(tree != ​null​) {
ArrayList<String> arr = ​new ​ArrayList<>(Arrays.​asList​(tree));
Collections.​sort​(arr);
​if​(!path.equals(​"/"​)){
arr.add(​0​, ​".."​);​//se não estamos na raiz, deve dar esta opção para voltar
​}
ArrayAdapter<String> adapter = ​new ​ArrayAdapter<>(​this​,
android.R.layout.​simple_list_item_1​, arr);
​lstArvore​.setAdapter(adapter);
}
}

29
Código 86: disponível em luiztools.com.br/livro-android-fontes

@Override
public void ​onWindowFocusChanged(​boolean ​hasFocus) {
​super​.onWindowFocusChanged(hasFocus);
atualizarArvore();
}

Código 87: disponível em luiztools.com.br/livro-android-fontes

<​uses-permission ​android​:name=​"android.permission.WRITE_EXTERNAL_STORAGE" ​/>


<​uses-permission ​android​:name=​"android.permission.READ_EXTERNAL_STORAGE" ​/>

Código 88: disponível em luiztools.com.br/livro-android-fontes

lstArvore ​= (ListView)findViewById(R.id.​lstArvore​);
lstArvore​.setOnItemClickListener(​new ​ListView.OnItemClickListener() {
​public void ​onItemClick(AdapterView<?> parent, View view, ​int ​position, ​long ​id) {
String path = ​txtPath​.getText().toString();
String item = ​lstArvore​.getItemAtPosition(position).toString();
​if​(!item.equals(​".."​)) {​//se não é o item 'voltar'
​File file = ​new ​File(Environment.​getExternalStorageDirectory​()+ path + ​"/" +​ item);
​if ​(file.isDirectory()) {​//se é uma pasta
​txtPath​.setText(path.endsWith(​"/"​) ? path + item : path + ​"/" ​+ item);
} ​else if ​(file.getName().endsWith(​".txt"​)) {​//se é um arquivo de texto
​Intent intent = ​new ​Intent(MainActivity.​this​, FormActivity.​class​);
intent.putExtra(​"path"​, file.getAbsolutePath());
intent.putExtra(​"edit"​, ​true​);
startActivity(intent);
} ​else ​{​//outros arquivos
​Toast.​makeText​(view.getContext(), "​ Arquivo não suportado!"​,
Toast.​LENGTH_LONG​).show();
}
}
​else​{
String[] partes = path.split(​"/"​);
String abovePath = path.replace(partes[partes.​length​-​1​], ​""​);
​txtPath​.setText(abovePath);
}
atualizarArvore();
}
});

30
Código 89: disponível em luiztools.com.br/livro-android-fontes

public class ​NovaPastaDialog ​extends ​DialogFragment {

​static ​String ​path​;

​@SuppressLint​(​"ValidFragment"​)
​public ​NovaPastaDialog(String path){
​this​();
​this​.​path ​= path;
}

​public ​NovaPastaDialog(){ ​super​(); }

​@Override
​public ​Dialog onCreateDialog(Bundle bundle){
​final ​Activity activity = getActivity();
LayoutInflater inflater = activity.getLayoutInflater();
View v = inflater.inflate(R.layout.​dialog_nova_pasta​, ​null​);

AlertDialog.Builder builder = ​new ​AlertDialog.Builder(activity);


builder.setTitle(​"Nova Pasta"​)
.setView(v)
.setPositiveButton(​"Criar"​, ​new ​DialogInterface.OnClickListener() {
​public void ​onClick(DialogInterface dialog, ​int ​which) {
EditText txtNovaPasta = (EditText)
((Dialog)dialog).findViewById(R.id.​txtNovaPasta​);
String novaPasta = NovaPastaDialog.​path ​+ ​"/" ​+ txtNovaPasta.getText();
​if ​(​new ​File(novaPasta).mkdir()) {
Toast.​makeText​(​activity​.getBaseContext(), "​ Pasta criada com sucesso!"​,
Toast.​LENGTH_LONG​).show();
} ​else ​{
Toast.​makeText​(​activity​.getBaseContext(), "​ Não foi possível criar a pasta!"​,
Toast.​LENGTH_LONG​).show();
}
}
});
​return ​builder.create();
}
}

Código 90: disponível em luiztools.com.br/livro-android-fontes

31
<?​xml version=​"1.0" ​encoding=​"utf-8"​?>
<​LinearLayout ​xmlns:​android​=​"http://schemas.android.com/apk/res/android"
​android​:orientation=​"vertical"
​android​:padding=​"10dp"
​android​:layout_width=​"match_parent"
​android​:layout_height=​"match_parent"​>

<​TextView
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"
​android​:text=​"Digite o nome da nova pasta:" ​/>

<​EditText
​android​:layout_width=​"match_parent"
​android​:layout_height=​"wrap_content"
​android​:id=​"@+id/txtNovaPasta" ​/>
</​LinearLayout​>

Código 91: disponível em luiztools.com.br/livro-android-fontes

public void ​btnNovoArquivo_OnClick(View v){


Intent intent = ​new ​Intent(​this​, FormActivity.​class​);
intent.putExtra(​"path"​, ​txtPath​.getText().toString());
intent.putExtra(​"edit"​, ​false​);
startActivity(intent);
}

Código 92: disponível em luiztools.com.br/livro-android-fontes

<​LinearLayout ​xmlns:​android​=​"http://schemas.android.com/apk/res/android"
​xmlns:​tools​=​"http://schemas.android.com/tools" ​android​:layout_width=​"match_parent"
​android​:layout_height=​"match_parent"
​android​:orientation=​"vertical"
​tools​:context=​"com.example.fernando.gerenciadordearquivos.FormActivity"​>

<​TextView
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"0dp"
​android​:layout_weight=​"1"
​android​:id=​"@+id/txtPath"
​android​:text=​"Pasta:"​/>

<​EditText
​android​:layout_width=​"fill_parent"

32
​android​:layout_height=​"0dp"
​android​:layout_weight=​"1"
​android​:text=​"Novo Arquivo.txt"
​android​:hint=​"Nome do Arquivo"
​android​:id=​"@+id/txtNomeArquivo"​/>

<​EditText
​android​:layout_width=​"fill_parent"
​android​:layout_height=​"0dp"
​android​:layout_weight=​"7"
​android​:text=​"Lorem ipsum dolor sit amet"
​android​:id=​"@+id/txtConteudoArquivo"​/>

<​LinearLayout
​android​:layout_width=​"fill_parent"
​android​:orientation=​"horizontal"
​android​:layout_height=​"0dp"
​android​:layout_weight=​"1"​>

<​Button
​android​:layout_width=​"0dp"
​android​:layout_height=​"wrap_content"
​android​:layout_weight=​"1"
​android​:text=​"Cancelar"
​android​:onClick=​"btnCancelar_OnClick"​/>

<​Button
​android​:layout_width=​"0dp"
​android​:layout_height=​"wrap_content"
​android​:layout_weight=​"1"
​android​:text=​"Salvar"
​android​:onClick=​"btnSalvar_OnClick"​/>

</​LinearLayout​>
</​LinearLayout​>

Código 93: disponível em luiztools.com.br/livro-android-fontes

TextView​ ​txtPath​;
EditText ​txtNomeArquivo​, ​txtConteudoArquivo​;
boolean ​edit​;
String ​path​;

@Override
protected void ​onCreate(Bundle savedInstanceState) {
​super​.onCreate(savedInstanceState);

33
setContentView(R.layout.​activity_form​);

Intent intent = getIntent();


​edit ​= intent.getBooleanExtra(​"edit"​, ​false​);
​path ​= intent.getStringExtra(​"path"​);

​txtPath ​= (​TextView​)findViewById(R.id.​txtPath​);
​txtNomeArquivo ​= (EditText)findViewById(R.id.​txtNomeArquivo​);
​txtConteudoArquivo ​= (EditText)findViewById(R.id.​txtConteudoArquivo​);

​if​(​edit​){
String[] partes = ​path​.split(​"/"​);
​ ​];
String arquivo = partes[partes.​length​-1
​txtNomeArquivo​.setText(arquivo);
​txtPath​.setText(​path​.replace(arquivo,​""​));
​txtConteudoArquivo​.setText(lerArquivo(​path​));
}​else​{
​txtPath​.setText(​path​);
}
}

Código 94: disponível em luiztools.com.br/livro-android-fontes

String​ lerArquivo(​String​ path){


File file = ​new ​File(Environment.​getExternalStorageDirectory​().getPath() + path);
StringBuilder text = ​new ​StringBuilder();

​try ​{
BufferedReader br = ​new ​BufferedReader(​new ​FileReader(file));
​String​ line;

​while ​((line = br.readLine()) != ​null​) {


text.append(line + ​"​\n​")​ ;
}
br.close();
}
​catch ​(IOException e) {
Toast.​makeText​(​this​, ​"Não foi possível ler o arquivo!"​, Toast.​LENGTH_LONG​).show();
}
​return ​text.toString();
}

Código 95: disponível em luiztools.com.br/livro-android-fontes

34
public void ​btnSalvar_OnClick(View v){
​try ​{
String arquivo = ​"/" ​+ ​txtPath​.getText() + ​"/" ​+ ​txtNomeArquivo​.getText();
File myFile = ​new ​File(Environment.​getExternalStorageDirectory​().getPath() + arquivo);
​if​(!myFile.exists())
myFile.createNewFile();
FileOutputStream fOut = ​new ​FileOutputStream(myFile);
fOut.write(​txtConteudoArquivo​.getText().toString().getBytes());
fOut.close();
finish();
} ​catch ​(Exception e) {
Toast.​makeText​(​this​, ​"Não foi possível salvar o arquivo!"​, Toast.​LENGTH_SHORT​).show();
}
}

public void ​btnCancelar_OnClick(View v){


finish();
}

Código 96: disponível em luiztools.com.br/livro-android-fontes

private​ ​static​ ​final​ ​int​ REQUEST_EXTERNAL_STORAGE = ​1​;

private​ ​static​ ​String​[] PERMISSIONS_STORAGE = {


Manifest​.permission.READ_EXTERNAL_STORAGE,
Manifest​.permission.WRITE_EXTERNAL_STORAGE };

public​ ​static​ ​void​ verifyStoragePermissions(​Activity​ activity) {

int​ permission = ​ActivityCompat​.checkSelfPermission(activity,


Manifest​.permission.WRITE_EXTERNAL_STORAGE);

if​ (permission != ​PackageManager​.PERMISSION_GRANTED) {

ActivityCompat​.requestPermissions( activity,
PERMISSIONS_STORAGE, REQUEST_EXTERNAL_STORAGE );

Código 97: disponível em luiztools.com.br/livro-android-fontes

35
<?​xml version=​"1.0" ​encoding=​"utf-8"​?>
<​menu ​xmlns:​android​=​"http://schemas.android.com/apk/res/android"​>
<​item
​android​:id=​"@+id/menu_ctx_editar"
​android​:title=​"Editar Arquivo" ​/>
<​item
​android​:id=​"@+id/menu_ctx_excluir"
​android​:title=​"Excluir Arquivo" ​/>
</​menu​>

Código 98: disponível em luiztools.com.br/livro-android-fontes

@Override
public void ​onCreateContextMenu(ContextMenu menu, View v,
ContextMenu.ContextMenuInfo menuInfo) {
​if ​(v.getId() == R.id.​lstArvore​) {
getMenuInflater().inflate(R.menu.​menu_context,​ menu);
}
}

Código 99: disponível em luiztools.com.br/livro-android-fontes

registerForContextMenu(​lstArvore​);
atualizarArvore();
}

Código 100: disponível em luiztools.com.br/livro-android-fontes

@Override
public boolean ​onContextItemSelected(MenuItem item) {
AdapterView.AdapterContextMenuInfo info =
(AdapterView.AdapterContextMenuInfo)item.getMenuInfo();

​final ​String itemSelecionado = ​lstArvore​.getItemAtPosition(info.​position​).toString();


​final ​String raiz = Environment.​getExternalStorageDirectory​().getPath();
​final ​String path = raiz + ​txtPath​.getText().toString() + ​"/" ​+ itemSelecionado;

​int ​id = item.getItemId();


​if​(id == R.id.​menu_ctx_editar​){
Intent intent = ​new ​Intent(MainActivity.​this​, FormActivity.​class​);
intent.putExtra(​"path"​, path);
intent.putExtra(​"edit"​, ​true​);

36
startActivity(intent);
​return true​;
}
​else if​(id == R.id.​menu_ctx_excluir​){
AlertDialog.Builder builder = ​new ​AlertDialog.Builder(​this​);
builder.setTitle(​"Excluir"​)
.setMessage(​"Tem certeza que deseja excluir " ​+ itemSelecionado + ​"?"​)
.setPositiveButton(​"Sim"​, ​new D ​ ialogInterface.OnClickListener() {
​public void ​onClick(DialogInterface dialog, ​int ​which) {
​if​(​new ​File(​path​).delete()){
Toast.​makeText​(getBaseContext(), i​ temSelecionado ​+ ​" excluído com sucesso!"​,
Toast.​LENGTH_LONG​).show();
}​else​{
Toast.​makeText​(getBaseContext(), "​ Não foi possível excluir " ​+
itemSelecionado ​+ ​"!"​, Toast.​LENGTH_LONG​).show();
}
}
})
.create()
.show();

​return true​;
}
​return super​.onContextItemSelected(item);
}

Código 101: disponível em luiztools.com.br/livro-android-fontes

public class ​DbHelper ​extends ​SQLiteOpenHelper {

​static final ​String ​DATABASE_NAME ​= ​"CadCli.db"​;


​static final int ​DATABASE_VERSION ​= ​1;​

​public ​DbHelper(Context context) {


​super​(context, ​DATABASE_NAME​, ​null​, ​DATABASE_VERSION​);
}

​@Override
​public void ​onCreate(SQLiteDatabase db) {
db.execSQL(​"CREATE TABLE Clientes(id integer primary key autoincrement," ​+
​"nome text not null, dataNascimento text not null," ​+
​"vip integer not null, uf text not null, cidade text not null," ​+
​"sexo text not null);"​);
}

​@Override

37
​public void ​onUpgrade(SQLiteDatabase db, ​int ​oldVersion, ​int ​newVersion) {

}
}

Código 102: disponível em luiztools.com.br/livro-android-fontes

"CREATE TABLE NomeDaTabela(coluna1 tipo nullable, coluna 2 tipo nullable);"

Código 103: disponível em luiztools.com.br/livro-android-fontes

public class ​DbAdapter {

SQLiteDatabase ​db ​= ​null​;


DbHelper ​dbHelper ​= ​null​;

​public ​DbAdapter(Context ctx){


​dbHelper ​= ​new ​DbHelper(ctx);
}

​private void ​abrirConexao(){


​if​(​db ​== ​null​)
​db ​= ​dbHelper​.getWritableDatabase();
}

​public void ​fecharConexao(){


​if​(​db​!= ​null ​&& ​db​.isOpen()) {
​db​.close();
​db ​= ​null​;
}
}

​public void ​executarComandoSQL(String sql){


abrirConexao();
​db​.execSQL(sql);
fecharConexao();
}

​public ​Cursor executarConsultaSQL(String sql){


abrirConexao();
​return ​db​.rawQuery(sql, ​null​);
}
}

38
Código 104: disponível em luiztools.com.br/livro-android-fontes

public class ​GerenciadorClientes {

​private ​Context ​ctx​;

​public ​GerenciadorClientes(Context ctx){ ​this​.​ctx ​= ctx; }

​public ​List<Cliente> retornarClientes(){


List<Cliente> clientes = ​new A
​ rrayList<>();
DbAdapter dba = ​new ​DbAdapter(​ctx​);
Cursor cursor = dba.executarConsultaSQL(​"SELECT
id,nome,datanascimento,sexo,cidade,uf,vip FROM Clientes"​);

​while​(cursor.moveToNext()){
​int ​id = cursor.getInt(​0​);
String nome = cursor.getString(​1​);
String data = cursor.getString(​2​);
String sexo = cursor.getString(​3​);
String cidade = cursor.getString(​4​);
String uf = cursor.getString(​5)​ ;
​boolean ​vip = cursor.getInt(​6​) == ​1 ​? ​true ​: ​false​;
Cliente cliente = ​new ​Cliente(id,nome,sexo,data,vip,cidade,uf);
clientes.add(cliente);
}
dba.fecharConexao();

​return ​clientes;
}
}

Código 105: disponível em luiztools.com.br/livro-android-fontes

public class ​Cliente ​implements ​Serializable {

i​ nt ​id​;
String ​nome​;
String ​sexo​;
String ​dataNascimento​;
​boolean ​vip​;
String ​cidade​;
String ​uf​;

39
​ ublic ​Cliente(String nome, String sexo, String dataNascimento, ​boolean ​vip, String cidade,
p
String uf){
​this​(​0​,nome,sexo,dataNascimento,vip,cidade,uf);
}

​public ​Cliente(​int ​id, String nome, String sexo, String dataNascimento, ​boolean ​vip, String
cidade, String uf){
​this​.​id ​= id;
​this​.​nome ​= nome;
​this​.​sexo ​= sexo;
​this​.​dataNascimento ​= dataNascimento;
​this​.​vip ​= vip;
​this​.​cidade ​= cidade;
​this​.​uf ​= uf;
}

​@Override
​public ​String toString(){
​return this​.​nome​;
}
}

Código 106: disponível em luiztools.com.br/livro-android-fontes

public class ​GerenciadorClientes {

​private ​Context ​ctx​;

​public ​GerenciadorClientes(Context ctx){ ​this​.​ctx ​= ctx; }

​public ​List<Cliente> retornarClientes(){ ​return r​ etornarClientes(​null​); }

​public ​List<Cliente> retornarClientes(String nomeB){


String sql = ​"SELECT id,nome,datanascimento,sexo,cidade,uf,vip FROM Clientes"​;
​if​(nomeB != ​null ​&& !nomeB.equals(​""​))
sql += ​" WHERE nome LIKE '%" ​+ nomeB.replace(​"'"​, ​"'"​) + ​"%'"​;

List<Cliente> clientes = ​new A


​ rrayList<>();
DbAdapter dba = ​new ​DbAdapter(​ctx​);
Cursor cursor = dba.executarConsultaSQL(sql);

​while​(cursor.moveToNext()){
​int ​id = cursor.getInt(​0​);
String nome = cursor.getString(​1​);
String data = cursor.getString(​2​);
String sexo = cursor.getString(​3​);

40
String cidade = cursor.getString(​4​);
String uf = cursor.getString(​5)​ ;
​boolean ​vip = cursor.getInt(​6​) == ​1 ​? ​true ​: ​false​;
Cliente cliente = ​new ​Cliente(id,nome,sexo,data,vip,cidade,uf);
clientes.add(cliente);
}
dba.fecharConexao();

​return ​clientes;
}
}

Código 107: disponível em luiztools.com.br/livro-android-fontes

public void ​salvarCliente(Cliente cliente){


DbAdapter dba = ​new ​DbAdapter(​ctx​);
String sql = String.format(​"INSERT INTO Clientes(nome,sexo,cidade,uf,datanascimento,vip)
VALUES ('%s','%s','%s','%s,'%s',%d)"​, cliente.​nome​.replace(​"'"​,​"''"​), cliente.​sexo​,
cliente.​dataNascimento​, cliente.​uf,​ cliente.​cidade​, cliente.​vip ​? 1 : 0);
dba.executarComandoSQL(sql);
}

Código 108: disponível em luiztools.com.br/livro-android-fontes

public void ​salvarCliente(Cliente cliente){


DbAdapter dba = ​new ​DbAdapter(​ctx​);
String sql = cliente.​id ​== ​0
​? ​"INSERT INTO Clientes(nome,sexo,cidade,uf,datanascimento,vip) VALUES
('%s','%s','%s','%s','%s',%d)"
​: ​"UPDATE Clientes SET
nome='%s',sexo='%s',cidade='%s',uf='%s',datanascimento='%s',vip=%d WHERE id=" ​+
cliente.​id​;

sql = String.​format​(sql, cliente.​nome​.replace(​"'"​,​"''"​),


cliente.​sexo​,
cliente.​cidade​.replace(​"'"​,​"''"​),
cliente.​uf​,
cliente.​dataNascimento​,
cliente.​vip ​? ​1 ​: ​0​);
dba.executarComandoSQL(sql);
}

Código 109: disponível em luiztools.com.br/livro-android-fontes

41
public void ​excluirCliente(​int ​id){
DbAdapter dba = ​new ​DbAdapter(​ctx​);
String sql = ​"DELETE FROM Clientes WHERE id=" ​+ id;
dba.executarComandoSQL(sql);
}

Código 110: disponível em luiztools.com.br/livro-android-fontes

<?​xml version=​"1.0" ​encoding=​"utf-8"​?>


<​RelativeLayout ​xmlns:​android​=​"http://schemas.android.com/apk/res/android"
​xmlns:​tools​=​"http://schemas.android.com/tools"
​android​:layout_width=​"match_parent"
​android​:layout_height=​"match_parent"
​tools​:context=​"com.example.luizfduartejr.cadastrodeclientes.MainActivity"​>

<​ListView
​android​:layout_width=​"match_parent"
​android​:layout_height=​"match_parent"
​android​:id=​"@+id/listView" ​/>
</​RelativeLayout​>

Código 111: disponível em luiztools.com.br/livro-android-fontes

public class ​MainActivity ​extends A


​ ppCompatActivity {

ListView ​listView​;

​@Override
​protected void ​onCreate(Bundle savedInstanceState) {
​super​.onCreate(savedInstanceState);
setContentView(R.layout.​activity_main​);
​listView ​= (ListView)findViewById(R.id.​listView​);
carregarListagem();
}

​public void ​carregarListagem(){


List<Cliente> clientes = ​new G ​ erenciadorClientes(​this​).retornarClientes();
​if​(clientes.size() == ​0​){
Toast.​makeText​(​this​, ​"Nenhum cliente cadastrado!"​, Toast.​LENGTH_SHORT​).show();
}
ArrayAdapter<Cliente> clientesAdapter =
​new ​ArrayAdapter<>(​this​, android.R.layout.​simple_list_item_1​, clientes);

42
​listView​.setAdapter(clientesAdapter);
}
}

Código 112: disponível em luiztools.com.br/livro-android-fontes

@Override
public ​String toString(){
​return this​.​nome​;
}

Código 113: disponível em luiztools.com.br/livro-android-fontes

<?​xml version=​"1.0" ​encoding=​"utf-8"​?>


<​RelativeLayout ​xmlns:​android​=​"http://schemas.android.com/apk/res/android"
​xmlns:​tools​=​"http://schemas.android.com/tools"
​android​:layout_width=​"match_parent"
​android​:layout_height=​"match_parent"
​tools​:context=​"com.example.luizfduartejr.cadastrodeclientes.CadastroActivity"​>

<​EditText
​android​:layout_width=​"match_parent"
​android​:layout_height=​"wrap_content"
​android​:inputType=​"textPersonName"
​android​:hint=​"Nome do Cliente"
​android​:ems=​"10"
​android​:id=​"@+id/txtNome" ​/>

<​EditText
​android​:layout_width=​"match_parent"
​android​:layout_height=​"wrap_content"
​android​:inputType=​"date"
​android​:hint=​"Data de Nascimento"
​android​:ems=​"10"
​android​:id=​"@+id/txtDataNascimento"
​android​:layout_below=​"@+id/txtNome" ​/>

Código 114: disponível em luiztools.com.br/livro-android-fontes

<​LinearLayout
​android​:layout_width=​"match_parent"
​android​:layout_height=​"wrap_content"

43
​android​:id=​"@+id/localizacao"
​android​:layout_below=​"@id/txtDataNascimento"
​android​:orientation=​"horizontal"​>

<​EditText
​android​:layout_width=​"0dp"
​android​:layout_height=​"wrap_content"
​android​:layout_weight=​"7"
​android​:inputType=​"textPersonName"
​android​:hint=​"Cidade"
​android​:ems=​"10"
​android​:id=​"@+id/txtCidade" ​/>

<​Spinner
​android​:layout_width=​"0dp"
​android​:layout_height=​"40dp"
​android​:layout_weight=​"3"
​android​:id=​"@+id/spnUf"
​android​:entries=​"@array/estados"​></​Spinner​>

</​LinearLayout​>

Código 115: disponível em luiztools.com.br/livro-android-fontes

<?​xml version=​"1.0" ​encoding=​"utf-8"​?>


<​resources​>
<​string-array ​name=​"estados"​>
<​item​>RS</​item​>
<​item​>SC</​item​>
<​item​>PR</​item​>
</​string-array​>
</​resources​>

Código 116: disponível em luiztools.com.br/livro-android-fontes

<​TextView
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"
​android​:text=​"Sexo:"
​android​:textAppearance=​"?android:attr/textAppearanceLarge"
​android​:id=​"@+id/lblSexo"
​android​:layout_below=​"@id/localizacao"​/>

<​RadioGroup

44
​android​:layout_width=​"match_parent"
​android​:layout_height=​"wrap_content"
​android​:orientation=​"horizontal"
​android​:id=​"@+id/grpSexo"
​android​:layout_toRightOf=​"@+id/lblSexo"
​android​:layout_below=​"@id/localizacao"​>
<​RadioButton
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"
​android​:text=​"Masculino"
​android​:id=​"@+id/radMasculino"​/>
<​RadioButton
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"
​android​:text=​"Feminino"
​android​:id=​"@+id/radFeminino"​/>
</​RadioGroup​>

Código 117: disponível em luiztools.com.br/livro-android-fontes

<​CheckBox
​android​:layout_width=​"match_parent"
​android​:layout_height=​"wrap_content"
​android​:text=​"Cliente VIP"
​android​:id=​"@+id/chkVip"
​android​:layout_below=​"@id/grpSexo"​/>

<​LinearLayout
​android​:layout_width=​"match_parent"
​android​:layout_height=​"wrap_content"
​android​:id=​"@+id/botoes"
​android​:layout_below=​"@id/chkVip"
​android​:orientation=​"horizontal"​>

<​Button
​android​:layout_width=​"0dp"
​android​:layout_height=​"wrap_content"
​android​:layout_weight=​"5"
​android​:text=​"Cancelar"
​android​:onClick=​"btnCancelarOnClick"
​android​:id=​"@+id/btnCancelar"​/>
<​Button
​android​:layout_width=​"0dp"
​android​:layout_height=​"wrap_content"
​android​:layout_weight=​"5"
​android​:text=​"Salvar"

45
​android​:onClick=​"btnSalvarOnClick"
​android​:id=​"@+id/btnSalvar"​/>

</​LinearLayout​>
</​RelativeLayout​>

Código 118: disponível em luiztools.com.br/livro-android-fontes

public class ​CadastroActivity ​extends ​AppCompatActivity {

Cliente ​cliente​;
EditText ​txtNome​, ​txtDataNascimento​, ​txtCidade​;
Spinner ​spnUf​;
RadioButton ​radMasculino​;
RadioGroup ​grpSexo​;
CheckBox ​chkVip​;

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

Código 119: disponível em luiztools.com.br/livro-android-fontes

public void ​btnCancelarOnClick(View v){


finish();
}

Código 120: disponível em luiztools.com.br/livro-android-fontes

public void ​btnSalvarOnClick(View v){


​int ​id = ​cliente ​== ​null ​? ​0 ​: ​cliente​.​id​;
String nome = ​txtNome​.getText().toString();
String cidade = ​txtCidade​.getText().toString();
String uf = ​spnUf​.getSelectedItem().toString();
String dataNascimento = ​txtDataNascimento​.getText().toString();
String sexo = ​radMasculino​.isChecked() ? ​"M" ​: ​"F"​;
​boolean ​vip = ​chkVip​.isChecked();
Cliente c = ​new ​Cliente(id,nome,dataNascimento,sexo,vip,uf,cidade);
​new ​GerenciadorClientes(​this​).salvarCliente(c);

46
Toast.​makeText​(​this​, ​"Cliente salvo com sucesso!"​, Toast.​LENGTH_LONG​).show();
finish();
}

Código 121: disponível em luiztools.com.br/livro-android-fontes

public static boolean ​validarCliente(Cliente c){


​if​(c == ​null​) ​return false​;
​if​(c.​nome ​== ​null ​|| c.​nome​.equals(​""​)) ​return false​;
​if​(c.​dataNascimento ​== ​null ​|| c.​dataNascimento​.equals(​""​)) ​return false​;
​if​(c.​uf ​== ​null ​|| c.​uf​.equals(​""​)) ​return false​;
​if​(c.​cidade ​== ​null ​|| c.​cidade​.equals(​""​)) ​return false​;
​if​(c.​sexo ​== ​null ​|| c.​sexo​.equals(​""​)) ​return false​;
​return true​;
}

Código 122: disponível em luiztools.com.br/livro-android-fontes

@Override
protected void ​onRestart(){
​super​.onRestart();
carregarListagem();
}

Código 123: disponível em luiztools.com.br/livro-android-fontes

@Override
public boolean ​onCreateOptionsMenu(Menu menu){
menu.add(​"Novo Cliente"​);
​return true​;
}

@Override
public boolean ​onOptionsItemSelected(MenuItem item){
Intent intent = ​new ​Intent(MainActivity.​this​, CadastroActivity.​class​);
startActivity(intent);
​return true​;
}

Código 124: disponível em luiztools.com.br/livro-android-fontes

47
@Override
protected void ​onCreate(Bundle savedInstanceState) {
​super​.onCreate(savedInstanceState);
setContentView(R.layout.​activity_main​);
​listView ​= (ListView)findViewById(R.id.​listView​);
carregarListagem();

​listView​.setOnItemLongClickListener(​new ​ListView.OnItemLongClickListener() {
​@Override
​public boolean ​onItemLongClick(AdapterView<?> parent, View view, ​int ​position, ​long ​id) {

​final ​Context ctx = view.getContext();


​final ​Cliente cliente = (Cliente)​listView​.getItemAtPosition(position);

AlertDialog.Builder builder = ​new ​AlertDialog.Builder(ctx);


builder.setTitle(​"Confirmação"​)
.setMessage(​"Tem certeza que deseja excluir este cliente?"​)
.setPositiveButton(​"Excluir"​, ​new ​DialogInterface.OnClickListener() {
​@Override
​public void ​onClick(DialogInterface dialog, i​ nt ​which) {
​new ​GerenciadorClientes(getBaseContext()).excluirCliente(​cliente​.​id​);
carregarListagem();
Toast.​makeText​(​ctx​, "​ Cliente excluído com sucesso!"​,
Toast.​LENGTH_LONG​).show();
}
})
.setNegativeButton(​"Cancelar"​, ​null​)
.create()
.show();
​return false​;
}
});
}

Código 125: disponível em luiztools.com.br/livro-android-fontes

public class ​Cliente ​implements ​Serializable {

Código 126: disponível em luiztools.com.br/livro-android-fontes

@Override
protected void ​onCreate(Bundle savedInstanceState) {

48
s​ uper​.onCreate(savedInstanceState);
setContentView(R.layout.​activity_main​);
​listView ​= (ListView)findViewById(R.id.​listView​);
carregarListagem();

​listView​.setOnItemClickListener(​new ​ListView.OnItemClickListener() {
​@Override
​public void ​onItemClick(AdapterView<?> parent, View view, ​int ​position, ​long ​id) {
Cliente cliente = (Cliente)​listView​.getItemAtPosition(position);
Intent intent = ​new ​Intent(MainActivity.​this​, CadastroActivity.​class​);
intent.putExtra(​"cliente"​, cliente);
startActivity(intent);
}
});
​//o resto do código continua igual

Código 127: disponível em luiztools.com.br/livro-android-fontes

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

​txtNome ​= (EditText)findViewById(R.id.​txtNome​);
​txtCidade ​= (EditText)findViewById(R.id.​txtCidade)​ ;
​txtDataNascimento ​= (EditText)findViewById(R.id.​txtDataNascimento​);
​spnUf ​= (Spinner)findViewById(R.id.​spnUf​);
​radMasculino ​= (RadioButton)findViewById(R.id.​radMasculino​);
​chkVip ​= (CheckBox)findViewById(R.id.​chkVip​);
​grpSexo ​= (RadioGroup)findViewById(R.id.​grpSexo​);

Intent intent = getIntent();


​if​(intent.hasExtra(​"cliente"​)){
​cliente ​= (Cliente)intent.getSerializableExtra(​"cliente"​);
​txtNome​.setText(​cliente​.​nome​);
​txtCidade​.setText(​cliente​.​cidade​);
​txtDataNascimento​.setText(​cliente​.​dataNascimento​);
​spnUf​.setSelection((((ArrayAdapter)​spnUf​.getAdapter()).getPosition(​cliente​.​uf​)));

​if​(​cliente​.​sexo​.equals(​"M"​))
​grpSexo​.check(R.id.​radMasculino​);
​else
​grpSexo​.check(R.id.​radFeminino​);
​chkVip​.setChecked(​cliente​.​vip​);
}
}

49
Código 128: disponível em luiztools.com.br/livro-android-fontes

public void ​btnSalvarOnClick(View v){


​int ​id = ​cliente ​== ​null ​? ​0 ​: ​cliente​.​id​;
String nome = ​txtNome​.getText().toString();
String cidade = ​txtCidade​.getText().toString();
String uf = ​spnUf​.getSelectedItem().toString();
String dataNascimento = ​txtDataNascimento​.getText().toString();
String sexo = ​radMasculino​.isChecked() ? ​"M" ​: ​"F"​;
​boolean ​vip = ​chkVip​.isChecked();
Cliente c = ​new ​Cliente(id,nome,dataNascimento,sexo,vip,uf,cidade);
​new ​GerenciadorClientes(​this​).salvarCliente(c);
Toast.​makeText​(​this​, ​"Cliente salvo com sucesso!"​, Toast.​LENGTH_LONG​).show();
finish();
}

Código 129: disponível em luiztools.com.br/livro-android-fontes

{"ip":"8.8.8.8","country_code":"US","country_name":"United
States","region_code":"","region_name":"","city":"","zip_code":"","time_zone":"","latitude":3
7.751,"longitude":-97.822,"metro_code":0}

Código 130: disponível em luiztools.com.br/livro-android-fontes

<​RelativeLayout ​xmlns:​android​=​"http://schemas.android.com/apk/res/android"
​xmlns:​tools​=​"http://schemas.android.com/tools"
​android​:layout_width=​"match_parent"
​android​:layout_height=​"match_parent"
​tools​:context=​".LocationActivity"​>

<​LinearLayout
​android​:layout_width=​"match_parent"
​android​:layout_height=​"wrap_content"
​android​:orientation=​"horizontal"
​android​:id=​"@+id/ip"​>
<​EditText
​android​:layout_width=​"0dp"
​android​:layout_height=​"wrap_content"
​android​:layout_weight=​"7"
​android​:text=​"177.155.44.231"
​android​:ems=​"10"

50
​android​:id=​"@+id/txtIP"
​android​:hint=​"Digite o IP"
​android​:inputType=​"number|text" ​/>

<​Button
​android​:layout_width=​"0dp"
​android​:layout_height=​"wrap_content"
​android​:layout_weight=​"3"
​android​:text=​"Carregar"
​android​:id=​"@+id/btnCarregar"
​android​:onClick=​"btnCarregarOnClick" ​/>
</​LinearLayout​>

Código 131: disponível em luiztools.com.br/livro-android-fontes

<​TextView
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"
​android​:textAppearance=​"?android:attr/textAppearanceLarge"
​android​:text=​"Geolocalização"
​android​:textStyle=​"bold"
​android​:id=​"@+id/lblTitulo"
​android​:layout_below=​"@+id/ip" ​/>
<​TextView
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"
​android​:textAppearance=​"?android:attr/textAppearanceLarge"
​android​:text=​"País: Brazil"
​android​:id=​"@+id/lblCountry"
​android​:layout_below=​"@+id/lblTitulo" ​/>
<​TextView
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"
​android​:textAppearance=​"?android:attr/textAppearanceLarge"
​android​:text=​"Estado: Rio Grande do Sul"
​android​:id=​"@+id/lblRegion"
​android​:layout_below=​"@+id/lblCountry" ​/>
<​TextView
​android​:layout_width=​"wrap_content"
​android​:layout_height=​"wrap_content"
​android​:textAppearance=​"?android:attr/textAppearanceLarge"
​android​:text=​"Cidade: Gravataí"
​android​:id=​"@+id/lblCity"
​android​:layout_below=​"@+id/lblRegion" ​/>
</​RelativeLayout​>

51
Código 132: disponível em luiztools.com.br/livro-android-fontes

public class ​LocationActivity ​extends ​Activity {

EditText ​txtIP​;
TextView ​lblCountry​, ​lblRegion​, ​lblCity​;

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

​txtIP ​= (EditText)findViewById(R.id.​txtIP​);
​lblCountry ​= (TextView)findViewById(R.id.​lblCountry​);
​lblRegion ​= (TextView)findViewById(R.id.​lblRegion​);
​lblCity ​= (TextView)findViewById(R.id.​lblCity​);
}
}

Código 133: disponível em luiztools.com.br/livro-android-fontes

public class ​Localizacao {


​private ​String ​country​;
​private ​String ​region​;
​private ​String ​city​;

​public ​Localizacao(String country,


String region, String city){
​this​.​country ​= country;
​this​.​region ​= region;
​this​.​city ​= city;
}

​public S ​ tring getCountry(){ ​return this​.​country​; }


​public S ​ tring getRegion(){ ​return this​.​region​; }
​public S ​ tring getCity(){ ​return this​.​city​; }
}

Código 134: disponível em luiztools.com.br/livro-android-fontes

public class ​ClienteGeoIP {

​private static ​String readStream(InputStream in){


BufferedReader r = ​new ​BufferedReader(​new ​InputStreamReader(in));
StringBuilder total = ​new ​StringBuilder();
String line;

​try ​{
​while ​((line = r.readLine()) != ​null​) {
total.append(line).append(​'​\n​'​);

52
}
}​catch​(Exception ex) {
ex.printStackTrace();
}
​return ​total.toString();
}

​public static ​String request(String stringUrl){


URL url = ​null​;
HttpURLConnection urlConnection = ​null​;
​try ​{
url = ​new ​URL(stringUrl);
urlConnection = (HttpURLConnection) url.openConnection();
InputStream in = ​new ​BufferedInputStream(urlConnection.getInputStream());
​return ​readStream​(in);
}
​catch ​(Exception e) {
e.printStackTrace();
}
​finally ​{
urlConnection.disconnect();
}
​return ​""​;
}

​public static ​Localizacao retornarLocalizacaoPorIp(String ip)


​throws ​IOException, JSONException {

String content = ​request​(​"http://freegeoip.net/json/" ​+ ip);


JSONObject obj = ​new ​JSONObject(content);
String pais = obj.getString(​"country_name"​);
String estado = obj.getString(​"region_name"​);
String cidade = obj.getString(​"city"​);
​return new ​Localizacao(pais, estado, cidade);
}
}

Código 135: disponível em luiztools.com.br/livro-android-fontes

public void ​btnCarregarOnClick(View view){

//permite conexão com a Internet na Thread principal


StrictMode.ThreadPolicy policy = ​new ​StrictMode.ThreadPolicy.Builder().permitAll().build();
StrictMode.​setThreadPolicy​(policy);

​try ​{
String ip = ​txtIP​.getText().toString();
Localizacao localizacao = ClienteGeoIP.​retornarLocalizacaoPorIp​(ip);
​lblRegion​.setText(​"Estado: " ​+ localizacao.getRegion());
​lblCity​.setText(​"Cidade: " ​+ localizacao.getCity());
​lblCountry​.setText(​"País: " ​+ localizacao.getCountry());
}
​catch​(Exception ex){
Toast.​makeText​(getBaseContext(), ex.getMessage(), Toast.​LENGTH_LONG​).show();
}
}

Código 136: disponível em luiztools.com.br/livro-android-fontes

53
<​uses-permission ​android​:name=​"android.permission.INTERNET" ​/>

Código 137: disponível em luiztools.com.br/livro-android-fontes

<?php
​// criamos um array com algumas informações básicas de uma pessoa
​$person_info​ ​=​ ​array​(
​"nome"​ ​=>​ ​"Luiz Fernando"​,
​"idade"​ ​=>​ ​28​,
​"profissao"​ ​=>​ ​"Professor"​,
​"cidade"​ ​=>​ ​utf8_encode​(​"Gravataí"​)
​)​;

​//agora transformamos esse array em uma String JSON


​$json​ ​=​ ​json_encode​(​$person_info​)​;

​ cho​ ​$json​;
e
?>

Código 138: disponível em luiztools.com.br/livro-android-fontes

{
"nome": "Luiz Fernando",
"idade": 28,
"profissao": "Professor",
"Cidade": "Gravataí"
}

Código 139: disponível em luiztools.com.br/livro-android-fontes

$nome ​=​ $_GET​[​"​nome​"​]​;

Código 140: disponível em luiztools.com.br/livro-android-fontes

namespace​ Percutz​.​Api
{
​[​ServiceContract​]
​public​ ​interface​ ITurmaService

54
​{
​[​OperationContract​]
​[​WebGet​(​UriTemplate ​=​ ​"​/EmAndamento​"​,​ ResponseFormat ​=​ WebMessageFormat​.​Json​)]
List​<​TurmaDTO​>​ RetornarTurmasEmAndamento​()​;

​[​OperationContract​]
​[​WebGet​(​UriTemplate ​=​ ​"​/EmFormacao​"​,​ ResponseFormat ​=​ WebMessageFormat​.​Json​)]
List​<​TurmaDTO​>​ RetornarTurmasEmFormacao​()​;

​[​OperationContract​]
​[​WebGet​(​UriTemplate ​=​ ​"​/Turma/{id}​"​,​ ResponseFormat ​=​ WebMessageFormat​.​Json​)]
TurmaDTO RetornarTurma​(​string​ id​)​;
​}
}

Código 141: disponível em luiztools.com.br/livro-android-fontes

namespace​ Percutz​.​Lib​.​DTO
{
​[​DataContract​]
​public​ ​class​ TurmaDTO
​{
​[​DataMember​]
​public​ ​string​ Filial ​{​ ​get​;​ ​set​;​ }​
​[​DataMember​]
​public​ ​string​ Nivel ​{​ g​ et​;​ ​set​;​ }​
​[​DataMember​]
​public​ ​short​ DiaSemana ​{​ ​get​;​ ​set​;​ ​}
​[​DataMember​]
​public​ ​short​ HoraInicio ​{​ ​get​;​ ​set​;​ ​}
​[​DataMember​]
​public​ ​short​ HoraFim ​{​ ​get​;​ ​set​;​ ​}

​public​ TurmaDTO​()​ ​{​ }​

​public​ TurmaDTO​(​Turma turma​)


{​
​this​.​Filial ​=​ turma​.​Filial​.​Nome​;
​this​.​Nivel ​=​ turma​.​Produto​.​Nome​;
​this​.​DiaSemana ​=​ turma​.​DiaSemana​;
​this​.​HoraInicio ​=​ turma​.​HoraInicio​;
​this​.​HoraFim ​=​ turma​.​HoraFim​;
}​
​}

55
Código 142: disponível em luiztools.com.br/livro-android-fontes

<%​@ ServiceHost Factory​=​"​System.ServiceModel.Activation.WebServiceHostFactory​"


Language​=​"​C#​"​ Debug​=​"​true​"​ Service​=​"​Percutz.Api.TurmaService​"
CodeBehind​=​"​TurmaService.svc.cs​"​ ​%>

Código 143: disponível em luiztools.com.br/livro-android-fontes

namespace​ Percutz​.​Api
{
​public​ ​class​ TurmaService ​:​ ITurmaService
​{
​public​ List​<​TurmaDTO​>​ RetornarTurmasEmAndamento​()
​{
​return​ ControladorTurma​.​RetornarTurmasEmAndamento​(​DateTime​.​Now​.​Year​)​;
​}

​public​ List​<​TurmaDTO​>​ RetornarTurmasEmFormacao​()


{​
​return​ ControladorTurma​.​RetornarTurmasEmFormacao​(​DateTime​.​Now​.​Year​)​;
}​

​public​ TurmaDTO RetornarTurma​(​string​ id​)


{​
​return​ ControladorTurma​.​RetornarTurma​(​int​.​Parse​(​id​))​;
}​
​}
}

Código 144: disponível em luiztools.com.br/livro-android-fontes

[{"DiaSemana":5,"Filial":"Cachoeirinha","HoraFim":1650,"HoraInicio":1415,"Nivel":"Intermediá
rio 1"}]

Código 145: disponível em luiztools.com.br/livro-android-fontes

public​ ​class​ CalculadoraServlet ​extends​ HttpServlet ​{

​@​Override
​protected​ ​void​ doGet​(​HttpServletRequest request​,
HttpServletResponse response​)

56
t​ hrows​ ServletException​,​ ​IOException​ ​{
response​.​setContentType​(​"application/json;charset=UTF-8"​)​;

​double​ valor1 ​=​ ​Double​.​parseDouble​(​request​.​getParameter​(​"v1"​))​;


​double​ valor2 ​=​ ​Double​.​parseDouble​(​request​.​getParameter​(​"v2"​))​;
​double​ resultado ​=​ ​0​;
​String​ operacao ​=​ request​.​getParameter​(​"operacao"​)​;

​switch​(​operacao​)​{
​case​ ​"Somar"​:​ resultado ​=​ valor1 ​+​ valor2​;​ ​break​;
​case​ ​"Subtrair"​:​ resultado ​=​ valor1 ​-​ valor2​;​ ​break​;
​case​ ​"Multiplicar"​:​ resultado ​=​ valor1 ​*​ valor2​;​ ​break​;
​case​ ​"Dividir"​:​ resultado ​=​ valor1 /​ ​ valor2​;​ ​break​;
}​

​try​ ​(​PrintWriter​ out ​=​ response​.​getWriter​())​ ​{


JSONObject obj ​=​ ​new​ JSONObject​()​;
obj​.​put​(​"resultado"​,​ resultado​)​;
out​.​println​(​obj​.​toJSONString​())​;
}​
​}
}

Código 146: disponível em luiztools.com.br/livro-android-fontes

{ "resultado" : 5.0 }

Código 147: disponível em luiztools.com.br/livro-android-fontes

C:\node>express apitest

Código 148: disponível em luiztools.com.br/livro-android-fontes

"​dependencies​"​:​ ​{
​"​body-parser​"​:​ ​"​>=1.15.2​"​,
​"​cookie-parser​"​:​ ​"​>=1.4.3​"​,
​"​date-format​"​:​ ​"​>=0.0.2​"​,
​"​debug​"​:​ ​"​>=2.2.0​"​,
​"​express​"​:​ ​"​^4.14.0​"​,
​"​mongodb​"​:​ ​"​^2.2.7​"​,

57
​"​mongoose​"​:​ ​"​^4.8.2​",​
​"​morgan​"​:​ ​"​>=1.7.0​"​,
​"​serve-favicon​"​:​ ​"​>=2.3.0​"
​}

Código 149: disponível em luiztools.com.br/livro-android-fontes

C:\node\apitest>npm install

Código 150: disponível em luiztools.com.br/livro-android-fontes

C:\node\apitest>npm start

Código 151: disponível em luiztools.com.br/livro-android-fontes

mongod --dbpath c:\node\apitest\data\

Código 152: disponível em luiztools.com.br/livro-android-fontes

mongo

Código 153: disponível em luiztools.com.br/livro-android-fontes

use apitest

Código 154: disponível em luiztools.com.br/livro-android-fontes

custArray = [{ "name" : "customer1", "email" : "cust1@testdomain.com" }, { "name" :


"customer2", "email" : "cust2@testdomain.com" }]
db.customers.insert(custArray);

Código 155: disponível em luiztools.com.br/livro-android-fontes

58
var​ mongoose ​=​ require​(​'m
​ ongoose​'​)​;
mongoose​.​connect​(​'​mongodb://localhost/apitest​'​)​;

var​ customerSchema ​=​ ​new​ mongoose​.​Schema​(​{


name​:​ ​String​,
email​:​ ​String
}​,​ ​{​ collection​:​ ​'​customers​'​ ​}​)​;

module​.​exports ​=​ ​{​ Mongoose​:​ mongoose​,​ CustomerSchema​:​ customerSchema ​}

Código 156: disponível em luiztools.com.br/livro-android-fontes

/* GET all customers. */


router​.​get​(​'​/customers​'​,​ ​function​ ​(​req​,​ res​,​ next​)​ ​{
​var​ db ​=​ require​(​'​../db​'​)​;
​var​ Customer ​=​ db​.​Mongoose​.​model​(​'​customers​'​,​ db​.​CustomerSchema​,
'​customers​'​)​;
Customer​.​find​(​{}​).​lean​().​exec​(​function​(​e​,​docs​)​{
res​.​json​(​docs​)​;
res​.​end​()​;
​}​)​;
}​)​;

Código 157: disponível em luiztools.com.br/livro-android-fontes

/* GET ONE customers. */


router​.​get​(​'​/customers/:id​'​,​ ​function​ ​(​req​,​ res​,​ next​)​ ​{
​var​ db ​=​ require​(​'​../db​'​)​;
​var​ Customer ​=​ db​.​Mongoose​.​model​(​'​customers​'​,​ db​.​CustomerSchema​,
'​customers​'​)​;
Customer​.​find​(​{​ _id​:​ req​.​params​.​id ​}​).​lean​().​exec​(​function​ ​(​e,​ ​ docs​)​ ​{
res​.​json​(​docs​)​;
res​.​end​()​;

59
​}​)​;
}​)​;

Código 158: disponível em luiztools.com.br/livro-android-fontes

/* POST ONE customer. */


router​.​post​(​'​/customers/​',​ ​ ​function​ ​(​req​,​ res​,​ next​)​ ​{
​var​ db ​=​ require​(​'​../db​'​)​;
​var​ Customer ​=​ db​.​Mongoose​.​model​(​'​customers​'​,​ db​.​CustomerSchema​,
'​customers​'​)​;
​var​ newcustomer ​=​ ​new​ Customer​(​{​ name​:​ req​.​body​.​name​,​ email​:​ req​.​body​.​email ​}​)​;
newcustomer​.​save​(​function​ ​(​err​)​ ​{
​if​ ​(​err​)​ ​{
res​.​status​(​500​).​json​(​{​ error​:​ err​.​message ​}​)​;
res​.​end​()​;
​return​;
​}
res​.​json​(​newcustomer​)​;
res​.​end​()​;
​}​)​;
}​)​;

Código 159: disponível em luiztools.com.br/livro-android-fontes

/* PUT ONE customer. */


router​.​put​(​'​/customers/:id​'​,​ ​function​ ​(​req​,​ res​,​ next​)​ ​{
​var​ db ​=​ require​(​'​../db​'​)​;
​var​ Customer ​=​ db​.​Mongoose​.​model​(​'​customers​'​,​ db​.​CustomerSchema​,
'​customers​'​)​;
Customer​.​findOneAndUpdate​({​ ​ _id​:​ req​.​params​.​id ​}​,​ req​.​body​,​ ​{​ upsert​:​ ​true​ ​}​,
function​ ​(​err​,​ doc​)​ ​{
​if​ ​(​err​)​ ​{
res​.​status​(​500​).​json​(​{​ error​:​ err​.​message ​}​)​;
res​.​end​()​;
​return​;

60
​}
res​.​json​(​req​.​body​);​
res​.​end​()​;
​}​)​;
}​)​;

Código 160: disponível em luiztools.com.br/livro-android-fontes

/* DELETE ONE customer. */


router​.​delete​(​'​/customers/:id​'​,​ ​function​ ​(​req​,​ res​,​ next​)​ ​{
​var​ db ​=​ require​(​'​../db​'​)​;
​var​ Customer ​=​ db​.​Mongoose​.​model​(​'​customers​'​,​ db​.​CustomerSchema​,
'​customers​'​)​;
Customer​.​find​(​{​ _id​:​ req​.​params​.​id ​}​).​remove​(​function​ ​(​err​)​ ​{
​if​ ​(​err​)​ ​{
res​.​status​(​500​).​json​(​{​ error​:​ err​.​message ​}​)​;
res​.​end​()​;
​return​;
​}
res​.​json​(​{​success​:​ ​true​}​)​;
res​.​end​()​;
​}​)​;
}​)​;

61

Interesses relacionados