Showing preview only (319K chars total). Download the full file or copy to clipboard to get everything.
Repository: chrisbanes/Android-PullToRefresh
Branch: master
Commit: 3bd8ef6869c3
Files: 108
Total size: 289.0 KB
Directory structure:
gitextract_jnxqu0qu/
├── .gitignore
├── LICENSE
├── README.md
├── extras/
│ ├── PullToRefreshListFragment/
│ │ ├── AndroidManifest.xml
│ │ ├── LICENSE
│ │ ├── libs/
│ │ │ └── android-support-v4.jar
│ │ ├── pom.xml
│ │ ├── project.properties
│ │ ├── res/
│ │ │ └── layout/
│ │ │ └── need_this_for_maven.xml
│ │ └── src/
│ │ └── com/
│ │ └── handmark/
│ │ └── pulltorefresh/
│ │ └── extras/
│ │ └── listfragment/
│ │ ├── PullToRefreshBaseListFragment.java
│ │ ├── PullToRefreshExpandableListFragment.java
│ │ └── PullToRefreshListFragment.java
│ ├── PullToRefreshViewPager/
│ │ ├── AndroidManifest.xml
│ │ ├── ant.properties
│ │ ├── libs/
│ │ │ └── android-support-v4.jar
│ │ ├── pom.xml
│ │ ├── proguard-project.txt
│ │ ├── project.properties
│ │ ├── res/
│ │ │ ├── layout/
│ │ │ │ └── need_this_for_maven.xml
│ │ │ └── values/
│ │ │ └── ids.xml
│ │ └── src/
│ │ └── com/
│ │ └── handmark/
│ │ └── pulltorefresh/
│ │ └── extras/
│ │ └── viewpager/
│ │ └── PullToRefreshViewPager.java
│ └── pom.xml
├── library/
│ ├── AndroidManifest.xml
│ ├── LICENSE
│ ├── pom.xml
│ ├── project.properties
│ ├── res/
│ │ ├── anim/
│ │ │ ├── slide_in_from_bottom.xml
│ │ │ ├── slide_in_from_top.xml
│ │ │ ├── slide_out_to_bottom.xml
│ │ │ └── slide_out_to_top.xml
│ │ ├── drawable/
│ │ │ ├── indicator_bg_bottom.xml
│ │ │ └── indicator_bg_top.xml
│ │ ├── layout/
│ │ │ ├── pull_to_refresh_header_horizontal.xml
│ │ │ └── pull_to_refresh_header_vertical.xml
│ │ ├── values/
│ │ │ ├── attrs.xml
│ │ │ ├── dimens.xml
│ │ │ ├── ids.xml
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-ar/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-cs/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-de/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-es/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-fi/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-fr/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-he/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-it/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-iw/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-ja/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-ko/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-nl/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-pl/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-pt/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-pt-rBR/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-ro/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-ru/
│ │ │ └── pull_refresh_strings.xml
│ │ └── values-zh/
│ │ └── pull_refresh_strings.xml
│ └── src/
│ └── com/
│ └── handmark/
│ └── pulltorefresh/
│ └── library/
│ ├── ILoadingLayout.java
│ ├── IPullToRefresh.java
│ ├── LoadingLayoutProxy.java
│ ├── OverscrollHelper.java
│ ├── PullToRefreshAdapterViewBase.java
│ ├── PullToRefreshBase.java
│ ├── PullToRefreshExpandableListView.java
│ ├── PullToRefreshGridView.java
│ ├── PullToRefreshHorizontalScrollView.java
│ ├── PullToRefreshListView.java
│ ├── PullToRefreshScrollView.java
│ ├── PullToRefreshWebView.java
│ ├── extras/
│ │ ├── PullToRefreshWebView2.java
│ │ └── SoundPullEventListener.java
│ └── internal/
│ ├── EmptyViewMethodAccessor.java
│ ├── FlipLoadingLayout.java
│ ├── IndicatorLayout.java
│ ├── LoadingLayout.java
│ ├── RotateLoadingLayout.java
│ ├── Utils.java
│ └── ViewCompat.java
├── pom.xml
└── sample/
├── AndroidManifest.xml
├── LICENSE
├── assets/
│ └── ptr_webview2_sample.html
├── libs/
│ └── android-support-v4.jar
├── pom.xml
├── project.properties
├── res/
│ ├── layout/
│ │ ├── activity_ptr_expandable_list.xml
│ │ ├── activity_ptr_grid.xml
│ │ ├── activity_ptr_horizontalscrollview.xml
│ │ ├── activity_ptr_list.xml
│ │ ├── activity_ptr_list_fragment.xml
│ │ ├── activity_ptr_list_in_vp.xml
│ │ ├── activity_ptr_scrollview.xml
│ │ ├── activity_ptr_viewpager.xml
│ │ ├── activity_ptr_webview.xml
│ │ ├── activity_ptr_webview2.xml
│ │ └── layout_listview_in_viewpager.xml
│ └── values/
│ ├── strings.xml
│ └── styles.xml
└── src/
└── com/
└── handmark/
└── pulltorefresh/
└── samples/
├── LauncherActivity.java
├── PullToRefreshExpandableListActivity.java
├── PullToRefreshGridActivity.java
├── PullToRefreshHorizontalScrollViewActivity.java
├── PullToRefreshListActivity.java
├── PullToRefreshListFragmentActivity.java
├── PullToRefreshListInViewPagerActivity.java
├── PullToRefreshScrollViewActivity.java
├── PullToRefreshViewPagerActivity.java
├── PullToRefreshWebView2Activity.java
└── PullToRefreshWebViewActivity.java
================================================
FILE CONTENTS
================================================
================================================
FILE: .gitignore
================================================
#Android generated
bin
gen
#Eclipse
.project
.classpath
.settings
#IntelliJ IDEA
.idea
*.iml
*.ipr
*.iws
out
#Maven
target
release.properties
pom.xml.*
#Ant
build.xml
local.properties
proguard.cfg
#OSX
.DS_Store
================================================
FILE: LICENSE
================================================
Apache License
Version 2.0, January 2004
http://www.apache.org/licenses/
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
1. Definitions.
"License" shall mean the terms and conditions for use, reproduction,
and distribution as defined by Sections 1 through 9 of this document.
"Licensor" shall mean the copyright owner or entity authorized by
the copyright owner that is granting the License.
"Legal Entity" shall mean the union of the acting entity and all
other entities that control, are controlled by, or are under common
control with that entity. For the purposes of this definition,
"control" means (i) the power, direct or indirect, to cause the
direction or management of such entity, whether by contract or
otherwise, or (ii) ownership of fifty percent (50%) or more of the
outstanding shares, or (iii) beneficial ownership of such entity.
"You" (or "Your") shall mean an individual or Legal Entity
exercising permissions granted by this License.
"Source" form shall mean the preferred form for making modifications,
including but not limited to software source code, documentation
source, and configuration files.
"Object" form shall mean any form resulting from mechanical
transformation or translation of a Source form, including but
not limited to compiled object code, generated documentation,
and conversions to other media types.
"Work" shall mean the work of authorship, whether in Source or
Object form, made available under the License, as indicated by a
copyright notice that is included in or attached to the work
(an example is provided in the Appendix below).
"Derivative Works" shall mean any work, whether in Source or Object
form, that is based on (or derived from) the Work and for which the
editorial revisions, annotations, elaborations, or other modifications
represent, as a whole, an original work of authorship. For the purposes
of this License, Derivative Works shall not include works that remain
separable from, or merely link (or bind by name) to the interfaces of,
the Work and Derivative Works thereof.
"Contribution" shall mean any work of authorship, including
the original version of the Work and any modifications or additions
to that Work or Derivative Works thereof, that is intentionally
submitted to Licensor for inclusion in the Work by the copyright owner
or by an individual or Legal Entity authorized to submit on behalf of
the copyright owner. For the purposes of this definition, "submitted"
means any form of electronic, verbal, or written communication sent
to the Licensor or its representatives, including but not limited to
communication on electronic mailing lists, source code control systems,
and issue tracking systems that are managed by, or on behalf of, the
Licensor for the purpose of discussing and improving the Work, but
excluding communication that is conspicuously marked or otherwise
designated in writing by the copyright owner as "Not a Contribution."
"Contributor" shall mean Licensor and any individual or Legal Entity
on behalf of whom a Contribution has been received by Licensor and
subsequently incorporated within the Work.
2. Grant of Copyright License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
copyright license to reproduce, prepare Derivative Works of,
publicly display, publicly perform, sublicense, and distribute the
Work and such Derivative Works in Source or Object form.
3. Grant of Patent License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
(except as stated in this section) patent license to make, have made,
use, offer to sell, sell, import, and otherwise transfer the Work,
where such license applies only to those patent claims licensable
by such Contributor that are necessarily infringed by their
Contribution(s) alone or by combination of their Contribution(s)
with the Work to which such Contribution(s) was submitted. If You
institute patent litigation against any entity (including a
cross-claim or counterclaim in a lawsuit) alleging that the Work
or a Contribution incorporated within the Work constitutes direct
or contributory patent infringement, then any patent licenses
granted to You under this License for that Work shall terminate
as of the date such litigation is filed.
4. Redistribution. You may reproduce and distribute copies of the
Work or Derivative Works thereof in any medium, with or without
modifications, and in Source or Object form, provided that You
meet the following conditions:
(a) You must give any other recipients of the Work or
Derivative Works a copy of this License; and
(b) You must cause any modified files to carry prominent notices
stating that You changed the files; and
(c) You must retain, in the Source form of any Derivative Works
that You distribute, all copyright, patent, trademark, and
attribution notices from the Source form of the Work,
excluding those notices that do not pertain to any part of
the Derivative Works; and
(d) If the Work includes a "NOTICE" text file as part of its
distribution, then any Derivative Works that You distribute must
include a readable copy of the attribution notices contained
within such NOTICE file, excluding those notices that do not
pertain to any part of the Derivative Works, in at least one
of the following places: within a NOTICE text file distributed
as part of the Derivative Works; within the Source form or
documentation, if provided along with the Derivative Works; or,
within a display generated by the Derivative Works, if and
wherever such third-party notices normally appear. The contents
of the NOTICE file are for informational purposes only and
do not modify the License. You may add Your own attribution
notices within Derivative Works that You distribute, alongside
or as an addendum to the NOTICE text from the Work, provided
that such additional attribution notices cannot be construed
as modifying the License.
You may add Your own copyright statement to Your modifications and
may provide additional or different license terms and conditions
for use, reproduction, or distribution of Your modifications, or
for any such Derivative Works as a whole, provided Your use,
reproduction, and distribution of the Work otherwise complies with
the conditions stated in this License.
5. Submission of Contributions. Unless You explicitly state otherwise,
any Contribution intentionally submitted for inclusion in the Work
by You to the Licensor shall be under the terms and conditions of
this License, without any additional terms or conditions.
Notwithstanding the above, nothing herein shall supersede or modify
the terms of any separate license agreement you may have executed
with Licensor regarding such Contributions.
6. Trademarks. This License does not grant permission to use the trade
names, trademarks, service marks, or product names of the Licensor,
except as required for reasonable and customary use in describing the
origin of the Work and reproducing the content of the NOTICE file.
7. Disclaimer of Warranty. Unless required by applicable law or
agreed to in writing, Licensor provides the Work (and each
Contributor provides its Contributions) on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
implied, including, without limitation, any warranties or conditions
of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
PARTICULAR PURPOSE. You are solely responsible for determining the
appropriateness of using or redistributing the Work and assume any
risks associated with Your exercise of permissions under this License.
8. Limitation of Liability. In no event and under no legal theory,
whether in tort (including negligence), contract, or otherwise,
unless required by applicable law (such as deliberate and grossly
negligent acts) or agreed to in writing, shall any Contributor be
liable to You for damages, including any direct, indirect, special,
incidental, or consequential damages of any character arising as a
result of this License or out of the use or inability to use the
Work (including but not limited to damages for loss of goodwill,
work stoppage, computer failure or malfunction, or any and all
other commercial damages or losses), even if such Contributor
has been advised of the possibility of such damages.
9. Accepting Warranty or Additional Liability. While redistributing
the Work or Derivative Works thereof, You may choose to offer,
and charge a fee for, acceptance of support, warranty, indemnity,
or other liability obligations and/or rights consistent with this
License. However, in accepting such obligations, You may act only
on Your own behalf and on Your sole responsibility, not on behalf
of any other Contributor, and only if You agree to indemnify,
defend, and hold each Contributor harmless for any liability
incurred by, or claims asserted against, such Contributor by reason
of your accepting any such warranty or additional liability.
END OF TERMS AND CONDITIONS
APPENDIX: How to apply the Apache License to your work.
To apply the Apache License to your work, attach the following
boilerplate notice, with the fields enclosed by brackets "[]"
replaced with your own identifying information. (Don't include
the brackets!) The text should be enclosed in the appropriate
comment syntax for the file format. We also recommend that a
file or class name and description of purpose be included on the
same "printed page" as the copyright notice for easier
identification within third-party archives.
Copyright [yyyy] [name of copyright owner]
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
================================================
FILE: README.md
================================================
# PLEASE NOTE, THIS PROJECT IS NO LONGER BEING MAINTAINED
* * *
# Pull To Refresh Views for Android

