├── .gitignore
├── .idea
├── compiler.xml
├── copyright
│ └── profiles_settings.xml
├── encodings.xml
├── gradle.xml
├── misc.xml
├── modules.xml
├── runConfigurations.xml
├── statistic.xml
└── vcs.xml
├── ImageEditor-Android.iml
├── README.md
├── build.gradle
├── demo
├── .gitignore
├── build.gradle
├── demo.iml
├── proguard-rules.pro
└── src
│ └── main
│ ├── AndroidManifest.xml
│ ├── assets
│ └── stickers
│ │ ├── type1
│ │ ├── 1.png
│ │ ├── 2.png
│ │ ├── 3.png
│ │ ├── 4.png
│ │ └── 5.png
│ │ ├── type2
│ │ ├── 11.png
│ │ ├── 12.png
│ │ ├── 6.png
│ │ ├── 7.png
│ │ └── 8.png
│ │ ├── type3
│ │ ├── 13.png
│ │ ├── 14.png
│ │ ├── 15.png
│ │ ├── 16.png
│ │ └── 17.png
│ │ ├── type4
│ │ ├── 18.png
│ │ ├── 21.png
│ │ ├── 22.png
│ │ ├── 23.png
│ │ └── 24.png
│ │ ├── type5
│ │ ├── 25.png
│ │ ├── 26.png
│ │ ├── 27.png
│ │ └── 28.png
│ │ └── type6
│ │ ├── 20.png
│ │ ├── 22.png
│ │ ├── 23.png
│ │ ├── 3.png
│ │ └── 7.png
│ ├── java
│ └── com
│ │ └── xinlan
│ │ └── imageeditandroid
│ │ ├── FileUtils.java
│ │ └── MainActivity.java
│ └── res
│ ├── layout
│ └── activity_main.xml
│ ├── menu
│ └── menu_main.xml
│ ├── mipmap-hdpi
│ └── ic_launcher.png
│ ├── mipmap-mdpi
│ └── ic_launcher.png
│ ├── mipmap-xhdpi
│ └── ic_launcher.png
│ ├── mipmap-xxhdpi
│ └── ic_launcher.png
│ ├── values-w820dp
│ └── dimens.xml
│ ├── values-zh
│ └── strings.xml
│ ├── values
│ ├── dimens.xml
│ ├── strings.xml
│ └── styles.xml
│ └── xml
│ └── file_paths.xml
├── gradle.properties
├── gradle
└── wrapper
│ ├── gradle-wrapper.jar
│ └── gradle-wrapper.properties
├── gradlew
├── gradlew.bat
├── imageeditlibrary
├── .gitignore
├── build.gradle
├── imageeditlibrary.iml
├── jni
│ ├── Android.mk
│ ├── Application.mk
│ ├── beauty.h
│ ├── bicubic_resize.c
│ ├── bitmap.c
│ ├── bitmap.h
│ ├── blur.c
│ ├── colour_space.c
│ ├── colour_space.h
│ ├── filter.c
│ ├── matrix.c
│ ├── mem_utils.c
│ ├── mem_utils.h
│ ├── nanojpeg.c
│ ├── photo_processing.c
│ ├── transform.c
│ └── transform.h
├── proguard-rules.pro
└── src
│ ├── main
│ ├── AndroidManifest.xml
│ ├── java
│ │ └── com
│ │ │ └── xinlan
│ │ │ └── imageeditlibrary
│ │ │ ├── BaseActivity.java
│ │ │ ├── editimage
│ │ │ ├── EditImageActivity.java
│ │ │ ├── ModuleConfig.java
│ │ │ ├── adapter
│ │ │ │ ├── ColorListAdapter.java
│ │ │ │ ├── StickerAdapter.java
│ │ │ │ └── StickerTypeAdapter.java
│ │ │ ├── fliter
│ │ │ │ └── PhotoProcessing.java
│ │ │ ├── fragment
│ │ │ │ ├── AddTextFragment.java
│ │ │ │ ├── BaseEditFragment.java
│ │ │ │ ├── BeautyFragment.java
│ │ │ │ ├── CropFragment.java
│ │ │ │ ├── FilterListFragment.java
│ │ │ │ ├── MainMenuFragment.java
│ │ │ │ ├── PaintFragment.java
│ │ │ │ ├── RotateFragment.java
│ │ │ │ └── StickerFragment.java
│ │ │ ├── model
│ │ │ │ ├── RatioItem.java
│ │ │ │ └── StickerBean.java
│ │ │ ├── task
│ │ │ │ └── StickerTask.java
│ │ │ ├── ui
│ │ │ │ └── ColorPicker.java
│ │ │ ├── utils
│ │ │ │ ├── BitmapUtils.java
│ │ │ │ ├── DensityUtil.java
│ │ │ │ ├── FileUtil.java
│ │ │ │ ├── ListUtil.java
│ │ │ │ ├── Matrix3.java
│ │ │ │ ├── PaintUtil.java
│ │ │ │ └── RectUtil.java
│ │ │ ├── view
│ │ │ │ ├── Constants.java
│ │ │ │ ├── CropImageView.java
│ │ │ │ ├── CustomPaintView.java
│ │ │ │ ├── CustomViewPager.java
│ │ │ │ ├── PaintModeView.java
│ │ │ │ ├── RotateImageView.java
│ │ │ │ ├── StickerItem.java
│ │ │ │ ├── StickerView.java
│ │ │ │ ├── TextStickerView.java
│ │ │ │ └── imagezoom
│ │ │ │ │ ├── ImageViewTouch.java
│ │ │ │ │ ├── ImageViewTouchBase.java
│ │ │ │ │ ├── easing
│ │ │ │ │ ├── Back.java
│ │ │ │ │ ├── Bounce.java
│ │ │ │ │ ├── Circ.java
│ │ │ │ │ ├── Cubic.java
│ │ │ │ │ ├── Easing.java
│ │ │ │ │ ├── Elastic.java
│ │ │ │ │ ├── Expo.java
│ │ │ │ │ ├── Linear.java
│ │ │ │ │ ├── Quad.java
│ │ │ │ │ ├── Quart.java
│ │ │ │ │ ├── Quint.java
│ │ │ │ │ └── Sine.java
│ │ │ │ │ ├── graphic
│ │ │ │ │ ├── FastBitmapDrawable.java
│ │ │ │ │ └── IBitmapDrawable.java
│ │ │ │ │ └── utils
│ │ │ │ │ ├── ExifUtils.java
│ │ │ │ │ ├── IDisposable.java
│ │ │ │ │ └── IOUtils.java
│ │ │ └── widget
│ │ │ │ ├── EditCache.java
│ │ │ │ └── RedoUndoController.java
│ │ │ └── picchooser
│ │ │ ├── BucketItem.java
│ │ │ ├── BucketsFragment.java
│ │ │ ├── GalleryAdapter.java
│ │ │ ├── GridItem.java
│ │ │ ├── ImagesFragment.java
│ │ │ ├── Logger.java
│ │ │ ├── SelectPictureActivity.java
│ │ │ └── SquareImageView.java
│ ├── jniLibs
│ │ ├── arm64-v8a
│ │ │ └── libphotoprocessing.so
│ │ ├── armeabi-v7a
│ │ │ └── libphotoprocessing.so
│ │ ├── x86
│ │ │ └── libphotoprocessing.so
│ │ └── x86_64
│ │ │ └── libphotoprocessing.so
│ └── res
│ │ ├── anim
│ │ ├── in_bottom_to_top.xml
│ │ ├── menuhide.xml
│ │ ├── menushow.xml
│ │ └── out_bottom_to_top.xml
│ │ ├── drawable-hdpi
│ │ ├── back_arrow.png
│ │ ├── blue_thumb_default.png
│ │ ├── blue_thumb_pressed.png
│ │ ├── green_thumb_default.png
│ │ ├── green_thumb_pressed.png
│ │ ├── red_thumb_default.png
│ │ ├── red_thumb_pressed.png
│ │ ├── redo.png
│ │ └── uodo.png
│ │ ├── drawable-mdpi
│ │ ├── blue_thumb_default.png
│ │ ├── blue_thumb_pressed.png
│ │ ├── green_thumb_default.png
│ │ ├── green_thumb_pressed.png
│ │ ├── red_thumb_default.png
│ │ └── red_thumb_pressed.png
│ │ ├── drawable-xhdpi
│ │ ├── back_arrow.png
│ │ ├── blue_thumb_default.png
│ │ ├── blue_thumb_pressed.png
│ │ ├── crop_normal.png
│ │ ├── crop_pressed.png
│ │ ├── eraser_normal.png
│ │ ├── eraser_seleced.png
│ │ ├── fliters_normal.png
│ │ ├── fliters_pressed.png
│ │ ├── green_thumb_default.png
│ │ ├── green_thumb_pressed.png
│ │ ├── ic_menu_gallery.png
│ │ ├── image_edit_back.png
│ │ ├── red_thumb_default.png
│ │ ├── red_thumb_pressed.png
│ │ ├── sticker_delete.png
│ │ ├── sticker_normal.png
│ │ ├── sticker_pressed.png
│ │ ├── sticker_rotate.png
│ │ ├── stickers_type_animal.png
│ │ ├── stickers_type_cos.png
│ │ ├── stickers_type_decoration.png
│ │ ├── stickers_type_frame.png
│ │ ├── stickers_type_mark.png
│ │ ├── stickers_type_motion.png
│ │ ├── stickers_type_number.png
│ │ ├── stickers_type_profession.png
│ │ ├── stickers_type_spring.png
│ │ ├── stickers_type_text.png
│ │ ├── texture_normal.png
│ │ ├── texture_pressed.png
│ │ └── yd_image_tx.png
│ │ ├── drawable-xxhdpi
│ │ ├── blue_thumb_default.png
│ │ ├── blue_thumb_pressed.png
│ │ ├── green_thumb_default.png
│ │ ├── green_thumb_pressed.png
│ │ ├── red_thumb_default.png
│ │ └── red_thumb_pressed.png
│ │ ├── drawable
│ │ ├── image_edit_icon_crop.xml
│ │ ├── image_edit_icon_filter.xml
│ │ ├── image_edit_icon_sticker.xml
│ │ ├── image_edit_icon_text.xml
│ │ ├── materialcolorpicker__blue_progress.xml
│ │ ├── materialcolorpicker__blue_thumb_drawable.xml
│ │ ├── materialcolorpicker__color_button.xml
│ │ ├── materialcolorpicker__color_button_16.xml
│ │ ├── materialcolorpicker__green_progress.xml
│ │ ├── materialcolorpicker__green_thumb_drawable.xml
│ │ ├── materialcolorpicker__red_thumb_drawable.xml
│ │ ├── red_progress.xml
│ │ └── shape_rect.xml
│ │ ├── layout
│ │ ├── activity_image_edit.xml
│ │ ├── activity_main.xml
│ │ ├── bucketitem.xml
│ │ ├── fragment_edit_image_add_text.xml
│ │ ├── fragment_edit_image_beauty.xml
│ │ ├── fragment_edit_image_crop.xml
│ │ ├── fragment_edit_image_fliter.xml
│ │ ├── fragment_edit_image_main_menu.xml
│ │ ├── fragment_edit_image_rotate.xml
│ │ ├── fragment_edit_image_sticker_type.xml
│ │ ├── fragment_edit_paint.xml
│ │ ├── gallery.xml
│ │ ├── imageitem.xml
│ │ ├── materialcolorpicker__layout_color_picker.xml
│ │ ├── materialcolorpicker__layout_color_picker_old_android.xml
│ │ ├── view_color_more_panel.xml
│ │ ├── view_color_panel.xml
│ │ ├── view_set_stoke_width.xml
│ │ ├── view_sticker_item.xml
│ │ └── view_sticker_type_item.xml
│ │ ├── values-w820dp
│ │ └── dimens.xml
│ │ ├── values-zh
│ │ └── strings.xml
│ │ └── values
│ │ ├── colors.xml
│ │ ├── dimens.xml
│ │ ├── strings.xml
│ │ └── styles.xml
│ └── test
│ └── java
│ └── imageeditlibrary
│ └── editimage
│ ├── EditCacheTest.java
│ └── ImageEditTest.java
├── screens
├── gif1.gif
├── gif2.gif
├── gif3.gif
├── gif4.gif
├── gif5.gif
├── gif6.gif
├── gif7.gif
└── gif8_redo_undo.gif
└── settings.gradle
/.gitignore:
--------------------------------------------------------------------------------
1 | .gradle
2 | /local.properties
3 | /.idea/workspace.xml
4 | /.idea/libraries
5 | .DS_Store
6 | /build
7 | /captures
8 |
--------------------------------------------------------------------------------
/.idea/compiler.xml:
--------------------------------------------------------------------------------
1 |
2 |
9 |
14 |
19 |
24 |
8 |
10 |
16 |
17 |
18 | ### v_3.2:
19 | - [x] add Smooth skin and White skin
20 |
21 |
22 | ### v_3.1:
23 | - [x] text support multiply line(done) save image when click save button (not apply)
24 | ### v_3.0:
25 | - [x] doodle mode (done)
26 | ### v_2.0:
27 | - [x] add the textimage
28 |
29 |
30 |
31 | ### 动态效果图
32 |
33 |
34 |
35 |
36 |
37 |
38 |
39 |
40 |
41 |
42 |
43 |
44 |
45 |
46 | #### 使用方法:见DEMO示例
47 | #### usage:see the demo project
48 |
49 | License
50 | -------
51 |
52 | MIT is open-sourced software licensed under the [MIT license](http://opensource.org/licenses/MIT).
53 |
54 |
--------------------------------------------------------------------------------
/build.gradle:
--------------------------------------------------------------------------------
1 | // Top-level build file where you can add configuration options common to all sub-projects/modules.
2 |
3 | buildscript {
4 | repositories {
5 | jcenter()
6 | google()
7 | }
8 | dependencies {
9 | classpath 'com.android.tools.build:gradle:3.4.0'
10 |
11 | // NOTE: Do not place your application dependencies here; they belong
12 | // in the individual module build.gradle files
13 | }
14 | }
15 |
16 | allprojects {
17 | repositories {
18 | jcenter()
19 | google()
20 | }
21 | }
22 |
--------------------------------------------------------------------------------
/demo/.gitignore:
--------------------------------------------------------------------------------
1 | /build
2 |
--------------------------------------------------------------------------------
/demo/build.gradle:
--------------------------------------------------------------------------------
1 | apply plugin: 'com.android.application'
2 |
3 | android {
4 | compileSdkVersion 28
5 | buildToolsVersion '28.0.3'
6 |
7 | defaultConfig {
8 | applicationId "com.xinlan.imageeditandroid"
9 | minSdkVersion 16
10 | targetSdkVersion 23
11 | versionCode 1
12 | versionName "1.0"
13 | }
14 | buildTypes {
15 | release {
16 | minifyEnabled false
17 | proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
18 | }
19 | }
20 | }
21 |
22 | dependencies {
23 | api fileTree(include: ['*.jar'], dir: 'libs')
24 | api 'androidx.appcompat:appcompat:1.0.0'
25 | api project(':imageeditlibrary')
26 | }
27 |
--------------------------------------------------------------------------------
/demo/proguard-rules.pro:
--------------------------------------------------------------------------------
1 | # Add project specific ProGuard rules here.
2 | # By default, the flags in this file are appended to flags specified
3 | # in D:\android\android-sdk-windows/tools/proguard/proguard-android.txt
4 | # You can edit the include path and order by changing the proguardFiles
5 | # directive in build.gradle.
6 | #
7 | # For more details, see
8 | # http://developer.android.com/guide/developing/tools/proguard.html
9 |
10 | # Add any project specific keep options here:
11 |
12 | # If your project uses WebView with JS, uncomment the following
13 | # and specify the fully qualified class name to the JavaScript interface
14 | # class:
15 | #-keepclassmembers class fqcn.of.javascript.interface.for.webview {
16 | # public *;
17 | #}
18 |
--------------------------------------------------------------------------------
/demo/src/main/AndroidManifest.xml:
--------------------------------------------------------------------------------
1 |
2 |
12 | * 前一步 后一步操作类
13 | */
14 | public class RedoUndoController implements View.OnClickListener {
15 | private View mRootView;
16 | private View mUndoBtn;//撤销按钮
17 | private View mRedoBtn;//重做按钮
18 | private EditImageActivity mActivity;
19 | private EditCache mEditCache = new EditCache();//保存前一次操作内容 用于撤销操作
20 |
21 | private EditCache.ListModify mObserver = new EditCache.ListModify() {
22 | @Override
23 | public void onCacheListChange(EditCache cache) {
24 | updateBtns();
25 | }
26 | };
27 |
28 | public RedoUndoController(EditImageActivity activity, View panelView) {
29 | this.mActivity = activity;
30 | this.mRootView = panelView;
31 |
32 | mUndoBtn = mRootView.findViewById(R.id.uodo_btn);
33 | mRedoBtn = mRootView.findViewById(R.id.redo_btn);
34 |
35 | mUndoBtn.setOnClickListener(this);
36 | mRedoBtn.setOnClickListener(this);
37 |
38 | updateBtns();
39 | mEditCache.addObserver(mObserver);
40 | }
41 |
42 | public void switchMainBit(Bitmap mainBitmap, Bitmap newBit) {
43 | if (mainBitmap == null || mainBitmap.isRecycled())
44 | return;
45 |
46 | mEditCache.push(mainBitmap);
47 | mEditCache.push(newBit);
48 | }
49 |
50 |
51 | @Override
52 | public void onClick(View v) {
53 | if (v == mUndoBtn) {
54 | undoClick();
55 | } else if (v == mRedoBtn) {
56 | redoClick();
57 | }//end if
58 | }
59 |
60 |
61 | /**
62 | * 撤销操作
63 | */
64 | protected void undoClick() {
65 | //System.out.println("Undo!!!");
66 | Bitmap lastBitmap = mEditCache.getNextCurrentBit();
67 | if (lastBitmap != null && !lastBitmap.isRecycled()) {
68 | mActivity.changeMainBitmap(lastBitmap, false);
69 | }
70 | }
71 |
72 | /**
73 | * 取消撤销
74 | */
75 | protected void redoClick() {
76 | //System.out.println("Redo!!!");
77 | Bitmap preBitmap = mEditCache.getPreCurrentBit();
78 | if (preBitmap != null && !preBitmap.isRecycled()) {
79 | mActivity.changeMainBitmap(preBitmap, false);
80 | }
81 | }
82 |
83 | /**
84 | * 根据状态更新按钮显示
85 | */
86 | public void updateBtns() {
87 | //System.out.println("缓存Size = " + mEditCache.getSize() + " current = " + mEditCache.getCur());
88 | //System.out.println("content = " + mEditCache.debugLog());
89 | mUndoBtn.setVisibility(mEditCache.checkNextBitExist() ? View.VISIBLE : View.INVISIBLE);
90 | mRedoBtn.setVisibility(mEditCache.checkPreBitExist() ? View.VISIBLE : View.INVISIBLE);
91 | }
92 |
93 | public void onDestroy() {
94 | if (mEditCache != null) {
95 | mEditCache.removeObserver(mObserver);
96 | mEditCache.removeAll();
97 | }
98 | }
99 |
100 | }//end class
101 |
--------------------------------------------------------------------------------
/imageeditlibrary/src/main/java/com/xinlan/imageeditlibrary/picchooser/BucketItem.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2013 Thomas Hoffmann
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | */
16 | package com.xinlan.imageeditlibrary.picchooser;
17 |
18 | class BucketItem extends GridItem {
19 |
20 | final int id;
21 | int images = 1;
22 |
23 | /**
24 | * Creates a new BucketItem
25 | *
26 | * @param n the name of the bucket
27 | * @param p the absolute path to the bucket
28 | * @param i the bucket ID
29 | */
30 | public BucketItem(final String n, final String p,final String taken, int i) {
31 | super(n, p,taken,0);
32 | id = i;
33 | }
34 |
35 | }
36 |
--------------------------------------------------------------------------------
/imageeditlibrary/src/main/java/com/xinlan/imageeditlibrary/picchooser/BucketsFragment.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2013 Thomas Hoffmann
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | */
16 | package com.xinlan.imageeditlibrary.picchooser;
17 |
18 | import java.util.ArrayList;
19 | import java.util.List;
20 |
21 | import android.database.Cursor;
22 | import android.os.Bundle;
23 | import android.provider.MediaStore;
24 | import androidx.fragment.app.Fragment;
25 | import android.view.LayoutInflater;
26 | import android.view.View;
27 | import android.view.ViewGroup;
28 | import android.widget.AdapterView;
29 | import android.widget.AdapterView.OnItemClickListener;
30 | import android.widget.GridView;
31 | import android.widget.Toast;
32 |
33 | import com.xinlan.imageeditlibrary.R;
34 |
35 |
36 | public class BucketsFragment extends Fragment {
37 |
38 | @Override
39 | public View onCreateView(final LayoutInflater inflater,
40 | final ViewGroup container, final Bundle savedInstanceState) {
41 | View v = inflater.inflate(R.layout.gallery, null);
42 |
43 | String[] projection = new String[] { MediaStore.Images.Media.DATA,
44 | MediaStore.Images.Media.BUCKET_DISPLAY_NAME,
45 | MediaStore.Images.Media.BUCKET_ID };
46 |
47 | Cursor cur = getActivity().getContentResolver().query(
48 | MediaStore.Images.Media.EXTERNAL_CONTENT_URI,
49 | projection,
50 | null,
51 | null,
52 | MediaStore.Images.Media.BUCKET_DISPLAY_NAME + " ASC, "
53 | + MediaStore.Images.Media.DATE_MODIFIED + " DESC");
54 |
55 | final List