MORTYFUL
Sunday, January 17, 2021
Wednesday, July 3, 2019
Android OpenGL ES Setting for Build up
To generate more powerful graphic effect, OpenGL ES(OpenGL for Embeded System) provides modern graphic processing api.
I will make a simple GLSurfaceView(pre-defined view class to use opengl in android) and Renderer to visualize effect only using fragment shader. Once I build this successfully, I can refer some interesting glsl codes in online like glsl sandbox or shader frog.
1. Manifest Setting
I will use gles 3.1 version. Way to checking of supported version is in developer docs.
<uses-feature android:glEsVersion="0x00030001" android:required="true" />
<application ... />
2. Custom GLSurfaceView Class
private lateinit var renderer:MyRenderer
override fun setRenderer(renderer: Renderer) {
super.setRenderer(renderer)
this.renderer = renderer as MyRenderer
}
}
3. Custom Renderer
Most of Renderer's codes are boilerplate code. Shader compile and attach processes are explained in dev docs. I will add tiny additional code.
...
private var hMouse = 0
private var hTime = 0
private var hResolution = 0
private var width = 0
private var height = 0
var mouseX : Float = 0f
var mouseY : Float = 0f
...
override fun onDrawFrame(gl: GL10?) {
...
GLES31.glClear(GLES31.GL_DEPTH_BUFFER_BIT or GLES31.GL_COLOR_BUFFER_BIT)
val time = SystemClock.uptimeMillis() % 10000L
GLES31.glUniform1f(hTime,(time/1000f))
GLES31.glUniform2f(hResolution,this.width.toFloat(),this.height.toFloat())
GLES31.glUniform2f(hMouse,-1f+(2*this.mouseX/this.width),1f-(2*this.mouseY/this.height))
GLES31.glUniformMatrix4fv(hScale,1,false, mScale,0)
...
}
override fun onSurfaceChanged(gl: GL10?, width: Int, height: Int) {
...
this.width = width
this.height = height
...
}
override fun onSurfaceCreated(gl: GL10?, config: EGLConfig?) {
...
hTime = GLES31.glGetUniformLocation(hProgram,"time")
hResolution = GLES31.glGetUniformLocation(hProgram,"resolution")
hMouse = GLES31.glGetUniformLocation(hProgram,"mouse")
...
}
Almost done. Override onTouchEvent in view class to pass the mouse location to renderer(mouseX,mouseY variables at above code).
this.renderer.mouseX = event.x
this.renderer.mouseY = event.y
return super.onTouchEvent(event)
}
4. etc
For vertex Shader, Any shape is possible. To see the fragment shader code's effect fully, use Square Shape.
And find some code in online, test and make own code.
Tuesday, June 25, 2019
Grid UI Launcher by ConstraintLayout
When we are trying to build a custom launcher, we could think about some layout options like grid, scroll view... In this post, we are implementing the grid layout by android default constraint layout.
1. Draw GuideLines
ConstraintLayout containing 5x4 grid with 6x5 guideline
Set constraint like the above picture(percent 0.2, 0.4, etc...) to each of vertical, horizontal lines.
2. Grid Element View
Make Custom Element View composed of upper-side Icon image, lower-side app name.
class AppIconView(context:Context) : View(context) {
private val paint = Paint()
private val iconDrawRegion = Rect()
private lateinit var label: String
lateinit var icon: Bitmap
lateinit var packageName: String
init{
paint.setTypeface(Typeface.create(Typeface.DEFAULT,Typeface.NORMAL))
paint.setAntiAlias(true)
}
fun setAppInfo(packageName:String, label:String ,icon:BitmapDrawable){
this.packageName = packageName
this.label = label
this.icon = icon.bitmap
}
override fun onDraw(canvas: Canvas) {
paint.textSize = width/7f
val paddingW = width/5
iconDrawRegion.set(paddingW,paddingW,width-paddingW,width-paddingW)
canvas.drawBitmap(icon,null,iconDrawRegion,paint)
val textDrawSize = paint.measureText(label)
canvas.drawText(label,(width-textDrawSize)/2f,height-(2*paint.textSize),paint)
}
Above code would make a view seems like simple and conventional launcher. For launcher's other behaviors such as drag and drop, We need some additional code that would also be covered by later post.
3. Compose Simple Activity
guideLineV = arrayOf(R.id.guide_v0,R.id.guide_v1,R.id.guide_v2,R.id.guide_v3,R.id.guide_v4)
guideLineH = arrayOf(R.id.guide_h0,R.id.guide_h1,R.id.guide_h2,R.id.guide_h3,R.id.guide_h4,R.id.guide_h5)
layout = findViewById(R.id.my_constraint_layout)
var app_count =0
val filter = Intent(Intent.ACTION_MAIN)
filter.addCategory(Intent.CATEGORY_LAUNCHER)
val allApps = packageManager.queryIntentActivities(filter, 0)
val cs = ConstraintSet()
for (info in allApps) {
val da = AppIconView(this).apply {
id = View.generateViewId()
setAppInfo(info.activityInfo.packageName, info.loadLabel(packageManager).toString() ,info.activityInfo.loadIcon(packageManager) as BitmapDrawable)
val col = app_count % 4
val row = app_count / 4
if(row>4){ // Because we didn't implement tab for multiple appPage, exceeded apps would be just skipped
break
}
apps[row][col] = da
da.col = col
da.row = row
layout.addView(da)
cs.connect(da.id,ConstraintSet.START,guideLineV[col],ConstraintSet.START)
cs.connect(da.id,ConstraintSet.END,guideLineV[col+1],ConstraintSet.START)
cs.connect(da.id,ConstraintSet.TOP,guideLineH[row],ConstraintSet.TOP)
cs.connect(da.id,ConstraintSet.BOTTOM,guideLineH[row+1],ConstraintSet.TOP)
app_count++
}
cs.applyTo(layout)
I referenced this article for getting installed apps for custom launcher. We can insert above code to oncreate method, and it's done.
4. Result
Now, Our view would be seems like below.
Friday, June 14, 2019
When you delete project in android studio by mistake
Few minutes ago, I had almost been dying after deleting my project by mistake, I tried some third-party recovery softwares. Though it had restored some files(.gitignore, .class, etc..), really most-helpful files(in my case, kotlin files) were not recovered.
Luckily, I found a solution before shutdown the android studio then it saved me to recover the complete project with all files.
If you delete a project in android studio and are still remaining the studio open, you can recover your project.
On Menubar, VCS -> Local History -> Show History.
Then window like below picture would be shown.
(Because I had deleted the project after creating new-project, In history it was recorded as EXTERNAL CHANGE)
Right-click the log, and click revert. it's done.
I hope it would save you.
Thursday, June 13, 2019
Sc create, devcon install Difference
In Window Driver, There are the pnp(plug-and-play) type drivers, and the non-pnp type drivers. When non-pnp type drivers have once installed, they would be supposed to be used continuously without uninstall. On the other hand, pnp drivers are namely for easy plug-in(out). For two different types of driver, two-ways of installing exists.
1. PNP Driver
sc create [service name] binpath=[c:\...] type=[kernel]
sc start [service name]
sc stop [service name]
Because sc command is used for creating wide-range window-services, this is Not used only for the device driver. But this is also useful for the device driver.
2. Non PNP Driver
devcon install [filename.inf] [hardware id]
Saturday, June 8, 2019
When Devcon install command failed on VM
I was missing two basic points for installing driver on virtualbox because I never experienced developing driver before.
1. Test-certificate driver could only be installed after recovery boot. ( on 32bit window it could be simple, see this )
Settings -> Update & Security -> Recovery tab -> Restart now -> Trouble Shoot ->
Advanced Options -> Startup Settings -> Restart -> F7
2. In INF file, hardware id place should be specified with real device id.
Way to call Default Launcher by Custom Launcher
It would not be guaranteed to work always properly, though it works well in my case
1. manifest example
<activity ... android:label="@string/app_name" android:name=".activities.LauncherActivity" android:theme="@style/FullscreenTheme">
<intent-filter>
<action android:name="android.intent.action.MAIN"/>
<category android:name="android.intent.category.HOME"/>
<category android:name="android.intent.category.DEFAULT"/>
</intent-filter>
</activity>
2. custom launcher code example
var launcher_list = packageManager.queryIntentActivities(Intent(Intent.ACTION_MAIN).apply { addCategory(Intent.CATEGORY_HOME) },0)
val name = ComponentName(
//expecting first element of launchers be the default
launcher_list[0].activityInfo.packageName,
launcher_list[0].activityInfo.name
)
val i = Intent(Intent.ACTION_MAIN)
i.addCategory(Intent.CATEGORY_LAUNCHER)
i.flags = Intent.FLAG_ACTIVITY_NEW_TASK or Intent.FLAG_ACTIVITY_RESET_TASK_IF_NEEDED
i.setComponent(name)
startActivity(i)
finish()
[osx command] file or folder monitoring
1. command fswatch [file or folder to monitor] | xargs -I {} echo $(date) {} >> [log file name] ...
-
When we are trying to build a custom launcher, we could think about some layout options like grid, scroll view... In this po...
-
To generate more powerful graphic effect, OpenGL ES(OpenGL for E mbeded S ystem) provides modern graphic processing api. ...