This project aims to provide a reusable Pull to Refresh widget for Android. It was originally based on Johan Nilsson's [library](https://github.com/johannilsson/android-pulltorefresh) (mainly for graphics, strings and animations), but these have been replaced since.
## Features
* Supports both Pulling Down from the top, and Pulling Up from the bottom (or even both).
* Animated Scrolling for all devices.
* Over Scroll supports for devices on Android v2.3+.
* Currently works with:
* **ListView**
* **ExpandableListView**
* **GridView**
* **WebView**
* **ScrollView**
* **HorizontalScrollView**
* **ViewPager**
* Integrated End of List Listener for use of detecting when the user has scrolled to the bottom.
* Maven Support.
* Indicators to show the user when a Pull-to-Refresh is available.
* Support for **ListFragment**!
* Lots of [Customisation](https://github.com/chrisbanes/Android-PullToRefresh/wiki/Customisation) options!
Repository at <https://github.com/chrisbanes/Android-PullToRefresh>.
## Sample Application
The sample application (the source is in the repository) has been published onto Google Play for easy access:
[](http://play.google.com/store/apps/details?id=com.handmark.pulltorefresh.samples)
## Usage
To begin using the library, please see the [Quick Start Guide](https://github.com/chrisbanes/Android-PullToRefresh/wiki/Quick-Start-Guide) page.
### Customisation
Please see the [Customisation](https://github.com/chrisbanes/Android-PullToRefresh/wiki/Customisation) page for more information on how to change the behaviour and look of the View.
### Pull Up to Refresh
By default this library is set to Pull Down to Refresh, but if you want to allow Pulling Up to Refresh then you can do so. You can even set the View to enable both Pulling Up and Pulling Down using the 'both' setting. See the [Customisation](https://github.com/chrisbanes/Android-PullToRefresh/wiki/Customisation) page for more information on how to set this.
## Apps
Want to see which Apps are already using Android-PullToRefresh? Have a look [here](https://github.com/chrisbanes/Android-PullToRefresh/wiki/Apps). If you have an App which is not on the list, [let me know](http://www.senab.co.uk/contact/).
## Changelog
Please see the new [Changelog](https://github.com/chrisbanes/Android-PullToRefresh/wiki/Changelog) page to see what's recently changed.
## Pull Requests
I will gladly accept pull requests for fixes and feature enhancements but please do them in the dev branch. The master branch is for the latest stable code, dev is where I try things out before releasing them as stable. Any pull requests that are against master from now on will be closed asking for you to do another pull against dev.
## Acknowledgments
* [Stefano Dacchille](https://github.com/stefanodacchille)
* [Steve Lhomme](https://github.com/robUx4)
* [Maxim Galkin](https://github.com/mgalkin)
* [Scorcher](https://github.com/Scorcher)
## License
Copyright 2011, 2012 Chris Banes
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
================================================
FILE: extras/PullToRefreshListFragment/AndroidManifest.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.handmark.pulltorefresh.extras.listfragment"
android:versionCode="2110"
android:versionName="2.1.1" >
<application />
</manifest>
================================================
FILE: extras/PullToRefreshListFragment/LICENSE
================================================
Apache License
Version 2.0, January 2004
http://www.apache.org/licenses/
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
1. Definitions.
"License" shall mean the terms and conditions for use, reproduction,
and distribution as defined by Sections 1 through 9 of this document.
"Licensor" shall mean the copyright owner or entity authorized by
the copyright owner that is granting the License.
"Legal Entity" shall mean the union of the acting entity and all
other entities that control, are controlled by, or are under common
control with that entity. For the purposes of this definition,
"control" means (i) the power, direct or indirect, to cause the
direction or management of such entity, whether by contract or
otherwise, or (ii) ownership of fifty percent (50%) or more of the
outstanding shares, or (iii) beneficial ownership of such entity.
"You" (or "Your") shall mean an individual or Legal Entity
exercising permissions granted by this License.
"Source" form shall mean the preferred form for making modifications,
including but not limited to software source code, documentation
source, and configuration files.
"Object" form shall mean any form resulting from mechanical
transformation or translation of a Source form, including but
not limited to compiled object code, generated documentation,
and conversions to other media types.
"Work" shall mean the work of authorship, whether in Source or
Object form, made available under the License, as indicated by a
copyright notice that is included in or attached to the work
(an example is provided in the Appendix below).
"Derivative Works" shall mean any work, whether in Source or Object
form, that is based on (or derived from) the Work and for which the
editorial revisions, annotations, elaborations, or other modifications
represent, as a whole, an original work of authorship. For the purposes
of this License, Derivative Works shall not include works that remain
separable from, or merely link (or bind by name) to the interfaces of,
the Work and Derivative Works thereof.
"Contribution" shall mean any work of authorship, including
the original version of the Work and any modifications or additions
to that Work or Derivative Works thereof, that is intentionally
submitted to Licensor for inclusion in the Work by the copyright owner
or by an individual or Legal Entity authorized to submit on behalf of
the copyright owner. For the purposes of this definition, "submitted"
means any form of electronic, verbal, or written communication sent
to the Licensor or its representatives, including but not limited to
communication on electronic mailing lists, source code control systems,
and issue tracking systems that are managed by, or on behalf of, the
Licensor for the purpose of discussing and improving the Work, but
excluding communication that is conspicuously marked or otherwise
designated in writing by the copyright owner as "Not a Contribution."
"Contributor" shall mean Licensor and any individual or Legal Entity
on behalf of whom a Contribution has been received by Licensor and
subsequently incorporated within the Work.
2. Grant of Copyright License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
copyright license to reproduce, prepare Derivative Works of,
publicly display, publicly perform, sublicense, and distribute the
Work and such Derivative Works in Source or Object form.
3. Grant of Patent License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
(except as stated in this section) patent license to make, have made,
use, offer to sell, sell, import, and otherwise transfer the Work,
where such license applies only to those patent claims licensable
by such Contributor that are necessarily infringed by their
Contribution(s) alone or by combination of their Contribution(s)
with the Work to which such Contribution(s) was submitted. If You
institute patent litigation against any entity (including a
cross-claim or counterclaim in a lawsuit) alleging that the Work
or a Contribution incorporated within the Work constitutes direct
or contributory patent infringement, then any patent licenses
granted to You under this License for that Work shall terminate
as of the date such litigation is filed.
4. Redistribution. You may reproduce and distribute copies of the
Work or Derivative Works thereof in any medium, with or without
modifications, and in Source or Object form, provided that You
meet the following conditions:
(a) You must give any other recipients of the Work or
Derivative Works a copy of this License; and
(b) You must cause any modified files to carry prominent notices
stating that You changed the files; and
(c) You must retain, in the Source form of any Derivative Works
that You distribute, all copyright, patent, trademark, and
attribution notices from the Source form of the Work,
excluding those notices that do not pertain to any part of
the Derivative Works; and
(d) If the Work includes a "NOTICE" text file as part of its
distribution, then any Derivative Works that You distribute must
include a readable copy of the attribution notices contained
within such NOTICE file, excluding those notices that do not
pertain to any part of the Derivative Works, in at least one
of the following places: within a NOTICE text file distributed
as part of the Derivative Works; within the Source form or
documentation, if provided along with the Derivative Works; or,
within a display generated by the Derivative Works, if and
wherever such third-party notices normally appear. The contents
of the NOTICE file are for informational purposes only and
do not modify the License. You may add Your own attribution
notices within Derivative Works that You distribute, alongside
or as an addendum to the NOTICE text from the Work, provided
that such additional attribution notices cannot be construed
as modifying the License.
You may add Your own copyright statement to Your modifications and
may provide additional or different license terms and conditions
for use, reproduction, or distribution of Your modifications, or
for any such Derivative Works as a whole, provided Your use,
reproduction, and distribution of the Work otherwise complies with
the conditions stated in this License.
5. Submission of Contributions. Unless You explicitly state otherwise,
any Contribution intentionally submitted for inclusion in the Work
by You to the Licensor shall be under the terms and conditions of
this License, without any additional terms or conditions.
Notwithstanding the above, nothing herein shall supersede or modify
the terms of any separate license agreement you may have executed
with Licensor regarding such Contributions.
6. Trademarks. This License does not grant permission to use the trade
names, trademarks, service marks, or product names of the Licensor,
except as required for reasonable and customary use in describing the
origin of the Work and reproducing the content of the NOTICE file.
7. Disclaimer of Warranty. Unless required by applicable law or
agreed to in writing, Licensor provides the Work (and each
Contributor provides its Contributions) on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
implied, including, without limitation, any warranties or conditions
of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
PARTICULAR PURPOSE. You are solely responsible for determining the
appropriateness of using or redistributing the Work and assume any
risks associated with Your exercise of permissions under this License.
8. Limitation of Liability. In no event and under no legal theory,
whether in tort (including negligence), contract, or otherwise,
unless required by applicable law (such as deliberate and grossly
negligent acts) or agreed to in writing, shall any Contributor be
liable to You for damages, including any direct, indirect, special,
incidental, or consequential damages of any character arising as a
result of this License or out of the use or inability to use the
Work (including but not limited to damages for loss of goodwill,
work stoppage, computer failure or malfunction, or any and all
other commercial damages or losses), even if such Contributor
has been advised of the possibility of such damages.
9. Accepting Warranty or Additional Liability. While redistributing
the Work or Derivative Works thereof, You may choose to offer,
and charge a fee for, acceptance of support, warranty, indemnity,
or other liability obligations and/or rights consistent with this
License. However, in accepting such obligations, You may act only
on Your own behalf and on Your sole responsibility, not on behalf
of any other Contributor, and only if You agree to indemnify,
defend, and hold each Contributor harmless for any liability
incurred by, or claims asserted against, such Contributor by reason
of your accepting any such warranty or additional liability.
END OF TERMS AND CONDITIONS
APPENDIX: How to apply the Apache License to your work.
To apply the Apache License to your work, attach the following
boilerplate notice, with the fields enclosed by brackets "[]"
replaced with your own identifying information. (Don't include
the brackets!) The text should be enclosed in the appropriate
comment syntax for the file format. We also recommend that a
file or class name and description of purpose be included on the
same "printed page" as the copyright notice for easier
identification within third-party archives.
Copyright [yyyy] [name of copyright owner]
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
================================================
FILE: extras/PullToRefreshListFragment/pom.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.github.chrisbanes.pulltorefresh</groupId>
<artifactId>extra-listfragment</artifactId>
<packaging>apklib</packaging>
<name>Android-PullToRefresh Extras: ListFragment</name>
<parent>
<groupId>com.github.chrisbanes.pulltorefresh</groupId>
<artifactId>extras</artifactId>
<version>2.1.2-SNAPSHOT</version>
</parent>
<dependencies>
<dependency>
<groupId>com.google.android</groupId>
<artifactId>android</artifactId>
</dependency>
<dependency>
<groupId>com.google.android</groupId>
<artifactId>support-v4</artifactId>
<version>r7</version>
</dependency>
<dependency>
<groupId>${project.groupId}</groupId>
<artifactId>library</artifactId>
<type>apklib</type>
<version>${project.version}</version>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>com.jayway.maven.plugins.android.generation2</groupId>
<artifactId>android-maven-plugin</artifactId>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-eclipse-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>
================================================
FILE: extras/PullToRefreshListFragment/project.properties
================================================
# This file is automatically generated by Android Tools.
# Do not modify this file -- YOUR CHANGES WILL BE ERASED!
#
# This file must be checked in Version Control Systems.
#
# To customize properties used by the Ant build system edit
# "ant.properties", and override values to adapt the script to your
# project structure.
#
# To enable ProGuard to shrink and obfuscate your code, uncomment this (available properties: sdk.dir, user.home):
#proguard.config=${sdk.dir}/tools/proguard/proguard-android.txt:proguard-project.txt
android.library=true
# Project target.
target=android-16
android.library.reference.1=../../library
================================================
FILE: extras/PullToRefreshListFragment/res/layout/need_this_for_maven.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical" >
<!-- Need this for Maven, otherwise it doesn't build. I hate Maven. -->
</LinearLayout>
================================================
FILE: extras/PullToRefreshListFragment/src/com/handmark/pulltorefresh/extras/listfragment/PullToRefreshBaseListFragment.java
================================================
/*******************************************************************************
* Copyright 2011, 2012 Chris Banes.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*******************************************************************************/
package com.handmark.pulltorefresh.extras.listfragment;
import android.os.Bundle;
import android.support.v4.app.ListFragment;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.AbsListView;
import android.widget.ListView;
import com.handmark.pulltorefresh.library.PullToRefreshBase;
abstract class PullToRefreshBaseListFragment<T extends PullToRefreshBase<? extends AbsListView>> extends ListFragment {
private T mPullToRefreshListView;
@Override
public final View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
View layout = super.onCreateView(inflater, container, savedInstanceState);
ListView lv = (ListView) layout.findViewById(android.R.id.list);
ViewGroup parent = (ViewGroup) lv.getParent();
// Remove ListView and add PullToRefreshListView in its place
int lvIndex = parent.indexOfChild(lv);
parent.removeViewAt(lvIndex);
mPullToRefreshListView = onCreatePullToRefreshListView(inflater, savedInstanceState);
parent.addView(mPullToRefreshListView, lvIndex, lv.getLayoutParams());
return layout;
}
/**
* @return The {@link PullToRefreshBase} attached to this ListFragment.
*/
public final T getPullToRefreshListView() {
return mPullToRefreshListView;
}
/**
* Returns the {@link PullToRefreshBase} which will replace the ListView
* created from ListFragment. You should override this method if you wish to
* customise the {@link PullToRefreshBase} from the default.
*
* @param inflater - LayoutInflater which can be used to inflate from XML.
* @param savedInstanceState - Bundle passed through from
* {@link ListFragment#onCreateView(LayoutInflater, ViewGroup, Bundle)
* onCreateView(...)}
* @return The {@link PullToRefreshBase} which will replace the ListView.
*/
protected abstract T onCreatePullToRefreshListView(LayoutInflater inflater, Bundle savedInstanceState);
}
================================================
FILE: extras/PullToRefreshListFragment/src/com/handmark/pulltorefresh/extras/listfragment/PullToRefreshExpandableListFragment.java
================================================
/*******************************************************************************
* Copyright 2011, 2012 Chris Banes.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*******************************************************************************/
package com.handmark.pulltorefresh.extras.listfragment;
import android.os.Bundle;
import android.support.v4.app.ListFragment;
import android.view.LayoutInflater;
import com.handmark.pulltorefresh.library.PullToRefreshExpandableListView;
/**
* A sample implementation of how to use {@link PullToRefreshExpandableListView}
* with {@link ListFragment}. This implementation simply replaces the ListView
* that {@code ListFragment} creates with a new
* {@code PullToRefreshExpandableListView}. This means that ListFragment still
* works 100% (e.g. <code>setListShown(...)</code> ).
* <p/>
* The new PullToRefreshListView is created in the method
* {@link #onCreatePullToRefreshListView(LayoutInflater, Bundle)}. If you wish
* to customise the {@code PullToRefreshExpandableListView} then override this
* method and return your customised instance.
*
* @author Chris Banes
*
*/
public class PullToRefreshExpandableListFragment extends PullToRefreshBaseListFragment<PullToRefreshExpandableListView> {
protected PullToRefreshExpandableListView onCreatePullToRefreshListView(LayoutInflater inflater,
Bundle savedInstanceState) {
return new PullToRefreshExpandableListView(getActivity());
}
}
================================================
FILE: extras/PullToRefreshListFragment/src/com/handmark/pulltorefresh/extras/listfragment/PullToRefreshListFragment.java
================================================
/*******************************************************************************
* Copyright 2011, 2012 Chris Banes.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*******************************************************************************/
package com.handmark.pulltorefresh.extras.listfragment;
import android.os.Bundle;
import android.support.v4.app.ListFragment;
import android.view.LayoutInflater;
import com.handmark.pulltorefresh.library.PullToRefreshListView;
/**
* A sample implementation of how to use {@link PullToRefreshListView} with
* {@link ListFragment}. This implementation simply replaces the ListView that
* {@code ListFragment} creates with a new PullToRefreshListView. This means
* that ListFragment still works 100% (e.g. <code>setListShown(...)</code> ).
* <p/>
* The new PullToRefreshListView is created in the method
* {@link #onCreatePullToRefreshListView(LayoutInflater, Bundle)}. If you wish
* to customise the {@code PullToRefreshListView} then override this method and
* return your customised instance.
*
* @author Chris Banes
*
*/
public class PullToRefreshListFragment extends PullToRefreshBaseListFragment<PullToRefreshListView> {
protected PullToRefreshListView onCreatePullToRefreshListView(LayoutInflater inflater, Bundle savedInstanceState) {
return new PullToRefreshListView(getActivity());
}
}
================================================
FILE: extras/PullToRefreshViewPager/AndroidManifest.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.handmark.pulltorefresh.extras.viewpager"
android:versionCode="2110"
android:versionName="2.1.1" >
<uses-sdk android:minSdkVersion="4" />
<application />
</manifest>
================================================
FILE: extras/PullToRefreshViewPager/ant.properties
================================================
# This file is used to override default values used by the Ant build system.
#
# This file must be checked into Version Control Systems, as it is
# integral to the build system of your project.
# This file is only used by the Ant script.
# You can use this to override default values such as
# 'source.dir' for the location of your java source folder and
# 'out.dir' for the location of your output folder.
# You can also use it define how the release builds are signed by declaring
# the following properties:
# 'key.store' for the location of your keystore and
# 'key.alias' for the name of the key to use.
# The password will be asked during the build when you use the 'release' target.
================================================
FILE: extras/PullToRefreshViewPager/pom.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.github.chrisbanes.pulltorefresh</groupId>
<artifactId>extra-viewpager</artifactId>
<packaging>apklib</packaging>
<name>Android-PullToRefresh Extras: ViewPager</name>
<parent>
<groupId>com.github.chrisbanes.pulltorefresh</groupId>
<artifactId>extras</artifactId>
<version>2.1.2-SNAPSHOT</version>
</parent>
<dependencies>
<dependency>
<groupId>com.google.android</groupId>
<artifactId>android</artifactId>
</dependency>
<dependency>
<groupId>com.google.android</groupId>
<artifactId>support-v4</artifactId>
<version>r7</version>
</dependency>
<dependency>
<groupId>${project.groupId}</groupId>
<artifactId>library</artifactId>
<type>apklib</type>
<version>${project.version}</version>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>com.jayway.maven.plugins.android.generation2</groupId>
<artifactId>android-maven-plugin</artifactId>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-eclipse-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>
================================================
FILE: extras/PullToRefreshViewPager/proguard-project.txt
================================================
# To enable ProGuard in your project, edit project.properties
# to define the proguard.config property as described in that file.
#
# Add project specific ProGuard rules here.
# By default, the flags in this file are appended to flags specified
# in ${sdk.dir}/tools/proguard/proguard-android.txt
# You can edit the include path and order by changing the ProGuard
# include property in project.properties.
#
# For more details, see
# http://developer.android.com/guide/developing/tools/proguard.html
# Add any project specific keep options here:
# If your project uses WebView with JS, uncomment the following
# and specify the fully qualified class name to the JavaScript interface
# class:
#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
# public *;
#}
================================================
FILE: extras/PullToRefreshViewPager/project.properties
================================================
# This file is automatically generated by Android Tools.
# Do not modify this file -- YOUR CHANGES WILL BE ERASED!
#
# This file must be checked in Version Control Systems.
#
# To customize properties used by the Ant build system edit
# "ant.properties", and override values to adapt the script to your
# project structure.
#
# To enable ProGuard to shrink and obfuscate your code, uncomment this (available properties: sdk.dir, user.home):
#proguard.config=${sdk.dir}/tools/proguard/proguard-android.txt:proguard-project.txt
android.library=true
# Project target.
target=android-16
android.library.reference.1=../../library
================================================
FILE: extras/PullToRefreshViewPager/res/layout/need_this_for_maven.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical" >
<!-- Need this for Maven, otherwise it doesn't build. I hate Maven. -->
</LinearLayout>
================================================
FILE: extras/PullToRefreshViewPager/res/values/ids.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<resources>
<item type="id" name="viewpager" />
</resources>
================================================
FILE: extras/PullToRefreshViewPager/src/com/handmark/pulltorefresh/extras/viewpager/PullToRefreshViewPager.java
================================================
/*******************************************************************************
* Copyright 2011, 2012 Chris Banes.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*******************************************************************************/
package com.handmark.pulltorefresh.extras.viewpager;
import android.content.Context;
import android.support.v4.view.PagerAdapter;
import android.support.v4.view.ViewPager;
import android.util.AttributeSet;
import com.handmark.pulltorefresh.library.PullToRefreshBase;
public class PullToRefreshViewPager extends PullToRefreshBase<ViewPager> {
public PullToRefreshViewPager(Context context) {
super(context);
}
public PullToRefreshViewPager(Context context, AttributeSet attrs) {
super(context, attrs);
}
@Override
public final Orientation getPullToRefreshScrollDirection() {
return Orientation.HORIZONTAL;
}
@Override
protected ViewPager createRefreshableView(Context context, AttributeSet attrs) {
ViewPager viewPager = new ViewPager(context, attrs);
viewPager.setId(R.id.viewpager);
return viewPager;
}
@Override
protected boolean isReadyForPullStart() {
ViewPager refreshableView = getRefreshableView();
PagerAdapter adapter = refreshableView.getAdapter();
if (null != adapter) {
return refreshableView.getCurrentItem() == 0;
}
return false;
}
@Override
protected boolean isReadyForPullEnd() {
ViewPager refreshableView = getRefreshableView();
PagerAdapter adapter = refreshableView.getAdapter();
if (null != adapter) {
return refreshableView.getCurrentItem() == adapter.getCount() - 1;
}
return false;
}
}
================================================
FILE: extras/pom.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.github.chrisbanes.pulltorefresh</groupId>
<artifactId>extras</artifactId>
<packaging>pom</packaging>
<name>Android-PullToRefresh Extras</name>
<parent>
<groupId>com.github.chrisbanes.pulltorefresh</groupId>
<artifactId>parent</artifactId>
<version>2.1.2-SNAPSHOT</version>
</parent>
<modules>
<module>PullToRefreshListFragment</module>
<module>PullToRefreshViewPager</module>
</modules>
</project>
================================================
FILE: library/AndroidManifest.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.handmark.pulltorefresh.library"
android:versionCode="2110"
android:versionName="2.1.1" >
<uses-sdk android:minSdkVersion="4" />
<application />
</manifest>
================================================
FILE: library/LICENSE
================================================
Apache License
Version 2.0, January 2004
http://www.apache.org/licenses/
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
1. Definitions.
"License" shall mean the terms and conditions for use, reproduction,
and distribution as defined by Sections 1 through 9 of this document.
"Licensor" shall mean the copyright owner or entity authorized by
the copyright owner that is granting the License.
"Legal Entity" shall mean the union of the acting entity and all
other entities that control, are controlled by, or are under common
control with that entity. For the purposes of this definition,
"control" means (i) the power, direct or indirect, to cause the
direction or management of such entity, whether by contract or
otherwise, or (ii) ownership of fifty percent (50%) or more of the
outstanding shares, or (iii) beneficial ownership of such entity.
"You" (or "Your") shall mean an individual or Legal Entity
exercising permissions granted by this License.
"Source" form shall mean the preferred form for making modifications,
including but not limited to software source code, documentation
source, and configuration files.
"Object" form shall mean any form resulting from mechanical
transformation or translation of a Source form, including but
not limited to compiled object code, generated documentation,
and conversions to other media types.
"Work" shall mean the work of authorship, whether in Source or
Object form, made available under the License, as indicated by a
copyright notice that is included in or attached to the work
(an example is provided in the Appendix below).
"Derivative Works" shall mean any work, whether in Source or Object
form, that is based on (or derived from) the Work and for which the
editorial revisions, annotations, elaborations, or other modifications
represent, as a whole, an original work of authorship. For the purposes
of this License, Derivative Works shall not include works that remain
separable from, or merely link (or bind by name) to the interfaces of,
the Work and Derivative Works thereof.
"Contribution" shall mean any work of authorship, including
the original version of the Work and any modifications or additions
to that Work or Derivative Works thereof, that is intentionally
submitted to Licensor for inclusion in the Work by the copyright owner
or by an individual or Legal Entity authorized to submit on behalf of
the copyright owner. For the purposes of this definition, "submitted"
means any form of electronic, verbal, or written communication sent
to the Licensor or its representatives, including but not limited to
communication on electronic mailing lists, source code control systems,
and issue tracking systems that are managed by, or on behalf of, the
Licensor for the purpose of discussing and improving the Work, but
excluding communication that is conspicuously marked or otherwise
designated in writing by the copyright owner as "Not a Contribution."
"Contributor" shall mean Licensor and any individual or Legal Entity
on behalf of whom a Contribution has been received by Licensor and
subsequently incorporated within the Work.
2. Grant of Copyright License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
copyright license to reproduce, prepare Derivative Works of,
publicly display, publicly perform, sublicense, and distribute the
Work and such Derivative Works in Source or Object form.
3. Grant of Patent License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
(except as stated in this section) patent license to make, have made,
use, offer to sell, sell, import, and otherwise transfer the Work,
where such license applies only to those patent claims licensable
by such Contributor that are necessarily infringed by their
Contribution(s) alone or by combination of their Contribution(s)
with the Work to which such Contribution(s) was submitted. If You
institute patent litigation against any entity (including a
cross-claim or counterclaim in a lawsuit) alleging that the Work
or a Contribution incorporated within the Work constitutes direct
or contributory patent infringement, then any patent licenses
granted to You under this License for that Work shall terminate
as of the date such litigation is filed.
4. Redistribution. You may reproduce and distribute copies of the
Work or Derivative Works thereof in any medium, with or without
modifications, and in Source or Object form, provided that You
meet the following conditions:
(a) You must give any other recipients of the Work or
Derivative Works a copy of this License; and
(b) You must cause any modified files to carry prominent notices
stating that You changed the files; and
(c) You must retain, in the Source form of any Derivative Works
that You distribute, all copyright, patent, trademark, and
attribution notices from the Source form of the Work,
excluding those notices that do not pertain to any part of
the Derivative Works; and
(d) If the Work includes a "NOTICE" text file as part of its
distribution, then any Derivative Works that You distribute must
include a readable copy of the attribution notices contained
within such NOTICE file, excluding those notices that do not
pertain to any part of the Derivative Works, in at least one
of the following places: within a NOTICE text file distributed
as part of the Derivative Works; within the Source form or
documentation, if provided along with the Derivative Works; or,
within a display generated by the Derivative Works, if and
wherever such third-party notices normally appear. The contents
of the NOTICE file are for informational purposes only and
do not modify the License. You may add Your own attribution
notices within Derivative Works that You distribute, alongside
or as an addendum to the NOTICE text from the Work, provided
that such additional attribution notices cannot be construed
as modifying the License.
You may add Your own copyright statement to Your modifications and
may provide additional or different license terms and conditions
for use, reproduction, or distribution of Your modifications, or
for any such Derivative Works as a whole, provided Your use,
reproduction, and distribution of the Work otherwise complies with
the conditions stated in this License.
5. Submission of Contributions. Unless You explicitly state otherwise,
any Contribution intentionally submitted for inclusion in the Work
by You to the Licensor shall be under the terms and conditions of
this License, without any additional terms or conditions.
Notwithstanding the above, nothing herein shall supersede or modify
the terms of any separate license agreement you may have executed
with Licensor regarding such Contributions.
6. Trademarks. This License does not grant permission to use the trade
names, trademarks, service marks, or product names of the Licensor,
except as required for reasonable and customary use in describing the
origin of the Work and reproducing the content of the NOTICE file.
7. Disclaimer of Warranty. Unless required by applicable law or
agreed to in writing, Licensor provides the Work (and each
Contributor provides its Contributions) on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
implied, including, without limitation, any warranties or conditions
of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
PARTICULAR PURPOSE. You are solely responsible for determining the
appropriateness of using or redistributing the Work and assume any
risks associated with Your exercise of permissions under this License.
8. Limitation of Liability. In no event and under no legal theory,
whether in tort (including negligence), contract, or otherwise,
unless required by applicable law (such as deliberate and grossly
negligent acts) or agreed to in writing, shall any Contributor be
liable to You for damages, including any direct, indirect, special,
incidental, or consequential damages of any character arising as a
result of this License or out of the use or inability to use the
Work (including but not limited to damages for loss of goodwill,
work stoppage, computer failure or malfunction, or any and all
other commercial damages or losses), even if such Contributor
has been advised of the possibility of such damages.
9. Accepting Warranty or Additional Liability. While redistributing
the Work or Derivative Works thereof, You may choose to offer,
and charge a fee for, acceptance of support, warranty, indemnity,
or other liability obligations and/or rights consistent with this
License. However, in accepting such obligations, You may act only
on Your own behalf and on Your sole responsibility, not on behalf
of any other Contributor, and only if You agree to indemnify,
defend, and hold each Contributor harmless for any liability
incurred by, or claims asserted against, such Contributor by reason
of your accepting any such warranty or additional liability.
END OF TERMS AND CONDITIONS
APPENDIX: How to apply the Apache License to your work.
To apply the Apache License to your work, attach the following
boilerplate notice, with the fields enclosed by brackets "[]"
replaced with your own identifying information. (Don't include
the brackets!) The text should be enclosed in the appropriate
comment syntax for the file format. We also recommend that a
file or class name and description of purpose be included on the
same "printed page" as the copyright notice for easier
identification within third-party archives.
Copyright [yyyy] [name of copyright owner]
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
================================================
FILE: library/pom.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.github.chrisbanes.pulltorefresh</groupId>
<artifactId>library</artifactId>
<packaging>apklib</packaging>
<name>Android-PullToRefresh Library</name>
<parent>
<groupId>com.github.chrisbanes.pulltorefresh</groupId>
<artifactId>parent</artifactId>
<version>2.1.2-SNAPSHOT</version>
</parent>
<dependencies>
<dependency>
<groupId>com.google.android</groupId>
<artifactId>android</artifactId>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>com.jayway.maven.plugins.android.generation2</groupId>
<artifactId>android-maven-plugin</artifactId>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-eclipse-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>
================================================
FILE: library/project.properties
================================================
# This file is automatically generated by Android Tools.
# Do not modify this file -- YOUR CHANGES WILL BE ERASED!
#
# This file must be checked in Version Control Systems.
#
# To customize properties used by the Ant build system use,
# "ant.properties", and override values to adapt the script to your
# project structure.
# Project target.
target=android-16
android.library=true
================================================
FILE: library/res/anim/slide_in_from_bottom.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<!--
Copyright (C) 2009 The Android Open Source Project
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<translate xmlns:android="http://schemas.android.com/apk/res/android"
android:duration="@android:integer/config_longAnimTime"
android:fromYDelta="100%p"
android:toYDelta="0" />
================================================
FILE: library/res/anim/slide_in_from_top.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<!--
Copyright (C) 2009 The Android Open Source Project
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<translate xmlns:android="http://schemas.android.com/apk/res/android"
android:duration="@android:integer/config_longAnimTime"
android:fromYDelta="-100%p"
android:toYDelta="0" />
================================================
FILE: library/res/anim/slide_out_to_bottom.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<!--
Copyright (C) 2009 The Android Open Source Project
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<translate xmlns:android="http://schemas.android.com/apk/res/android"
android:duration="@android:integer/config_longAnimTime"
android:fromYDelta="0"
android:toYDelta="100%p" />
================================================
FILE: library/res/anim/slide_out_to_top.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<!--
Copyright (C) 2009 The Android Open Source Project
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<translate xmlns:android="http://schemas.android.com/apk/res/android"
android:duration="@android:integer/config_longAnimTime"
android:fromYDelta="0"
android:toYDelta="-100%p" />
================================================
FILE: library/res/drawable/indicator_bg_bottom.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="rectangle" >
<solid android:color="#40000000" />
<!--
I know the android:radius is useless here but it's needed to fix an old bug:
http://code.google.com/p/android/issues/detail?id=939
-->
<corners
android:bottomLeftRadius="0dp"
android:bottomRightRadius="0dp"
android:radius="1dp"
android:topLeftRadius="@dimen/indicator_corner_radius"
android:topRightRadius="@dimen/indicator_corner_radius" />
</shape>
================================================
FILE: library/res/drawable/indicator_bg_top.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="rectangle" >
<solid android:color="#40000000" />
<!--
I know the android:radius is useless here but it's needed to fix an old bug:
http://code.google.com/p/android/issues/detail?id=939
-->
<corners
android:bottomLeftRadius="@dimen/indicator_corner_radius"
android:bottomRightRadius="@dimen/indicator_corner_radius"
android:radius="1dp"
android:topLeftRadius="0dp"
android:topRightRadius="0dp" />
</shape>
================================================
FILE: library/res/layout/pull_to_refresh_header_horizontal.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<merge xmlns:android="http://schemas.android.com/apk/res/android" >
<FrameLayout
android:id="@+id/fl_inner"
android:layout_width="wrap_content"
android:layout_height="fill_parent"
android:paddingBottom="@dimen/header_footer_top_bottom_padding"
android:paddingLeft="@dimen/header_footer_left_right_padding"
android:paddingRight="@dimen/header_footer_left_right_padding"
android:paddingTop="@dimen/header_footer_top_bottom_padding" >
<ImageView
android:id="@+id/pull_to_refresh_image"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center" />
<ProgressBar
android:id="@+id/pull_to_refresh_progress"
style="?android:attr/progressBarStyleSmall"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:indeterminate="true"
android:visibility="gone" />
</FrameLayout>
</merge>
================================================
FILE: library/res/layout/pull_to_refresh_header_vertical.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<merge xmlns:android="http://schemas.android.com/apk/res/android" >
<FrameLayout
android:id="@+id/fl_inner"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:paddingBottom="@dimen/header_footer_top_bottom_padding"
android:paddingLeft="@dimen/header_footer_left_right_padding"
android:paddingRight="@dimen/header_footer_left_right_padding"
android:paddingTop="@dimen/header_footer_top_bottom_padding" >
<FrameLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="left|center_vertical" >
<ImageView
android:id="@+id/pull_to_refresh_image"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center" />
<ProgressBar
android:id="@+id/pull_to_refresh_progress"
style="?android:attr/progressBarStyleSmall"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:indeterminate="true"
android:visibility="gone" />
</FrameLayout>
<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:gravity="center_horizontal"
android:orientation="vertical" >
<TextView
android:id="@+id/pull_to_refresh_text"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:singleLine="true"
android:textAppearance="?android:attr/textAppearance"
android:textStyle="bold" />
<TextView
android:id="@+id/pull_to_refresh_sub_text"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:singleLine="true"
android:textAppearance="?android:attr/textAppearanceSmall"
android:visibility="gone" />
</LinearLayout>
</FrameLayout>
</merge>
================================================
FILE: library/res/values/attrs.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<resources>
<declare-styleable name="PullToRefresh">
<!-- A drawable to use as the background of the Refreshable View -->
<attr name="ptrRefreshableViewBackground" format="reference|color" />
<!-- A drawable to use as the background of the Header and Footer Loading Views -->
<attr name="ptrHeaderBackground" format="reference|color" />
<!-- Text Color of the Header and Footer Loading Views -->
<attr name="ptrHeaderTextColor" format="reference|color" />
<!-- Text Color of the Header and Footer Loading Views Sub Header -->
<attr name="ptrHeaderSubTextColor" format="reference|color" />
<!-- Mode of Pull-to-Refresh that should be used -->
<attr name="ptrMode">
<flag name="disabled" value="0x0" />
<flag name="pullFromStart" value="0x1" />
<flag name="pullFromEnd" value="0x2" />
<flag name="both" value="0x3" />
<flag name="manualOnly" value="0x4" />
<!-- These last two are depreacted -->
<flag name="pullDownFromTop" value="0x1" />
<flag name="pullUpFromBottom" value="0x2" />
</attr>
<!-- Whether the Indicator overlay(s) should be used -->
<attr name="ptrShowIndicator" format="reference|boolean" />
<!-- Drawable to use as Loading Indicator. Changes both Header and Footer. -->
<attr name="ptrDrawable" format="reference" />
<!-- Drawable to use as Loading Indicator in the Header View. Overrides value set in ptrDrawable. -->
<attr name="ptrDrawableStart" format="reference" />
<!-- Drawable to use as Loading Indicator in the Footer View. Overrides value set in ptrDrawable. -->
<attr name="ptrDrawableEnd" format="reference" />
<!-- Whether Android's built-in Over Scroll should be utilised for Pull-to-Refresh. -->
<attr name="ptrOverScroll" format="reference|boolean" />
<!-- Base text color, typeface, size, and style for Header and Footer Loading Views -->
<attr name="ptrHeaderTextAppearance" format="reference" />
<!-- Base text color, typeface, size, and style for Header and Footer Loading Views Sub Header -->
<attr name="ptrSubHeaderTextAppearance" format="reference" />
<!-- Style of Animation should be used displayed when pulling. -->
<attr name="ptrAnimationStyle">
<flag name="rotate" value="0x0" />
<flag name="flip" value="0x1" />
</attr>
<!-- Whether the user can scroll while the View is Refreshing -->
<attr name="ptrScrollingWhileRefreshingEnabled" format="reference|boolean" />
<!--
Whether PullToRefreshListView has it's extras enabled. This allows the user to be
able to scroll while refreshing, and behaves better. It acheives this by adding
Header and/or Footer Views to the ListView.
-->
<attr name="ptrListViewExtrasEnabled" format="reference|boolean" />
<!--
Whether the Drawable should be continually rotated as you pull. This only
takes effect when using the 'Rotate' Animation Style.
-->
<attr name="ptrRotateDrawableWhilePulling" format="reference|boolean" />
<!-- BELOW HERE ARE DEPRECEATED. DO NOT USE. -->
<attr name="ptrAdapterViewBackground" format="reference|color" />
<attr name="ptrDrawableTop" format="reference" />
<attr name="ptrDrawableBottom" format="reference" />
</declare-styleable>
</resources>
================================================
FILE: library/res/values/dimens.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<resources>
<dimen name="indicator_right_padding">10dp</dimen>
<dimen name="indicator_corner_radius">12dp</dimen>
<dimen name="indicator_internal_padding">4dp</dimen>
<dimen name="header_footer_left_right_padding">24dp</dimen>
<dimen name="header_footer_top_bottom_padding">12dp</dimen>
</resources>
================================================
FILE: library/res/values/ids.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<resources>
<item type="id" name="gridview" />
<item type="id" name="webview" />
<item type="id" name="scrollview" />
</resources>
================================================
FILE: library/res/values/pull_refresh_strings.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<resources>
<string name="pull_to_refresh_pull_label">Pull to refresh…</string>
<string name="pull_to_refresh_release_label">Release to refresh…</string>
<string name="pull_to_refresh_refreshing_label">Loading…</string>
<!-- Just use standard Pull Down String when pulling up. These can be set for languages which require it -->
<string name="pull_to_refresh_from_bottom_pull_label">@string/pull_to_refresh_pull_label</string>
<string name="pull_to_refresh_from_bottom_release_label">@string/pull_to_refresh_release_label</string>
<string name="pull_to_refresh_from_bottom_refreshing_label">@string/pull_to_refresh_refreshing_label</string>
</resources>
================================================
FILE: library/res/values-ar/pull_refresh_strings.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<resources>
<string name="pull_to_refresh_pull_label">اسحب للتحديث…</string>
<string name="pull_to_refresh_release_label">اترك للتحديث…</string>
<string name="pull_to_refresh_refreshing_label">تحميل…</string>
</resources>
================================================
FILE: library/res/values-cs/pull_refresh_strings.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<resources>
<string name="pull_to_refresh_pull_label">Tažením aktualizujete…</string>
<string name="pull_to_refresh_release_label">Uvolněním aktualizujete…</string>
<string name="pull_to_refresh_refreshing_label">Načítání…</string>
</resources>
================================================
FILE: library/res/values-de/pull_refresh_strings.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<resources>
<string name="pull_to_refresh_pull_label">Ziehen zum Aktualisieren…</string>
<string name="pull_to_refresh_release_label">Loslassen zum Aktualisieren…</string>
<string name="pull_to_refresh_refreshing_label">Laden…</string>
</resources>
================================================
FILE: library/res/values-es/pull_refresh_strings.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<resources>
<string name="pull_to_refresh_pull_label">Tirar para actualizar…</string>
<string name="pull_to_refresh_release_label">Soltar para actualizar…</string>
<string name="pull_to_refresh_refreshing_label">Cargando…</string>
</resources>
================================================
FILE: library/res/values-fi/pull_refresh_strings.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<resources>
<string name="pull_to_refresh_pull_label">Päivitä vetämällä alas…</string>
<string name="pull_to_refresh_release_label">Päivitä vapauttamalla…</string>
<string name="pull_to_refresh_refreshing_label">Päivitetään…</string>
<!-- Just use standard Pull Down String when pulling up. These can be set for languages which require it -->
<string name="pull_to_refresh_from_bottom_pull_label">Päivitä vetämällä ylös…</string>
<string name="pull_to_refresh_from_bottom_release_label">@string/pull_to_refresh_release_label</string>
<string name="pull_to_refresh_from_bottom_refreshing_label">@string/pull_to_refresh_refreshing_label</string>
</resources>
================================================
FILE: library/res/values-fr/pull_refresh_strings.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<resources>
<string name="pull_to_refresh_pull_label">Tirez pour rafraîchir…</string>
<string name="pull_to_refresh_release_label">Relâcher pour rafraîchir…</string>
<string name="pull_to_refresh_refreshing_label">Chargement…</string>
</resources>
================================================
FILE: library/res/values-he/pull_refresh_strings.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<resources>
<string name="pull_to_refresh_pull_label">משוך לרענון…</string>
<string name="pull_to_refresh_release_label">שחרר לרענון…</string>
<string name="pull_to_refresh_refreshing_label">טוען…</string>
</resources>
================================================
FILE: library/res/values-it/pull_refresh_strings.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<resources>
<string name="pull_to_refresh_pull_label">Tira per aggiornare…</string>
<string name="pull_to_refresh_release_label">Rilascia per aggionare…</string>
<string name="pull_to_refresh_refreshing_label">Caricamento…</string>
</resources>
================================================
FILE: library/res/values-iw/pull_refresh_strings.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<resources>
<string name="pull_to_refresh_pull_label">משוך לרענון…</string>
<string name="pull_to_refresh_release_label">שחרר לרענון…</string>
<string name="pull_to_refresh_refreshing_label">טוען…</string>
</resources>
================================================
FILE: library/res/values-ja/pull_refresh_strings.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<resources>
<string name="pull_to_refresh_pull_label">画面を引っ張って…</string>
<string name="pull_to_refresh_release_label">指を離して更新…</string>
<string name="pull_to_refresh_refreshing_label">読み込み中…</string>
</resources>
================================================
FILE: library/res/values-ko/pull_refresh_strings.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<resources>
<string name="pull_to_refresh_pull_label">당겨서 새로 고침…</string>
<string name="pull_to_refresh_release_label">놓아서 새로 고침…</string>
<string name="pull_to_refresh_refreshing_label">로드 중…</string>
</resources>
================================================
FILE: library/res/values-nl/pull_refresh_strings.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<resources>
<string name="pull_to_refresh_pull_label">Sleep om te vernieuwen…</string>
<string name="pull_to_refresh_release_label">Loslaten om te vernieuwen…</string>
<string name="pull_to_refresh_refreshing_label">Laden…</string>
</resources>
================================================
FILE: library/res/values-pl/pull_refresh_strings.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<resources>
<string name="pull_to_refresh_pull_label">Pociągnij, aby odświeżyć…</string>
<string name="pull_to_refresh_release_label">Puść, aby odświeżyć…</string>
<string name="pull_to_refresh_refreshing_label">Wczytywanie…</string>
</resources>
================================================
FILE: library/res/values-pt/pull_refresh_strings.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<resources>
<string name="pull_to_refresh_pull_label">Puxe para atualizar…</string>
<string name="pull_to_refresh_release_label">Liberação para atualizar…</string>
<string name="pull_to_refresh_refreshing_label">A carregar…</string>
</resources>
================================================
FILE: library/res/values-pt-rBR/pull_refresh_strings.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<resources>
<string name="pull_to_refresh_pull_label">Puxe para atualizar…</string>
<string name="pull_to_refresh_release_label">Libere para atualizar…</string>
<string name="pull_to_refresh_refreshing_label">Carregando…</string>
</resources>
================================================
FILE: library/res/values-ro/pull_refresh_strings.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<resources>
<string name="pull_to_refresh_pull_label">Trage pentru a reîmprospăta…</string>
<string name="pull_to_refresh_release_label">Eliberează pentru a reîmprospăta…</string>
<string name="pull_to_refresh_refreshing_label">Încărcare…</string>
</resources>
================================================
FILE: library/res/values-ru/pull_refresh_strings.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<resources>
<string name="pull_to_refresh_pull_label">Потяните для обновления…</string>
<string name="pull_to_refresh_release_label">Отпустите для обновления…</string>
<string name="pull_to_refresh_refreshing_label">Загрузка…</string>
</resources>
================================================
FILE: library/res/values-zh/pull_refresh_strings.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<resources>
<string name="pull_to_refresh_pull_label">下拉刷新…</string>
<string name="pull_to_refresh_release_label">放开以刷新…</string>
<string name="pull_to_refresh_refreshing_label">正在载入…</string>
</resources>
================================================
FILE: library/src/com/handmark/pulltorefresh/library/ILoadingLayout.java
================================================
package com.handmark.pulltorefresh.library;
import android.graphics.Typeface;
import android.graphics.drawable.Drawable;
public interface ILoadingLayout {
/**
* Set the Last Updated Text. This displayed under the main label when
* Pulling
*
* @param label - Label to set
*/
public void setLastUpdatedLabel(CharSequence label);
/**
* Set the drawable used in the loading layout. This is the same as calling
* <code>setLoadingDrawable(drawable, Mode.BOTH)</code>
*
* @param drawable - Drawable to display
*/
public void setLoadingDrawable(Drawable drawable);
/**
* Set Text to show when the Widget is being Pulled
* <code>setPullLabel(releaseLabel, Mode.BOTH)</code>
*
* @param pullLabel - CharSequence to display
*/
public void setPullLabel(CharSequence pullLabel);
/**
* Set Text to show when the Widget is refreshing
* <code>setRefreshingLabel(releaseLabel, Mode.BOTH)</code>
*
* @param refreshingLabel - CharSequence to display
*/
public void setRefreshingLabel(CharSequence refreshingLabel);
/**
* Set Text to show when the Widget is being pulled, and will refresh when
* released. This is the same as calling
* <code>setReleaseLabel(releaseLabel, Mode.BOTH)</code>
*
* @param releaseLabel - CharSequence to display
*/
public void setReleaseLabel(CharSequence releaseLabel);
/**
* Set's the Sets the typeface and style in which the text should be
* displayed. Please see
* {@link android.widget.TextView#setTypeface(Typeface)
* TextView#setTypeface(Typeface)}.
*/
public void setTextTypeface(Typeface tf);
}
================================================
FILE: library/src/com/handmark/pulltorefresh/library/IPullToRefresh.java
================================================
/*******************************************************************************
* Copyright 2011, 2012 Chris Banes.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*******************************************************************************/
package com.handmark.pulltorefresh.library;
import android.view.View;
import android.view.animation.Interpolator;
import com.handmark.pulltorefresh.library.PullToRefreshBase.Mode;
import com.handmark.pulltorefresh.library.PullToRefreshBase.OnPullEventListener;
import com.handmark.pulltorefresh.library.PullToRefreshBase.OnRefreshListener;
import com.handmark.pulltorefresh.library.PullToRefreshBase.OnRefreshListener2;
import com.handmark.pulltorefresh.library.PullToRefreshBase.State;
public interface IPullToRefresh<T extends View> {
/**
* Demos the Pull-to-Refresh functionality to the user so that they are
* aware it is there. This could be useful when the user first opens your
* app, etc. The animation will only happen if the Refresh View (ListView,
* ScrollView, etc) is in a state where a Pull-to-Refresh could occur by a
* user's touch gesture (i.e. scrolled to the top/bottom).
*
* @return true - if the Demo has been started, false if not.
*/
public boolean demo();
/**
* Get the mode that this view is currently in. This is only really useful
* when using <code>Mode.BOTH</code>.
*
* @return Mode that the view is currently in
*/
public Mode getCurrentMode();
/**
* Returns whether the Touch Events are filtered or not. If true is
* returned, then the View will only use touch events where the difference
* in the Y-axis is greater than the difference in the X-axis. This means
* that the View will not interfere when it is used in a horizontal
* scrolling View (such as a ViewPager).
*
* @return boolean - true if the View is filtering Touch Events
*/
public boolean getFilterTouchEvents();
/**
* Returns a proxy object which allows you to call methods on all of the
* LoadingLayouts (the Views which show when Pulling/Refreshing).
* <p />
* You should not keep the result of this method any longer than you need
* it.
*
* @return Object which will proxy any calls you make on it, to all of the
* LoadingLayouts.
*/
public ILoadingLayout getLoadingLayoutProxy();
/**
* Returns a proxy object which allows you to call methods on the
* LoadingLayouts (the Views which show when Pulling/Refreshing). The actual
* LoadingLayout(s) which will be affected, are chosen by the parameters you
* give.
* <p />
* You should not keep the result of this method any longer than you need
* it.
*
* @param includeStart - Whether to include the Start/Header Views
* @param includeEnd - Whether to include the End/Footer Views
* @return Object which will proxy any calls you make on it, to the
* LoadingLayouts included.
*/
public ILoadingLayout getLoadingLayoutProxy(boolean includeStart, boolean includeEnd);
/**
* Get the mode that this view has been set to. If this returns
* <code>Mode.BOTH</code>, you can use <code>getCurrentMode()</code> to
* check which mode the view is currently in
*
* @return Mode that the view has been set to
*/
public Mode getMode();
/**
* Get the Wrapped Refreshable View. Anything returned here has already been
* added to the content view.
*
* @return The View which is currently wrapped
*/
public T getRefreshableView();
/**
* Get whether the 'Refreshing' View should be automatically shown when
* refreshing. Returns true by default.
*
* @return - true if the Refreshing View will be show
*/
public boolean getShowViewWhileRefreshing();
/**
* @return - The state that the View is currently in.
*/
public State getState();
/**
* Whether Pull-to-Refresh is enabled
*
* @return enabled
*/
public boolean isPullToRefreshEnabled();
/**
* Gets whether Overscroll support is enabled. This is different to
* Android's standard Overscroll support (the edge-glow) which is available
* from GINGERBREAD onwards
*
* @return true - if both PullToRefresh-OverScroll and Android's inbuilt
* OverScroll are enabled
*/
public boolean isPullToRefreshOverScrollEnabled();
/**
* Returns whether the Widget is currently in the Refreshing mState
*
* @return true if the Widget is currently refreshing
*/
public boolean isRefreshing();
/**
* Returns whether the widget has enabled scrolling on the Refreshable View
* while refreshing.
*
* @return true if the widget has enabled scrolling while refreshing
*/
public boolean isScrollingWhileRefreshingEnabled();
/**
* Mark the current Refresh as complete. Will Reset the UI and hide the
* Refreshing View
*/
public void onRefreshComplete();
/**
* Set the Touch Events to be filtered or not. If set to true, then the View
* will only use touch events where the difference in the Y-axis is greater
* than the difference in the X-axis. This means that the View will not
* interfere when it is used in a horizontal scrolling View (such as a
* ViewPager), but will restrict which types of finger scrolls will trigger
* the View.
*
* @param filterEvents - true if you want to filter Touch Events. Default is
* true.
*/
public void setFilterTouchEvents(boolean filterEvents);
/**
* Set the mode of Pull-to-Refresh that this view will use.
*
* @param mode - Mode to set the View to
*/
public void setMode(Mode mode);
/**
* Set OnPullEventListener for the Widget
*
* @param listener - Listener to be used when the Widget has a pull event to
* propogate.
*/
public void setOnPullEventListener(OnPullEventListener<T> listener);
/**
* Set OnRefreshListener for the Widget
*
* @param listener - Listener to be used when the Widget is set to Refresh
*/
public void setOnRefreshListener(OnRefreshListener<T> listener);
/**
* Set OnRefreshListener for the Widget
*
* @param listener - Listener to be used when the Widget is set to Refresh
*/
public void setOnRefreshListener(OnRefreshListener2<T> listener);
/**
* Sets whether Overscroll support is enabled. This is different to
* Android's standard Overscroll support (the edge-glow). This setting only
* takes effect when running on device with Android v2.3 or greater.
*
* @param enabled - true if you want Overscroll enabled
*/
public void setPullToRefreshOverScrollEnabled(boolean enabled);
/**
* Sets the Widget to be in the refresh state. The UI will be updated to
* show the 'Refreshing' view, and be scrolled to show such.
*/
public void setRefreshing();
/**
* Sets the Widget to be in the refresh state. The UI will be updated to
* show the 'Refreshing' view.
*
* @param doScroll - true if you want to force a scroll to the Refreshing
* view.
*/
public void setRefreshing(boolean doScroll);
/**
* Sets the Animation Interpolator that is used for animated scrolling.
* Defaults to a DecelerateInterpolator
*
* @param interpolator - Interpolator to use
*/
public void setScrollAnimationInterpolator(Interpolator interpolator);
/**
* By default the Widget disables scrolling on the Refreshable View while
* refreshing. This method can change this behaviour.
*
* @param scrollingWhileRefreshingEnabled - true if you want to enable
* scrolling while refreshing
*/
public void setScrollingWhileRefreshingEnabled(boolean scrollingWhileRefreshingEnabled);
/**
* A mutator to enable/disable whether the 'Refreshing' View should be
* automatically shown when refreshing.
*
* @param showView
*/
public void setShowViewWhileRefreshing(boolean showView);
}
================================================
FILE: library/src/com/handmark/pulltorefresh/library/LoadingLayoutProxy.java
================================================
package com.handmark.pulltorefresh.library;
import java.util.HashSet;
import android.graphics.Typeface;
import android.graphics.drawable.Drawable;
import com.handmark.pulltorefresh.library.internal.LoadingLayout;
public class LoadingLayoutProxy implements ILoadingLayout {
private final HashSet<LoadingLayout> mLoadingLayouts;
LoadingLayoutProxy() {
mLoadingLayouts = new HashSet<LoadingLayout>();
}
/**
* This allows you to add extra LoadingLayout instances to this proxy. This
* is only necessary if you keep your own instances, and want to have them
* included in any
* {@link PullToRefreshBase#createLoadingLayoutProxy(boolean, boolean)
* createLoadingLayoutProxy(...)} calls.
*
* @param layout - LoadingLayout to have included.
*/
public void addLayout(LoadingLayout layout) {
if (null != layout) {
mLoadingLayouts.add(layout);
}
}
@Override
public void setLastUpdatedLabel(CharSequence label) {
for (LoadingLayout layout : mLoadingLayouts) {
layout.setLastUpdatedLabel(label);
}
}
@Override
public void setLoadingDrawable(Drawable drawable) {
for (LoadingLayout layout : mLoadingLayouts) {
layout.setLoadingDrawable(drawable);
}
}
@Override
public void setRefreshingLabel(CharSequence refreshingLabel) {
for (LoadingLayout layout : mLoadingLayouts) {
layout.setRefreshingLabel(refreshingLabel);
}
}
@Override
public void setPullLabel(CharSequence label) {
for (LoadingLayout layout : mLoadingLayouts) {
layout.setPullLabel(label);
}
}
@Override
public void setReleaseLabel(CharSequence label) {
for (LoadingLayout layout : mLoadingLayouts) {
layout.setReleaseLabel(label);
}
}
public void setTextTypeface(Typeface tf) {
for (LoadingLayout layout : mLoadingLayouts) {
layout.setTextTypeface(tf);
}
}
}
================================================
FILE: library/src/com/handmark/pulltorefresh/library/OverscrollHelper.java
================================================
/*******************************************************************************
* Copyright 2011, 2012 Chris Banes.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*******************************************************************************/
package com.handmark.pulltorefresh.library;
import android.annotation.TargetApi;
import android.util.Log;
import android.view.View;
import com.handmark.pulltorefresh.library.PullToRefreshBase.Mode;
import com.handmark.pulltorefresh.library.PullToRefreshBase.State;
@TargetApi(9)
public final class OverscrollHelper {
static final String LOG_TAG = "OverscrollHelper";
static final float DEFAULT_OVERSCROLL_SCALE = 1f;
/**
* Helper method for Overscrolling that encapsulates all of the necessary
* function.
* <p/>
* This should only be used on AdapterView's such as ListView as it just
* calls through to overScrollBy() with the scrollRange = 0. AdapterView's
* do not have a scroll range (i.e. getScrollY() doesn't work).
*
* @param view - PullToRefreshView that is calling this.
* @param deltaX - Change in X in pixels, passed through from from
* overScrollBy call
* @param scrollX - Current X scroll value in pixels before applying deltaY,
* passed through from from overScrollBy call
* @param deltaY - Change in Y in pixels, passed through from from
* overScrollBy call
* @param scrollY - Current Y scroll value in pixels before applying deltaY,
* passed through from from overScrollBy call
* @param isTouchEvent - true if this scroll operation is the result of a
* touch event, passed through from from overScrollBy call
*/
public static void overScrollBy(final PullToRefreshBase<?> view, final int deltaX, final int scrollX,
final int deltaY, final int scrollY, final boolean isTouchEvent) {
overScrollBy(view, deltaX, scrollX, deltaY, scrollY, 0, isTouchEvent);
}
/**
* Helper method for Overscrolling that encapsulates all of the necessary
* function. This version of the call is used for Views that need to specify
* a Scroll Range but scroll back to it's edge correctly.
*
* @param view - PullToRefreshView that is calling this.
* @param deltaX - Change in X in pixels, passed through from from
* overScrollBy call
* @param scrollX - Current X scroll value in pixels before applying deltaY,
* passed through from from overScrollBy call
* @param deltaY - Change in Y in pixels, passed through from from
* overScrollBy call
* @param scrollY - Current Y scroll value in pixels before applying deltaY,
* passed through from from overScrollBy call
* @param scrollRange - Scroll Range of the View, specifically needed for
* ScrollView
* @param isTouchEvent - true if this scroll operation is the result of a
* touch event, passed through from from overScrollBy call
*/
public static void overScrollBy(final PullToRefreshBase<?> view, final int deltaX, final int scrollX,
final int deltaY, final int scrollY, final int scrollRange, final boolean isTouchEvent) {
overScrollBy(view, deltaX, scrollX, deltaY, scrollY, scrollRange, 0, DEFAULT_OVERSCROLL_SCALE, isTouchEvent);
}
/**
* Helper method for Overscrolling that encapsulates all of the necessary
* function. This is the advanced version of the call.
*
* @param view - PullToRefreshView that is calling this.
* @param deltaX - Change in X in pixels, passed through from from
* overScrollBy call
* @param scrollX - Current X scroll value in pixels before applying deltaY,
* passed through from from overScrollBy call
* @param deltaY - Change in Y in pixels, passed through from from
* overScrollBy call
* @param scrollY - Current Y scroll value in pixels before applying deltaY,
* passed through from from overScrollBy call
* @param scrollRange - Scroll Range of the View, specifically needed for
* ScrollView
* @param fuzzyThreshold - Threshold for which the values how fuzzy we
* should treat the other values. Needed for WebView as it
* doesn't always scroll back to it's edge. 0 = no fuzziness.
* @param scaleFactor - Scale Factor for overscroll amount
* @param isTouchEvent - true if this scroll operation is the result of a
* touch event, passed through from from overScrollBy call
*/
public static void overScrollBy(final PullToRefreshBase<?> view, final int deltaX, final int scrollX,
final int deltaY, final int scrollY, final int scrollRange, final int fuzzyThreshold,
final float scaleFactor, final boolean isTouchEvent) {
final int deltaValue, currentScrollValue, scrollValue;
switch (view.getPullToRefreshScrollDirection()) {
case HORIZONTAL:
deltaValue = deltaX;
scrollValue = scrollX;
currentScrollValue = view.getScrollX();
break;
case VERTICAL:
default:
deltaValue = deltaY;
scrollValue = scrollY;
currentScrollValue = view.getScrollY();
break;
}
// Check that OverScroll is enabled and that we're not currently
// refreshing.
if (view.isPullToRefreshOverScrollEnabled() && !view.isRefreshing()) {
final Mode mode = view.getMode();
// Check that Pull-to-Refresh is enabled, and the event isn't from
// touch
if (mode.permitsPullToRefresh() && !isTouchEvent && deltaValue != 0) {
final int newScrollValue = (deltaValue + scrollValue);
if (PullToRefreshBase.DEBUG) {
Log.d(LOG_TAG, "OverScroll. DeltaX: " + deltaX + ", ScrollX: " + scrollX + ", DeltaY: " + deltaY
+ ", ScrollY: " + scrollY + ", NewY: " + newScrollValue + ", ScrollRange: " + scrollRange
+ ", CurrentScroll: " + currentScrollValue);
}
if (newScrollValue < (0 - fuzzyThreshold)) {
// Check the mode supports the overscroll direction, and
// then move scroll
if (mode.showHeaderLoadingLayout()) {
// If we're currently at zero, we're about to start
// overscrolling, so change the state
if (currentScrollValue == 0) {
view.setState(State.OVERSCROLLING);
}
view.setHeaderScroll((int) (scaleFactor * (currentScrollValue + newScrollValue)));
}
} else if (newScrollValue > (scrollRange + fuzzyThreshold)) {
// Check the mode supports the overscroll direction, and
// then move scroll
if (mode.showFooterLoadingLayout()) {
// If we're currently at zero, we're about to start
// overscrolling, so change the state
if (currentScrollValue == 0) {
view.setState(State.OVERSCROLLING);
}
view.setHeaderScroll((int) (scaleFactor * (currentScrollValue + newScrollValue - scrollRange)));
}
} else if (Math.abs(newScrollValue) <= fuzzyThreshold
|| Math.abs(newScrollValue - scrollRange) <= fuzzyThreshold) {
// Means we've stopped overscrolling, so scroll back to 0
view.setState(State.RESET);
}
} else if (isTouchEvent && State.OVERSCROLLING == view.getState()) {
// This condition means that we were overscrolling from a fling,
// but the user has touched the View and is now overscrolling
// from touch instead. We need to just reset.
view.setState(State.RESET);
}
}
}
static boolean isAndroidOverScrollEnabled(View view) {
return view.getOverScrollMode() != View.OVER_SCROLL_NEVER;
}
}
================================================
FILE: library/src/com/handmark/pulltorefresh/library/PullToRefreshAdapterViewBase.java
================================================
/*******************************************************************************
* Copyright 2011, 2012 Chris Banes.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*******************************************************************************/
package com.handmark.pulltorefresh.library;
import android.content.Context;
import android.content.res.TypedArray;
import android.util.AttributeSet;
import android.util.Log;
import android.view.Gravity;
import android.view.View;
import android.view.ViewGroup;
import android.view.ViewParent;
import android.widget.AbsListView;
import android.widget.AbsListView.OnScrollListener;
import android.widget.Adapter;
import android.widget.AdapterView;
import android.widget.AdapterView.OnItemClickListener;
import android.widget.FrameLayout;
import android.widget.LinearLayout;
import android.widget.ListAdapter;
import com.handmark.pulltorefresh.library.internal.EmptyViewMethodAccessor;
import com.handmark.pulltorefresh.library.internal.IndicatorLayout;
public abstract class PullToRefreshAdapterViewBase<T extends AbsListView> extends PullToRefreshBase<T> implements
OnScrollListener {
private static FrameLayout.LayoutParams convertEmptyViewLayoutParams(ViewGroup.LayoutParams lp) {
FrameLayout.LayoutParams newLp = null;
if (null != lp) {
newLp = new FrameLayout.LayoutParams(lp);
if (lp instanceof LinearLayout.LayoutParams) {
newLp.gravity = ((LinearLayout.LayoutParams) lp).gravity;
} else {
newLp.gravity = Gravity.CENTER;
}
}
return newLp;
}
private boolean mLastItemVisible;
private OnScrollListener mOnScrollListener;
private OnLastItemVisibleListener mOnLastItemVisibleListener;
private View mEmptyView;
private IndicatorLayout mIndicatorIvTop;
private IndicatorLayout mIndicatorIvBottom;
private boolean mShowIndicator;
private boolean mScrollEmptyView = true;
public PullToRefreshAdapterViewBase(Context context) {
super(context);
mRefreshableView.setOnScrollListener(this);
}
public PullToRefreshAdapterViewBase(Context context, AttributeSet attrs) {
super(context, attrs);
mRefreshableView.setOnScrollListener(this);
}
public PullToRefreshAdapterViewBase(Context context, Mode mode) {
super(context, mode);
mRefreshableView.setOnScrollListener(this);
}
public PullToRefreshAdapterViewBase(Context context, Mode mode, AnimationStyle animStyle) {
super(context, mode, animStyle);
mRefreshableView.setOnScrollListener(this);
}
/**
* Gets whether an indicator graphic should be displayed when the View is in
* a state where a Pull-to-Refresh can happen. An example of this state is
* when the Adapter View is scrolled to the top and the mode is set to
* {@link Mode#PULL_FROM_START}. The default value is <var>true</var> if
* {@link PullToRefreshBase#isPullToRefreshOverScrollEnabled()
* isPullToRefreshOverScrollEnabled()} returns false.
*
* @return true if the indicators will be shown
*/
public boolean getShowIndicator() {
return mShowIndicator;
}
public final void onScroll(final AbsListView view, final int firstVisibleItem, final int visibleItemCount,
final int totalItemCount) {
if (DEBUG) {
Log.d(LOG_TAG, "First Visible: " + firstVisibleItem + ". Visible Count: " + visibleItemCount
+ ". Total Items:" + totalItemCount);
}
/**
* Set whether the Last Item is Visible. lastVisibleItemIndex is a
* zero-based index, so we minus one totalItemCount to check
*/
if (null != mOnLastItemVisibleListener) {
mLastItemVisible = (totalItemCount > 0) && (firstVisibleItem + visibleItemCount >= totalItemCount - 1);
}
// If we're showing the indicator, check positions...
if (getShowIndicatorInternal()) {
updateIndicatorViewsVisibility();
}
// Finally call OnScrollListener if we have one
if (null != mOnScrollListener) {
mOnScrollListener.onScroll(view, firstVisibleItem, visibleItemCount, totalItemCount);
}
}
public final void onScrollStateChanged(final AbsListView view, final int state) {
/**
* Check that the scrolling has stopped, and that the last item is
* visible.
*/
if (state == OnScrollListener.SCROLL_STATE_IDLE && null != mOnLastItemVisibleListener && mLastItemVisible) {
mOnLastItemVisibleListener.onLastItemVisible();
}
if (null != mOnScrollListener) {
mOnScrollListener.onScrollStateChanged(view, state);
}
}
/**
* Pass-through method for {@link PullToRefreshBase#getRefreshableView()
* getRefreshableView()}.
* {@link AdapterView#setAdapter(android.widget.Adapter)}
* setAdapter(adapter)}. This is just for convenience!
*
* @param adapter - Adapter to set
*/
public void setAdapter(ListAdapter adapter) {
((AdapterView<ListAdapter>) mRefreshableView).setAdapter(adapter);
}
/**
* Sets the Empty View to be used by the Adapter View.
* <p/>
* We need it handle it ourselves so that we can Pull-to-Refresh when the
* Empty View is shown.
* <p/>
* Please note, you do <strong>not</strong> usually need to call this method
* yourself. Calling setEmptyView on the AdapterView will automatically call
* this method and set everything up. This includes when the Android
* Framework automatically sets the Empty View based on it's ID.
*
* @param newEmptyView - Empty View to be used
*/
public final void setEmptyView(View newEmptyView) {
FrameLayout refreshableViewWrapper = getRefreshableViewWrapper();
if (null != newEmptyView) {
// New view needs to be clickable so that Android recognizes it as a
// target for Touch Events
newEmptyView.setClickable(true);
ViewParent newEmptyViewParent = newEmptyView.getParent();
if (null != newEmptyViewParent && newEmptyViewParent instanceof ViewGroup) {
((ViewGroup) newEmptyViewParent).removeView(newEmptyView);
}
// We need to convert any LayoutParams so that it works in our
// FrameLayout
FrameLayout.LayoutParams lp = convertEmptyViewLayoutParams(newEmptyView.getLayoutParams());
if (null != lp) {
refreshableViewWrapper.addView(newEmptyView, lp);
} else {
refreshableViewWrapper.addView(newEmptyView);
}
}
if (mRefreshableView instanceof EmptyViewMethodAccessor) {
((EmptyViewMethodAccessor) mRefreshableView).setEmptyViewInternal(newEmptyView);
} else {
mRefreshableView.setEmptyView(newEmptyView);
}
mEmptyView = newEmptyView;
}
/**
* Pass-through method for {@link PullToRefreshBase#getRefreshableView()
* getRefreshableView()}.
* {@link AdapterView#setOnItemClickListener(OnItemClickListener)
* setOnItemClickListener(listener)}. This is just for convenience!
*
* @param listener - OnItemClickListener to use
*/
public void setOnItemClickListener(OnItemClickListener listener) {
mRefreshableView.setOnItemClickListener(listener);
}
public final void setOnLastItemVisibleListener(OnLastItemVisibleListener listener) {
mOnLastItemVisibleListener = listener;
}
public final void setOnScrollListener(OnScrollListener listener) {
mOnScrollListener = listener;
}
public final void setScrollEmptyView(boolean doScroll) {
mScrollEmptyView = doScroll;
}
/**
* Sets whether an indicator graphic should be displayed when the View is in
* a state where a Pull-to-Refresh can happen. An example of this state is
* when the Adapter View is scrolled to the top and the mode is set to
* {@link Mode#PULL_FROM_START}
*
* @param showIndicator - true if the indicators should be shown.
*/
public void setShowIndicator(boolean showIndicator) {
mShowIndicator = showIndicator;
if (getShowIndicatorInternal()) {
// If we're set to Show Indicator, add/update them
addIndicatorViews();
} else {
// If not, then remove then
removeIndicatorViews();
}
}
;
@Override
protected void onPullToRefresh() {
super.onPullToRefresh();
if (getShowIndicatorInternal()) {
switch (getCurrentMode()) {
case PULL_FROM_END:
mIndicatorIvBottom.pullToRefresh();
break;
case PULL_FROM_START:
mIndicatorIvTop.pullToRefresh();
break;
default:
// NO-OP
break;
}
}
}
protected void onRefreshing(boolean doScroll) {
super.onRefreshing(doScroll);
if (getShowIndicatorInternal()) {
updateIndicatorViewsVisibility();
}
}
@Override
protected void onReleaseToRefresh() {
super.onReleaseToRefresh();
if (getShowIndicatorInternal()) {
switch (getCurrentMode()) {
case PULL_FROM_END:
mIndicatorIvBottom.releaseToRefresh();
break;
case PULL_FROM_START:
mIndicatorIvTop.releaseToRefresh();
break;
default:
// NO-OP
break;
}
}
}
@Override
protected void onReset() {
super.onReset();
if (getShowIndicatorInternal()) {
updateIndicatorViewsVisibility();
}
}
@Override
protected void handleStyledAttributes(TypedArray a) {
// Set Show Indicator to the XML value, or default value
mShowIndicator = a.getBoolean(R.styleable.PullToRefresh_ptrShowIndicator, !isPullToRefreshOverScrollEnabled());
}
protected boolean isReadyForPullStart() {
return isFirstItemVisible();
}
protected boolean isReadyForPullEnd() {
return isLastItemVisible();
}
@Override
protected void onScrollChanged(int l, int t, int oldl, int oldt) {
super.onScrollChanged(l, t, oldl, oldt);
if (null != mEmptyView && !mScrollEmptyView) {
mEmptyView.scrollTo(-l, -t);
}
}
@Override
protected void updateUIForMode() {
super.updateUIForMode();
// Check Indicator Views consistent with new Mode
if (getShowIndicatorInternal()) {
addIndicatorViews();
} else {
removeIndicatorViews();
}
}
private void addIndicatorViews() {
Mode mode = getMode();
FrameLayout refreshableViewWrapper = getRefreshableViewWrapper();
if (mode.showHeaderLoadingLayout() && null == mIndicatorIvTop) {
// If the mode can pull down, and we don't have one set already
mIndicatorIvTop = new IndicatorLayout(getContext(), Mode.PULL_FROM_START);
FrameLayout.LayoutParams params = new FrameLayout.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT,
ViewGroup.LayoutParams.WRAP_CONTENT);
params.rightMargin = getResources().getDimensionPixelSize(R.dimen.indicator_right_padding);
params.gravity = Gravity.TOP | Gravity.RIGHT;
refreshableViewWrapper.addView(mIndicatorIvTop, params);
} else if (!mode.showHeaderLoadingLayout() && null != mIndicatorIvTop) {
// If we can't pull down, but have a View then remove it
refreshableViewWrapper.removeView(mIndicatorIvTop);
mIndicatorIvTop = null;
}
if (mode.showFooterLoadingLayout() && null == mIndicatorIvBottom) {
// If the mode can pull down, and we don't have one set already
mIndicatorIvBottom = new IndicatorLayout(getContext(), Mode.PULL_FROM_END);
FrameLayout.LayoutParams params = new FrameLayout.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT,
ViewGroup.LayoutParams.WRAP_CONTENT);
params.rightMargin = getResources().getDimensionPixelSize(R.dimen.indicator_right_padding);
params.gravity = Gravity.BOTTOM | Gravity.RIGHT;
refreshableViewWrapper.addView(mIndicatorIvBottom, params);
} else if (!mode.showFooterLoadingLayout() && null != mIndicatorIvBottom) {
// If we can't pull down, but have a View then remove it
refreshableViewWrapper.removeView(mIndicatorIvBottom);
mIndicatorIvBottom = null;
}
}
private boolean getShowIndicatorInternal() {
return mShowIndicator && isPullToRefreshEnabled();
}
private boolean isFirstItemVisible() {
final Adapter adapter = mRefreshableView.getAdapter();
if (null == adapter || adapter.isEmpty()) {
if (DEBUG) {
Log.d(LOG_TAG, "isFirstItemVisible. Empty View.");
}
return true;
} else {
/**
* This check should really just be:
* mRefreshableView.getFirstVisiblePosition() == 0, but PtRListView
* internally use a HeaderView which messes the positions up. For
* now we'll just add one to account for it and rely on the inner
* condition which checks getTop().
*/
if (mRefreshableView.getFirstVisiblePosition() <= 1) {
final View firstVisibleChild = mRefreshableView.getChildAt(0);
if (firstVisibleChild != null) {
return firstVisibleChild.getTop() >= mRefreshableView.getTop();
}
}
}
return false;
}
private boolean isLastItemVisible() {
final Adapter adapter = mRefreshableView.getAdapter();
if (null == adapter || adapter.isEmpty()) {
if (DEBUG) {
Log.d(LOG_TAG, "isLastItemVisible. Empty View.");
}
return true;
} else {
final int lastItemPosition = mRefreshableView.getCount() - 1;
final int lastVisiblePosition = mRefreshableView.getLastVisiblePosition();
if (DEBUG) {
Log.d(LOG_TAG, "isLastItemVisible. Last Item Position: " + lastItemPosition + " Last Visible Pos: "
+ lastVisiblePosition);
}
/**
* This check should really just be: lastVisiblePosition ==
* lastItemPosition, but PtRListView internally uses a FooterView
* which messes the positions up. For me we'll just subtract one to
* account for it and rely on the inner condition which checks
* getBottom().
*/
if (lastVisiblePosition >= lastItemPosition - 1) {
final int childIndex = lastVisiblePosition - mRefreshableView.getFirstVisiblePosition();
final View lastVisibleChild = mRefreshableView.getChildAt(childIndex);
if (lastVisibleChild != null) {
return lastVisibleChild.getBottom() <= mRefreshableView.getBottom();
}
}
}
return false;
}
private void removeIndicatorViews() {
if (null != mIndicatorIvTop) {
getRefreshableViewWrapper().removeView(mIndicatorIvTop);
mIndicatorIvTop = null;
}
if (null != mIndicatorIvBottom) {
getRefreshableViewWrapper().removeView(mIndicatorIvBottom);
mIndicatorIvBottom = null;
}
}
private void updateIndicatorViewsVisibility() {
if (null != mIndicatorIvTop) {
if (!isRefreshing() && isReadyForPullStart()) {
if (!mIndicatorIvTop.isVisible()) {
mIndicatorIvTop.show();
}
} else {
if (mIndicatorIvTop.isVisible()) {
mIndicatorIvTop.hide();
}
}
}
if (null != mIndicatorIvBottom) {
if (!isRefreshing() && isReadyForPullEnd()) {
if (!mIndicatorIvBottom.isVisible()) {
mIndicatorIvBottom.show();
}
} else {
if (mIndicatorIvBottom.isVisible()) {
mIndicatorIvBottom.hide();
}
}
}
}
}
================================================
FILE: library/src/com/handmark/pulltorefresh/library/PullToRefreshBase.java
================================================
/*******************************************************************************
* Copyright 2011, 2012 Chris Banes.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*******************************************************************************/
package com.handmark.pulltorefresh.library;
import android.content.Context;
import android.content.res.TypedArray;
import android.graphics.drawable.Drawable;
import android.os.Build.VERSION;
import android.os.Build.VERSION_CODES;
import android.os.Bundle;
import android.os.Parcelable;
import android.util.AttributeSet;
import android.util.Log;
import android.view.Gravity;
import android.view.MotionEvent;
import android.view.View;
import android.view.ViewConfiguration;
import android.view.ViewGroup;
import android.view.animation.DecelerateInterpolator;
import android.view.animation.Interpolator;
import android.widget.FrameLayout;
import android.widget.LinearLayout;
import com.handmark.pulltorefresh.library.internal.FlipLoadingLayout;
import com.handmark.pulltorefresh.library.internal.LoadingLayout;
import com.handmark.pulltorefresh.library.internal.RotateLoadingLayout;
import com.handmark.pulltorefresh.library.internal.Utils;
import com.handmark.pulltorefresh.library.internal.ViewCompat;
public abstract class PullToRefreshBase<T extends View> extends LinearLayout implements IPullToRefresh<T> {
// ===========================================================
// Constants
// ===========================================================
static final boolean DEBUG = true;
static final boolean USE_HW_LAYERS = false;
static final String LOG_TAG = "PullToRefresh";
static final float FRICTION = 2.0f;
public static final int SMOOTH_SCROLL_DURATION_MS = 200;
public static final int SMOOTH_SCROLL_LONG_DURATION_MS = 325;
static final int DEMO_SCROLL_INTERVAL = 225;
static final String STATE_STATE = "ptr_state";
static final String STATE_MODE = "ptr_mode";
static final String STATE_CURRENT_MODE = "ptr_current_mode";
static final String STATE_SCROLLING_REFRESHING_ENABLED = "ptr_disable_scrolling";
static final String STATE_SHOW_REFRESHING_VIEW = "ptr_show_refreshing_view";
static final String STATE_SUPER = "ptr_super";
// ===========================================================
// Fields
// ===========================================================
private int mTouchSlop;
private float mLastMotionX, mLastMotionY;
private float mInitialMotionX, mInitialMotionY;
private boolean mIsBeingDragged = false;
private State mState = State.RESET;
private Mode mMode = Mode.getDefault();
private Mode mCurrentMode;
T mRefreshableView;
private FrameLayout mRefreshableViewWrapper;
private boolean mShowViewWhileRefreshing = true;
private boolean mScrollingWhileRefreshingEnabled = false;
private boolean mFilterTouchEvents = true;
private boolean mOverScrollEnabled = true;
private boolean mLayoutVisibilityChangesEnabled = true;
private Interpolator mScrollAnimationInterpolator;
private AnimationStyle mLoadingAnimationStyle = AnimationStyle.getDefault();
private LoadingLayout mHeaderLayout;
private LoadingLayout mFooterLayout;
private OnRefreshListener<T> mOnRefreshListener;
private OnRefreshListener2<T> mOnRefreshListener2;
private OnPullEventListener<T> mOnPullEventListener;
private SmoothScrollRunnable mCurrentSmoothScrollRunnable;
// ===========================================================
// Constructors
// ===========================================================
public PullToRefreshBase(Context context) {
super(context);
init(context, null);
}
public PullToRefreshBase(Context context, AttributeSet attrs) {
super(context, attrs);
init(context, attrs);
}
public PullToRefreshBase(Context context, Mode mode) {
super(context);
mMode = mode;
init(context, null);
}
public PullToRefreshBase(Context context, Mode mode, AnimationStyle animStyle) {
super(context);
mMode = mode;
mLoadingAnimationStyle = animStyle;
init(context, null);
}
@Override
public void addView(View child, int index, ViewGroup.LayoutParams params) {
if (DEBUG) {
Log.d(LOG_TAG, "addView: " + child.getClass().getSimpleName());
}
final T refreshableView = getRefreshableView();
if (refreshableView instanceof ViewGroup) {
((ViewGroup) refreshableView).addView(child, index, params);
} else {
throw new UnsupportedOperationException("Refreshable View is not a ViewGroup so can't addView");
}
}
@Override
public final boolean demo() {
if (mMode.showHeaderLoadingLayout() && isReadyForPullStart()) {
smoothScrollToAndBack(-getHeaderSize() * 2);
return true;
} else if (mMode.showFooterLoadingLayout() && isReadyForPullEnd()) {
smoothScrollToAndBack(getFooterSize() * 2);
return true;
}
return false;
}
@Override
public final Mode getCurrentMode() {
return mCurrentMode;
}
@Override
public final boolean getFilterTouchEvents() {
return mFilterTouchEvents;
}
@Override
public final ILoadingLayout getLoadingLayoutProxy() {
return getLoadingLayoutProxy(true, true);
}
@Override
public final ILoadingLayout getLoadingLayoutProxy(boolean includeStart, boolean includeEnd) {
return createLoadingLayoutProxy(includeStart, includeEnd);
}
@Override
public final Mode getMode() {
return mMode;
}
@Override
public final T getRefreshableView() {
return mRefreshableView;
}
@Override
public final boolean getShowViewWhileRefreshing() {
return mShowViewWhileRefreshing;
}
@Override
public final State getState() {
return mState;
}
/**
* @deprecated See {@link #isScrollingWhileRefreshingEnabled()}.
*/
public final boolean isDisableScrollingWhileRefreshing() {
return !isScrollingWhileRefreshingEnabled();
}
@Override
public final boolean isPullToRefreshEnabled() {
return mMode.permitsPullToRefresh();
}
@Override
public final boolean isPullToRefreshOverScrollEnabled() {
return VERSION.SDK_INT >= VERSION_CODES.GINGERBREAD && mOverScrollEnabled
&& OverscrollHelper.isAndroidOverScrollEnabled(mRefreshableView);
}
@Override
public final boolean isRefreshing() {
return mState == State.REFRESHING || mState == State.MANUAL_REFRESHING;
}
@Override
public final boolean isScrollingWhileRefreshingEnabled() {
return mScrollingWhileRefreshingEnabled;
}
@Override
public final boolean onInterceptTouchEvent(MotionEvent event) {
if (!isPullToRefreshEnabled()) {
return false;
}
final int action = event.getAction();
if (action == MotionEvent.ACTION_CANCEL || action == MotionEvent.ACTION_UP) {
mIsBeingDragged = false;
return false;
}
if (action != MotionEvent.ACTION_DOWN && mIsBeingDragged) {
return true;
}
switch (action) {
case MotionEvent.ACTION_MOVE: {
// If we're refreshing, and the flag is set. Eat all MOVE events
if (!mScrollingWhileRefreshingEnabled && isRefreshing()) {
return true;
}
if (isReadyForPull()) {
final float y = event.getY(), x = event.getX();
final float diff, oppositeDiff, absDiff;
// We need to use the correct values, based on scroll
// direction
switch (getPullToRefreshScrollDirection()) {
case HORIZONTAL:
diff = x - mLastMotionX;
oppositeDiff = y - mLastMotionY;
break;
case VERTICAL:
default:
diff = y - mLastMotionY;
oppositeDiff = x - mLastMotionX;
break;
}
absDiff = Math.abs(diff);
if (absDiff > mTouchSlop && (!mFilterTouchEvents || absDiff > Math.abs(oppositeDiff))) {
if (mMode.showHeaderLoadingLayout() && diff >= 1f && isReadyForPullStart()) {
mLastMotionY = y;
mLastMotionX = x;
mIsBeingDragged = true;
if (mMode == Mode.BOTH) {
mCurrentMode = Mode.PULL_FROM_START;
}
} else if (mMode.showFooterLoadingLayout() && diff <= -1f && isReadyForPullEnd()) {
mLastMotionY = y;
mLastMotionX = x;
mIsBeingDragged = true;
if (mMode == Mode.BOTH) {
mCurrentMode = Mode.PULL_FROM_END;
}
}
}
}
break;
}
case MotionEvent.ACTION_DOWN: {
if (isReadyForPull()) {
mLastMotionY = mInitialMotionY = event.getY();
mLastMotionX = mInitialMotionX = event.getX();
mIsBeingDragged = false;
}
break;
}
}
return mIsBeingDragged;
}
@Override
public final void onRefreshComplete() {
if (isRefreshing()) {
setState(State.RESET);
}
}
@Override
public final boolean onTouchEvent(MotionEvent event) {
if (!isPullToRefreshEnabled()) {
return false;
}
// If we're refreshing, and the flag is set. Eat the event
if (!mScrollingWhileRefreshingEnabled && isRefreshing()) {
return true;
}
if (event.getAction() == MotionEvent.ACTION_DOWN && event.getEdgeFlags() != 0) {
return false;
}
switch (event.getAction()) {
case MotionEvent.ACTION_MOVE: {
if (mIsBeingDragged) {
mLastMotionY = event.getY();
mLastMotionX = event.getX();
pullEvent();
return true;
}
break;
}
case MotionEvent.ACTION_DOWN: {
if (isReadyForPull()) {
mLastMotionY = mInitialMotionY = event.getY();
mLastMotionX = mInitialMotionX = event.getX();
return true;
}
break;
}
case MotionEvent.ACTION_CANCEL:
case MotionEvent.ACTION_UP: {
if (mIsBeingDragged) {
mIsBeingDragged = false;
if (mState == State.RELEASE_TO_REFRESH
&& (null != mOnRefreshListener || null != mOnRefreshListener2)) {
setState(State.REFRESHING, true);
return true;
}
// If we're already refreshing, just scroll back to the top
if (isRefreshing()) {
smoothScrollTo(0);
return true;
}
// If we haven't returned by here, then we're not in a state
// to pull, so just reset
setState(State.RESET);
return true;
}
break;
}
}
return false;
}
public final void setScrollingWhileRefreshingEnabled(boolean allowScrollingWhileRefreshing) {
mScrollingWhileRefreshingEnabled = allowScrollingWhileRefreshing;
}
/**
* @deprecated See {@link #setScrollingWhileRefreshingEnabled(boolean)}
*/
public void setDisableScrollingWhileRefreshing(boolean disableScrollingWhileRefreshing) {
setScrollingWhileRefreshingEnabled(!disableScrollingWhileRefreshing);
}
@Override
public final void setFilterTouchEvents(boolean filterEvents) {
mFilterTouchEvents = filterEvents;
}
/**
* @deprecated You should now call this method on the result of
* {@link #getLoadingLayoutProxy()}.
*/
public void setLastUpdatedLabel(CharSequence label) {
getLoadingLayoutProxy().setLastUpdatedLabel(label);
}
/**
* @deprecated You should now call this method on the result of
* {@link #getLoadingLayoutProxy()}.
*/
public void setLoadingDrawable(Drawable drawable) {
getLoadingLayoutProxy().setLoadingDrawable(drawable);
}
/**
* @deprecated You should now call this method on the result of
* {@link #getLoadingLayoutProxy(boolean, boolean)}.
*/
public void setLoadingDrawable(Drawable drawable, Mode mode) {
getLoadingLayoutProxy(mode.showHeaderLoadingLayout(), mode.showFooterLoadingLayout()).setLoadingDrawable(
drawable);
}
@Override
public void setLongClickable(boolean longClickable) {
getRefreshableView().setLongClickable(longClickable);
}
@Override
public final void setMode(Mode mode) {
if (mode != mMode) {
if (DEBUG) {
Log.d(LOG_TAG, "Setting mode to: " + mode);
}
mMode = mode;
updateUIForMode();
}
}
public void setOnPullEventListener(OnPullEventListener<T> listener) {
mOnPullEventListener = listener;
}
@Override
public final void setOnRefreshListener(OnRefreshListener<T> listener) {
mOnRefreshListener = listener;
mOnRefreshListener2 = null;
}
@Override
public final void setOnRefreshListener(OnRefreshListener2<T> listener) {
mOnRefreshListener2 = listener;
mOnRefreshListener = null;
}
/**
* @deprecated You should now call this method on the result of
* {@link #getLoadingLayoutProxy()}.
*/
public void setPullLabel(CharSequence pullLabel) {
getLoadingLayoutProxy().setPullLabel(pullLabel);
}
/**
* @deprecated You should now call this method on the result of
* {@link #getLoadingLayoutProxy(boolean, boolean)}.
*/
public void setPullLabel(CharSequence pullLabel, Mode mode) {
getLoadingLayoutProxy(mode.showHeaderLoadingLayout(), mode.showFooterLoadingLayout()).setPullLabel(pullLabel);
}
/**
* @param enable Whether Pull-To-Refresh should be used
* @deprecated This simple calls setMode with an appropriate mode based on
* the passed value.
*/
public final void setPullToRefreshEnabled(boolean enable) {
setMode(enable ? Mode.getDefault() : Mode.DISABLED);
}
@Override
public final void setPullToRefreshOverScrollEnabled(boolean enabled) {
mOverScrollEnabled = enabled;
}
@Override
public final void setRefreshing() {
setRefreshing(true);
}
@Override
public final void setRefreshing(boolean doScroll) {
if (!isRefreshing()) {
setState(State.MANUAL_REFRESHING, doScroll);
}
}
/**
* @deprecated You should now call this method on the result of
* {@link #getLoadingLayoutProxy()}.
*/
public void setRefreshingLabel(CharSequence refreshingLabel) {
getLoadingLayoutProxy().setRefreshingLabel(refreshingLabel);
}
/**
* @deprecated You should now call this method on the result of
* {@link #getLoadingLayoutProxy(boolean, boolean)}.
*/
public void setRefreshingLabel(CharSequence refreshingLabel, Mode mode) {
getLoadingLayoutProxy(mode.showHeaderLoadingLayout(), mode.showFooterLoadingLayout()).setRefreshingLabel(
refreshingLabel);
}
/**
* @deprecated You should now call this method on the result of
* {@link #getLoadingLayoutProxy()}.
*/
public void setReleaseLabel(CharSequence releaseLabel) {
setReleaseLabel(releaseLabel, Mode.BOTH);
}
/**
* @deprecated You should now call this method on the result of
* {@link #getLoadingLayoutProxy(boolean, boolean)}.
*/
public void setReleaseLabel(CharSequence releaseLabel, Mode mode) {
getLoadingLayoutProxy(mode.showHeaderLoadingLayout(), mode.showFooterLoadingLayout()).setReleaseLabel(
releaseLabel);
}
public void setScrollAnimationInterpolator(Interpolator interpolator) {
mScrollAnimationInterpolator = interpolator;
}
@Override
public final void setShowViewWhileRefreshing(boolean showView) {
mShowViewWhileRefreshing = showView;
}
/**
* @return Either {@link Orientation#VERTICAL} or
* {@link Orientation#HORIZONTAL} depending on the scroll direction.
*/
public abstract Orientation getPullToRefreshScrollDirection();
final void setState(State state, final boolean... params) {
mState = state;
if (DEBUG) {
Log.d(LOG_TAG, "State: " + mState.name());
}
switch (mState) {
case RESET:
onReset();
break;
case PULL_TO_REFRESH:
onPullToRefresh();
break;
case RELEASE_TO_REFRESH:
onReleaseToRefresh();
break;
case REFRESHING:
case MANUAL_REFRESHING:
onRefreshing(params[0]);
break;
case OVERSCROLLING:
// NO-OP
break;
}
// Call OnPullEventListener
if (null != mOnPullEventListener) {
mOnPullEventListener.onPullEvent(this, mState, mCurrentMode);
}
}
/**
* Used internally for adding view. Need because we override addView to
* pass-through to the Refreshable View
*/
protected final void addViewInternal(View child, int index, ViewGroup.LayoutParams params) {
super.addView(child, index, params);
}
/**
* Used internally for adding view. Need because we override addView to
* pass-through to the Refreshable View
*/
protected final void addViewInternal(View child, ViewGroup.LayoutParams params) {
super.addView(child, -1, params);
}
protected LoadingLayout createLoadingLayout(Context context, Mode mode, TypedArray attrs) {
LoadingLayout layout = mLoadingAnimationStyle.createLoadingLayout(context, mode,
getPullToRefreshScrollDirection(), attrs);
layout.setVisibility(View.INVISIBLE);
return layout;
}
/**
* Used internally for {@link #getLoadingLayoutProxy(boolean, boolean)}.
* Allows derivative classes to include any extra LoadingLayouts.
*/
protected LoadingLayoutProxy createLoadingLayoutProxy(final boolean includeStart, final boolean includeEnd) {
LoadingLayoutProxy proxy = new LoadingLayoutProxy();
if (includeStart && mMode.showHeaderLoadingLayout()) {
proxy.addLayout(mHeaderLayout);
}
if (includeEnd && mMode.showFooterLoadingLayout()) {
proxy.addLayout(mFooterLayout);
}
return proxy;
}
/**
* This is implemented by derived classes to return the created View. If you
* need to use a custom View (such as a custom ListView), override this
* method and return an instance of your custom class.
* <p/>
* Be sure to set the ID of the view in this method, especially if you're
* using a ListActivity or ListFragment.
*
* @param context Context to create view with
* @param attrs AttributeSet from wrapped class. Means that anything you
* include in the XML layout declaration will be routed to the
* created View
* @return New instance of the Refreshable View
*/
protected abstract T createRefreshableView(Context context, AttributeSet attrs);
protected final void disableLoadingLayoutVisibilityChanges() {
mLayoutVisibilityChangesEnabled = false;
}
protected final LoadingLayout getFooterLayout() {
return mFooterLayout;
}
protected final int getFooterSize() {
return mFooterLayout.getContentSize();
}
protected final LoadingLayout getHeaderLayout() {
return mHeaderLayout;
}
protected final int getHeaderSize() {
return mHeaderLayout.getContentSize();
}
protected int getPullToRefreshScrollDuration() {
return SMOOTH_SCROLL_DURATION_MS;
}
protected int getPullToRefreshScrollDurationLonger() {
return SMOOTH_SCROLL_LONG_DURATION_MS;
}
protected FrameLayout getRefreshableViewWrapper() {
return mRefreshableViewWrapper;
}
/**
* Allows Derivative classes to handle the XML Attrs without creating a
* TypedArray themsevles
*
* @param a - TypedArray of PullToRefresh Attributes
*/
protected void handleStyledAttributes(TypedArray a) {
}
/**
* Implemented by derived class to return whether the View is in a state
* where the user can Pull to Refresh by scrolling from the end.
*
* @return true if the View is currently in the correct state (for example,
* bottom of a ListView)
*/
protected abstract boolean isReadyForPullEnd();
/**
* Implemented by derived class to return whether the View is in a state
* where the user can Pull to Refresh by scrolling from the start.
*
* @return true if the View is currently the correct state (for example, top
* of a ListView)
*/
protected abstract boolean isReadyForPullStart();
/**
* Called by {@link #onRestoreInstanceState(Parcelable)} so that derivative
* classes can handle their saved instance state.
*
* @param savedInstanceState - Bundle which contains saved instance state.
*/
protected void onPtrRestoreInstanceState(Bundle savedInstanceState) {
}
/**
* Called by {@link #onSaveInstanceState()} so that derivative classes can
* save their instance state.
*
* @param saveState - Bundle to be updated with saved state.
*/
protected void onPtrSaveInstanceState(Bundle saveState) {
}
/**
* Called when the UI has been to be updated to be in the
* {@link State#PULL_TO_REFRESH} state.
*/
protected void onPullToRefresh() {
switch (mCurrentMode) {
case PULL_FROM_END:
mFooterLayout.pullToRefresh();
break;
case PULL_FROM_START:
mHeaderLayout.pullToRefresh();
break;
default:
// NO-OP
break;
}
}
/**
* Called when the UI has been to be updated to be in the
* {@link State#REFRESHING} or {@link State#MANUAL_REFRESHING} state.
*
* @param doScroll - Whether the UI should scroll for this event.
*/
protected void onRefreshing(final boolean doScroll) {
if (mMode.showHeaderLoadingLayout()) {
mHeaderLayout.refreshing();
}
if (mMode.showFooterLoadingLayout()) {
mFooterLayout.refreshing();
}
if (doScroll) {
if (mShowViewWhileRefreshing) {
// Call Refresh Listener when the Scroll has finished
OnSmoothScrollFinishedListener listener = new OnSmoothScrollFinishedListener() {
@Override
public void onSmoothScrollFinished() {
callRefreshListener();
}
};
switch (mCurrentMode) {
case MANUAL_REFRESH_ONLY:
case PULL_FROM_END:
smoothScrollTo(getFooterSize(), listener);
break;
default:
case PULL_FROM_START:
smoothScrollTo(-getHeaderSize(), listener);
break;
}
} else {
smoothScrollTo(0);
}
} else {
// We're not scrolling, so just call Refresh Listener now
callRefreshListener();
}
}
/**
* Called when the UI has been to be updated to be in the
* {@link State#RELEASE_TO_REFRESH} state.
*/
protected void onReleaseToRefresh() {
switch (mCurrentMode) {
case PULL_FROM_END:
mFooterLayout.releaseToRefresh();
break;
case PULL_FROM_START:
mHeaderLayout.releaseToRefresh();
break;
default:
// NO-OP
break;
}
}
/**
* Called when the UI has been to be updated to be in the
* {@link State#RESET} state.
*/
protected void onReset() {
mIsBeingDragged = false;
mLayoutVisibilityChangesEnabled = true;
// Always reset both layouts, just in case...
mHeaderLayout.reset();
mFooterLayout.reset();
smoothScrollTo(0);
}
@Override
protected final void onRestoreInstanceState(Parcelable state) {
if (state instanceof Bundle) {
Bundle bundle = (Bundle) state;
setMode(Mode.mapIntToValue(bundle.getInt(STATE_MODE, 0)));
mCurrentMode = Mode.mapIntToValue(bundle.getInt(STATE_CURRENT_MODE, 0));
mScrollingWhileRefreshingEnabled = bundle.getBoolean(STATE_SCROLLING_REFRESHING_ENABLED, false);
mShowViewWhileRefreshing = bundle.getBoolean(STATE_SHOW_REFRESHING_VIEW, true);
// Let super Restore Itself
super.onRestoreInstanceState(bundle.getParcelable(STATE_SUPER));
State viewState = State.mapIntToValue(bundle.getInt(STATE_STATE, 0));
if (viewState == State.REFRESHING || viewState == State.MANUAL_REFRESHING) {
setState(viewState, true);
}
// Now let derivative classes restore their state
onPtrRestoreInstanceState(bundle);
return;
}
super.onRestoreInstanceState(state);
}
@Override
protected final Parcelable onSaveInstanceState() {
Bundle bundle = new Bundle();
// Let derivative classes get a chance to save state first, that way we
// can make sure they don't overrite any of our values
onPtrSaveInstanceState(bundle);
bundle.putInt(STATE_STATE, mState.getIntValue());
bundle.putInt(STATE_MODE, mMode.getIntValue());
bundle.putInt(STATE_CURRENT_MODE, mCurrentMode.getIntValue());
bundle.putBoolean(STATE_SCROLLING_REFRESHING_ENABLED, mScrollingWhileRefreshingEnabled);
bundle.putBoolean(STATE_SHOW_REFRESHING_VIEW, mShowViewWhileRefreshing);
bundle.putParcelable(STATE_SUPER, super.onSaveInstanceState());
return bundle;
}
@Override
protected final void onSizeChanged(int w, int h, int oldw, int oldh) {
if (DEBUG) {
Log.d(LOG_TAG, String.format("onSizeChanged. W: %d, H: %d", w, h));
}
super.onSizeChanged(w, h, oldw, oldh);
// We need to update the header/footer when our size changes
refreshLoadingViewsSize();
// Update the Refreshable View layout
refreshRefreshableViewSize(w, h);
/**
* As we're currently in a Layout Pass, we need to schedule another one
* to layout any changes we've made here
*/
post(new Runnable() {
@Override
public void run() {
requestLayout();
}
});
}
/**
* Re-measure the Loading Views height, and adjust internal padding as
* necessary
*/
protected final void refreshLoadingViewsSize() {
final int maximumPullScroll = (int) (getMaximumPullScroll() * 1.2f);
int pLeft = getPaddingLeft();
int pTop = getPaddingTop();
int pRight = getPaddingRight();
int pBottom = getPaddingBottom();
switch (getPullToRefreshScrollDirection()) {
case HORIZONTAL:
if (mMode.showHeaderLoadingLayout()) {
mHeaderLayout.setWidth(maximumPullScroll);
pLeft = -maximumPullScroll;
} else {
pLeft = 0;
}
if (mMode.showFooterLoadingLayout()) {
mFooterLayout.setWidth(maximumPullScroll);
pRight = -maximumPullScroll;
} else {
pRight = 0;
}
break;
case VERTICAL:
if (mMode.showHeaderLoadingLayout()) {
mHeaderLayout.setHeight(maximumPullScroll);
pTop = -maximumPullScroll;
} else {
pTop = 0;
}
if (mMode.showFooterLoadingLayout()) {
mFooterLayout.setHeight(maximumPullScroll);
pBottom = -maximumPullScroll;
} else {
pBottom = 0;
}
break;
}
if (DEBUG) {
Log.d(LOG_TAG, String.format("Setting Padding. L: %d, T: %d, R: %d, B: %d", pLeft, pTop, pRight, pBottom));
}
setPadding(pLeft, pTop, pRight, pBottom);
}
protected final void refreshRefreshableViewSize(int width, int height) {
// We need to set the Height of the Refreshable View to the same as
// this layout
LinearLayout.LayoutParams lp = (LinearLayout.LayoutParams) mRefreshableViewWrapper.getLayoutParams();
switch (getPullToRefreshScrollDirection()) {
case HORIZONTAL:
if (lp.width != width) {
lp.width = width;
mRefreshableViewWrapper.requestLayout();
}
break;
case VERTICAL:
if (lp.height != height) {
lp.height = height;
mRefreshableViewWrapper.requestLayout();
}
break;
}
}
/**
* Helper method which just calls scrollTo() in the correct scrolling
* direction.
*
* @param value - New Scroll value
*/
protected final void setHeaderScroll(int value) {
if (DEBUG) {
Log.d(LOG_TAG, "setHeaderScroll: " + value);
}
// Clamp value to with pull scroll range
final int maximumPullScroll = getMaximumPullScroll();
value = Math.min(maximumPullScroll, Math.max(-maximumPullScroll, value));
if (mLayoutVisibilityChangesEnabled) {
if (value < 0) {
mHeaderLayout.setVisibility(View.VISIBLE);
} else if (value > 0) {
mFooterLayout.setVisibility(View.VISIBLE);
} else {
mHeaderLayout.setVisibility(View.INVISIBLE);
mFooterLayout.setVisibility(View.INVISIBLE);
}
}
if (USE_HW_LAYERS) {
/**
* Use a Hardware Layer on the Refreshable View if we've scrolled at
* all. We don't use them on the Header/Footer Views as they change
* often, which would negate any HW layer performance boost.
*/
ViewCompat.setLayerType(mRefreshableViewWrapper, value != 0 ? View.LAYER_TYPE_HARDWARE
: View.LAYER_TYPE_NONE);
}
switch (getPullToRefreshScrollDirection()) {
case VERTICAL:
scrollTo(0, value);
break;
case HORIZONTAL:
scrollTo(value, 0);
break;
}
}
/**
* Smooth Scroll to position using the default duration of
* {@value #SMOOTH_SCROLL_DURATION_MS} ms.
*
* @param scrollValue - Position to scroll to
*/
protected final void smoothScrollTo(int scrollValue) {
smoothScrollTo(scrollValue, getPullToRefreshScrollDuration());
}
/**
* Smooth Scroll to position using the default duration of
* {@value #SMOOTH_SCROLL_DURATION_MS} ms.
*
* @param scrollValue - Position to scroll to
* @param listener - Listener for scroll
*/
protected final void smoothScrollTo(int scrollValue, OnSmoothScrollFinishedListener listener) {
smoothScrollTo(scrollValue, getPullToRefreshScrollDuration(), 0, listener);
}
/**
* Smooth Scroll to position using the longer default duration of
* {@value #SMOOTH_SCROLL_LONG_DURATION_MS} ms.
*
* @param scrollValue - Position to scroll to
*/
protected final void smoothScrollToLonger(int scrollValue) {
smoothScrollTo(scrollValue, getPullToRefreshScrollDurationLonger());
}
/**
* Updates the View State when the mode has been set. This does not do any
* checking that the mode is different to current state so always updates.
*/
protected void updateUIForMode() {
// We need to use the correct LayoutParam values, based on scroll
// direction
final LinearLayout.LayoutParams lp = getLoadingLayoutLayoutParams();
// Remove Header, and then add Header Loading View again if needed
if (this == mHeaderLayout.getParent()) {
removeView(mHeaderLayout);
}
if (mMode.showHeaderLoadingLayout()) {
addViewInternal(mHeaderLayout, 0, lp);
}
// Remove Footer, and then add Footer Loading View again if needed
if (this == mFooterLayout.getParent()) {
removeView(mFooterLayout);
}
if (mMode.showFooterLoadingLayout()) {
addViewInternal(mFooterLayout, lp);
}
// Hide Loading Views
refreshLoadingViewsSize();
// If we're not using Mode.BOTH, set mCurrentMode to mMode, otherwise
// set it to pull down
mCurrentMode = (mMode != Mode.BOTH) ? mMode : Mode.PULL_FROM_START;
}
private void addRefreshableView(Context context, T refreshableView) {
mRefreshableViewWrapper = new FrameLayout(context);
mRefreshableViewWrapper.addView(refreshableView, ViewGroup.LayoutParams.MATCH_PARENT,
ViewGroup.LayoutParams.MATCH_PARENT);
addViewInternal(mRefreshableViewWrapper, new LinearLayout.LayoutParams(LayoutParams.MATCH_PARENT,
LayoutParams.MATCH_PARENT));
}
private void callRefreshListener() {
if (null != mOnRefreshListener) {
mOnRefreshListener.onRefresh(this);
} else if (null != mOnRefreshListener2) {
if (mCurrentMode == Mode.PULL_FROM_START) {
mOnRefreshListener2.onPullDownToRefresh(this);
} else if (mCurrentMode == Mode.PULL_FROM_END) {
mOnRefreshListener2.onPullUpToRefresh(this);
}
}
}
@SuppressWarnings("deprecation")
private void init(Context context, AttributeSet attrs) {
switch (getPullToRefreshScrollDirection()) {
case HORIZONTAL:
setOrientation(LinearLayout.HORIZONTAL);
break;
case VERTICAL:
default:
setOrientation(LinearLayout.VERTICAL);
break;
}
setGravity(Gravity.CENTER);
ViewConfiguration config = ViewConfiguration.get(context);
mTouchSlop = config.getScaledTouchSlop();
// Styleables from XML
TypedArray a = context.obtainStyledAttributes(attrs, R.styleable.PullToRefresh);
if (a.hasValue(R.styleable.PullToRefresh_ptrMode)) {
mMode = Mode.mapIntToValue(a.getInteger(R.styleable.PullToRefresh_ptrMode, 0));
}
if (a.hasValue(R.styleable.PullToRefresh_ptrAnimationStyle)) {
mLoadingAnimationStyle = AnimationStyle.mapIntToValue(a.getInteger(
R.styleable.PullToRefresh_ptrAnimationStyle, 0));
}
// Refreshable View
// By passing the attrs, we can add ListView/GridView params via XML
mRefreshableView = createRefreshableView(context, attrs);
addRefreshableView(context, mRefreshableView);
// We need to create now layouts now
mHeaderLayout = createLoadingLayout(context, Mode.PULL_FROM_START, a);
mFooterLayout = createLoadingLayout(context, Mode.PULL_FROM_END, a);
/**
* Styleables from XML
*/
if (a.hasValue(R.styleable.PullToRefresh_ptrRefreshableViewBackground)) {
Drawable background = a.getDrawable(R.styleable.PullToRefresh_ptrRefreshableViewBackground);
if (null != background) {
mRefreshableView.setBackgroundDrawable(background);
}
} else if (a.hasValue(R.styleable.PullToRefresh_ptrAdapterViewBackground)) {
Utils.warnDeprecation("ptrAdapterViewBackground", "ptrRefreshableViewBackground");
Drawable background = a.getDrawable(R.styleable.PullToRefresh_ptrAdapterViewBackground);
if (null != background) {
mRefreshableView.setBackgroundDrawable(background);
}
}
if (a.hasValue(R.styleable.PullToRefresh_ptrOverScroll)) {
mOverScrollEnabled = a.getBoolean(R.styleable.PullToRefresh_ptrOverScroll, true);
}
if (a.hasValue(R.styleable.PullToRefresh_ptrScrollingWhileRefreshingEnabled)) {
mScrollingWhileRefreshingEnabled = a.getBoolean(
R.styleable.PullToRefresh_ptrScrollingWhileRefreshingEnabled, false);
}
// Let the derivative classes have a go at handling attributes, then
// recycle them...
handleStyledAttributes(a);
a.recycle();
// Finally update the UI for the modes
updateUIForMode();
}
private boolean isReadyForPull() {
switch (mMode) {
case PULL_FROM_START:
return isReadyForPullStart();
case PULL_FROM_END:
return isReadyForPullEnd();
case BOTH:
return isReadyForPullEnd() || isReadyForPullStart();
default:
return false;
}
}
/**
* Actions a Pull Event
*
* @return true if the Event has been handled, false if there has been no
* change
*/
private void pullEvent() {
final int newScrollValue;
final int itemDimension;
final float initialMotionValue, lastMotionValue;
switch (getPullToRefreshScrollDirection()) {
case HORIZONTAL:
initialMotionValue = mInitialMotionX;
lastMotionValue = mLastMotionX;
break;
case VERTICAL:
default:
initialMotionValue = mInitialMotionY;
lastMotionValue = mLastMotionY;
break;
}
switch (mCurrentMode) {
case PULL_FROM_END:
newScrollValue = Math.round(Math.max(initialMotionValue - lastMotionValue, 0) / FRICTION);
itemDimension = getFooterSize();
break;
case PULL_FROM_START:
default:
newScrollValue = Math.round(Math.min(initialMotionValue - lastMotionValue, 0) / FRICTION);
itemDimension = getHeaderSize();
break;
}
setHeaderScroll(newScrollValue);
if (newScrollValue != 0 && !isRefreshing()) {
float scale = Math.abs(newScrollValue) / (float) itemDimension;
switch (mCurrentMode) {
case PULL_FROM_END:
mFooterLayout.onPull(scale);
break;
case PULL_FROM_START:
default:
mHeaderLayout.onPull(scale);
break;
}
if (mState != State.PULL_TO_REFRESH && itemDimension >= Math.abs(newScrollValue)) {
setState(State.PULL_TO_REFRESH);
} else if (mState == State.PULL_TO_REFRESH && itemDimension < Math.abs(newScrollValue)) {
setState(State.RELEASE_TO_REFRESH);
}
}
}
private LinearLayout.LayoutParams getLoadingLayoutLayoutParams() {
switch (getPullToRefreshScrollDirection()) {
case HORIZONTAL:
return new LinearLayout.LayoutParams(LinearLayout.LayoutParams.WRAP_CONTENT,
LinearLayout.LayoutParams.MATCH_PARENT);
case VERTICAL:
default:
return new LinearLayout.LayoutParams(LinearLayout.LayoutParams.MATCH_PARENT,
LinearLayout.LayoutParams.WRAP_CONTENT);
}
}
private int getMaximumPullScroll() {
switch (getPullToRefreshScrollDirection()) {
case HORIZONTAL:
return Math.round(getWidth() / FRICTION);
case VERTICAL:
default:
return Math.round(getHeight() / FRICTION);
}
}
/**
* Smooth Scroll to position using the specific duration
*
* @param scrollValue - Position to scroll to
* @param duration - Duration of animation in milliseconds
*/
private final void smoothScrollTo(int scrollValue, long duration) {
smoothScrollTo(scrollValue, duration, 0, null);
}
private final void smoothScrollTo(int newScrollValue, long duration, long delayMillis,
OnSmoothScrollFinishedListener listener) {
if (null != mCurrentSmoothScrollRunnable) {
mCurrentSmoothScrollRunnable.stop();
}
final int oldScrollValue;
switch (getPullToRefreshScrollDirection()) {
case HORIZONTAL:
oldScrollValue = getScrollX();
break;
case VERTICAL:
default:
oldScrollValue = getScrollY();
break;
}
if (oldScrollValue != newScrollValue) {
if (null == mScrollAnimationInterpolator) {
// Default interpolator is a Decelerate Interpolator
mScrollAnimationInterpolator = new DecelerateInterpolator();
}
mCurrentSmoothScrollRunnable = new SmoothScrollRunnable(oldScrollValue, newScrollValue, duration, listener);
if (delayMillis > 0) {
postDelayed(mCurrentSmoothScrollRunnable, delayMillis);
} else {
post(mCurrentSmoothScrollRunnable);
}
}
}
private final void smoothScrollToAndBack(int y) {
smoothScrollTo(y, SMOOTH_SCROLL_DURATION_MS, 0, new OnSmoothScrollFinishedListener() {
@Override
public void onSmoothScrollFinished() {
smoothScrollTo(0, SMOOTH_SCROLL_DURATION_MS, DEMO_SCROLL_INTERVAL, null);
}
});
}
public static enum AnimationStyle {
/**
* This is the default for Android-PullToRefresh. Allows you to use any
* drawable, which is automatically rotated and used as a Progress Bar.
*/
ROTATE,
/**
* This is the old default, and what is commonly used on iOS. Uses an
* arrow image which flips depending on where the user has scrolled.
*/
FLIP;
static AnimationStyle getDefault() {
return ROTATE;
}
/**
* Maps an int to a specific mode. This is needed when saving state, or
* inflating the view from XML where the mode is given through a attr
* int.
*
* @param modeInt - int to map a Mode to
* @return Mode that modeInt maps to, or ROTATE by default.
*/
static AnimationStyle mapIntToValue(int modeInt) {
switch (modeInt) {
case 0x0:
default:
return ROTATE;
case 0x1:
return FLIP;
}
}
LoadingLayout createLoadingLayout(Context context, Mode mode, Orientation scrollDirection, TypedArray attrs) {
switch (this) {
case ROTATE:
default:
return new RotateLoadingLayout(context, mode, scrollDirection, attrs);
case FLIP:
return new FlipLoadingLayout(context, mode, scrollDirection, attrs);
}
}
}
public static enum Mode {
/**
* Disable all Pull-to-Refresh gesture and Refreshing handling
*/
DISABLED(0x0),
/**
* Only allow the user to Pull from the start of the Refreshable View to
* refresh. The start is either the Top or Left, depending on the
* scrolling direction.
*/
PULL_FROM_START(0x1),
/**
* Only allow the user to Pull from the end of the Refreshable View to
* refresh. The start is either the Bottom or Right, depending on the
* scrolling direction.
*/
PULL_FROM_END(0x2),
/**
* Allow the user to both Pull from the start, from the end to refresh.
*/
BOTH(0x3),
/**
* Disables Pull-to-Refresh gesture handling, but allows manually
* setting the Refresh state via
* {@link PullToRefreshBase#setRefreshing() setRefreshing()}.
*/
MANUAL_REFRESH_ONLY(0x4);
/**
* @deprecated Use {@link #PULL_FROM_START} from now on.
*/
public static Mode PULL_DOWN_TO_REFRESH = Mode.PULL_FROM_START;
/**
* @deprecated Use {@link #PULL_FROM_END} from now on.
*/
public static Mode PULL_UP_TO_REFRESH = Mode.PULL_FROM_END;
/**
* Maps an int to a specific mode. This is needed when saving state, or
* inflating the view from XML where the mode is given through a attr
* int.
*
* @param modeInt - int to map a Mode to
* @return Mode that modeInt maps to, or PULL_FROM_START by default.
*/
static Mode mapIntToValue(final int modeInt) {
for (Mode value : Mode.values()) {
if (modeInt == value.getIntValue()) {
return value;
}
}
// If not, return default
return getDefault();
}
static Mode getDefault() {
return PULL_FROM_START;
}
private int mIntValue;
// The modeInt values need to match those from attrs.xml
Mode(int modeInt) {
mIntValue = modeInt;
}
/**
* @return true if the mode permits Pull-to-Refresh
*/
boolean permitsPullToRefresh() {
return !(this == DISABLED || this == MANUAL_REFRESH_ONLY);
}
/**
* @return true if this mode wants the Loading Layout Header to be shown
*/
public boolean showHeaderLoadingLayout() {
return this == PULL_FROM_START || this == BOTH;
}
/**
* @return true if this mode wants the Loading Layout Footer to be shown
*/
public boolean showFooterLoadingLayout() {
return this == PULL_FROM_END || this == BOTH || this == MANUAL_REFRESH_ONLY;
}
int getIntValue() {
return mIntValue;
}
}
// ===========================================================
// Inner, Anonymous Classes, and Enumerations
// ===========================================================
/**
* Simple Listener that allows you to be notified when the user has scrolled
* to the end of the AdapterView. See (
* {@link PullToRefreshAdapterViewBase#setOnLastItemVisibleListener}.
*
* @author Chris Banes
*/
public static interface OnLastItemVisibleListener {
/**
* Called when the user has scrolled to the end of the list
*/
public void onLastItemVisible();
}
/**
* Listener that allows you to be notified when the user has started or
* finished a touch event. Useful when you want to append extra UI events
* (such as sounds). See (
* {@link PullToRefreshAdapterViewBase#setOnPullEventListener}.
*
* @author Chris Banes
*/
public static interface OnPullEventListener<V extends View> {
/**
* Called when the internal state has been changed, usually by the user
* pulling.
*
* @param refreshView - View which has had it's state change.
* @param state - The new state of View.
* @param direction - One of {@link Mode#PULL_FROM_START} or
* {@link Mode#PULL_FROM_END} depending on which direction
* the user is pulling. Only useful when <var>state</var> is
* {@link State#PULL_TO_REFRESH} or
* {@link State#RELEASE_TO_REFRESH}.
*/
public void onPullEvent(final PullToRefreshBase<V> refreshView, State state, Mode direction);
}
/**
* Simple Listener to listen for any callbacks to Refresh.
*
* @author Chris Banes
*/
public static interface OnRefreshListener<V extends View> {
/**
* onRefresh will be called for both a Pull from start, and Pull from
* end
*/
public void onRefresh(final PullToRefreshBase<V> refreshView);
}
/**
* An advanced version of the Listener to listen for callbacks to Refresh.
* This listener is different as it allows you to differentiate between Pull
* Ups, and Pull Downs.
*
* @author Chris Banes
*/
public static interface OnRefreshListener2<V extends View> {
// TODO These methods need renaming to START/END rather than DOWN/UP
/**
* onPullDownToRefresh will be called only when the user has Pulled from
* the start, and released.
*/
public void onPullDownToRefresh(final PullToRefreshBase<V> refreshView);
/**
* onPullUpToRefresh will be called only when the user has Pulled from
* the end, and released.
*/
public void onPullUpToRefresh(final PullToRefreshBase<V> refreshView);
}
public static enum Orientation {
VERTICAL, HORIZONTAL;
}
public static enum State {
/**
* When the UI is in a state which means that user is not interacting
* with the Pull-to-Refresh function.
*/
RESET(0x0),
/**
* When the UI is being pulled by the user, but has not been pulled far
* enough so that it refreshes when released.
*/
PULL_TO_REFRESH(0x1),
/**
* When the UI is being pulled by the user, and <strong>has</strong>
* been pulled far enough so that it will refresh when released.
*/
RELEASE_TO_REFRESH(0x2),
/**
* When the UI is currently refreshing, caused by a pull gesture.
*/
REFRESHING(0x8),
/**
* When the UI is currently refreshing, caused by a call to
* {@link PullToRefreshBase#setRefreshing() setRefreshing()}.
*/
MANUAL_REFRESHING(0x9),
/**
* When the UI is currently overscrolling, caused by a fling on the
* Refreshable View.
*/
OVERSCROLLING(0x10);
/**
* Maps an int to a specific state. This is needed when saving state.
*
* @param stateInt - int to map a State to
* @return State that stateInt maps to
*/
static State mapIntToValue(final int stateInt) {
for (State value : State.values()) {
if (stateInt == value.getIntValue()) {
return value;
}
}
// If not, return default
return RESET;
}
private int mIntValue;
State(int intValue) {
mIntValue = intValue;
}
int getIntValue() {
return mIntValue;
}
}
final class SmoothScrollRunnable implements Runnable {
private final Interpolator mInterpolator;
private final int mScrollToY;
private final int mScrollFromY;
private final long mDuration;
private OnSmoothScrollFinishedListener mListener;
private boolean mContinueRunning = true;
private long mStartTime = -1;
private int mCurrentY = -1;
public SmoothScrollRunnable(int fromY, int toY, long duration, OnSmoothScrollFinishedListener listener) {
mScrollFromY = fromY;
mScrollToY = toY;
mInterpolator = mScrollAnimationInterpolator;
mDuration = duration;
mListener = listener;
}
@Override
public void run() {
/**
* Only set mStartTime if this is the first time we're starting,
* else actually calculate the Y delta
*/
if (mStartTime == -1) {
mStartTime = System.currentTimeMillis();
} else {
/**
* We do do all calculations in long to reduce software float
* calculations. We use 1000 as it gives us good accuracy and
* small rounding errors
*/
long normalizedTime = (1000 * (System.currentTimeMillis() - mStartTime)) / mDuration;
normalizedTime = Math.max(Math.min(normalizedTime, 1000), 0);
final int deltaY = Math.round((mScrollFromY - mScrollToY)
* mInterpolator.getInterpolation(normalizedTime / 1000f));
mCurrentY = mScrollFromY - deltaY;
setHeaderScroll(mCurrentY);
}
// If we're not at the target Y, keep going...
if (mContinueRunning && mScrollToY != mCurrentY) {
ViewCompat.postOnAnimation(PullToRefreshBase.this, this);
} else {
if (null != mListener) {
mListener.onSmoothScrollFinished();
}
}
}
public void stop() {
mContinueRunning = false;
removeCallbacks(this);
}
}
static interface OnSmoothScrollFinishedListener {
void onSmoothScrollFinished();
}
}
================================================
FILE: library/src/com/handmark/pulltorefresh/library/PullToRefreshExpandableListView.java
================================================
/*******************************************************************************
* Copyright 2011, 2012 Chris Banes.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*******************************************************************************/
package com.handmark.pulltorefresh.library;
import android.annotation.TargetApi;
import android.content.Context;
import android.os.Build.VERSION;
import android.os.Build.VERSION_CODES;
import android.util.AttributeSet;
import android.view.View;
import android.widget.ExpandableListView;
import com.handmark.pulltorefresh.library.internal.EmptyViewMethodAccessor;
public class PullToRefreshExpandableListView extends PullToRefreshAdapterViewBase<ExpandableListView> {
public PullToRefreshExpandableListView(Context context) {
super(context);
}
public PullToRefreshExpandableListView(Context context, AttributeSet attrs) {
super(context, attrs);
}
public PullToRefreshExpandableListView(Context context, Mode mode) {
super(context, mode);
}
public PullToRefreshExpandableListView(Context context, Mode mode, AnimationStyle style) {
super(context, mode, style);
}
@Override
public final Orientation getPullToRefreshScrollDirection() {
return Orientation.VERTICAL;
}
@Override
protected ExpandableListView createRefreshableView(Context context, AttributeSet attrs) {
final ExpandableListView lv;
if (VERSION.SDK_INT >= VERSION_CODES.GINGERBREAD) {
lv = new InternalExpandableListViewSDK9(context, attrs);
} else {
lv = new InternalExpandableListView(context, attrs);
}
// Set it to this so it can be used in ListActivity/ListFragment
lv.setId(android.R.id.list);
return lv;
}
class InternalExpandableListView extends ExpandableListView implements EmptyViewMethodAccessor {
public InternalExpandableListView(Context context, AttributeSet attrs) {
super(context, attrs);
}
@Override
public void setEmptyView(View emptyView) {
PullToRefreshExpandableListView.this.setEmptyView(emptyView);
}
@Override
public void setEmptyViewInternal(View emptyView) {
super.setEmptyView(emptyView);
}
}
@TargetApi(9)
final class InternalExpandableListViewSDK9 extends InternalExpandableListView {
public InternalExpandableListViewSDK9(Context context, AttributeSet attrs) {
super(context, attrs);
}
@Override
protected boolean overScrollBy(int deltaX, int deltaY, int scrollX, int scrollY, int scrollRangeX,
int scrollRangeY, int maxOverScrollX, int maxOverScrollY, boolean isTouchEvent) {
final boolean returnValue = super.overScrollBy(deltaX, deltaY, scrollX, scrollY, scrollRangeX,
scrollRangeY, maxOverScrollX, maxOverScrollY, isTouchEvent);
// Does all of the hard work...
OverscrollHelper.overScrollBy(PullToRefreshExpandableListView.this, deltaX, scrollX, deltaY, scrollY,
isTouchEvent);
return returnValue;
}
}
}
================================================
FILE: library/src/com/handmark/pulltorefresh/library/PullToRefreshGridView.java
================================================
/*******************************************************************************
* Copyright 2011, 2012 Chris Banes.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*******************************************************************************/
package com.handmark.pulltorefresh.library;
import android.annotation.TargetApi;
import android.content.Context;
import android.os.Build.VERSION;
import android.os.Build.VERSION_CODES;
import android.util.AttributeSet;
import android.view.View;
import android.widget.GridView;
import com.handmark.pulltorefresh.library.internal.EmptyViewMethodAccessor;
public class PullToRefreshGridView extends PullToRefreshAdapterViewBase<GridView> {
public PullToRefreshGridView(Context context) {
super(context);
}
public PullToRefreshGridView(Context context, AttributeSet attrs) {
super(context, attrs);
}
public PullToRefreshGridView(Context context, Mode mode) {
super(context, mode);
}
public PullToRefreshGridView(Context context, Mode mode, AnimationStyle style) {
super(context, mode, style);
}
@Override
public final Orientation getPullToRefreshScrollDirection() {
return Orientation.VERTICAL;
}
@Override
protected final GridView createRefreshableView(Context context, AttributeSet attrs) {
final GridView gv;
if (VERSION.SDK_INT >= VERSION_CODES.GINGERBREAD) {
gv = new InternalGridViewSDK9(context, attrs);
} else {
gv = new InternalGridView(context, attrs);
}
// Use Generated ID (from res/values/ids.xml)
gv.setId(R.id.gridview);
return gv;
}
class InternalGridView extends GridView implements EmptyViewMethodAccessor {
public InternalGridView(Context context, AttributeSet attrs) {
super(context, attrs);
}
@Override
public void setEmptyView(View emptyView) {
PullToRefreshGridView.this.setEmptyView(emptyView);
}
@Override
public void setEmptyViewInternal(View emptyView) {
super.setEmptyView(emptyView);
}
}
@TargetApi(9)
final class InternalGridViewSDK9 extends InternalGridView {
public InternalGridViewSDK9(Context context, AttributeSet attrs) {
super(context, attrs);
}
@Override
protected boolean overScrollBy(int deltaX, int deltaY, int scrollX, int scrollY, int scrollRangeX,
int scrollRangeY, int maxOverScrollX, int maxOverScrollY, boolean isTouchEvent) {
final boolean returnValue = super.overScrollBy(deltaX, deltaY, scrollX, scrollY, scrollRangeX,
scrollRangeY, maxOverScrollX, maxOverScrollY, isTouchEvent);
// Does all of the hard work...
OverscrollHelper.overScrollBy(PullToRefreshGridView.this, deltaX, scrollX, deltaY, scrollY, isTouchEvent);
return returnValue;
}
}
}
================================================
FILE: library/src/com/handmark/pulltorefresh/library/PullToRefreshHorizontalScrollView.java
================================================
/*******************************************************************************
* Copyright 2011, 2012 Chris Banes.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*******************************************************************************/
package com.handmark.pulltorefresh.library;
import android.annotation.TargetApi;
import android.content.Context;
import android.os.Build.VERSION;
import android.os.Build.VERSION_CODES;
import android.util.AttributeSet;
import android.view.View;
import android.widget.HorizontalScrollView;
public class PullToRefreshHorizontalScrollView extends PullToRefreshBase<HorizontalScrollView> {
public PullToRefreshHorizontalScrollView(Context context) {
super(context);
}
public PullToRefreshHorizontalScrollView(Context context, AttributeSet attrs) {
super(context, attrs);
}
public PullToRefreshHorizontalScrollView(Context context, Mode mode) {
super(context, mode);
}
public PullToRefreshHorizontalScrollView(Context context, Mode mode, AnimationStyle style) {
super(context, mode, style);
}
@Override
public final Orientation getPullToRefreshScrollDirection() {
return Orientation.HORIZONTAL;
}
@Override
protected HorizontalScrollView createRefreshableView(Context context, AttributeSet attrs) {
HorizontalScrollView scrollView;
if (VERSION.SDK_INT >= VERSION_CODES.GINGERBREAD) {
scrollView = new InternalHorizontalScrollViewSDK9(context, attrs);
} else {
scrollView = new HorizontalScrollView(context, attrs);
}
scrollView.setId(R.id.scrollview);
return scrollView;
}
@Override
protected boolean isReadyForPullStart() {
return mRefreshableView.getScrollX() == 0;
}
@Override
protected boolean isReadyForPullEnd() {
View scrollViewChild = mRefreshableView.getChildAt(0);
if (null != scrollViewChild) {
return mRefreshableView.getScrollX() >= (scrollViewChild.getWidth() - getWidth());
}
return false;
}
@TargetApi(9)
final class InternalHorizontalScrollViewSDK9 extends HorizontalScrollView {
public InternalHorizontalScrollViewSDK9(Context context, AttributeSet attrs) {
super(context, attrs);
}
@Override
protected boolean overScrollBy(int deltaX, int deltaY, int scrollX, int scrollY, int scrollRangeX,
int scrollRangeY, int maxOverScrollX, int maxOverScrollY, boolean isTouchEvent) {
final boolean returnValue = super.overScrollBy(deltaX, deltaY, scrollX, scrollY, scrollRangeX,
scrollRangeY, maxOverScrollX, maxOverScrollY, isTouchEvent);
// Does all of the hard work...
OverscrollHelper.overScrollBy(PullToRefreshHorizontalScrollView.this, deltaX, scrollX, deltaY, scrollY,
getScrollRange(), isTouchEvent);
return returnValue;
}
/**
* Taken from the AOSP ScrollView source
*/
private int getScrollRange() {
int scrollRange = 0;
if (getChildCount() > 0) {
View child = getChildAt(0);
scrollRange = Math.max(0, child.getWidth() - (getWidth() - getPaddingLeft() - getPaddingRight()));
}
return scrollRange;
}
}
}
================================================
FILE: library/src/com/handmark/pulltorefresh/library/PullToRefreshListView.java
================================================
/*******************************************************************************
* Copyright 2011, 2012 Chris Banes.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*******************************************************************************/
package com.handmark.pulltorefresh.library;
import android.annotation.TargetApi;
import android.content.Context;
import android.content.res.TypedArray;
import android.graphics.Canvas;
import android.os.Build.VERSION;
import android.os.Build.VERSION_CODES;
import android.util.AttributeSet;
import android.view.Gravity;
import android.view.MotionEvent;
import android.view.View;
import android.widget.FrameLayout;
import android.widget.ListAdapter;
import android.widget.ListView;
import com.handmark.pulltorefresh.library.internal.EmptyViewMethodAccessor;
import com.handmark.pulltorefresh.library.internal.LoadingLayout;
public class PullToRefreshListView extends PullToRefreshAdapterViewBase<ListView> {
private LoadingLayout mHeaderLoadingView;
private LoadingLayout mFooterLoadingView;
private FrameLayout mLvFooterLoadingFrame;
private boolean mListViewExtrasEnabled;
public PullToRefreshListView(Context context) {
super(context);
}
public PullToRefreshListView(Context context, AttributeSet attrs) {
super(context, attrs);
}
public PullToRefreshListView(Context context, Mode mode) {
super(context, mode);
}
public PullToRefreshListView(Context context, Mode mode, AnimationStyle style) {
super(context, mode, style);
}
@Override
public final Orientation getPullToRefreshScrollDirection() {
return Orientation.VERTICAL;
}
@Override
protected void onRefreshing(final boolean doScroll) {
/**
* If we're not showing the Refreshing view, or the list is empty, the
* the header/footer views won't show so we use the normal method.
*/
ListAdapter adapter = mRefreshableView.getAdapter();
if (!mListViewExtrasEnabled || !getShowViewWhileRefreshing() || null == adapter || adapter.isEmpty()) {
super.onRefreshing(doScroll);
return;
}
super.onRefreshing(false);
final LoadingLayout origLoadingView, listViewLoadingView, oppositeListViewLoadingView;
final int selection, scrollToY;
switch (getCurrentMode()) {
case MANUAL_REFRESH_ONLY:
case PULL_FROM_END:
origLoadingView = getFooterLayout();
listViewLoadingView = mFooterLoadingView;
oppositeListViewLoadingView = mHeaderLoadingView;
selection = mRefreshableView.getCount() - 1;
scrollToY = getScrollY() - getFooterSize();
break;
case PULL_FROM_START:
default:
origLoadingView = getHeaderLayout();
listViewLoadingView = mHeaderLoadingView;
oppositeListViewLoadingView = mFooterLoadingView;
selection = 0;
scrollToY = getScrollY() + getHeaderSize();
break;
}
// Hide our original Loading View
origLoadingView.reset();
origLoadingView.hideAllViews();
// Make sure the opposite end is hidden too
oppositeListViewLoadingView.setVisibility(View.GONE);
// Show the ListView Loading View and set it to refresh.
listViewLoadingView.setVisibility(View.VISIBLE);
listViewLoadingView.refreshing();
if (doScroll) {
// We need to disable the automatic visibility changes for now
disableLoadingLayoutVisibilityChanges();
// We scroll slightly so that the ListView's header/footer is at the
// same Y position as our normal header/footer
setHeaderScroll(scrollToY);
// Make sure the ListView is scrolled to show the loading
// header/footer
mRefreshableView.setSelection(selection);
// Smooth scroll as normal
smoothScrollTo(0);
}
}
@Override
protected void onReset() {
/**
* If the extras are not enabled, just call up to super and return.
*/
if (!mListViewExtrasEnabled) {
super.onReset();
return;
}
final LoadingLayout originalLoadingLayout, listViewLoadingLayout;
final int scrollToHeight, selection;
final boolean scrollLvToEdge;
switch (getCurrentMode()) {
case MANUAL_REFRESH_ONLY:
case PULL_FROM_END:
originalLoadingLayout = getFooterLayout();
listViewLoadingLayout = mFooterLoadingView;
selection = mRefreshableView.getCount() - 1;
scrollToHeight = getFooterSize();
scrollLvToEdge = Math.abs(mRefreshableView.getLastVisiblePosition() - selection) <= 1;
break;
case PULL_FROM_START:
default:
originalLoadingLayout = getHeaderLayout();
listViewLoadingLayout = mHeaderLoadingView;
scrollToHeight = -getHeaderSize();
selection = 0;
scrollLvToEdge = Math.abs(mRefreshableView.getFirstVisiblePosition() - selection) <= 1;
break;
}
// If the ListView header loading layout is showing, then we need to
// flip so that the original one is showing instead
if (listViewLoadingLayout.getVisibility() == View.VISIBLE) {
// Set our Original View to Visible
originalLoadingLayout.showInvisibleViews();
// Hide the ListView Header/Footer
listViewLoadingLayout.setVisibility(View.GONE);
/**
* Scroll so the View is at the same Y as the ListView
* header/footer, but only scroll if: we've pulled to refresh, it's
* positioned correctly
*/
if (scrollLvToEdge && getState() != State.MANUAL_REFRESHING) {
mRefreshableView.setSelection(selection);
setHeaderScroll(scrollToHeight);
}
}
// Finally, call up to super
super.onReset();
}
@Override
protected LoadingLayoutProxy createLoadingLayoutProxy(final boolean includeStart, final boolean includeEnd) {
LoadingLayoutProxy proxy = super.createLoadingLayoutProxy(includeStart, includeEnd);
if (mListViewExtrasEnabled) {
final Mode mode = getMode();
if (includeStart && mode.showHeaderLoadingLayout()) {
proxy.addLayout(mHeaderLoadingView);
}
if (includeEnd && mode.showFooterLoadingLayout()) {
proxy.addLayout(mFooterLoadingView);
}
}
return proxy;
}
protected ListView createListView(Context context, AttributeSet attrs) {
final ListView lv;
if (VERSION.SDK_INT >= VERSION_CODES.GINGERBREAD) {
lv = new InternalListViewSDK9(context, attrs);
} else {
lv = new InternalListView(context, attrs);
}
return lv;
}
@Override
protected ListView createRefreshableView(Context context, AttributeSet attrs) {
ListView lv = createListView(context, attrs);
// Set it to this so it can be used in ListActivity/ListFragment
lv.setId(android.R.id.list);
return lv;
}
@Override
protected void handleStyledAttributes(TypedArray a) {
super.handleStyledAttributes(a);
mListViewExtrasEnabled = a.getBoolean(R.styleable.PullToRefresh_ptrListViewExtrasEnabled, true);
if (mListViewExtrasEnabled) {
final FrameLayout.LayoutParams lp = new FrameLayout.LayoutParams(FrameLayout.LayoutParams.MATCH_PARENT,
FrameLayout.LayoutParams.WRAP_CONTENT, Gravity.CENTER_HORIZONTAL);
// Create Loading Views ready for use later
FrameLayout frame = new FrameLayout(getContext());
mHeaderLoadingView = createLoadingLayout(getContext(), Mode.PULL_FROM_START, a);
mHeaderLoadingView.setVisibility(View.GONE);
frame.addView(mHeaderLoadingView, lp);
mRefreshableView.addHeaderView(frame, null, false);
mLvFooterLoadingFrame = new FrameLayout(getContext());
mFooterLoadingView = createLoadingLayout(getContext(), Mode.PULL_FROM_END, a);
mFooterLoadingView.setVisibility(View.GONE);
mLvFooterLoadingFrame.addView(mFooterLoadingView, lp);
/**
* If the value for Scrolling While Refreshing hasn't been
* explicitly set via XML, enable Scrolling While Refreshing.
*/
if (!a.hasValue(R.styleable.PullToRefresh_ptrScrollingWhileRefreshingEnabled)) {
setScrollingWhileRefreshingEnabled(true);
}
}
}
@TargetApi(9)
final class InternalListViewSDK9 extends InternalListView {
public InternalListViewSDK9(Context context, AttributeSet attrs) {
super(context, attrs);
}
@Override
protected boolean overScrollBy(int deltaX, int deltaY, int scrollX, int scrollY, int scrollRangeX,
int scrollRangeY, int maxOverScrollX, int maxOverScrollY, boolean isTouchEvent) {
final boolean returnValue = super.overScrollBy(deltaX, deltaY, scrollX, scrollY, scrollRangeX,
scrollRangeY, maxOverScrollX, maxOverScrollY, isTouchEvent);
// Does all of the hard work...
OverscrollHelper.overScrollBy(PullToRefreshListView.this, deltaX, scrollX, deltaY, scrollY, isTouchEvent);
return returnValue;
}
}
protected class InternalListView extends ListView implements EmptyViewMethodAccessor {
private boolean mAddedLvFooter = false;
public InternalListView(Context context, AttributeSet attrs) {
super(context, attrs);
}
@Override
protected void dispatchDraw(Canvas canvas) {
/**
* This is a bit hacky, but Samsung's ListView has got a bug in it
* when using Header/Footer Views and the list is empty. This masks
* the issue so that it doesn't cause an FC. See Issue #66.
*/
try {
super.dispatchDraw(canvas);
} catch (IndexOutOfBoundsException e) {
e.printStackTrace();
}
}
@Override
public boolean dispatchTouchEvent(MotionEvent ev) {
/**
* This is a bit hacky, but Samsung's ListView has got a bug in it
* when using Header/Footer Views and the list is empty. This masks
* the issue so that it doesn't cause an FC. See Issue #66.
*/
try {
return super.dispatchTouchEvent(ev);
} catch (IndexOutOfBoundsException e) {
e.printStackTrace();
return false;
}
}
@Override
public void setAdapter(ListAdapter adapter) {
// Add the Footer View at the last possible moment
if (null != mLvFooterLoadingFrame && !mAddedLvFooter) {
addFooterView(mLvFooterLoadingFrame, null, false);
mAddedLvFooter = true;
}
super.setAdapter(adapter);
}
@Override
public void setEmptyView(View emptyView) {
PullToRefreshListView.this.setEmptyView(emptyView);
}
@Override
public void setEmptyViewInternal(View emptyView) {
super.setEmptyView(emptyView);
}
}
}
================================================
FILE: library/src/com/handmark/pulltorefresh/library/PullToRefreshScrollView.java
================================================
/*******************************************************************************
* Copyright 2011, 2012 Chris Banes.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*******************************************************************************/
package com.handmark.pulltorefresh.library;
import android.annotation.TargetApi;
import android.content.Context;
import android.os.Build.VERSION;
import android.os.Build.VERSION_CODES;
import android.util.AttributeSet;
import android.view.View;
import android.widget.ScrollView;
public class PullToRefreshScrollView extends PullToRefreshBase<ScrollView> {
public PullToRefreshScrollView(Context context) {
super(context);
}
public PullToRefreshScrollView(Context context, AttributeSet attrs) {
super(context, attrs);
}
public PullToRefreshScrollView(Context context, Mode mode) {
super(context, mode);
}
public PullToRefreshScrollView(Context context, Mode mode, AnimationStyle style) {
super(context, mode, style);
}
@Override
public final Orientation getPullToRefreshScrollDirection() {
return Orientation.VERTICAL;
}
@Override
protected ScrollView createRefreshableView(Context context, AttributeSet attrs) {
ScrollView scrollView;
if (VERSION.SDK_INT >= VERSION_CODES.GINGERBREAD) {
scrollView = new InternalScrollViewSDK9(context, attrs);
} else {
scrollView = new ScrollView(context, attrs);
}
scrollView.setId(R.id.scrollview);
return scrollView;
}
@Override
protected boolean isReadyForPullStart() {
return mRefreshableView.getScrollY() == 0;
}
@Override
protected boolean isReadyForPullEnd() {
View scrollViewChild = mRefreshableView.getChildAt(0);
if (null != scrollViewChild) {
return mRefreshableView.getScrollY() >= (scrollViewChild.getHeight() - getHeight());
}
return false;
}
@TargetApi(9)
final class InternalScrollViewSDK9 extends ScrollView {
public InternalScrollViewSDK9(Context context, AttributeSet attrs) {
super(context, attrs);
}
@Override
protected boolean overScrollBy(int deltaX, int deltaY, int scrollX, int scrollY, int scrollRangeX,
int scrollRangeY, int maxOverScrollX, int maxOverScrollY, boolean isTouchEvent) {
final boolean returnValue = super.overScrollBy(deltaX, deltaY, scrollX, scrollY, scrollRangeX,
scrollRangeY, maxOverScrollX, maxOverScrollY, isTouchEvent);
// Does all of the hard work...
OverscrollHelper.overScrollBy(PullToRefreshScrollView.this, deltaX, scrollX, deltaY, scrollY,
getScrollRange(), isTouchEvent);
return returnValue;
}
/**
* Taken from the AOSP ScrollView source
*/
private int getScrollRange() {
int scrollRange = 0;
if (getChildCount() > 0) {
View child = getChildAt(0);
scrollRange = Math.max(0, child.getHeight() - (getHeight() - getPaddingBottom() - getPaddingTop()));
}
return scrollRange;
}
}
}
================================================
FILE: library/src/com/handmark/pulltorefresh/library/PullToRefreshWebView.java
================================================
/*******************************************************************************
* Copyright 2011, 2012 Chris Banes.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*******************************************************************************/
package com.handmark.pulltorefresh.library;
import android.annotation.TargetApi;
import android.content.Context;
import android.os.Build.VERSION;
import android.os.Build.VERSION_CODES;
import android.os.Bundle;
import android.util.AttributeSet;
import android.util.FloatMath;
import android.webkit.WebChromeClient;
import android.webkit.WebView;
public class PullToRefreshWebView extends PullToRefreshBase<WebView> {
private static final OnRefreshListener<WebView> defaultOnRefreshListener = new OnRefreshListener<WebView>() {
@Override
public void onRefresh(PullToRefreshBase<WebView> refreshView) {
refreshView.getRefreshableView().reload();
}
};
private final WebChromeClient defaultWebChromeClient = new WebChromeClient() {
@Override
public void onProgressChanged(WebView view, int newProgress) {
if (newProgress == 100) {
onRefreshComplete();
}
}
};
public PullToRefreshWebView(Context context) {
super(context);
/**
* Added so that by default, Pull-to-Refresh refreshes the page
*/
setOnRefreshListener(defaultOnRefreshListener);
mRefreshableView.setWebChromeClient(defaultWebChromeClient);
}
public PullToRefreshWebView(Context context, AttributeSet attrs) {
super(context, attrs);
/**
* Added so that by default, Pull-to-Refresh refreshes the page
*/
setOnRefreshListener(defaultOnRefreshListener);
mRefreshableView.setWebChromeClient(defaultWebChromeClient);
}
public PullToRefreshWebView(Context context, Mode mode) {
super(context, mode);
/**
* Added so that by default, Pull-to-Refresh refreshes the page
*/
setOnRefreshListener(defaultOnRefreshListener);
mRefreshableView.setWebChromeClient(defaultWebChromeClient);
}
public PullToRefreshWebView(Context context, Mode mode, AnimationStyle style) {
super(context, mode, style);
/**
* Added so that by default, Pull-to-Refresh refreshes the page
*/
setOnRefreshListener(defaultOnRefreshListener);
mRefreshableView.setWebChromeClient(defaultWebChromeClient);
}
@Override
public final Orientation getPullToRefreshScrollDirection() {
return Orientation.VERTICAL;
}
@Override
protected WebView createRefreshableView(Context context, AttributeSet attrs) {
WebView webView;
if (VERSION.SDK_INT >= VERSION_CODES.GINGERBREAD) {
webView = new InternalWebViewSDK9(context, attrs);
} else {
webView = new WebView(context, attrs);
}
webView.setId(R.id.webview);
return webView;
}
@Override
protected boolean isReadyForPullStart() {
return mRefreshableView.getScrollY() == 0;
}
@Override
protected boolean isReadyForPullEnd() {
float exactContentHeight = FloatMath.floor(mRefreshableView.getContentHeight() * mRefreshableView.getScale());
return mRefreshableView.getScrollY() >= (exactContentHeight - mRefreshableView.getHeight());
}
@Override
protected void onPtrRestoreInstanceState(Bundle savedInstanceState) {
super.onPtrRestoreInstanceState(savedInstanceState);
mRefreshableView.restoreState(savedInstanceState);
}
@Override
protected void onPtrSaveInstanceState(Bundle saveState) {
super.onPtrSaveInstanceState(saveState);
mRefreshableView.saveState(saveState);
}
@TargetApi(9)
final class InternalWebViewSDK9 extends WebView {
// WebView doesn't always scroll back to it's edge so we add some
// fuzziness
static final int OVERSCROLL_FUZZY_THRESHOLD = 2;
// WebView seems quite reluctant to overscroll so we use the scale
// factor to scale it's value
static final float OVERSCROLL_SCALE_FACTOR = 1.5f;
public InternalWebViewSDK9(Context context, AttributeSet attrs) {
super(context, attrs);
}
@Override
protected boolean overScrollBy(int deltaX, int deltaY, int scrollX, int scrollY, int scrollRangeX,
int scrollRangeY, int maxOverScrollX, int maxOverScrollY, boolean isTouchEvent) {
final boolean returnValue = super.overScrollBy(deltaX, deltaY, scrollX, scrollY, scrollRangeX,
scrollRangeY, maxOverScrollX, maxOverScrollY, isTouchEvent);
// Does all of the hard work...
OverscrollHelper.overScrollBy(PullToRefreshWebView.this, deltaX, scrollX, deltaY, scrollY,
getScrollRange(), OVERSCROLL_FUZZY_THRESHOLD, OVERSCROLL_SCALE_FACTOR, isTouchEvent);
return returnValue;
}
private int getScrollRange() {
return (int) Math.max(0, FloatMath.floor(mRefreshableView.getContentHeight() * mRefreshableView.getScale())
- (getHeight() - getPaddingBottom() - getPaddingTop()));
}
}
}
================================================
FILE: library/src/com/handmark/pulltorefresh/library/extras/PullToRefreshWebView2.java
================================================
/*******************************************************************************
* Copyright 2011, 2012 Chris Banes.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*******************************************************************************/
package com.handmark.pulltorefresh.library.extras;
import java.util.concurrent.atomic.AtomicBoolean;
import android.content.Context;
import android.util.AttributeSet;
import android.webkit.WebView;
import com.handmark.pulltorefresh.library.PullToRefreshWebView;
/**
* An advanced version of {@link PullToRefreshWebView} which delegates the
* triggering of the PullToRefresh gesture to the Javascript running within the
* WebView. This means that you should only use this class if:
* <p/>
* <ul>
* <li>{@link PullToRefreshWebView} doesn't work correctly because you're using
* <code>overflow:scroll</code> or something else which means
* {@link WebView#getScrollY()} doesn't return correct values.</li>
* <li>You control the web content being displayed, as you need to write some
* Javascript callbacks.</li>
* </ul>
* <p/>
* <p/>
* The way this call works is that when a PullToRefresh gesture is in action,
* the following Javascript methods will be called:
* <code>isReadyForPullDown()</code> and <code>isReadyForPullUp()</code>, it is
* your job to calculate whether the view is in a state where a PullToRefresh
* can happen, and return the result via the callback mechanism. An example can
* be seen below:
* <p/>
*
* <pre>
* function isReadyForPullDown() {
* var result = ... // Probably using the .scrollTop DOM attribute
* ptr.isReadyForPullDownResponse(result);
* }
*
* function isReadyForPullUp() {
* var result = ... // Probably using the .scrollBottom DOM attribute
* ptr.isReadyForPullUpResponse(result);
* }
* </pre>
*
* @author Chris Banes
*/
public class PullToRefreshWebView2 extends PullToRefreshWebView {
static final String JS_INTERFACE_PKG = "ptr";
static final String DEF_JS_READY_PULL_DOWN_CALL = "javascript:isReadyForPullDown();";
static final String DEF_JS_READY_PULL_UP_CALL = "javascript:isReadyForPullUp();";
public PullToRefreshWebView2(Context context) {
super(context);
}
public PullToRefreshWebView2(Context context, AttributeSet attrs) {
super(context, attrs);
}
public PullToRefreshWebView2(Context context, Mode mode) {
super(context, mode);
}
private JsValueCallback mJsCallback;
private final AtomicBoolean mIsReadyForPullDown = new AtomicBoolean(false);
private final AtomicBoolean mIsReadyForPullUp = new AtomicBoolean(false);
@Override
protected WebView createRefreshableView(Context context, AttributeSet attrs) {
WebView webView = super.createRefreshableView(context, attrs);
// Need to add JS Interface so we can get the response back
mJsCallback = new JsValueCallback();
webView.addJavascriptInterface(mJsCallback, JS_INTERFACE_PKG);
return webView;
}
@Override
protected boolean isReadyForPullStart() {
// Call Javascript...
getRefreshableView().loadUrl(DEF_JS_READY_PULL_DOWN_CALL);
// Response will be given to JsValueCallback, which will update
// mIsReadyForPullDown
return mIsReadyForPullDown.get();
}
@Override
protected boolean isReadyForPullEnd() {
// Call Javascript...
getRefreshableView().loadUrl(DEF_JS_READY_PULL_UP_CALL);
// Response will be given to JsValueCallback, which will update
// mIsReadyForPullUp
return mIsReadyForPullUp.get();
}
/**
* Used for response from Javascript
*
* @author Chris Banes
*/
final class JsValueCallback {
public void isReadyForPullUpResponse(boolean response) {
mIsReadyForPullUp.set(response);
}
public void isReadyForPullDownResponse(boolean response) {
mIsReadyForPullDown.set(response);
}
}
}
================================================
FILE: library/src/com/handmark/pulltorefresh/library/extras/SoundPullEventListener.java
================================================
/*******************************************************************************
* Copyright 2011, 2012 Chris Banes.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you
gitextract_jnxqu0qu/
├── .gitignore
├── LICENSE
├── README.md
├── extras/
│ ├── PullToRefreshListFragment/
│ │ ├── AndroidManifest.xml
│ │ ├── LICENSE
│ │ ├── libs/
│ │ │ └── android-support-v4.jar
│ │ ├── pom.xml
│ │ ├── project.properties
│ │ ├── res/
│ │ │ └── layout/
│ │ │ └── need_this_for_maven.xml
│ │ └── src/
│ │ └── com/
│ │ └── handmark/
│ │ └── pulltorefresh/
│ │ └── extras/
│ │ └── listfragment/
│ │ ├── PullToRefreshBaseListFragment.java
│ │ ├── PullToRefreshExpandableListFragment.java
│ │ └── PullToRefreshListFragment.java
│ ├── PullToRefreshViewPager/
│ │ ├── AndroidManifest.xml
│ │ ├── ant.properties
│ │ ├── libs/
│ │ │ └── android-support-v4.jar
│ │ ├── pom.xml
│ │ ├── proguard-project.txt
│ │ ├── project.properties
│ │ ├── res/
│ │ │ ├── layout/
│ │ │ │ └── need_this_for_maven.xml
│ │ │ └── values/
│ │ │ └── ids.xml
│ │ └── src/
│ │ └── com/
│ │ └── handmark/
│ │ └── pulltorefresh/
│ │ └── extras/
│ │ └── viewpager/
│ │ └── PullToRefreshViewPager.java
│ └── pom.xml
├── library/
│ ├── AndroidManifest.xml
│ ├── LICENSE
│ ├── pom.xml
│ ├── project.properties
│ ├── res/
│ │ ├── anim/
│ │ │ ├── slide_in_from_bottom.xml
│ │ │ ├── slide_in_from_top.xml
│ │ │ ├── slide_out_to_bottom.xml
│ │ │ └── slide_out_to_top.xml
│ │ ├── drawable/
│ │ │ ├── indicator_bg_bottom.xml
│ │ │ └── indicator_bg_top.xml
│ │ ├── layout/
│ │ │ ├── pull_to_refresh_header_horizontal.xml
│ │ │ └── pull_to_refresh_header_vertical.xml
│ │ ├── values/
│ │ │ ├── attrs.xml
│ │ │ ├── dimens.xml
│ │ │ ├── ids.xml
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-ar/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-cs/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-de/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-es/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-fi/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-fr/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-he/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-it/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-iw/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-ja/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-ko/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-nl/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-pl/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-pt/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-pt-rBR/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-ro/
│ │ │ └── pull_refresh_strings.xml
│ │ ├── values-ru/
│ │ │ └── pull_refresh_strings.xml
│ │ └── values-zh/
│ │ └── pull_refresh_strings.xml
│ └── src/
│ └── com/
│ └── handmark/
│ └── pulltorefresh/
│ └── library/
│ ├── ILoadingLayout.java
│ ├── IPullToRefresh.java
│ ├── LoadingLayoutProxy.java
│ ├── OverscrollHelper.java
│ ├── PullToRefreshAdapterViewBase.java
│ ├── PullToRefreshBase.java
│ ├── PullToRefreshExpandableListView.java
│ ├── PullToRefreshGridView.java
│ ├── PullToRefreshHorizontalScrollView.java
│ ├── PullToRefreshListView.java
│ ├── PullToRefreshScrollView.java
│ ├── PullToRefreshWebView.java
│ ├── extras/
│ │ ├── PullToRefreshWebView2.java
│ │ └── SoundPullEventListener.java
│ └── internal/
│ ├── EmptyViewMethodAccessor.java
│ ├── FlipLoadingLayout.java
│ ├── IndicatorLayout.java
│ ├── LoadingLayout.java
│ ├── RotateLoadingLayout.java
│ ├── Utils.java
│ └── ViewCompat.java
├── pom.xml
└── sample/
├── AndroidManifest.xml
├── LICENSE
├── assets/
│ └── ptr_webview2_sample.html
├── libs/
│ └── android-support-v4.jar
├── pom.xml
├── project.properties
├── res/
│ ├── layout/
│ │ ├── activity_ptr_expandable_list.xml
│ │ ├── activity_ptr_grid.xml
│ │ ├── activity_ptr_horizontalscrollview.xml
│ │ ├── activity_ptr_list.xml
│ │ ├── activity_ptr_list_fragment.xml
│ │ ├── activity_ptr_list_in_vp.xml
│ │ ├── activity_ptr_scrollview.xml
│ │ ├── activity_ptr_viewpager.xml
│ │ ├── activity_ptr_webview.xml
│ │ ├── activity_ptr_webview2.xml
│ │ └── layout_listview_in_viewpager.xml
│ └── values/
│ ├── strings.xml
│ └── styles.xml
└── src/
└── com/
└── handmark/
└── pulltorefresh/
└── samples/
├── LauncherActivity.java
├── PullToRefreshExpandableListActivity.java
├── PullToRefreshGridActivity.java
├── PullToRefreshHorizontalScrollViewActivity.java
├── PullToRefreshListActivity.java
├── PullToRefreshListFragmentActivity.java
├── PullToRefreshListInViewPagerActivity.java
├── PullToRefreshScrollViewActivity.java
├── PullToRefreshViewPagerActivity.java
├── PullToRefreshWebView2Activity.java
└── PullToRefreshWebViewActivity.java
SYMBOL INDEX (472 symbols across 36 files)
FILE: extras/PullToRefreshListFragment/src/com/handmark/pulltorefresh/extras/listfragment/PullToRefreshBaseListFragment.java
class PullToRefreshBaseListFragment (line 28) | abstract class PullToRefreshBaseListFragment<T extends PullToRefreshBase...
method onCreateView (line 32) | @Override
method getPullToRefreshListView (line 51) | public final T getPullToRefreshListView() {
method onCreatePullToRefreshListView (line 66) | protected abstract T onCreatePullToRefreshListView(LayoutInflater infl...
FILE: extras/PullToRefreshListFragment/src/com/handmark/pulltorefresh/extras/listfragment/PullToRefreshExpandableListFragment.java
class PullToRefreshExpandableListFragment (line 39) | public class PullToRefreshExpandableListFragment extends PullToRefreshBa...
method onCreatePullToRefreshListView (line 41) | protected PullToRefreshExpandableListView onCreatePullToRefreshListVie...
FILE: extras/PullToRefreshListFragment/src/com/handmark/pulltorefresh/extras/listfragment/PullToRefreshListFragment.java
class PullToRefreshListFragment (line 38) | public class PullToRefreshListFragment extends PullToRefreshBaseListFrag...
method onCreatePullToRefreshListView (line 40) | protected PullToRefreshListView onCreatePullToRefreshListView(LayoutIn...
FILE: extras/PullToRefreshViewPager/src/com/handmark/pulltorefresh/extras/viewpager/PullToRefreshViewPager.java
class PullToRefreshViewPager (line 25) | public class PullToRefreshViewPager extends PullToRefreshBase<ViewPager> {
method PullToRefreshViewPager (line 27) | public PullToRefreshViewPager(Context context) {
method PullToRefreshViewPager (line 31) | public PullToRefreshViewPager(Context context, AttributeSet attrs) {
method getPullToRefreshScrollDirection (line 35) | @Override
method createRefreshableView (line 40) | @Override
method isReadyForPullStart (line 47) | @Override
method isReadyForPullEnd (line 59) | @Override
FILE: library/src/com/handmark/pulltorefresh/library/ILoadingLayout.java
type ILoadingLayout (line 6) | public interface ILoadingLayout {
method setLastUpdatedLabel (line 14) | public void setLastUpdatedLabel(CharSequence label);
method setLoadingDrawable (line 22) | public void setLoadingDrawable(Drawable drawable);
method setPullLabel (line 30) | public void setPullLabel(CharSequence pullLabel);
method setRefreshingLabel (line 38) | public void setRefreshingLabel(CharSequence refreshingLabel);
method setReleaseLabel (line 47) | public void setReleaseLabel(CharSequence releaseLabel);
method setTextTypeface (line 55) | public void setTextTypeface(Typeface tf);
FILE: library/src/com/handmark/pulltorefresh/library/IPullToRefresh.java
type IPullToRefresh (line 27) | public interface IPullToRefresh<T extends View> {
method demo (line 38) | public boolean demo();
method getCurrentMode (line 46) | public Mode getCurrentMode();
method getFilterTouchEvents (line 57) | public boolean getFilterTouchEvents();
method getLoadingLayoutProxy (line 69) | public ILoadingLayout getLoadingLayoutProxy();
method getLoadingLayoutProxy (line 85) | public ILoadingLayout getLoadingLayoutProxy(boolean includeStart, bool...
method getMode (line 94) | public Mode getMode();
method getRefreshableView (line 102) | public T getRefreshableView();
method getShowViewWhileRefreshing (line 110) | public boolean getShowViewWhileRefreshing();
method getState (line 115) | public State getState();
method isPullToRefreshEnabled (line 122) | public boolean isPullToRefreshEnabled();
method isPullToRefreshOverScrollEnabled (line 132) | public boolean isPullToRefreshOverScrollEnabled();
method isRefreshing (line 139) | public boolean isRefreshing();
method isScrollingWhileRefreshingEnabled (line 147) | public boolean isScrollingWhileRefreshingEnabled();
method onRefreshComplete (line 153) | public void onRefreshComplete();
method setFilterTouchEvents (line 166) | public void setFilterTouchEvents(boolean filterEvents);
method setMode (line 173) | public void setMode(Mode mode);
method setOnPullEventListener (line 181) | public void setOnPullEventListener(OnPullEventListener<T> listener);
method setOnRefreshListener (line 188) | public void setOnRefreshListener(OnRefreshListener<T> listener);
method setOnRefreshListener (line 195) | public void setOnRefreshListener(OnRefreshListener2<T> listener);
method setPullToRefreshOverScrollEnabled (line 204) | public void setPullToRefreshOverScrollEnabled(boolean enabled);
method setRefreshing (line 210) | public void setRefreshing();
method setRefreshing (line 219) | public void setRefreshing(boolean doScroll);
method setScrollAnimationInterpolator (line 227) | public void setScrollAnimationInterpolator(Interpolator interpolator);
method setScrollingWhileRefreshingEnabled (line 236) | public void setScrollingWhileRefreshingEnabled(boolean scrollingWhileR...
method setShowViewWhileRefreshing (line 244) | public void setShowViewWhileRefreshing(boolean showView);
FILE: library/src/com/handmark/pulltorefresh/library/LoadingLayoutProxy.java
class LoadingLayoutProxy (line 10) | public class LoadingLayoutProxy implements ILoadingLayout {
method LoadingLayoutProxy (line 14) | LoadingLayoutProxy() {
method addLayout (line 27) | public void addLayout(LoadingLayout layout) {
method setLastUpdatedLabel (line 33) | @Override
method setLoadingDrawable (line 40) | @Override
method setRefreshingLabel (line 47) | @Override
method setPullLabel (line 54) | @Override
method setReleaseLabel (line 61) | @Override
method setTextTypeface (line 68) | public void setTextTypeface(Typeface tf) {
FILE: library/src/com/handmark/pulltorefresh/library/OverscrollHelper.java
class OverscrollHelper (line 25) | @TargetApi(9)
method overScrollBy (line 51) | public static void overScrollBy(final PullToRefreshBase<?> view, final...
method overScrollBy (line 75) | public static void overScrollBy(final PullToRefreshBase<?> view, final...
method overScrollBy (line 102) | public static void overScrollBy(final PullToRefreshBase<?> view, final...
method isAndroidOverScrollEnabled (line 175) | static boolean isAndroidOverScrollEnabled(View view) {
FILE: library/src/com/handmark/pulltorefresh/library/PullToRefreshAdapterViewBase.java
class PullToRefreshAdapterViewBase (line 38) | public abstract class PullToRefreshAdapterViewBase<T extends AbsListView...
method convertEmptyViewLayoutParams (line 41) | private static FrameLayout.LayoutParams convertEmptyViewLayoutParams(V...
method PullToRefreshAdapterViewBase (line 68) | public PullToRefreshAdapterViewBase(Context context) {
method PullToRefreshAdapterViewBase (line 73) | public PullToRefreshAdapterViewBase(Context context, AttributeSet attr...
method PullToRefreshAdapterViewBase (line 78) | public PullToRefreshAdapterViewBase(Context context, Mode mode) {
method PullToRefreshAdapterViewBase (line 83) | public PullToRefreshAdapterViewBase(Context context, Mode mode, Animat...
method getShowIndicator (line 98) | public boolean getShowIndicator() {
method onScroll (line 102) | public final void onScroll(final AbsListView view, final int firstVisi...
method onScrollStateChanged (line 129) | public final void onScrollStateChanged(final AbsListView view, final i...
method setAdapter (line 151) | public void setAdapter(ListAdapter adapter) {
method setEmptyView (line 168) | public final void setEmptyView(View newEmptyView) {
method setOnItemClickListener (line 207) | public void setOnItemClickListener(OnItemClickListener listener) {
method setOnLastItemVisibleListener (line 211) | public final void setOnLastItemVisibleListener(OnLastItemVisibleListen...
method setOnScrollListener (line 215) | public final void setOnScrollListener(OnScrollListener listener) {
method setScrollEmptyView (line 219) | public final void setScrollEmptyView(boolean doScroll) {
method setShowIndicator (line 231) | public void setShowIndicator(boolean showIndicator) {
method onPullToRefresh (line 245) | @Override
method onRefreshing (line 264) | protected void onRefreshing(boolean doScroll) {
method onReleaseToRefresh (line 272) | @Override
method onReset (line 291) | @Override
method handleStyledAttributes (line 300) | @Override
method isReadyForPullStart (line 306) | protected boolean isReadyForPullStart() {
method isReadyForPullEnd (line 310) | protected boolean isReadyForPullEnd() {
method onScrollChanged (line 314) | @Override
method updateUIForMode (line 322) | @Override
method addIndicatorViews (line 334) | private void addIndicatorViews() {
method getShowIndicatorInternal (line 369) | private boolean getShowIndicatorInternal() {
method isFirstItemVisible (line 373) | private boolean isFirstItemVisible() {
method isLastItemVisible (line 402) | private boolean isLastItemVisible() {
method removeIndicatorViews (line 438) | private void removeIndicatorViews() {
method updateIndicatorViewsVisibility (line 450) | private void updateIndicatorViewsVisibility() {
FILE: library/src/com/handmark/pulltorefresh/library/PullToRefreshBase.java
class PullToRefreshBase (line 43) | public abstract class PullToRefreshBase<T extends View> extends LinearLa...
method PullToRefreshBase (line 106) | public PullToRefreshBase(Context context) {
method PullToRefreshBase (line 111) | public PullToRefreshBase(Context context, AttributeSet attrs) {
method PullToRefreshBase (line 116) | public PullToRefreshBase(Context context, Mode mode) {
method PullToRefreshBase (line 122) | public PullToRefreshBase(Context context, Mode mode, AnimationStyle an...
method addView (line 129) | @Override
method demo (line 144) | @Override
method getCurrentMode (line 157) | @Override
method getFilterTouchEvents (line 162) | @Override
method getLoadingLayoutProxy (line 167) | @Override
method getLoadingLayoutProxy (line 172) | @Override
method getMode (line 177) | @Override
method getRefreshableView (line 182) | @Override
method getShowViewWhileRefreshing (line 187) | @Override
method getState (line 192) | @Override
method isDisableScrollingWhileRefreshing (line 200) | public final boolean isDisableScrollingWhileRefreshing() {
method isPullToRefreshEnabled (line 204) | @Override
method isPullToRefreshOverScrollEnabled (line 209) | @Override
method isRefreshing (line 215) | @Override
method isScrollingWhileRefreshingEnabled (line 220) | @Override
method onInterceptTouchEvent (line 225) | @Override
method onRefreshComplete (line 302) | @Override
method onTouchEvent (line 309) | @Override
method setScrollingWhileRefreshingEnabled (line 375) | public final void setScrollingWhileRefreshingEnabled(boolean allowScro...
method setDisableScrollingWhileRefreshing (line 382) | public void setDisableScrollingWhileRefreshing(boolean disableScrollin...
method setFilterTouchEvents (line 386) | @Override
method setLastUpdatedLabel (line 395) | public void setLastUpdatedLabel(CharSequence label) {
method setLoadingDrawable (line 403) | public void setLoadingDrawable(Drawable drawable) {
method setLoadingDrawable (line 411) | public void setLoadingDrawable(Drawable drawable, Mode mode) {
method setLongClickable (line 416) | @Override
method setMode (line 421) | @Override
method setOnPullEventListener (line 432) | public void setOnPullEventListener(OnPullEventListener<T> listener) {
method setOnRefreshListener (line 436) | @Override
method setOnRefreshListener (line 442) | @Override
method setPullLabel (line 452) | public void setPullLabel(CharSequence pullLabel) {
method setPullLabel (line 460) | public void setPullLabel(CharSequence pullLabel, Mode mode) {
method setPullToRefreshEnabled (line 469) | public final void setPullToRefreshEnabled(boolean enable) {
method setPullToRefreshOverScrollEnabled (line 473) | @Override
method setRefreshing (line 478) | @Override
method setRefreshing (line 483) | @Override
method setRefreshingLabel (line 494) | public void setRefreshingLabel(CharSequence refreshingLabel) {
method setRefreshingLabel (line 502) | public void setRefreshingLabel(CharSequence refreshingLabel, Mode mode) {
method setReleaseLabel (line 511) | public void setReleaseLabel(CharSequence releaseLabel) {
method setReleaseLabel (line 519) | public void setReleaseLabel(CharSequence releaseLabel, Mode mode) {
method setScrollAnimationInterpolator (line 524) | public void setScrollAnimationInterpolator(Interpolator interpolator) {
method setShowViewWhileRefreshing (line 528) | @Override
method getPullToRefreshScrollDirection (line 537) | public abstract Orientation getPullToRefreshScrollDirection();
method setState (line 539) | final void setState(State state, final boolean... params) {
method addViewInternal (line 574) | protected final void addViewInternal(View child, int index, ViewGroup....
method addViewInternal (line 582) | protected final void addViewInternal(View child, ViewGroup.LayoutParam...
method createLoadingLayout (line 586) | protected LoadingLayout createLoadingLayout(Context context, Mode mode...
method createLoadingLayoutProxy (line 597) | protected LoadingLayoutProxy createLoadingLayoutProxy(final boolean in...
method createRefreshableView (line 624) | protected abstract T createRefreshableView(Context context, AttributeS...
method disableLoadingLayoutVisibilityChanges (line 626) | protected final void disableLoadingLayoutVisibilityChanges() {
method getFooterLayout (line 630) | protected final LoadingLayout getFooterLayout() {
method getFooterSize (line 634) | protected final int getFooterSize() {
method getHeaderLayout (line 638) | protected final LoadingLayout getHeaderLayout() {
method getHeaderSize (line 642) | protected final int getHeaderSize() {
method getPullToRefreshScrollDuration (line 646) | protected int getPullToRefreshScrollDuration() {
method getPullToRefreshScrollDurationLonger (line 650) | protected int getPullToRefreshScrollDurationLonger() {
method getRefreshableViewWrapper (line 654) | protected FrameLayout getRefreshableViewWrapper() {
method handleStyledAttributes (line 664) | protected void handleStyledAttributes(TypedArray a) {
method isReadyForPullEnd (line 674) | protected abstract boolean isReadyForPullEnd();
method isReadyForPullStart (line 683) | protected abstract boolean isReadyForPullStart();
method onPtrRestoreInstanceState (line 691) | protected void onPtrRestoreInstanceState(Bundle savedInstanceState) {
method onPtrSaveInstanceState (line 700) | protected void onPtrSaveInstanceState(Bundle saveState) {
method onPullToRefresh (line 707) | protected void onPullToRefresh() {
method onRefreshing (line 727) | protected void onRefreshing(final boolean doScroll) {
method onReleaseToRefresh (line 769) | protected void onReleaseToRefresh() {
method onReset (line 787) | protected void onReset() {
method onRestoreInstanceState (line 798) | @Override
method onSaveInstanceState (line 825) | @Override
method onSizeChanged (line 843) | @Override
method refreshLoadingViewsSize (line 873) | protected final void refreshLoadingViewsSize() {
method refreshRefreshableViewSize (line 921) | protected final void refreshRefreshableViewSize(int width, int height) {
method setHeaderScroll (line 948) | protected final void setHeaderScroll(int value) {
method smoothScrollTo (line 994) | protected final void smoothScrollTo(int scrollValue) {
method smoothScrollTo (line 1005) | protected final void smoothScrollTo(int scrollValue, OnSmoothScrollFin...
method smoothScrollToLonger (line 1015) | protected final void smoothScrollToLonger(int scrollValue) {
method updateUIForMode (line 1023) | protected void updateUIForMode() {
method addRefreshableView (line 1052) | private void addRefreshableView(Context context, T refreshableView) {
method callRefreshListener (line 1061) | private void callRefreshListener() {
method init (line 1073) | @SuppressWarnings("deprecation")
method isReadyForPull (line 1145) | private boolean isReadyForPull() {
method pullEvent (line 1164) | private void pullEvent() {
method getLoadingLayoutLayoutParams (line 1215) | private LinearLayout.LayoutParams getLoadingLayoutLayoutParams() {
method getMaximumPullScroll (line 1227) | private int getMaximumPullScroll() {
method smoothScrollTo (line 1243) | private final void smoothScrollTo(int scrollValue, long duration) {
method smoothScrollTo (line 1247) | private final void smoothScrollTo(int newScrollValue, long duration, l...
method smoothScrollToAndBack (line 1279) | private final void smoothScrollToAndBack(int y) {
type AnimationStyle (line 1289) | public static enum AnimationStyle {
method getDefault (line 1302) | static AnimationStyle getDefault() {
method mapIntToValue (line 1314) | static AnimationStyle mapIntToValue(int modeInt) {
method createLoadingLayout (line 1324) | LoadingLayout createLoadingLayout(Context context, Mode mode, Orient...
type Mode (line 1335) | public static enum Mode {
method mapIntToValue (line 1386) | static Mode mapIntToValue(final int modeInt) {
method getDefault (line 1397) | static Mode getDefault() {
method Mode (line 1404) | Mode(int modeInt) {
method permitsPullToRefresh (line 1411) | boolean permitsPullToRefresh() {
method showHeaderLoadingLayout (line 1418) | public boolean showHeaderLoadingLayout() {
method showFooterLoadingLayout (line 1425) | public boolean showFooterLoadingLayout() {
method getIntValue (line 1429) | int getIntValue() {
type OnLastItemVisibleListener (line 1446) | public static interface OnLastItemVisibleListener {
method onLastItemVisible (line 1451) | public void onLastItemVisible();
type OnPullEventListener (line 1463) | public static interface OnPullEventListener<V extends View> {
method onPullEvent (line 1477) | public void onPullEvent(final PullToRefreshBase<V> refreshView, Stat...
type OnRefreshListener (line 1486) | public static interface OnRefreshListener<V extends View> {
method onRefresh (line 1492) | public void onRefresh(final PullToRefreshBase<V> refreshView);
type OnRefreshListener2 (line 1503) | public static interface OnRefreshListener2<V extends View> {
method onPullDownToRefresh (line 1510) | public void onPullDownToRefresh(final PullToRefreshBase<V> refreshVi...
method onPullUpToRefresh (line 1516) | public void onPullUpToRefresh(final PullToRefreshBase<V> refreshView);
type Orientation (line 1520) | public static enum Orientation {
type State (line 1524) | public static enum State {
method mapIntToValue (line 1567) | static State mapIntToValue(final int stateInt) {
method State (line 1580) | State(int intValue) {
method getIntValue (line 1584) | int getIntValue() {
class SmoothScrollRunnable (line 1589) | final class SmoothScrollRunnable implements Runnable {
method SmoothScrollRunnable (line 1600) | public SmoothScrollRunnable(int fromY, int toY, long duration, OnSmo...
method run (line 1608) | @Override
method stop (line 1643) | public void stop() {
type OnSmoothScrollFinishedListener (line 1649) | static interface OnSmoothScrollFinishedListener {
method onSmoothScrollFinished (line 1650) | void onSmoothScrollFinished();
FILE: library/src/com/handmark/pulltorefresh/library/PullToRefreshExpandableListView.java
class PullToRefreshExpandableListView (line 28) | public class PullToRefreshExpandableListView extends PullToRefreshAdapte...
method PullToRefreshExpandableListView (line 30) | public PullToRefreshExpandableListView(Context context) {
method PullToRefreshExpandableListView (line 34) | public PullToRefreshExpandableListView(Context context, AttributeSet a...
method PullToRefreshExpandableListView (line 38) | public PullToRefreshExpandableListView(Context context, Mode mode) {
method PullToRefreshExpandableListView (line 42) | public PullToRefreshExpandableListView(Context context, Mode mode, Ani...
method getPullToRefreshScrollDirection (line 46) | @Override
method createRefreshableView (line 51) | @Override
class InternalExpandableListView (line 65) | class InternalExpandableListView extends ExpandableListView implements...
method InternalExpandableListView (line 67) | public InternalExpandableListView(Context context, AttributeSet attr...
method setEmptyView (line 71) | @Override
method setEmptyViewInternal (line 76) | @Override
class InternalExpandableListViewSDK9 (line 82) | @TargetApi(9)
method InternalExpandableListViewSDK9 (line 85) | public InternalExpandableListViewSDK9(Context context, AttributeSet ...
method overScrollBy (line 89) | @Override
FILE: library/src/com/handmark/pulltorefresh/library/PullToRefreshGridView.java
class PullToRefreshGridView (line 28) | public class PullToRefreshGridView extends PullToRefreshAdapterViewBase<...
method PullToRefreshGridView (line 30) | public PullToRefreshGridView(Context context) {
method PullToRefreshGridView (line 34) | public PullToRefreshGridView(Context context, AttributeSet attrs) {
method PullToRefreshGridView (line 38) | public PullToRefreshGridView(Context context, Mode mode) {
method PullToRefreshGridView (line 42) | public PullToRefreshGridView(Context context, Mode mode, AnimationStyl...
method getPullToRefreshScrollDirection (line 46) | @Override
method createRefreshableView (line 51) | @Override
class InternalGridView (line 65) | class InternalGridView extends GridView implements EmptyViewMethodAcce...
method InternalGridView (line 67) | public InternalGridView(Context context, AttributeSet attrs) {
method setEmptyView (line 71) | @Override
method setEmptyViewInternal (line 76) | @Override
class InternalGridViewSDK9 (line 82) | @TargetApi(9)
method InternalGridViewSDK9 (line 85) | public InternalGridViewSDK9(Context context, AttributeSet attrs) {
method overScrollBy (line 89) | @Override
FILE: library/src/com/handmark/pulltorefresh/library/PullToRefreshHorizontalScrollView.java
class PullToRefreshHorizontalScrollView (line 26) | public class PullToRefreshHorizontalScrollView extends PullToRefreshBase...
method PullToRefreshHorizontalScrollView (line 28) | public PullToRefreshHorizontalScrollView(Context context) {
method PullToRefreshHorizontalScrollView (line 32) | public PullToRefreshHorizontalScrollView(Context context, AttributeSet...
method PullToRefreshHorizontalScrollView (line 36) | public PullToRefreshHorizontalScrollView(Context context, Mode mode) {
method PullToRefreshHorizontalScrollView (line 40) | public PullToRefreshHorizontalScrollView(Context context, Mode mode, A...
method getPullToRefreshScrollDirection (line 44) | @Override
method createRefreshableView (line 49) | @Override
method isReadyForPullStart (line 63) | @Override
method isReadyForPullEnd (line 68) | @Override
class InternalHorizontalScrollViewSDK9 (line 77) | @TargetApi(9)
method InternalHorizontalScrollViewSDK9 (line 80) | public InternalHorizontalScrollViewSDK9(Context context, AttributeSe...
method overScrollBy (line 84) | @Override
method getScrollRange (line 101) | private int getScrollRange() {
FILE: library/src/com/handmark/pulltorefresh/library/PullToRefreshListView.java
class PullToRefreshListView (line 35) | public class PullToRefreshListView extends PullToRefreshAdapterViewBase<...
method PullToRefreshListView (line 44) | public PullToRefreshListView(Context context) {
method PullToRefreshListView (line 48) | public PullToRefreshListView(Context context, AttributeSet attrs) {
method PullToRefreshListView (line 52) | public PullToRefreshListView(Context context, Mode mode) {
method PullToRefreshListView (line 56) | public PullToRefreshListView(Context context, Mode mode, AnimationStyl...
method getPullToRefreshScrollDirection (line 60) | @Override
method onRefreshing (line 65) | @Override
method onReset (line 129) | @Override
method createLoadingLayoutProxy (line 187) | @Override
method createListView (line 205) | protected ListView createListView(Context context, AttributeSet attrs) {
method createRefreshableView (line 215) | @Override
method handleStyledAttributes (line 224) | @Override
class InternalListViewSDK9 (line 256) | @TargetApi(9)
method InternalListViewSDK9 (line 259) | public InternalListViewSDK9(Context context, AttributeSet attrs) {
method overScrollBy (line 263) | @Override
class InternalListView (line 277) | protected class InternalListView extends ListView implements EmptyView...
method InternalListView (line 281) | public InternalListView(Context context, AttributeSet attrs) {
method dispatchDraw (line 285) | @Override
method dispatchTouchEvent (line 299) | @Override
method setAdapter (line 314) | @Override
method setEmptyView (line 325) | @Override
method setEmptyViewInternal (line 330) | @Override
FILE: library/src/com/handmark/pulltorefresh/library/PullToRefreshScrollView.java
class PullToRefreshScrollView (line 26) | public class PullToRefreshScrollView extends PullToRefreshBase<ScrollVie...
method PullToRefreshScrollView (line 28) | public PullToRefreshScrollView(Context context) {
method PullToRefreshScrollView (line 32) | public PullToRefreshScrollView(Context context, AttributeSet attrs) {
method PullToRefreshScrollView (line 36) | public PullToRefreshScrollView(Context context, Mode mode) {
method PullToRefreshScrollView (line 40) | public PullToRefreshScrollView(Context context, Mode mode, AnimationSt...
method getPullToRefreshScrollDirection (line 44) | @Override
method createRefreshableView (line 49) | @Override
method isReadyForPullStart (line 62) | @Override
method isReadyForPullEnd (line 67) | @Override
class InternalScrollViewSDK9 (line 76) | @TargetApi(9)
method InternalScrollViewSDK9 (line 79) | public InternalScrollViewSDK9(Context context, AttributeSet attrs) {
method overScrollBy (line 83) | @Override
method getScrollRange (line 100) | private int getScrollRange() {
FILE: library/src/com/handmark/pulltorefresh/library/PullToRefreshWebView.java
class PullToRefreshWebView (line 28) | public class PullToRefreshWebView extends PullToRefreshBase<WebView> {
method onRefresh (line 32) | @Override
method onProgressChanged (line 41) | @Override
method PullToRefreshWebView (line 50) | public PullToRefreshWebView(Context context) {
method PullToRefreshWebView (line 60) | public PullToRefreshWebView(Context context, AttributeSet attrs) {
method PullToRefreshWebView (line 70) | public PullToRefreshWebView(Context context, Mode mode) {
method PullToRefreshWebView (line 80) | public PullToRefreshWebView(Context context, Mode mode, AnimationStyle...
method getPullToRefreshScrollDirection (line 90) | @Override
method createRefreshableView (line 95) | @Override
method isReadyForPullStart (line 108) | @Override
method isReadyForPullEnd (line 113) | @Override
method onPtrRestoreInstanceState (line 119) | @Override
method onPtrSaveInstanceState (line 125) | @Override
class InternalWebViewSDK9 (line 131) | @TargetApi(9)
method InternalWebViewSDK9 (line 142) | public InternalWebViewSDK9(Context context, AttributeSet attrs) {
method overScrollBy (line 146) | @Override
method getScrollRange (line 160) | private int getScrollRange() {
FILE: library/src/com/handmark/pulltorefresh/library/extras/PullToRefreshWebView2.java
class PullToRefreshWebView2 (line 62) | public class PullToRefreshWebView2 extends PullToRefreshWebView {
method PullToRefreshWebView2 (line 68) | public PullToRefreshWebView2(Context context) {
method PullToRefreshWebView2 (line 72) | public PullToRefreshWebView2(Context context, AttributeSet attrs) {
method PullToRefreshWebView2 (line 76) | public PullToRefreshWebView2(Context context, Mode mode) {
method createRefreshableView (line 84) | @Override
method isReadyForPullStart (line 95) | @Override
method isReadyForPullEnd (line 106) | @Override
class JsValueCallback (line 122) | final class JsValueCallback {
method isReadyForPullUpResponse (line 124) | public void isReadyForPullUpResponse(boolean response) {
method isReadyForPullDownResponse (line 128) | public void isReadyForPullDownResponse(boolean response) {
FILE: library/src/com/handmark/pulltorefresh/library/extras/SoundPullEventListener.java
class SoundPullEventListener (line 28) | public class SoundPullEventListener<V extends View> implements PullToRef...
method SoundPullEventListener (line 40) | public SoundPullEventListener(Context context) {
method onPullEvent (line 45) | @Override
method addSoundEvent (line 65) | public void addSoundEvent(State event, int resId) {
method clearSounds (line 72) | public void clearSounds() {
method getCurrentMediaPlayer (line 79) | public MediaPlayer getCurrentMediaPlayer() {
method playSound (line 83) | private void playSound(int resId) {
FILE: library/src/com/handmark/pulltorefresh/library/internal/EmptyViewMethodAccessor.java
type EmptyViewMethodAccessor (line 26) | public interface EmptyViewMethodAccessor {
method setEmptyViewInternal (line 33) | public void setEmptyViewInternal(View emptyView);
method setEmptyView (line 41) | public void setEmptyView(View emptyView);
FILE: library/src/com/handmark/pulltorefresh/library/internal/FlipLoadingLayout.java
class FlipLoadingLayout (line 33) | @SuppressLint("ViewConstructor")
method FlipLoadingLayout (line 40) | public FlipLoadingLayout(Context context, final Mode mode, final Orien...
method onLoadingDrawableSet (line 58) | @Override
method onPullImpl (line 85) | @Override
method pullToRefreshImpl (line 90) | @Override
method refreshingImpl (line 98) | @Override
method releaseToRefreshImpl (line 105) | @Override
method resetImpl (line 110) | @Override
method getDefaultDrawableResId (line 117) | @Override
method getDrawableRotationAngle (line 122) | private float getDrawableRotationAngle() {
FILE: library/src/com/handmark/pulltorefresh/library/internal/IndicatorLayout.java
class IndicatorLayout (line 36) | @SuppressLint("ViewConstructor")
method IndicatorLayout (line 46) | public IndicatorLayout(Context context, PullToRefreshBase.Mode mode) {
method isVisible (line 99) | public final boolean isVisible() {
method hide (line 108) | public void hide() {
method show (line 112) | public void show() {
method onAnimationEnd (line 117) | @Override
method onAnimationRepeat (line 129) | @Override
method onAnimationStart (line 134) | @Override
method releaseToRefresh (line 139) | public void releaseToRefresh() {
method pullToRefresh (line 143) | public void pullToRefresh() {
FILE: library/src/com/handmark/pulltorefresh/library/internal/LoadingLayout.java
class LoadingLayout (line 43) | @SuppressLint("ViewConstructor")
method LoadingLayout (line 67) | public LoadingLayout(Context context, final Mode mode, final Orientati...
method setHeight (line 183) | public final void setHeight(int height) {
method setWidth (line 189) | public final void setWidth(int width) {
method getContentSize (line 195) | public final int getContentSize() {
method hideAllViews (line 205) | public final void hideAllViews() {
method onPull (line 220) | public final void onPull(float scaleOfLayout) {
method pullToRefresh (line 226) | public final void pullToRefresh() {
method refreshing (line 235) | public final void refreshing() {
method releaseToRefresh (line 252) | public final void releaseToRefresh() {
method reset (line 261) | public final void reset() {
method setLastUpdatedLabel (line 283) | @Override
method setLoadingDrawable (line 288) | public final void setLoadingDrawable(Drawable imageDrawable) {
method setPullLabel (line 297) | public void setPullLabel(CharSequence pullLabel) {
method setRefreshingLabel (line 301) | public void setRefreshingLabel(CharSequence refreshingLabel) {
method setReleaseLabel (line 305) | public void setReleaseLabel(CharSequence releaseLabel) {
method setTextTypeface (line 309) | @Override
method showInvisibleViews (line 314) | public final void showInvisibleViews() {
method getDefaultDrawableResId (line 333) | protected abstract int getDefaultDrawableResId();
method onLoadingDrawableSet (line 335) | protected abstract void onLoadingDrawableSet(Drawable imageDrawable);
method onPullImpl (line 337) | protected abstract void onPullImpl(float scaleOfLayout);
method pullToRefreshImpl (line 339) | protected abstract void pullToRefreshImpl();
method refreshingImpl (line 341) | protected abstract void refreshingImpl();
method releaseToRefreshImpl (line 343) | protected abstract void releaseToRefreshImpl();
method resetImpl (line 345) | protected abstract void resetImpl();
method setSubHeaderText (line 347) | private void setSubHeaderText(CharSequence label) {
method setSubTextAppearance (line 363) | private void setSubTextAppearance(int value) {
method setSubTextColor (line 369) | private void setSubTextColor(ColorStateList color) {
method setTextAppearance (line 375) | private void setTextAppearance(int value) {
method setTextColor (line 384) | private void setTextColor(ColorStateList color) {
FILE: library/src/com/handmark/pulltorefresh/library/internal/RotateLoadingLayout.java
class RotateLoadingLayout (line 30) | public class RotateLoadingLayout extends LoadingLayout {
method RotateLoadingLayout (line 41) | public RotateLoadingLayout(Context context, Mode mode, Orientation scr...
method onLoadingDrawableSet (line 58) | public void onLoadingDrawableSet(Drawable imageDrawable) {
method onPullImpl (line 65) | protected void onPullImpl(float scaleOfLayout) {
method refreshingImpl (line 77) | @Override
method resetImpl (line 82) | @Override
method resetImageRotation (line 88) | private void resetImageRotation() {
method pullToRefreshImpl (line 95) | @Override
method releaseToRefreshImpl (line 100) | @Override
method getDefaultDrawableResId (line 105) | @Override
FILE: library/src/com/handmark/pulltorefresh/library/internal/Utils.java
class Utils (line 5) | public class Utils {
method warnDeprecation (line 9) | public static void warnDeprecation(String depreacted, String replaceme...
FILE: library/src/com/handmark/pulltorefresh/library/internal/ViewCompat.java
class ViewCompat (line 24) | @SuppressWarnings("deprecation")
method postOnAnimation (line 27) | public static void postOnAnimation(View view, Runnable runnable) {
method setBackground (line 35) | public static void setBackground(View view, Drawable background) {
method setLayerType (line 43) | public static void setLayerType(View view, int layerType) {
class SDK11 (line 49) | @TargetApi(11)
method setLayerType (line 52) | public static void setLayerType(View view, int layerType) {
class SDK16 (line 57) | @TargetApi(16)
method postOnAnimation (line 60) | public static void postOnAnimation(View view, Runnable runnable) {
method setBackground (line 64) | public static void setBackground(View view, Drawable background) {
FILE: sample/src/com/handmark/pulltorefresh/samples/LauncherActivity.java
class LauncherActivity (line 25) | public class LauncherActivity extends ListActivity {
method onCreate (line 30) | @Override
method onListItemClick (line 36) | @Override
FILE: sample/src/com/handmark/pulltorefresh/samples/PullToRefreshExpandableListActivity.java
class PullToRefreshExpandableListActivity (line 33) | public final class PullToRefreshExpandableListActivity extends Expandabl...
method onCreate (line 43) | @Override
class GetDataTask (line 79) | private class GetDataTask extends AsyncTask<Void, Void, String[]> {
method doInBackground (line 81) | @Override
method onPostExecute (line 91) | @Override
FILE: sample/src/com/handmark/pulltorefresh/samples/PullToRefreshGridActivity.java
class PullToRefreshGridActivity (line 37) | public final class PullToRefreshGridActivity extends Activity {
method onCreate (line 47) | @Override
class GetDataTask (line 83) | private class GetDataTask extends AsyncTask<Void, Void, String[]> {
method doInBackground (line 85) | @Override
method onPostExecute (line 95) | @Override
method onCreateOptionsMenu (line 108) | @Override
method onPrepareOptionsMenu (line 116) | @Override
method onOptionsItemSelected (line 125) | @Override
FILE: sample/src/com/handmark/pulltorefresh/samples/PullToRefreshHorizontalScrollViewActivity.java
class PullToRefreshHorizontalScrollViewActivity (line 27) | public final class PullToRefreshHorizontalScrollViewActivity extends Act...
method onCreate (line 33) | @Override
class GetDataTask (line 50) | private class GetDataTask extends AsyncTask<Void, Void, String[]> {
method doInBackground (line 52) | @Override
method onPostExecute (line 62) | @Override
FILE: sample/src/com/handmark/pulltorefresh/samples/PullToRefreshListActivity.java
class PullToRefreshListActivity (line 43) | public final class PullToRefreshListActivity extends ListActivity {
method onCreate (line 55) | @Override
class GetDataTask (line 110) | private class GetDataTask extends AsyncTask<Void, Void, String[]> {
method doInBackground (line 112) | @Override
method onPostExecute (line 122) | @Override
method onCreateOptionsMenu (line 134) | @Override
method onCreateContextMenu (line 146) | @Override
method onPrepareOptionsMenu (line 159) | @Override
method onOptionsItemSelected (line 173) | @Override
FILE: sample/src/com/handmark/pulltorefresh/samples/PullToRefreshListFragmentActivity.java
class PullToRefreshListFragmentActivity (line 32) | public final class PullToRefreshListFragmentActivity extends FragmentAct...
method onCreate (line 41) | @Override
method onRefresh (line 69) | @Override
class GetDataTask (line 75) | private class GetDataTask extends AsyncTask<Void, Void, String[]> {
method doInBackground (line 77) | @Override
method onPostExecute (line 87) | @Override
FILE: sample/src/com/handmark/pulltorefresh/samples/PullToRefreshListInViewPagerActivity.java
class PullToRefreshListInViewPagerActivity (line 23) | public class PullToRefreshListInViewPagerActivity extends Activity imple...
method onCreate (line 33) | @Override
class ListViewPagerAdapter (line 42) | private class ListViewPagerAdapter extends PagerAdapter {
method instantiateItem (line 44) | @Override
method destroyItem (line 63) | @Override
method isViewFromObject (line 68) | @Override
method getCount (line 73) | @Override
method onRefresh (line 80) | @Override
class GetDataTask (line 85) | private static class GetDataTask extends AsyncTask<Void, Void, Void> {
method GetDataTask (line 89) | public GetDataTask(PullToRefreshBase<?> refreshedView) {
method doInBackground (line 93) | @Override
method onPostExecute (line 103) | @Override
FILE: sample/src/com/handmark/pulltorefresh/samples/PullToRefreshScrollViewActivity.java
class PullToRefreshScrollViewActivity (line 27) | public final class PullToRefreshScrollViewActivity extends Activity {
method onCreate (line 33) | @Override
class GetDataTask (line 50) | private class GetDataTask extends AsyncTask<Void, Void, String[]> {
method doInBackground (line 52) | @Override
method onPostExecute (line 62) | @Override
FILE: sample/src/com/handmark/pulltorefresh/samples/PullToRefreshViewPagerActivity.java
class PullToRefreshViewPagerActivity (line 32) | public class PullToRefreshViewPagerActivity extends Activity implements ...
method onCreate (line 36) | @Override
method onRefresh (line 48) | @Override
class SamplePagerAdapter (line 53) | static class SamplePagerAdapter extends PagerAdapter {
method getCount (line 58) | @Override
method instantiateItem (line 63) | @Override
method destroyItem (line 74) | @Override
method isViewFromObject (line 79) | @Override
class GetDataTask (line 85) | private class GetDataTask extends AsyncTask<Void, Void, Void> {
method doInBackground (line 87) | @Override
method onPostExecute (line 97) | @Override
FILE: sample/src/com/handmark/pulltorefresh/samples/PullToRefreshWebView2Activity.java
class PullToRefreshWebView2Activity (line 27) | public final class PullToRefreshWebView2Activity extends Activity implem...
method onCreate (line 30) | @Override
class SampleWebViewClient (line 47) | private static class SampleWebViewClient extends WebViewClient {
method shouldOverrideUrlLoading (line 48) | @Override
method onRefresh (line 55) | @Override
FILE: sample/src/com/handmark/pulltorefresh/samples/PullToRefreshWebViewActivity.java
class PullToRefreshWebViewActivity (line 25) | public final class PullToRefreshWebViewActivity extends Activity {
method onCreate (line 31) | @Override
class SampleWebViewClient (line 45) | private static class SampleWebViewClient extends WebViewClient {
method shouldOverrideUrlLoading (line 46) | @Override
Condensed preview — 108 files, each showing path, character count, and a content snippet. Download the .json file or copy for the full structured content (324K chars).
[
{
"path": ".gitignore",
"chars": 217,
"preview": "#Android generated\nbin\ngen\n\n#Eclipse\n.project\n.classpath\n.settings\n\n#IntelliJ IDEA\n.idea\n*.iml\n*.ipr\n*.iws\nout\n\n#Maven\nt"
},
{
"path": "LICENSE",
"chars": 11358,
"preview": "\n Apache License\n Version 2.0, January 2004\n "
},
{
"path": "README.md",
"chars": 3854,
"preview": "# PLEASE NOTE, THIS PROJECT IS NO LONGER BEING MAINTAINED\n\n* * *\n\n# Pull To Refresh Views for Android\n\n 2009 The Android Open Source Project\n\n Licensed under"
},
{
"path": "library/res/anim/slide_in_from_top.xml",
"chars": 866,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<!--\n Copyright (C) 2009 The Android Open Source Project\n\n Licensed under"
},
{
"path": "library/res/anim/slide_out_to_bottom.xml",
"chars": 865,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<!--\n Copyright (C) 2009 The Android Open Source Project\n\n Licensed under"
},
{
"path": "library/res/anim/slide_out_to_top.xml",
"chars": 866,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<!--\n Copyright (C) 2009 The Android Open Source Project\n\n Licensed under"
},
{
"path": "library/res/drawable/indicator_bg_bottom.xml",
"chars": 595,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<shape xmlns:android=\"http://schemas.android.com/apk/res/android\"\n android:sha"
},
{
"path": "library/res/drawable/indicator_bg_top.xml",
"chars": 595,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<shape xmlns:android=\"http://schemas.android.com/apk/res/android\"\n android:sha"
},
{
"path": "library/res/layout/pull_to_refresh_header_horizontal.xml",
"chars": 1132,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<merge xmlns:android=\"http://schemas.android.com/apk/res/android\" >\n\n <FrameLa"
},
{
"path": "library/res/layout/pull_to_refresh_header_vertical.xml",
"chars": 2355,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<merge xmlns:android=\"http://schemas.android.com/apk/res/android\" >\n\n <FrameLa"
},
{
"path": "library/res/values/attrs.xml",
"chars": 3609,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<resources>\n\n <declare-styleable name=\"PullToRefresh\">\n\n <!-- A drawabl"
},
{
"path": "library/res/values/dimens.xml",
"chars": 360,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<resources>\n\n <dimen name=\"indicator_right_padding\">10dp</dimen>\n <dimen na"
},
{
"path": "library/res/values/ids.xml",
"chars": 183,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<resources>\n\n <item type=\"id\" name=\"gridview\" />\n <item type=\"id\" name=\"web"
},
{
"path": "library/res/values/pull_refresh_strings.xml",
"chars": 723,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<resources>\n\n <string name=\"pull_to_refresh_pull_label\">Pull to refresh…</stri"
},
{
"path": "library/res/values-ar/pull_refresh_strings.xml",
"chars": 273,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\r\n<resources>\r\n <string name=\"pull_to_refresh_pull_label\">اسحب للتحديث…</string>\r"
},
{
"path": "library/res/values-cs/pull_refresh_strings.xml",
"chars": 296,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\r\n<resources>\r\n <string name=\"pull_to_refresh_pull_label\">Tažením aktualizujete…<"
},
{
"path": "library/res/values-de/pull_refresh_strings.xml",
"chars": 300,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\r\n<resources>\r\n <string name=\"pull_to_refresh_pull_label\">Ziehen zum Aktualisiere"
},
{
"path": "library/res/values-es/pull_refresh_strings.xml",
"chars": 295,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\r\n<resources>\r\n <string name=\"pull_to_refresh_pull_label\">Tirar para actualizar…<"
},
{
"path": "library/res/values-fi/pull_refresh_strings.xml",
"chars": 726,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<resources>\n\n <string name=\"pull_to_refresh_pull_label\">Päivitä vetämällä alas"
},
{
"path": "library/res/values-fr/pull_refresh_strings.xml",
"chars": 299,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\r\n<resources>\r\n <string name=\"pull_to_refresh_pull_label\">Tirez pour rafraîchir…<"
},
{
"path": "library/res/values-he/pull_refresh_strings.xml",
"chars": 270,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\r\n<resources>\r\n <string name=\"pull_to_refresh_pull_label\">משוך לרענון…</string>\r\n"
},
{
"path": "library/res/values-it/pull_refresh_strings.xml",
"chars": 296,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\r\n<resources>\r\n <string name=\"pull_to_refresh_pull_label\">Tira per aggiornare…</s"
},
{
"path": "library/res/values-iw/pull_refresh_strings.xml",
"chars": 270,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\r\n<resources>\r\n <string name=\"pull_to_refresh_pull_label\">משוך לרענון…</string>\r\n"
},
{
"path": "library/res/values-ja/pull_refresh_strings.xml",
"chars": 264,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\r\n<resources>\r\n <string name=\"pull_to_refresh_pull_label\">画面を引っ張って…</string>\r\n <"
},
{
"path": "library/res/values-ko/pull_refresh_strings.xml",
"chars": 266,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\r\n<resources>\r\n <string name=\"pull_to_refresh_pull_label\">당겨서 새로 고침…</string>\r\n "
},
{
"path": "library/res/values-nl/pull_refresh_strings.xml",
"chars": 296,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\r\n<resources>\r\n <string name=\"pull_to_refresh_pull_label\">Sleep om te vernieuwen…"
},
{
"path": "library/res/values-pl/pull_refresh_strings.xml",
"chars": 298,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\r\n<resources>\r\n <string name=\"pull_to_refresh_pull_label\">Pociągnij, aby odświeży"
},
{
"path": "library/res/values-pt/pull_refresh_strings.xml",
"chars": 297,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\r\n<resources>\r\n <string name=\"pull_to_refresh_pull_label\">Puxe para atualizar…</s"
},
{
"path": "library/res/values-pt-rBR/pull_refresh_strings.xml",
"chars": 294,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\r\n<resources>\r\n <string name=\"pull_to_refresh_pull_label\">Puxe para atualizar…</s"
},
{
"path": "library/res/values-ro/pull_refresh_strings.xml",
"chars": 312,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\r\n<resources>\r\n <string name=\"pull_to_refresh_pull_label\">Trage pentru a reîmpros"
},
{
"path": "library/res/values-ru/pull_refresh_strings.xml",
"chars": 299,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\r\n<resources>\r\n <string name=\"pull_to_refresh_pull_label\">Потяните для обновления"
},
{
"path": "library/res/values-zh/pull_refresh_strings.xml",
"chars": 257,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\r\n<resources>\r\n <string name=\"pull_to_refresh_pull_label\">下拉刷新…</string>\r\n <stri"
},
{
"path": "library/src/com/handmark/pulltorefresh/library/ILoadingLayout.java",
"chars": 1599,
"preview": "package com.handmark.pulltorefresh.library;\n\nimport android.graphics.Typeface;\nimport android.graphics.drawable.Drawable"
},
{
"path": "library/src/com/handmark/pulltorefresh/library/IPullToRefresh.java",
"chars": 8254,
"preview": "/*******************************************************************************\n * Copyright 2011, 2012 Chris Banes.\n *"
},
{
"path": "library/src/com/handmark/pulltorefresh/library/LoadingLayoutProxy.java",
"chars": 1811,
"preview": "package com.handmark.pulltorefresh.library;\n\nimport java.util.HashSet;\n\nimport android.graphics.Typeface;\nimport android"
},
{
"path": "library/src/com/handmark/pulltorefresh/library/OverscrollHelper.java",
"chars": 7903,
"preview": "/*******************************************************************************\n * Copyright 2011, 2012 Chris Banes.\n *"
},
{
"path": "library/src/com/handmark/pulltorefresh/library/PullToRefreshAdapterViewBase.java",
"chars": 14824,
"preview": "/*******************************************************************************\n * Copyright 2011, 2012 Chris Banes.\n *"
},
{
"path": "library/src/com/handmark/pulltorefresh/library/PullToRefreshBase.java",
"chars": 46418,
"preview": "/*******************************************************************************\n * Copyright 2011, 2012 Chris Banes.\n *"
},
{
"path": "library/src/com/handmark/pulltorefresh/library/PullToRefreshExpandableListView.java",
"chars": 3385,
"preview": "/*******************************************************************************\n * Copyright 2011, 2012 Chris Banes.\n *"
},
{
"path": "library/src/com/handmark/pulltorefresh/library/PullToRefreshGridView.java",
"chars": 3173,
"preview": "/*******************************************************************************\n * Copyright 2011, 2012 Chris Banes.\n *"
},
{
"path": "library/src/com/handmark/pulltorefresh/library/PullToRefreshHorizontalScrollView.java",
"chars": 3523,
"preview": "/*******************************************************************************\n * Copyright 2011, 2012 Chris Banes.\n *"
},
{
"path": "library/src/com/handmark/pulltorefresh/library/PullToRefreshListView.java",
"chars": 10466,
"preview": "/*******************************************************************************\n * Copyright 2011, 2012 Chris Banes.\n *"
},
{
"path": "library/src/com/handmark/pulltorefresh/library/PullToRefreshScrollView.java",
"chars": 3374,
"preview": "/*******************************************************************************\n * Copyright 2011, 2012 Chris Banes.\n *"
},
{
"path": "library/src/com/handmark/pulltorefresh/library/PullToRefreshWebView.java",
"chars": 5226,
"preview": "/*******************************************************************************\n * Copyright 2011, 2012 Chris Banes.\n *"
},
{
"path": "library/src/com/handmark/pulltorefresh/library/extras/PullToRefreshWebView2.java",
"chars": 4294,
"preview": "/*******************************************************************************\n * Copyright 2011, 2012 Chris Banes.\n *"
},
{
"path": "library/src/com/handmark/pulltorefresh/library/extras/SoundPullEventListener.java",
"chars": 2955,
"preview": "/*******************************************************************************\n * Copyright 2011, 2012 Chris Banes.\n *"
},
{
"path": "library/src/com/handmark/pulltorefresh/library/internal/EmptyViewMethodAccessor.java",
"chars": 1383,
"preview": "/*******************************************************************************\n * Copyright 2011, 2012 Chris Banes.\n *"
},
{
"path": "library/src/com/handmark/pulltorefresh/library/internal/FlipLoadingLayout.java",
"chars": 4632,
"preview": "/*******************************************************************************\n * Copyright 2011, 2012 Chris Banes.\n *"
},
{
"path": "library/src/com/handmark/pulltorefresh/library/internal/IndicatorLayout.java",
"chars": 4780,
"preview": "/*******************************************************************************\n * Copyright 2011, 2012 Chris Banes.\n *"
},
{
"path": "library/src/com/handmark/pulltorefresh/library/internal/LoadingLayout.java",
"chars": 12030,
"preview": "/*******************************************************************************\n * Copyright 2011, 2012 Chris Banes.\n *"
},
{
"path": "library/src/com/handmark/pulltorefresh/library/internal/RotateLoadingLayout.java",
"chars": 3522,
"preview": "/*******************************************************************************\n * Copyright 2011, 2012 Chris Banes.\n *"
},
{
"path": "library/src/com/handmark/pulltorefresh/library/internal/Utils.java",
"chars": 345,
"preview": "package com.handmark.pulltorefresh.library.internal;\n\nimport android.util.Log;\n\npublic class Utils {\n\n\tstatic final Stri"
},
{
"path": "library/src/com/handmark/pulltorefresh/library/internal/ViewCompat.java",
"chars": 2061,
"preview": "/*******************************************************************************\n * Copyright 2011, 2012 Chris Banes.\n *"
},
{
"path": "pom.xml",
"chars": 4304,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<project xmlns=\"http://maven.apache.org/POM/4.0.0\" xmlns:xsi=\"http://www.w3.org/2"
},
{
"path": "sample/AndroidManifest.xml",
"chars": 2443,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<manifest xmlns:android=\"http://schemas.android.com/apk/res/android\"\n package="
},
{
"path": "sample/LICENSE",
"chars": 11358,
"preview": "\n Apache License\n Version 2.0, January 2004\n "
},
{
"path": "sample/assets/ptr_webview2_sample.html",
"chars": 3344,
"preview": "<html>\n<head>\n<title>PullToRefreshWebView2 Sample</title>\n\n<script language=\"javascript\" type=\"text/javascript\">\n functi"
},
{
"path": "sample/pom.xml",
"chars": 1855,
"preview": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<project xmlns=\"http://maven.apache.org/POM/4.0.0\" xmlns:xsi=\"http://www.w3.org/2"
},
{
"path": "sample/project.properties",
"chars": 525,
"preview": "# This file is automatically generated by Android Tools.\n# Do not modify this file -- YOUR CHANGES WILL BE ERASED!\n#\n# T"
},
{
"path": "sample/res/layout/activity_ptr_expandable_list.xml",
"chars": 773,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<LinearLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n andr"
},
{
"path": "sample/res/layout/activity_ptr_grid.xml",
"chars": 869,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<LinearLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n andr"
},
{
"path": "sample/res/layout/activity_ptr_horizontalscrollview.xml",
"chars": 2557,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<LinearLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n andr"
},
{
"path": "sample/res/layout/activity_ptr_list.xml",
"chars": 840,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<LinearLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n andr"
},
{
"path": "sample/res/layout/activity_ptr_list_fragment.xml",
"chars": 452,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<FrameLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n andro"
},
{
"path": "sample/res/layout/activity_ptr_list_in_vp.xml",
"chars": 485,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<LinearLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n andr"
},
{
"path": "sample/res/layout/activity_ptr_scrollview.xml",
"chars": 966,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<LinearLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n andr"
},
{
"path": "sample/res/layout/activity_ptr_viewpager.xml",
"chars": 698,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<FrameLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n andro"
},
{
"path": "sample/res/layout/activity_ptr_webview.xml",
"chars": 605,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<LinearLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n andr"
},
{
"path": "sample/res/layout/activity_ptr_webview2.xml",
"chars": 614,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<LinearLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n andr"
},
{
"path": "sample/res/layout/layout_listview_in_viewpager.xml",
"chars": 351,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<com.handmark.pulltorefresh.library.PullToRefreshListView xmlns:android=\"http://s"
},
{
"path": "sample/res/values/strings.xml",
"chars": 3086,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<resources>\n\n <string name=\"hello\">Hello World, PullToRefreshActivity!</string"
},
{
"path": "sample/res/values/styles.xml",
"chars": 473,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<resources xmlns:android=\"http://schemas.android.com/apk/res/android\">\n\n <styl"
},
{
"path": "sample/src/com/handmark/pulltorefresh/samples/LauncherActivity.java",
"chars": 2563,
"preview": "/*******************************************************************************\n * Copyright 2011, 2012 Chris Banes.\n *"
},
{
"path": "sample/src/com/handmark/pulltorefresh/samples/PullToRefreshExpandableListActivity.java",
"chars": 4301,
"preview": "/*******************************************************************************\n * Copyright 2011, 2012 Chris Banes.\n *"
},
{
"path": "sample/src/com/handmark/pulltorefresh/samples/PullToRefreshGridActivity.java",
"chars": 4697,
"preview": "/*******************************************************************************\n * Copyright 2011, 2012 Chris Banes.\n *"
},
{
"path": "sample/src/com/handmark/pulltorefresh/samples/PullToRefreshHorizontalScrollViewActivity.java",
"chars": 2459,
"preview": "/*******************************************************************************\n * Copyright 2011, 2012 Chris Banes.\n *"
},
{
"path": "sample/src/com/handmark/pulltorefresh/samples/PullToRefreshListActivity.java",
"chars": 7371,
"preview": "/*******************************************************************************\n * Copyright 2011, 2012 Chris Banes.\n *"
},
{
"path": "sample/src/com/handmark/pulltorefresh/samples/PullToRefreshListFragmentActivity.java",
"chars": 3894,
"preview": "/*******************************************************************************\n * Copyright 2011, 2012 Chris Banes.\n *"
},
{
"path": "sample/src/com/handmark/pulltorefresh/samples/PullToRefreshListInViewPagerActivity.java",
"chars": 3286,
"preview": "package com.handmark.pulltorefresh.samples;\n\nimport java.util.Arrays;\n\nimport android.app.Activity;\nimport android.conte"
},
{
"path": "sample/src/com/handmark/pulltorefresh/samples/PullToRefreshScrollViewActivity.java",
"chars": 2359,
"preview": "/*******************************************************************************\n * Copyright 2011, 2012 Chris Banes.\n *"
},
{
"path": "sample/src/com/handmark/pulltorefresh/samples/PullToRefreshViewPagerActivity.java",
"chars": 3332,
"preview": "/*******************************************************************************\n * Copyright 2011, 2012 Chris Banes.\n *"
},
{
"path": "sample/src/com/handmark/pulltorefresh/samples/PullToRefreshWebView2Activity.java",
"chars": 2494,
"preview": "/*******************************************************************************\n * Copyright 2011, 2012 Chris Banes.\n *"
},
{
"path": "sample/src/com/handmark/pulltorefresh/samples/PullToRefreshWebViewActivity.java",
"chars": 1819,
"preview": "/*******************************************************************************\n * Copyright 2011, 2012 Chris Banes.\n *"
}
]
// ... and 3 more files (download for full content)
About this extraction
This page contains the full source code of the chrisbanes/Android-PullToRefresh GitHub repository, extracted and formatted as plain text for AI agents and large language models (LLMs). The extraction includes 108 files (289.0 KB), approximately 73.2k tokens, and a symbol index with 472 extracted functions, classes, methods, constants, and types. Use this with OpenClaw, Claude, ChatGPT, Cursor, Windsurf, or any other AI tool that accepts text input. You can copy the full output to your clipboard or download it as a .txt file.
Extracted by GitExtract — free GitHub repo to text converter for AI. Built by Nikandr Surkov.