Feature: FontManager

This commit is contained in:
zt515
2017-07-03 01:28:05 +08:00
parent 249df0a34e
commit d4c1e8e0fb
17 changed files with 214 additions and 50 deletions

View File

@ -34,7 +34,7 @@
android:theme="@style/AppTheme.NoActionBar" />
<activity
android:name=".ui.customization.CustomizationActivity"
android:label="@string/pref_ui_customization"
android:label="@string/customization_settings"
android:theme="@style/Theme.AppCompat.NoActionBar"
android:windowSoftInputMode="adjustResize|stateHidden" />
<activity

View File

@ -1,8 +1,8 @@
package io.neoterm
import android.app.Application
import io.neoterm.customize.color.ColorSchemeManager
import io.neoterm.customize.font.FontManager
import io.neoterm.preference.NeoPreference
/**
* @author kiva
@ -10,7 +10,7 @@ import io.neoterm.preference.NeoPreference
class App : Application() {
override fun onCreate() {
super.onCreate()
ColorSchemeManager.init(this)
FontManager.init(this)
NeoPreference.init(this)
}
}

View File

@ -12,8 +12,11 @@ object NeoTermPath {
const val USR_PATH = "$ROOT_PATH/usr"
const val HOME_PATH = "$ROOT_PATH/home"
const val EKS_PATH = "$USR_PATH/share/eks"
const val CUSTOM_PATH = "$HOME_PATH/.neoterm"
const val EKS_PATH = "$CUSTOM_PATH/eks"
const val EKS_DEFAULT_FILE = "$EKS_PATH/default.eks"
const val FONT_PATH = "$CUSTOM_PATH/font"
const val COLORS_PATH = "$CUSTOM_PATH/color"
const val SOURCE_FILE = "$USR_PATH/etc/apt/sources.list"
const val PACKAGE_LIST_DIR = "$USR_PATH/var/lib/apt/lists"

View File

@ -1,11 +1,18 @@
package io.neoterm.customize.color
import android.content.Context
import io.neoterm.backend.TerminalEmulator
import io.neoterm.customize.NeoTermPath
import java.io.File
/**
* @author kiva
*/
object ColorSchemeManager {
fun init(context: Context) {
File(NeoTermPath.COLORS_PATH).mkdirs()
}
fun applyColorScheme(emulator: TerminalEmulator?, colorScheme: NeoColorScheme?) {
if (emulator != null && colorScheme != null) {
colorScheme.applyLocal(emulator)

View File

@ -2,17 +2,38 @@ package io.neoterm.customize.font
import android.content.Context
import android.graphics.Typeface
import io.neoterm.R
import io.neoterm.customize.NeoTermPath
import io.neoterm.preference.NeoPreference
import io.neoterm.utils.FileUtils
import java.io.File
/**
* @author kiva
*/
object FontManager {
private val DEFAULT_FONT_NAME = "UbuntuMono"
private lateinit var DEFAULT_FONT: NeoFont
private lateinit var fonts: MutableList<String>
private lateinit var fonts: MutableMap<String, NeoFont>
fun init(context: Context) {
fonts = mutableListOf()
DEFAULT_FONT = NeoFont(Typeface.createFromAsset(context.assets, "font.ttf"))
File(NeoTermPath.FONT_PATH).mkdirs()
fonts = mutableMapOf()
val defaultFontFile = fontFile(DEFAULT_FONT_NAME)
if (!defaultFontFile.exists()) {
if (!extractDefaultFont(context, defaultFontFile)) {
DEFAULT_FONT = loadDefaultFontFromAsset(context)
fonts.put(DEFAULT_FONT_NAME, DEFAULT_FONT)
return
}
}
if (!refreshFontList()) {
DEFAULT_FONT = loadDefaultFontFromAsset(context)
fonts.put(DEFAULT_FONT_NAME, DEFAULT_FONT)
}
}
fun getDefaultFont(): NeoFont {
@ -20,6 +41,71 @@ object FontManager {
}
fun getCurrentFont(): NeoFont {
return getDefaultFont()
return fonts[getCurrentFontName()]!!
}
fun setCurrentFont(fontName: String) {
NeoPreference.store(R.string.key_customization_font, fontName)
}
fun getCurrentFontName(): String {
var currentFontName = NeoPreference.loadString(R.string.key_customization_font, DEFAULT_FONT_NAME)
if (!fonts.containsKey(currentFontName)) {
currentFontName = DEFAULT_FONT_NAME
NeoPreference.store(R.string.key_customization_font, DEFAULT_FONT)
}
return currentFontName
}
fun getFont(fontName: String): NeoFont {
return if (fonts.containsKey(fontName)) fonts[fontName]!! else getCurrentFont()
}
fun getFontNames(): List<String> {
val list = ArrayList<String>()
list += fonts.keys
return list
}
fun refreshFontList(): Boolean {
fonts.clear()
fonts.put("Android Monospace", NeoFont(Typeface.MONOSPACE))
fonts.put("Android Sans Serif", NeoFont(Typeface.SANS_SERIF))
fonts.put("Android Serif", NeoFont(Typeface.SERIF))
val fontDir = File(NeoTermPath.FONT_PATH)
for (file in fontDir.listFiles({ pathname -> pathname.name.endsWith(".ttf") })) {
val fontName = fontName(file)
val font = NeoFont(file)
fonts.put(fontName, font)
}
if (fonts.containsKey(DEFAULT_FONT_NAME)) {
DEFAULT_FONT = fonts[DEFAULT_FONT_NAME]!!
return true
}
return false
}
private fun loadDefaultFontFromAsset(context: Context): NeoFont {
return NeoFont(Typeface.createFromAsset(context.assets, "$DEFAULT_FONT_NAME.ttf"))
}
private fun extractDefaultFont(context: Context, defaultFontFile: File): Boolean {
try {
val assets = context.assets
val ttfInput = assets.open("$DEFAULT_FONT_NAME.ttf")
FileUtils.writeFile(defaultFontFile, ttfInput)
ttfInput.close()
return true
} catch (e: Exception) {
return false
}
}
private fun fontFile(fontName: String): File {
return File("${NeoTermPath.FONT_PATH}/$fontName.ttf")
}
private fun fontName(fontFile: File): String {
return fontFile.nameWithoutExtension
}
}

View File

@ -1,13 +1,31 @@
package io.neoterm.customize.font
import android.graphics.Typeface
import io.neoterm.view.TerminalView
import java.io.File
/**
* @author kiva
*/
class NeoFont(val typeface: Typeface) {
fun applyLocal(terminalView: TerminalView?) {
terminalView?.setTypeface(typeface)
class NeoFont {
private var fontFile: File? = null
private var typeface: Typeface? = null
constructor(fontFile: File) {
this.fontFile = fontFile
}
constructor(typeface: Typeface) {
this.typeface = typeface
}
fun getTypeFace(): Typeface? {
if (typeface == null && fontFile == null) {
return null
}
if (typeface == null) {
typeface = Typeface.createFromFile(fontFile)
}
return typeface
}
}

View File

@ -50,6 +50,7 @@ class NeoTermActivity : AppCompatActivity(), ServiceConnection, SharedPreference
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
NeoPreference.init(this)
NeoPermission.initAppPermission(this, NeoPermission.REQUEST_APP_PERMISSION)
val fullscreen = NeoPreference.loadBoolean(R.string.key_ui_fullscreen, false)

View File

@ -4,9 +4,14 @@ import android.os.Bundle
import android.support.v7.app.AppCompatActivity
import android.support.v7.widget.Toolbar
import android.view.MenuItem
import android.view.View
import android.widget.AdapterView
import android.widget.ArrayAdapter
import android.widget.Spinner
import io.neoterm.R
import io.neoterm.backend.TerminalSession
import io.neoterm.customize.NeoTermPath
import io.neoterm.customize.font.FontManager
import io.neoterm.utils.TerminalUtils
import io.neoterm.view.BasicSessionCallback
import io.neoterm.view.BasicViewClient
@ -35,6 +40,26 @@ class CustomizationActivity: AppCompatActivity() {
session = TerminalUtils.createSession(this, "${NeoTermPath.USR_PATH}/bin/applets/echo",
arrayOf("echo", "Hello NeoTerm."), null, null, sessionCallback, false)
terminalView.attachSession(session)
setupSpinner(R.id.custom_font_spinner, FontManager.getFontNames(), FontManager.getCurrentFontName(), object : AdapterView.OnItemSelectedListener {
override fun onNothingSelected(parent: AdapterView<*>?) {
}
override fun onItemSelected(parent: AdapterView<*>?, view: View?, position: Int, id: Long) {
val fontName = parent!!.adapter!!.getItem(position) as String
terminalView.setTypeface(FontManager.getFont(fontName).getTypeFace())
FontManager.setCurrentFont(fontName)
}
})
}
private fun setupSpinner(id: Int, data: List<String>, selected: String, listener: AdapterView.OnItemSelectedListener) {
val spinner = findViewById(id) as Spinner
val adapter = ArrayAdapter<String>(this, android.R.layout.simple_spinner_item, data)
adapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item)
spinner.adapter = adapter
spinner.onItemSelectedListener = listener
spinner.setSelection(if (data.contains(selected)) data.indexOf(selected) else 0)
}
override fun onDestroy() {

View File

@ -17,7 +17,7 @@ import java.io.File
object TerminalUtils {
fun setupTerminalView(terminalView: TerminalView, terminalViewClient: BasicViewClient? = null) {
terminalView.textSize = NeoPreference.loadInt(NeoPreference.KEY_FONT_SIZE, 30)
terminalView.setTypeface(FontManager.getCurrentFont().typeface)
terminalView.setTypeface(FontManager.getCurrentFont().getTypeFace())
if (terminalViewClient != null) {
terminalView.setOnKeyListener(terminalViewClient)
}

View File

@ -185,7 +185,7 @@ public final class ExtraKeysView extends LinearLayout {
button = new Button(getContext(), null, android.R.attr.buttonBarButtonStyle);
}
button.setTypeface(FontManager.INSTANCE.getCurrentFont().getTypeface());
button.setTypeface(FontManager.INSTANCE.getCurrentFont().getTypeFace());
button.setText(extraButton.buttonText);
button.setTextColor(NORMAL_TEXT_COLOR);
button.setAllCaps(false);

View File

@ -20,28 +20,42 @@
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"
android:layout_margin="@dimen/text_margin"
android:orientation="vertical">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginBottom="@dimen/text_margin"
android:orientation="horizontal">
<Button
style="?buttonBarButtonStyle"
android:layout_width="0dp"
android:layout_height="match_parent"
android:layout_weight="1.0"
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/pref_customization_font" />
<Button
style="?buttonBarButtonStyle"
android:layout_width="0dp"
android:layout_height="match_parent"
android:layout_weight="1.0"
<Spinner
android:id="@+id/custom_font_spinner"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginStart="@dimen/text_margin" />
</LinearLayout>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal">
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/pref_customization_color_scheme" />
<Button
style="?buttonBarButtonStyle"
android:layout_width="0dp"
android:layout_height="match_parent"
android:layout_weight="1.0"
android:text="@string/pref_customization_eks" />
<Spinner
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginStart="@dimen/text_margin" />
</LinearLayout>
</LinearLayout>
<RelativeLayout

View File

@ -19,8 +19,8 @@
<string name="pref_package_source">软件源</string>
<string name="pref_ui_close_tab_anim_next_tab">向下切换窗口</string>
<string name="pref_ui_close_tab_anim_next_tab_desc">关闭当前窗口时切换到下一个窗口而不是上一个</string>
<string name="pref_ui_customization_desc">字体 &amp; 主题 &amp; 拓展键盘</string>
<string name="pref_ui_customization">个性化</string>
<string name="customization_settings_desc">字体,主题,拓展键盘</string>
<string name="customization_settings">个性化</string>
<string name="pref_ui_fullscreen">全屏</string>
<string name="pref_ui_hide_toolbar">隐藏标题栏</string>
<string name="pref_ui_hide_toolbar_desc">键盘显示时隐藏标题栏</string>
@ -47,7 +47,7 @@
<string name="package_details">软件包: %s\n版本: %s\n依赖: %s\n占用空间: %s\n描述: %s\n主页: %s</string>
<string name="package_list_empty">软件包列表为空,请检查你的软件源</string>
<string name="menu_refresh_list">刷新</string>
<string name="menu_update">更新 &amp; 刷新</string>
<string name="menu_update">更新 刷新</string>
<string-array name="pref_general_program_selection_entries">
<item>只使用 NeoTerm</item>
@ -63,4 +63,7 @@
<item>输入…</item>
</string-array>
<string name="pref_customization_eks">拓展键盘</string>
<string name="general_settings_desc">响铃振动Shell</string>
<string name="ui_settings_desc">全屏,标题栏,快捷键盘</string>
<string name="package_settings_desc">源,更新,升级</string>
</resources>

View File

@ -8,11 +8,12 @@
<string name="key_ui_fullscreen" translatable="false">neoterm_ui_fullscreen</string>
<string name="key_ui_hide_toolbar" translatable="false">neoterm_ui_hide_toolbar</string>
<string name="key_ui_font" translatable="false">neoterm_ui_font</string>
<string name="key_ui_color_scheme" translatable="false">neoterm_ui_color_scheme</string>
<string name="key_ui_next_tab_anim" translatable="false">neoterm_ui_next_tab_anim</string>
<string name="key_ui_suggestions" translatable="false">neoterm_ui_suggestions</string>
<string name="key_ui_wide_char_weigh_explicit" translatable="false">neoterm_ui_wide_char_explicit</string>
<string name="key_package_source" translatable="false">neoterm_package_source</string>
<string name="key_customization_font" translatable="false">neoterm_ui_font</string>
<string name="key_customization_color_scheme" translatable="false">neoterm_ui_color_scheme</string>
</resources>

View File

@ -10,8 +10,13 @@
<string name="about">About</string>
<string name="settings">Settings</string>
<string name="general_settings">General Settings</string>
<string name="general_settings_desc">Bell, Vibrate, Shell</string>
<string name="ui_settings">UI Settings</string>
<string name="ui_settings_desc">FullScreen, Title Bar, Suggestions</string>
<string name="package_settings">Package Settings</string>
<string name="package_settings_desc">Source, Updates, Upgrades</string>
<string name="customization_settings_desc">Font, ColorScheme, ExtraKeys</string>
<string name="customization_settings">Customization</string>
<string name="installer_message">Installing</string>
<string name="installer_install_zsh_manually">You may install zsh and setup suggestions by executing: ~/install-zsh.sh</string>
@ -26,8 +31,6 @@
<string name="pref_general_shell_desc">Which shell should we use when login</string>
<string name="pref_general_program_selection">Program Selection</string>
<string name="pref_general_program_selection_desc">When both Neo Term and your Android OS have a program, which one should we choose?</string>
<string name="pref_ui_customization_desc">Font &amp; ColorScheme &amp; ExtraKeys</string>
<string name="pref_ui_customization">Customization</string>
<string name="pref_ui_fullscreen">Full Screen</string>
<string name="pref_ui_hide_toolbar">Hide Toolbar</string>
<string name="pref_ui_hide_toolbar_desc">Hide toolbar when keyboard is showing</string>
@ -54,7 +57,7 @@
<string name="package_details">Package: %s\nVersion: %s\nDepends: %s\nInstalled Size: %s\nDescription: %s\nHome Page: %s</string>
<string name="package_list_empty">Package list is empty, please check out your source.</string>
<string name="menu_refresh_list">Refresh</string>
<string name="menu_update">Update &amp; Refresh</string>
<string name="menu_update">Update, Refresh</string>
<string-array name="pref_general_shell_entries" translatable="false">
<item>sh</item>

View File

@ -3,6 +3,7 @@
<Preference
android:icon="@drawable/ic_general_white_36dp"
android:summary="@string/general_settings_desc"
android:title="@string/general_settings">
<intent
android:targetClass="io.neoterm.ui.settings.GeneralSettingsActivity"
@ -11,14 +12,25 @@
<Preference
android:icon="@drawable/ic_ui_white_36dp"
android:summary="@string/ui_settings_desc"
android:title="@string/ui_settings">
<intent
android:targetClass="io.neoterm.ui.settings.UISettingsActivity"
android:targetPackage="io.neoterm" />
</Preference>
<Preference
android:icon="@drawable/ic_customization_white_36dp"
android:summary="@string/customization_settings_desc"
android:title="@string/customization_settings">
<intent
android:targetClass="io.neoterm.ui.customization.CustomizationActivity"
android:targetPackage="io.neoterm" />
</Preference>
<Preference
android:icon="@drawable/ic_apps_white_36dp"
android:summary="@string/package_settings_desc"
android:title="@string/package_settings">
<intent
android:targetClass="io.neoterm.ui.pm.PackageManagerActivity"

View File

@ -1,14 +1,5 @@
<?xml version="1.0" encoding="utf-8"?>
<PreferenceScreen xmlns:android="http://schemas.android.com/apk/res/android">
<Preference
android:summary="@string/pref_ui_customization_desc"
android:title="@string/pref_ui_customization">
<intent
android:targetClass="io.neoterm.ui.customization.CustomizationActivity"
android:targetPackage="io.neoterm" />
</Preference>
<CheckBoxPreference
android:defaultValue="false"
android:key="@string/key_ui_fullscreen"