MainActivity.java 30 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875
  1. package com.afollestad.materialdialogssample;
  2. import android.Manifest;
  3. import android.annotation.TargetApi;
  4. import android.content.Intent;
  5. import android.content.pm.PackageManager;
  6. import android.graphics.Color;
  7. import android.graphics.drawable.ColorDrawable;
  8. import android.os.Build;
  9. import android.os.Bundle;
  10. import android.os.Handler;
  11. import android.support.annotation.ColorInt;
  12. import android.support.annotation.StringRes;
  13. import android.support.v4.app.ActivityCompat;
  14. import android.support.v4.content.ContextCompat;
  15. import android.support.v7.app.AppCompatActivity;
  16. import android.text.Editable;
  17. import android.text.Html;
  18. import android.text.InputType;
  19. import android.text.TextWatcher;
  20. import android.text.method.PasswordTransformationMethod;
  21. import android.view.Menu;
  22. import android.view.MenuItem;
  23. import android.view.View;
  24. import android.widget.CheckBox;
  25. import android.widget.EditText;
  26. import android.widget.Toast;
  27. import butterknife.ButterKnife;
  28. import butterknife.OnClick;
  29. import com.afollestad.materialdialogs.DialogAction;
  30. import com.afollestad.materialdialogs.GravityEnum;
  31. import com.afollestad.materialdialogs.MaterialDialog;
  32. import com.afollestad.materialdialogs.StackingBehavior;
  33. import com.afollestad.materialdialogs.Theme;
  34. import com.afollestad.materialdialogs.color.CircleView;
  35. import com.afollestad.materialdialogs.color.ColorChooserDialog;
  36. import com.afollestad.materialdialogs.folderselector.FileChooserDialog;
  37. import com.afollestad.materialdialogs.folderselector.FolderChooserDialog;
  38. import com.afollestad.materialdialogs.internal.MDTintHelper;
  39. import com.afollestad.materialdialogs.internal.ThemeSingleton;
  40. import com.afollestad.materialdialogs.simplelist.MaterialSimpleListAdapter;
  41. import com.afollestad.materialdialogs.simplelist.MaterialSimpleListItem;
  42. import com.afollestad.materialdialogs.util.DialogUtils;
  43. import java.io.File;
  44. /** @author Aidan Follestad (afollestad) */
  45. public class MainActivity extends AppCompatActivity
  46. implements FolderChooserDialog.FolderCallback,
  47. FileChooserDialog.FileCallback,
  48. ColorChooserDialog.ColorCallback {
  49. private static final int STORAGE_PERMISSION_RC = 69;
  50. static int index = 0;
  51. // Custom View Dialog
  52. private EditText passwordInput;
  53. private View positiveAction;
  54. // color chooser dialog
  55. private int primaryPreselect;
  56. // UTILITY METHODS
  57. private int accentPreselect;
  58. private Toast toast;
  59. private Thread thread;
  60. private Handler handler;
  61. private int chooserDialog;
  62. private void showToast(String message) {
  63. if (toast != null) {
  64. toast.cancel();
  65. toast = null;
  66. }
  67. toast = Toast.makeText(this, message, Toast.LENGTH_SHORT);
  68. toast.show();
  69. }
  70. private void startThread(Runnable run) {
  71. if (thread != null) {
  72. thread.interrupt();
  73. }
  74. thread = new Thread(run);
  75. thread.start();
  76. }
  77. // BEGIN SAMPLE
  78. private void showToast(@StringRes int message) {
  79. showToast(getString(message));
  80. }
  81. @Override
  82. protected void onCreate(Bundle savedInstanceState) {
  83. super.onCreate(savedInstanceState);
  84. setContentView(R.layout.activity_main);
  85. ButterKnife.bind(this);
  86. handler = new Handler();
  87. primaryPreselect = DialogUtils.resolveColor(this, R.attr.colorPrimary);
  88. accentPreselect = DialogUtils.resolveColor(this, R.attr.colorAccent);
  89. }
  90. @Override
  91. protected void onDestroy() {
  92. super.onDestroy();
  93. handler = null;
  94. }
  95. @Override
  96. protected void onPause() {
  97. super.onPause();
  98. if (thread != null && !thread.isInterrupted() && thread.isAlive()) {
  99. thread.interrupt();
  100. }
  101. }
  102. @OnClick(R.id.basicNoTitle)
  103. public void showBasicNoTitle() {
  104. new MaterialDialog.Builder(this)
  105. .content(R.string.shareLocationPrompt)
  106. .positiveText(R.string.agree)
  107. .negativeText(R.string.disagree)
  108. .show();
  109. }
  110. @OnClick(R.id.basic)
  111. public void showBasic() {
  112. new MaterialDialog.Builder(this)
  113. .title(R.string.useGoogleLocationServices)
  114. .content(R.string.useGoogleLocationServicesPrompt, true)
  115. .positiveText(R.string.agree)
  116. .negativeText(R.string.disagree)
  117. .show();
  118. }
  119. @OnClick(R.id.basicLongContent)
  120. public void showBasicLongContent() {
  121. new MaterialDialog.Builder(this)
  122. .title(R.string.useGoogleLocationServices)
  123. .content(R.string.loremIpsum)
  124. .positiveText(R.string.agree)
  125. .negativeText(R.string.disagree)
  126. .checkBoxPrompt("Hello, world!", true, null)
  127. .show();
  128. }
  129. @OnClick(R.id.basicIcon)
  130. public void showBasicIcon() {
  131. new MaterialDialog.Builder(this)
  132. .iconRes(R.mipmap.ic_launcher)
  133. .limitIconToDefaultSize() // limits the displayed icon size to 48dp
  134. .title(R.string.useGoogleLocationServices)
  135. .content(R.string.useGoogleLocationServicesPrompt, true)
  136. .positiveText(R.string.agree)
  137. .negativeText(R.string.disagree)
  138. .show();
  139. }
  140. @OnClick(R.id.basicCheckPrompt)
  141. public void showBasicCheckPrompt() {
  142. new MaterialDialog.Builder(this)
  143. .iconRes(R.mipmap.ic_launcher)
  144. .limitIconToDefaultSize()
  145. .title(Html.fromHtml(getString(R.string.permissionSample, getString(R.string.app_name))))
  146. .positiveText(R.string.allow)
  147. .negativeText(R.string.deny)
  148. .onAny((dialog, which) -> showToast("Prompt checked? " + dialog.isPromptCheckBoxChecked()))
  149. .checkBoxPromptRes(R.string.dont_ask_again, false, null)
  150. .show();
  151. }
  152. @OnClick(R.id.stacked)
  153. public void showStacked() {
  154. new MaterialDialog.Builder(this)
  155. .title(R.string.useGoogleLocationServices)
  156. .content(R.string.useGoogleLocationServicesPrompt, true)
  157. .positiveText(R.string.speedBoost)
  158. .negativeText(R.string.noThanks)
  159. .btnStackedGravity(GravityEnum.END)
  160. .stackingBehavior(
  161. StackingBehavior
  162. .ALWAYS) // this generally should not be forced, but is used for demo purposes
  163. .show();
  164. }
  165. @OnClick(R.id.neutral)
  166. public void showNeutral() {
  167. new MaterialDialog.Builder(this)
  168. .title(R.string.useGoogleLocationServices)
  169. .content(R.string.useGoogleLocationServicesPrompt, true)
  170. .positiveText(R.string.agree)
  171. .negativeText(R.string.disagree)
  172. .neutralText(R.string.more_info)
  173. .show();
  174. }
  175. @OnClick(R.id.callbacks)
  176. public void showCallbacks() {
  177. new MaterialDialog.Builder(this)
  178. .title(R.string.useGoogleLocationServices)
  179. .content(R.string.useGoogleLocationServicesPrompt, true)
  180. .positiveText(R.string.agree)
  181. .negativeText(R.string.disagree)
  182. .neutralText(R.string.more_info)
  183. .onAny((dialog, which) -> showToast(which.name() + "!"))
  184. .show();
  185. }
  186. @OnClick(R.id.list)
  187. public void showList() {
  188. new MaterialDialog.Builder(this)
  189. .title(R.string.socialNetworks)
  190. .items(R.array.socialNetworks)
  191. .itemsCallback((dialog, view, which, text) -> showToast(which + ": " + text))
  192. .show();
  193. }
  194. @OnClick(R.id.listNoTitle)
  195. public void showListNoTitle() {
  196. new MaterialDialog.Builder(this)
  197. .items(R.array.socialNetworks)
  198. .itemsCallback((dialog, view, which, text) -> showToast(which + ": " + text))
  199. .show();
  200. }
  201. @OnClick(R.id.longList)
  202. public void showLongList() {
  203. new MaterialDialog.Builder(this)
  204. .title(R.string.states)
  205. .items(R.array.states)
  206. .itemsCallback((dialog, view, which, text) -> showToast(which + ": " + text))
  207. .positiveText(android.R.string.cancel)
  208. .show();
  209. }
  210. @OnClick(R.id.list_longItems)
  211. public void showListLongItems() {
  212. new MaterialDialog.Builder(this)
  213. .title(R.string.socialNetworks)
  214. .items(R.array.socialNetworks_longItems)
  215. .itemsCallback((dialog, view, which, text) -> showToast(which + ": " + text))
  216. .show();
  217. }
  218. @OnClick(R.id.list_checkPrompt)
  219. public void showListCheckPrompt() {
  220. new MaterialDialog.Builder(this)
  221. .title(R.string.socialNetworks)
  222. .items(R.array.socialNetworks)
  223. .itemsCallback((dialog, view, which, text) -> showToast(which + ": " + text))
  224. .checkBoxPromptRes(R.string.example_prompt, true, null)
  225. .negativeText(android.R.string.cancel)
  226. .show();
  227. }
  228. @SuppressWarnings("ConstantConditions")
  229. @OnClick(R.id.list_longPress)
  230. public void showListLongPress() {
  231. index = 0;
  232. new MaterialDialog.Builder(this)
  233. .title(R.string.socialNetworks)
  234. .items(R.array.socialNetworks)
  235. .itemsCallback((dialog, view, which, text) -> showToast(which + ": " + text))
  236. .autoDismiss(false)
  237. .itemsLongCallback(
  238. (dialog, itemView, position, text) -> {
  239. dialog.getItems().remove(position);
  240. dialog.notifyItemsChanged();
  241. return false;
  242. })
  243. .onNeutral(
  244. (dialog, which) -> {
  245. index++;
  246. dialog.getItems().add("Item " + index);
  247. dialog.notifyItemInserted(dialog.getItems().size() - 1);
  248. })
  249. .neutralText(R.string.add_item)
  250. .show();
  251. }
  252. @OnClick(R.id.singleChoice)
  253. public void showSingleChoice() {
  254. new MaterialDialog.Builder(this)
  255. .title(R.string.socialNetworks)
  256. .items(R.array.socialNetworks)
  257. .itemsDisabledIndices(1, 3)
  258. .itemsCallbackSingleChoice(
  259. 2,
  260. (dialog, view, which, text) -> {
  261. showToast(which + ": " + text);
  262. return true; // allow selection
  263. })
  264. .positiveText(R.string.md_choose_label)
  265. .show();
  266. }
  267. @OnClick(R.id.singleChoice_longItems)
  268. public void showSingleChoiceLongItems() {
  269. new MaterialDialog.Builder(this)
  270. .title(R.string.socialNetworks)
  271. .items(R.array.socialNetworks_longItems)
  272. .itemsCallbackSingleChoice(
  273. 2,
  274. (dialog, view, which, text) -> {
  275. showToast(which + ": " + text);
  276. return true; // allow selection
  277. })
  278. .positiveText(R.string.md_choose_label)
  279. .show();
  280. }
  281. @OnClick(R.id.multiChoice)
  282. public void showMultiChoice() {
  283. new MaterialDialog.Builder(this)
  284. .title(R.string.socialNetworks)
  285. .items(R.array.socialNetworks)
  286. .itemsCallbackMultiChoice(
  287. new Integer[] {1, 3},
  288. (dialog, which, text) -> {
  289. StringBuilder str = new StringBuilder();
  290. for (int i = 0; i < which.length; i++) {
  291. if (i > 0) {
  292. str.append('\n');
  293. }
  294. str.append(which[i]);
  295. str.append(": ");
  296. str.append(text[i]);
  297. }
  298. showToast(str.toString());
  299. return true; // allow selection
  300. })
  301. .onNeutral((dialog, which) -> dialog.clearSelectedIndices())
  302. .onPositive((dialog, which) -> dialog.dismiss())
  303. .alwaysCallMultiChoiceCallback()
  304. .positiveText(R.string.md_choose_label)
  305. .autoDismiss(false)
  306. .neutralText(R.string.clear_selection)
  307. .show();
  308. }
  309. @OnClick(R.id.multiChoiceLimited)
  310. public void showMultiChoiceLimited() {
  311. new MaterialDialog.Builder(this)
  312. .title(R.string.socialNetworks)
  313. .items(R.array.socialNetworks)
  314. .itemsCallbackMultiChoice(
  315. new Integer[] {1},
  316. (dialog, which, text) -> {
  317. boolean allowSelectionChange =
  318. which.length
  319. <= 2; // limit selection to 2, the new (un)selection is included in the which array
  320. if (!allowSelectionChange) {
  321. showToast(R.string.selection_limit_reached);
  322. }
  323. return allowSelectionChange;
  324. })
  325. .positiveText(R.string.dismiss)
  326. .alwaysCallMultiChoiceCallback() // the callback will always be called, to check if (un)selection is still allowed
  327. .show();
  328. }
  329. @OnClick(R.id.multiChoiceLimitedMin)
  330. public void showMultiChoiceLimitedMin() {
  331. new MaterialDialog.Builder(this)
  332. .title(R.string.socialNetworks)
  333. .items(R.array.socialNetworks)
  334. .itemsCallbackMultiChoice(
  335. new Integer[] {1},
  336. (dialog, which, text) -> {
  337. boolean allowSelectionChange =
  338. which.length
  339. >= 1; // selection count must stay above 1, the new (un)selection is included in the which array
  340. if (!allowSelectionChange) {
  341. showToast(R.string.selection_min_limit_reached);
  342. }
  343. return allowSelectionChange;
  344. })
  345. .positiveText(R.string.dismiss)
  346. .alwaysCallMultiChoiceCallback() // the callback will always be called, to check if (un)selection is still allowed
  347. .show();
  348. }
  349. @OnClick(R.id.multiChoice_longItems)
  350. public void showMultiChoiceLongItems() {
  351. new MaterialDialog.Builder(this)
  352. .title(R.string.socialNetworks)
  353. .items(R.array.socialNetworks_longItems)
  354. .itemsCallbackMultiChoice(
  355. new Integer[] {1, 3},
  356. (dialog, which, text) -> {
  357. StringBuilder str = new StringBuilder();
  358. for (int i = 0; i < which.length; i++) {
  359. if (i > 0) {
  360. str.append('\n');
  361. }
  362. str.append(which[i]);
  363. str.append(": ");
  364. str.append(text[i]);
  365. }
  366. showToast(str.toString());
  367. return true; // allow selection
  368. })
  369. .positiveText(R.string.md_choose_label)
  370. .show();
  371. }
  372. @OnClick(R.id.multiChoice_disabledItems)
  373. public void showMultiChoiceDisabledItems() {
  374. new MaterialDialog.Builder(this)
  375. .title(R.string.socialNetworks)
  376. .items(R.array.socialNetworks)
  377. .itemsCallbackMultiChoice(
  378. new Integer[] {0, 1, 2},
  379. (dialog, which, text) -> {
  380. StringBuilder str = new StringBuilder();
  381. for (int i = 0; i < which.length; i++) {
  382. if (i > 0) {
  383. str.append('\n');
  384. }
  385. str.append(which[i]);
  386. str.append(": ");
  387. str.append(text[i]);
  388. }
  389. showToast(str.toString());
  390. return true; // allow selection
  391. })
  392. .onNeutral((dialog, which) -> dialog.clearSelectedIndices())
  393. .alwaysCallMultiChoiceCallback()
  394. .positiveText(R.string.md_choose_label)
  395. .autoDismiss(false)
  396. .neutralText(R.string.clear_selection)
  397. .itemsDisabledIndices(0, 1)
  398. .show();
  399. }
  400. @OnClick(R.id.simpleList)
  401. public void showSimpleList() {
  402. final MaterialSimpleListAdapter adapter =
  403. new MaterialSimpleListAdapter(
  404. (dialog, index1, item) -> showToast(item.getContent().toString()));
  405. adapter.add(
  406. new MaterialSimpleListItem.Builder(this)
  407. .content("username@gmail.com")
  408. .icon(R.drawable.ic_account_circle)
  409. .backgroundColor(Color.WHITE)
  410. .build());
  411. adapter.add(
  412. new MaterialSimpleListItem.Builder(this)
  413. .content("user02@gmail.com")
  414. .icon(R.drawable.ic_account_circle)
  415. .backgroundColor(Color.WHITE)
  416. .build());
  417. adapter.add(
  418. new MaterialSimpleListItem.Builder(this)
  419. .content(R.string.add_account)
  420. .icon(R.drawable.ic_content_add)
  421. .iconPaddingDp(8)
  422. .build());
  423. new MaterialDialog.Builder(this).title(R.string.set_backup).adapter(adapter, null).show();
  424. }
  425. @OnClick(R.id.customListItems)
  426. public void showCustomList() {
  427. final ButtonItemAdapter adapter = new ButtonItemAdapter(this, R.array.socialNetworks);
  428. adapter.setCallbacks(
  429. itemIndex -> showToast("Item clicked: " + itemIndex),
  430. buttonIndex -> showToast("Button clicked: " + buttonIndex));
  431. new MaterialDialog.Builder(this).title(R.string.socialNetworks).adapter(adapter, null).show();
  432. }
  433. @SuppressWarnings("ResourceAsColor")
  434. @OnClick(R.id.customView)
  435. public void showCustomView() {
  436. MaterialDialog dialog =
  437. new MaterialDialog.Builder(this)
  438. .title(R.string.googleWifi)
  439. .customView(R.layout.dialog_customview, true)
  440. .positiveText(R.string.connect)
  441. .negativeText(android.R.string.cancel)
  442. .onPositive(
  443. (dialog1, which) -> showToast("Password: " + passwordInput.getText().toString()))
  444. .build();
  445. positiveAction = dialog.getActionButton(DialogAction.POSITIVE);
  446. //noinspection ConstantConditions
  447. passwordInput = dialog.getCustomView().findViewById(R.id.password);
  448. passwordInput.addTextChangedListener(
  449. new TextWatcher() {
  450. @Override
  451. public void beforeTextChanged(CharSequence s, int start, int count, int after) {}
  452. @Override
  453. public void onTextChanged(CharSequence s, int start, int before, int count) {
  454. positiveAction.setEnabled(s.toString().trim().length() > 0);
  455. }
  456. @Override
  457. public void afterTextChanged(Editable s) {}
  458. });
  459. // Toggling the show password CheckBox will mask or unmask the password input EditText
  460. CheckBox checkbox = dialog.getCustomView().findViewById(R.id.showPassword);
  461. checkbox.setOnCheckedChangeListener(
  462. (buttonView, isChecked) -> {
  463. passwordInput.setInputType(
  464. !isChecked ? InputType.TYPE_TEXT_VARIATION_PASSWORD : InputType.TYPE_CLASS_TEXT);
  465. passwordInput.setTransformationMethod(
  466. !isChecked ? PasswordTransformationMethod.getInstance() : null);
  467. });
  468. int widgetColor = ThemeSingleton.get().widgetColor;
  469. MDTintHelper.setTint(
  470. checkbox, widgetColor == 0 ? ContextCompat.getColor(this, R.color.accent) : widgetColor);
  471. MDTintHelper.setTint(
  472. passwordInput,
  473. widgetColor == 0 ? ContextCompat.getColor(this, R.color.accent) : widgetColor);
  474. dialog.show();
  475. positiveAction.setEnabled(false); // disabled by default
  476. }
  477. @OnClick(R.id.customView_webView)
  478. public void showCustomWebView() {
  479. int accentColor = ThemeSingleton.get().widgetColor;
  480. if (accentColor == 0) {
  481. accentColor = ContextCompat.getColor(this, R.color.accent);
  482. }
  483. ChangelogDialog.create(false, accentColor).show(getSupportFragmentManager(), "changelog");
  484. }
  485. @OnClick(R.id.customView_datePicker)
  486. public void showCustomDatePicker() {
  487. new MaterialDialog.Builder(this)
  488. .title(R.string.date_picker)
  489. .customView(R.layout.dialog_datepicker, false)
  490. .positiveText(android.R.string.ok)
  491. .negativeText(android.R.string.cancel)
  492. .show();
  493. }
  494. @OnClick(R.id.colorChooser_primary)
  495. public void showColorChooserPrimary() {
  496. new ColorChooserDialog.Builder(this, R.string.color_palette)
  497. .titleSub(R.string.colors)
  498. .preselect(primaryPreselect)
  499. .show(this);
  500. }
  501. @OnClick(R.id.colorChooser_accent)
  502. public void showColorChooserAccent() {
  503. new ColorChooserDialog.Builder(this, R.string.color_palette)
  504. .titleSub(R.string.colors)
  505. .accentMode(true)
  506. .preselect(accentPreselect)
  507. .show(this);
  508. }
  509. @OnClick(R.id.colorChooser_customColors)
  510. public void showColorChooserCustomColors() {
  511. int[][] subColors =
  512. new int[][] {
  513. new int[] {
  514. Color.parseColor("#EF5350"), Color.parseColor("#F44336"), Color.parseColor("#E53935")
  515. },
  516. new int[] {
  517. Color.parseColor("#EC407A"), Color.parseColor("#E91E63"), Color.parseColor("#D81B60")
  518. },
  519. new int[] {
  520. Color.parseColor("#AB47BC"), Color.parseColor("#9C27B0"), Color.parseColor("#8E24AA")
  521. },
  522. new int[] {
  523. Color.parseColor("#7E57C2"), Color.parseColor("#673AB7"), Color.parseColor("#5E35B1")
  524. },
  525. new int[] {
  526. Color.parseColor("#5C6BC0"), Color.parseColor("#3F51B5"), Color.parseColor("#3949AB")
  527. },
  528. new int[] {
  529. Color.parseColor("#42A5F5"), Color.parseColor("#2196F3"), Color.parseColor("#1E88E5")
  530. }
  531. };
  532. new ColorChooserDialog.Builder(this, R.string.color_palette)
  533. .titleSub(R.string.colors)
  534. .preselect(primaryPreselect)
  535. .customColors(R.array.custom_colors, subColors)
  536. .show(this);
  537. }
  538. @OnClick(R.id.colorChooser_customColorsNoSub)
  539. public void showColorChooserCustomColorsNoSub() {
  540. new ColorChooserDialog.Builder(this, R.string.color_palette)
  541. .titleSub(R.string.colors)
  542. .preselect(primaryPreselect)
  543. .customColors(R.array.custom_colors, null)
  544. .show(this);
  545. }
  546. // Receives callback from color chooser dialog
  547. @Override
  548. public void onColorSelection(ColorChooserDialog dialog, @ColorInt int color) {
  549. if (dialog.isAccentMode()) {
  550. accentPreselect = color;
  551. ThemeSingleton.get().positiveColor = DialogUtils.getActionTextStateList(this, color);
  552. ThemeSingleton.get().neutralColor = DialogUtils.getActionTextStateList(this, color);
  553. ThemeSingleton.get().negativeColor = DialogUtils.getActionTextStateList(this, color);
  554. ThemeSingleton.get().widgetColor = color;
  555. } else {
  556. primaryPreselect = color;
  557. if (getSupportActionBar() != null) {
  558. getSupportActionBar().setBackgroundDrawable(new ColorDrawable(color));
  559. }
  560. if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
  561. getWindow().setStatusBarColor(CircleView.shiftColorDown(color));
  562. getWindow().setNavigationBarColor(color);
  563. }
  564. }
  565. }
  566. @Override
  567. public void onColorChooserDismissed(ColorChooserDialog dialog) {
  568. showToast("Color chooser dismissed!");
  569. }
  570. @OnClick(R.id.themed)
  571. public void showThemed() {
  572. new MaterialDialog.Builder(this)
  573. .title(R.string.useGoogleLocationServices)
  574. .content(R.string.useGoogleLocationServicesPrompt, true)
  575. .positiveText(R.string.agree)
  576. .negativeText(R.string.disagree)
  577. .positiveColorRes(R.color.material_red_400)
  578. .negativeColorRes(R.color.material_red_400)
  579. .titleGravity(GravityEnum.CENTER)
  580. .titleColorRes(R.color.material_red_400)
  581. .contentColorRes(android.R.color.white)
  582. .backgroundColorRes(R.color.material_blue_grey_800)
  583. .dividerColorRes(R.color.accent)
  584. .btnSelector(R.drawable.md_btn_selector_custom, DialogAction.POSITIVE)
  585. .positiveColor(Color.WHITE)
  586. .negativeColorAttr(android.R.attr.textColorSecondaryInverse)
  587. .theme(Theme.DARK)
  588. .show();
  589. }
  590. @OnClick(R.id.showCancelDismiss)
  591. public void showShowCancelDismissCallbacks() {
  592. new MaterialDialog.Builder(this)
  593. .title(R.string.useGoogleLocationServices)
  594. .content(R.string.useGoogleLocationServicesPrompt)
  595. .positiveText(R.string.agree)
  596. .negativeText(R.string.disagree)
  597. .neutralText(R.string.more_info)
  598. .showListener(dialog -> showToast("onShow"))
  599. .cancelListener(dialog -> showToast("onCancel"))
  600. .dismissListener(dialog -> showToast("onDismiss"))
  601. .show();
  602. }
  603. @TargetApi(Build.VERSION_CODES.JELLY_BEAN)
  604. @OnClick(R.id.file_chooser)
  605. public void showFileChooser() {
  606. chooserDialog = R.id.file_chooser;
  607. if (ActivityCompat.checkSelfPermission(
  608. MainActivity.this, Manifest.permission.READ_EXTERNAL_STORAGE)
  609. != PackageManager.PERMISSION_GRANTED) {
  610. ActivityCompat.requestPermissions(
  611. MainActivity.this,
  612. new String[] {Manifest.permission.READ_EXTERNAL_STORAGE},
  613. STORAGE_PERMISSION_RC);
  614. return;
  615. }
  616. new FileChooserDialog.Builder(this).show(this);
  617. }
  618. @Override
  619. public void onFileSelection(FileChooserDialog dialog, File file) {
  620. showToast(file.getAbsolutePath());
  621. }
  622. @Override
  623. public void onFileChooserDismissed(FileChooserDialog dialog) {
  624. showToast("File chooser dismissed!");
  625. }
  626. @TargetApi(Build.VERSION_CODES.JELLY_BEAN)
  627. @OnClick(R.id.folder_chooser)
  628. public void showFolderChooser() {
  629. chooserDialog = R.id.folder_chooser;
  630. if (ActivityCompat.checkSelfPermission(
  631. MainActivity.this, Manifest.permission.WRITE_EXTERNAL_STORAGE)
  632. != PackageManager.PERMISSION_GRANTED) {
  633. ActivityCompat.requestPermissions(
  634. MainActivity.this,
  635. new String[] {Manifest.permission.WRITE_EXTERNAL_STORAGE},
  636. STORAGE_PERMISSION_RC);
  637. return;
  638. }
  639. new FolderChooserDialog.Builder(MainActivity.this)
  640. .chooseButton(R.string.md_choose_label)
  641. .allowNewFolder(true, 0)
  642. .show(this);
  643. }
  644. @Override
  645. public void onFolderSelection(FolderChooserDialog dialog, File folder) {
  646. showToast(folder.getAbsolutePath());
  647. }
  648. @Override
  649. public void onFolderChooserDismissed(FolderChooserDialog dialog) {
  650. showToast("Folder chooser dismissed!");
  651. }
  652. @OnClick(R.id.input)
  653. public void showInputDialog() {
  654. new MaterialDialog.Builder(this)
  655. .title(R.string.input)
  656. .content(R.string.input_content)
  657. .inputType(
  658. InputType.TYPE_CLASS_TEXT
  659. | InputType.TYPE_TEXT_VARIATION_PERSON_NAME
  660. | InputType.TYPE_TEXT_FLAG_CAP_WORDS)
  661. .inputRange(2, 16)
  662. .positiveText(R.string.submit)
  663. .input(
  664. R.string.input_hint,
  665. R.string.input_hint,
  666. false,
  667. (dialog, input) -> showToast("Hello, " + input.toString() + "!"))
  668. .show();
  669. }
  670. @OnClick(R.id.input_custominvalidation)
  671. public void showInputDialogCustomInvalidation() {
  672. new MaterialDialog.Builder(this)
  673. .title(R.string.input)
  674. .content(R.string.input_content_custominvalidation)
  675. .inputType(
  676. InputType.TYPE_CLASS_TEXT
  677. | InputType.TYPE_TEXT_VARIATION_PERSON_NAME
  678. | InputType.TYPE_TEXT_FLAG_CAP_WORDS)
  679. .positiveText(R.string.submit)
  680. .alwaysCallInputCallback() // this forces the callback to be invoked with every input change
  681. .input(
  682. R.string.input_hint,
  683. 0,
  684. false,
  685. (dialog, input) -> {
  686. if (input.toString().equalsIgnoreCase("hello")) {
  687. dialog.setContent("I told you not to type that!");
  688. dialog.getActionButton(DialogAction.POSITIVE).setEnabled(false);
  689. } else {
  690. dialog.setContent(R.string.input_content_custominvalidation);
  691. dialog.getActionButton(DialogAction.POSITIVE).setEnabled(true);
  692. }
  693. })
  694. .show();
  695. }
  696. @OnClick(R.id.input_checkPrompt)
  697. public void showInputDialogCheckPrompt() {
  698. new MaterialDialog.Builder(this)
  699. .title(R.string.input)
  700. .content(R.string.input_content)
  701. .inputType(
  702. InputType.TYPE_CLASS_TEXT
  703. | InputType.TYPE_TEXT_VARIATION_PERSON_NAME
  704. | InputType.TYPE_TEXT_FLAG_CAP_WORDS)
  705. .inputRange(2, 16)
  706. .positiveText(R.string.submit)
  707. .input(
  708. R.string.input_hint,
  709. R.string.input_hint,
  710. false,
  711. (dialog, input) -> showToast("Hello, " + input.toString() + "!"))
  712. .checkBoxPromptRes(R.string.example_prompt, true, null)
  713. .show();
  714. }
  715. @OnClick(R.id.progress1)
  716. public void showProgressDeterminateDialog() {
  717. new MaterialDialog.Builder(this)
  718. .title(R.string.progress_dialog)
  719. .content(R.string.please_wait)
  720. .contentGravity(GravityEnum.CENTER)
  721. .progress(false, 150, true)
  722. .cancelListener(
  723. dialog -> {
  724. if (thread != null) {
  725. thread.interrupt();
  726. }
  727. })
  728. .showListener(
  729. dialogInterface -> {
  730. final MaterialDialog dialog = (MaterialDialog) dialogInterface;
  731. startThread(
  732. () -> {
  733. while (dialog.getCurrentProgress() != dialog.getMaxProgress()
  734. && !Thread.currentThread().isInterrupted()) {
  735. if (dialog.isCancelled()) {
  736. break;
  737. }
  738. try {
  739. Thread.sleep(50);
  740. } catch (InterruptedException e) {
  741. break;
  742. }
  743. dialog.incrementProgress(1);
  744. }
  745. runOnUiThread(
  746. () -> {
  747. thread = null;
  748. dialog.setContent(getString(R.string.md_done_label));
  749. });
  750. });
  751. })
  752. .show();
  753. }
  754. @OnClick(R.id.progress2)
  755. public void showProgressIndeterminateDialog() {
  756. showIndeterminateProgressDialog(false);
  757. }
  758. @OnClick(R.id.progress3)
  759. public void showProgressHorizontalIndeterminateDialog() {
  760. showIndeterminateProgressDialog(true);
  761. }
  762. private void showIndeterminateProgressDialog(boolean horizontal) {
  763. new MaterialDialog.Builder(this)
  764. .title(R.string.progress_dialog)
  765. .content(R.string.please_wait)
  766. .progress(true, 0)
  767. .progressIndeterminateStyle(horizontal)
  768. .show();
  769. }
  770. @OnClick(R.id.preference_dialogs)
  771. public void showPreferenceDialogs() {
  772. startActivity(new Intent(getApplicationContext(), PreferenceActivity.class));
  773. }
  774. @Override
  775. public boolean onCreateOptionsMenu(Menu menu) {
  776. getMenuInflater().inflate(R.menu.main, menu);
  777. return super.onCreateOptionsMenu(menu);
  778. }
  779. @Override
  780. public boolean onOptionsItemSelected(MenuItem item) {
  781. if (item.getItemId() == R.id.about) {
  782. AboutDialog.show(this);
  783. return true;
  784. }
  785. return super.onOptionsItemSelected(item);
  786. }
  787. @Override
  788. public void onRequestPermissionsResult(
  789. int requestCode, String[] permissions, int[] grantResults) {
  790. super.onRequestPermissionsResult(requestCode, permissions, grantResults);
  791. if (requestCode == STORAGE_PERMISSION_RC) {
  792. if (grantResults[0] == PackageManager.PERMISSION_GRANTED) {
  793. handler.postDelayed(() -> findViewById(chooserDialog).performClick(), 1000);
  794. } else {
  795. Toast.makeText(
  796. this,
  797. "The folder or file chooser will not work without "
  798. + "permission to read external storage.",
  799. Toast.LENGTH_LONG)
  800. .show();
  801. }
  802. }
  803. }
  804. }