mirror of
https://github.com/lacerta-doc/Lacerta.git
synced 2026-11-07 19:47:36 +00:00
Compare commits
8
Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
6f94b3408f | ||
|
|
9d229a2857 | ||
|
|
da9cd9be8e | ||
|
|
0b2d58470b | ||
|
|
ed5e699493 | ||
|
|
29737303af | ||
|
|
151c2dde25 | ||
|
|
2b9a68b6f5 |
No files matched your search
@@ -1,8 +1,9 @@
|
|||||||
# Lacerta
|
# Lacerta
|
||||||
WIP
|
学習に便利な機能とGit-like VCSを持ったドキュメントスキャナ (Work In Progress)
|
||||||
|
|
||||||
## モジュール設計
|
## モジュール設計
|
||||||
|

|
||||||
|
|
||||||

|
|
||||||
|
|
||||||
## メモ
|
## メモ
|
||||||
- アイコン: Google Material Icons https://fonts.google.com/icons (Weight:300, Grade:0, Optical size: 24px)
|
- アイコン: Google Material Icons https://fonts.google.com/icons (Weight:300, Grade:0, Optical size: 24px)
|
||||||
@@ -11,45 +12,28 @@ WIP
|
|||||||
### モジュール一覧
|
### モジュール一覧
|
||||||
- `component` : コンポーネント
|
- `component` : コンポーネント
|
||||||
- `common` : 共通コンポーネント
|
- `common` : 共通コンポーネント
|
||||||
- UIの中で共通で使う要素(メニューアイテムとか)
|
- `scanner` : スキャナー
|
||||||
- `scanner` : スキャナー
|
|
||||||
- スキャナーの実装
|
|
||||||
- `viewer` : ビューワー
|
- `viewer` : ビューワー
|
||||||
- ドキュメントビューワーの実装
|
- `data` : UIからデータを取得/保存するためのラッパーモジュール
|
||||||
- `data` : データ
|
|
||||||
- UIからデータを取得/保存するためのラッパーモジュール
|
|
||||||
- `Document` : ドキュメント関係
|
|
||||||
- WIP(JavaDocを参照してください, 余裕があったら追記します)
|
|
||||||
- `feature` : 機能モジュール(ナビゲーションからみた機能で分割)
|
- `feature` : 機能モジュール(ナビゲーションからみた機能で分割)
|
||||||
- `common`: 共通機能
|
- `common`: 共通機能
|
||||||
- 設定画面とか、どこからでも呼ばれうる画面
|
|
||||||
- `debug`: デバッグメニュー
|
- `debug`: デバッグメニュー
|
||||||
- `home`: ホーム画面
|
- `home`: ホーム画面
|
||||||
- `library`: ライブラリ画面
|
- `library`: ライブラリ画面
|
||||||
- `scan`: スキャン画面
|
- `scan`: スキャン画面 (廃止予定)
|
||||||
- `search`: 検索画面
|
- `search`: 検索画面
|
||||||
- `model` : モデル
|
- `model` : データモデルをまとめたモジュール
|
||||||
- データモデルをまとめたモジュール (WIP)
|
- `processor` : プロセッサ(例: `DocumentProcessor` : ドキュメント処理(ドキュメントにページを追加したり更新したり))
|
||||||
- `document` : ドキュメント
|
- `shared`: 共有リソース
|
||||||
- `meta` : メタデータ
|
- `ui`: UI要素(Theme, Drawable, Colorなど)
|
||||||
- `processor` : プロセッサ
|
- `source` : ソース(DB/FileManagerなど)
|
||||||
- いくつかの処理をまとめたモジュール
|
- `utils` : ユーティリティ(ちょっとしたユーティリティをまとめたモジュール)
|
||||||
- `DocumentProcessor` : ドキュメント処理(ドキュメントにページを追加したり更新したり)
|
|
||||||
- `shared` :
|
|
||||||
- 共有リソース
|
|
||||||
- `source` : ソース
|
|
||||||
- (バックエンドが使うのでとりあえず後回し、フロントから直接操作することは絶対にありません)
|
|
||||||
- `utils` : ユーティリティ
|
|
||||||
- ちょっとしたユーティリティをまとめたモジュール
|
|
||||||
- `LacertaLogger` : ロガー
|
|
||||||
- `XmlMetaParser` : XMLメタデータパーサー(フロントから直接操作することは絶対にありません)
|
|
||||||
|
|
||||||
|
|
||||||
## コーディング規則/推奨(WIP)
|
## コーディング規則/推奨(WIP)
|
||||||
### 規則
|
|
||||||
- `// TODO`コメントには任意のsuffixを付ける
|
- `// TODO`コメントには任意のsuffixを付ける
|
||||||
- 全員が同じ`// TODO:`を使っていると検索がむずかしくなるため
|
- 全員が同じ`// TODO:`を使っていると検索がむずかしくなるため
|
||||||
- (例: `// TODO-rca:`)
|
- (例: `// TODO-rca:`)
|
||||||
### 推奨
|
|
||||||
- マジックナンバーは控える(必要な場合もあるので)
|
## Thanks for
|
||||||
|
- [SDA-SE/document-scanner-android](https://github.com/SDA-SE/document-scanner-android)
|
||||||
|
-
|
||||||
@@ -45,4 +45,8 @@ dependencies {
|
|||||||
// shared
|
// shared
|
||||||
implementation project(':shared:ui')
|
implementation project(':shared:ui')
|
||||||
|
|
||||||
|
// https://mvnrepository.com/artifact/androidx.preference/preference
|
||||||
|
implementation 'androidx.preference:preference:1.2.1'
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
+10
-13
@@ -2,8 +2,12 @@ package one.nem.lacerta.setting;
|
|||||||
|
|
||||||
import android.os.Bundle;
|
import android.os.Bundle;
|
||||||
|
|
||||||
|
import androidx.annotation.Nullable;
|
||||||
import androidx.fragment.app.Fragment;
|
import androidx.fragment.app.Fragment;
|
||||||
|
import androidx.fragment.app.FragmentTransaction;
|
||||||
|
import androidx.preference.PreferenceFragmentCompat;
|
||||||
|
|
||||||
|
import android.preference.PreferenceFragment;
|
||||||
import android.view.LayoutInflater;
|
import android.view.LayoutInflater;
|
||||||
import android.view.View;
|
import android.view.View;
|
||||||
import android.view.ViewGroup;
|
import android.view.ViewGroup;
|
||||||
@@ -13,12 +17,17 @@ import android.view.ViewGroup;
|
|||||||
* Use the {@link SettingScanPageFragment#newInstance} factory method to
|
* Use the {@link SettingScanPageFragment#newInstance} factory method to
|
||||||
* create an instance of this fragment.
|
* create an instance of this fragment.
|
||||||
*/
|
*/
|
||||||
public class SettingScanPageFragment extends Fragment {
|
public class SettingScanPageFragment extends PreferenceFragmentCompat {
|
||||||
|
|
||||||
public SettingScanPageFragment() {
|
public SettingScanPageFragment() {
|
||||||
// Required empty public constructor
|
// Required empty public constructor
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onCreatePreferences(@Nullable Bundle savedInstanceState, @Nullable String rootKey) {
|
||||||
|
addPreferencesFromResource(R.xml.scan_preferences);
|
||||||
|
}
|
||||||
|
|
||||||
public static SettingScanPageFragment newInstance() {
|
public static SettingScanPageFragment newInstance() {
|
||||||
SettingScanPageFragment fragment = new SettingScanPageFragment();
|
SettingScanPageFragment fragment = new SettingScanPageFragment();
|
||||||
Bundle args = new Bundle();
|
Bundle args = new Bundle();
|
||||||
@@ -26,16 +35,4 @@ public class SettingScanPageFragment extends Fragment {
|
|||||||
return fragment;
|
return fragment;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onCreate(Bundle savedInstanceState) {
|
|
||||||
super.onCreate(savedInstanceState);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public View onCreateView(LayoutInflater inflater, ViewGroup container,
|
|
||||||
Bundle savedInstanceState) {
|
|
||||||
// Inflate the layout for this fragment
|
|
||||||
return inflater.inflate(R.layout.fragment_setting_scan_page, container, false);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
@@ -1,14 +1,50 @@
|
|||||||
<?xml version="1.0" encoding="utf-8"?>
|
|
||||||
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||||
xmlns:tools="http://schemas.android.com/tools"
|
xmlns:app="http://schemas.android.com/apk/res-auto"
|
||||||
android:layout_width="match_parent"
|
android:layout_width="match_parent"
|
||||||
android:layout_height="match_parent"
|
android:layout_height="match_parent"
|
||||||
tools:context=".SettingScanPageFragment">
|
android:background="@color/colorSurface">
|
||||||
|
|
||||||
<!-- TODO: Update blank fragment layout -->
|
<androidx.coordinatorlayout.widget.CoordinatorLayout
|
||||||
<TextView
|
|
||||||
android:layout_width="match_parent"
|
android:layout_width="match_parent"
|
||||||
android:layout_height="match_parent"
|
android:layout_height="match_parent">
|
||||||
android:text="@string/hello_blank_fragment" />
|
|
||||||
|
<com.google.android.material.appbar.AppBarLayout
|
||||||
|
android:id="@+id/app_bar_layout"
|
||||||
|
android:layout_width="match_parent"
|
||||||
|
android:layout_height="wrap_content">
|
||||||
|
|
||||||
|
<com.google.android.material.appbar.CollapsingToolbarLayout
|
||||||
|
android:id="@+id/collapsing_toolbar"
|
||||||
|
app:contentScrim="@color/colorSecondaryContainer"
|
||||||
|
android:background="@color/colorSurface"
|
||||||
|
android:layout_width="match_parent"
|
||||||
|
android:layout_height="160dp"
|
||||||
|
android:fitsSystemWindows="true"
|
||||||
|
android:minHeight="?attr/actionBarSize"
|
||||||
|
app:collapsedTitleGravity="start|center_vertical"
|
||||||
|
app:expandedTitleGravity="start|bottom"
|
||||||
|
app:expandedTitleMarginBottom="16dp"
|
||||||
|
app:expandedTitleMarginStart="16dp"
|
||||||
|
app:expandedTitleTextAppearance="@style/TextAppearance.MaterialComponents.Headline4"
|
||||||
|
app:layout_scrollFlags="scroll|exitUntilCollapsed">
|
||||||
|
|
||||||
|
<androidx.appcompat.widget.Toolbar
|
||||||
|
android:id="@+id/toolbar"
|
||||||
|
android:layout_width="match_parent"
|
||||||
|
android:layout_height="?attr/actionBarSize"
|
||||||
|
app:layout_collapseMode="pin"
|
||||||
|
app:title="@string/setting_top_scan_title" />
|
||||||
|
|
||||||
|
</com.google.android.material.appbar.CollapsingToolbarLayout>
|
||||||
|
|
||||||
|
</com.google.android.material.appbar.AppBarLayout>
|
||||||
|
|
||||||
|
<FrameLayout
|
||||||
|
android:id="@+id/setting_scan_page_container"
|
||||||
|
android:layout_width="match_parent"
|
||||||
|
android:layout_height="match_parent"
|
||||||
|
app:layout_behavior="@string/appbar_scrolling_view_behavior" />
|
||||||
|
|
||||||
|
</androidx.coordinatorlayout.widget.CoordinatorLayout>
|
||||||
|
|
||||||
</FrameLayout>
|
</FrameLayout>
|
||||||
@@ -0,0 +1,11 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<resources>
|
||||||
|
<array name="png_quality_array">
|
||||||
|
<item name="5">5</item>
|
||||||
|
<item name="6">6</item>
|
||||||
|
<item name="7">7</item>
|
||||||
|
<item name="8">8</item>
|
||||||
|
<item name="9">9</item>
|
||||||
|
</array>
|
||||||
|
|
||||||
|
</resources>
|
||||||
@@ -0,0 +1,6 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<resources>
|
||||||
|
<integer name="png_quality_default">70</integer>
|
||||||
|
<integer name="png_quality_min">5</integer>
|
||||||
|
<integer name="png_quality_max">100</integer>
|
||||||
|
</resources>
|
||||||
@@ -0,0 +1,29 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<PreferenceScreen xmlns:android="http://schemas.android.com/apk/res/android"
|
||||||
|
xmlns:app="http://schemas.android.com/apk/res-auto">
|
||||||
|
|
||||||
|
<PreferenceCategory android:title="@string/setting_scan_quality_title">
|
||||||
|
<SeekBarPreference
|
||||||
|
android:defaultValue="@integer/png_quality_default"
|
||||||
|
android:key="png_quality"
|
||||||
|
android:max="@integer/png_quality_max"
|
||||||
|
android:min="@integer/png_quality_min"
|
||||||
|
android:summary="@string/setting_scan_quality_png_quality_description"
|
||||||
|
android:title="@string/setting_scan_quality_png_quality_title" />
|
||||||
|
</PreferenceCategory>
|
||||||
|
<PreferenceCategory android:title="@string/setting_scan_default_title">
|
||||||
|
|
||||||
|
<EditTextPreference
|
||||||
|
android:defaultValue="Untitled"
|
||||||
|
android:key="new_doc_default_title"
|
||||||
|
android:selectAllOnFocus="true"
|
||||||
|
android:singleLine="true"
|
||||||
|
android:title="@string/setting_scan_default_document_name" />
|
||||||
|
<EditTextPreference
|
||||||
|
android:defaultValue="NewFolder"
|
||||||
|
android:key="new_dir_default_title"
|
||||||
|
android:selectAllOnFocus="true"
|
||||||
|
android:singleLine="true"
|
||||||
|
android:title="@string/setting_scan_default_folder_name" />
|
||||||
|
</PreferenceCategory>
|
||||||
|
</PreferenceScreen>
|
||||||
@@ -19,6 +19,14 @@
|
|||||||
<string name="setting_top_scan_title">スキャン</string>
|
<string name="setting_top_scan_title">スキャン</string>
|
||||||
<string name="setting_top_scan_description">画質, 保存先</string>
|
<string name="setting_top_scan_description">画質, 保存先</string>
|
||||||
|
|
||||||
|
<string name="setting_scan_quality_title">画質</string>
|
||||||
|
<string name="setting_scan_quality_png_quality_title">PNG画質</string>
|
||||||
|
<string name="setting_scan_quality_png_quality_description">PNG画質を設定します. 画質が高いほどファイルサイズが大きくなります.</string>
|
||||||
|
|
||||||
|
<string name="setting_scan_default_title">保存先</string>
|
||||||
|
<string name="setting_scan_default_document_name">新規ドキュメントのデフォルトタイトル</string>
|
||||||
|
<string name="setting_scan_default_folder_name">新規フォルダのデフォルト名</string>
|
||||||
|
|
||||||
<string name="setting_top_display_title">表示</string>
|
<string name="setting_top_display_title">表示</string>
|
||||||
<string name="setting_top_display_description">テーマ, フォントサイズ</string>
|
<string name="setting_top_display_description">テーマ, フォントサイズ</string>
|
||||||
|
|
||||||
|
|||||||
@@ -22,6 +22,7 @@ import dagger.assisted.AssistedInject;
|
|||||||
import one.nem.lacerta.source.file.FileManager;
|
import one.nem.lacerta.source.file.FileManager;
|
||||||
|
|
||||||
import one.nem.lacerta.utils.LacertaLogger;
|
import one.nem.lacerta.utils.LacertaLogger;
|
||||||
|
import one.nem.lacerta.utils.Store;
|
||||||
|
|
||||||
public class FileManagerImpl implements FileManager {
|
public class FileManagerImpl implements FileManager {
|
||||||
|
|
||||||
@@ -303,7 +304,16 @@ public class FileManagerImpl implements FileManager {
|
|||||||
private void saveBitmapInternal(Bitmap bitmap, Path path) throws IOException {
|
private void saveBitmapInternal(Bitmap bitmap, Path path) throws IOException {
|
||||||
try {
|
try {
|
||||||
logger.debug("saveBitmapInternal", "path: " + path);
|
logger.debug("saveBitmapInternal", "path: " + path);
|
||||||
bitmap.compress(Bitmap.CompressFormat.PNG, 100, Files.newOutputStream(path));
|
// Bitmapの長辺を1024pxにする
|
||||||
|
int width = bitmap.getWidth();
|
||||||
|
int height = bitmap.getHeight();
|
||||||
|
float scale = 1.0f;
|
||||||
|
if (width > height) {
|
||||||
|
scale = Store.Scan.MAX_RESOLUTION_LONG / width;
|
||||||
|
} else {
|
||||||
|
scale = Store.Scan.MAX_RESOLUTION_LONG / height;
|
||||||
|
}
|
||||||
|
bitmap.compress(new Store.Scan().COMPRESS_FORMAT, Store.Scan.QUALITY, Files.newOutputStream(path));
|
||||||
} catch (Exception e) {
|
} catch (Exception e) {
|
||||||
logger.error("saveBitmapInternal", e.getMessage());
|
logger.error("saveBitmapInternal", e.getMessage());
|
||||||
throw new IOException("Failed to save bitmap");
|
throw new IOException("Failed to save bitmap");
|
||||||
|
|||||||
@@ -8,7 +8,7 @@ public class FeatureSwitch {
|
|||||||
|
|
||||||
public static class FeatureMaster {
|
public static class FeatureMaster {
|
||||||
public static boolean enableSearch = false;
|
public static boolean enableSearch = false;
|
||||||
public static boolean enableDebugMenu = false;
|
public static boolean enableDebugMenu = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static class Vcs {
|
public static class Vcs {
|
||||||
|
|||||||
@@ -0,0 +1,11 @@
|
|||||||
|
package one.nem.lacerta.utils;
|
||||||
|
|
||||||
|
import android.graphics.Bitmap;
|
||||||
|
|
||||||
|
public class Store {
|
||||||
|
public static class Scan {
|
||||||
|
public Bitmap.CompressFormat COMPRESS_FORMAT = Bitmap.CompressFormat.JPEG;
|
||||||
|
public static final int QUALITY = 60;
|
||||||
|
public static final float MAX_RESOLUTION_LONG = 2048;
|
||||||
|
}
|
||||||
|
}
|
||||||
Reference in new issue
Block a user