├── .gitignore ├── res ├── drawable-xhdpi │ └── icon.png └── layout │ └── activity_main.xml ├── README.md ├── src └── pl │ └── czak │ └── handbuilt │ └── MainActivity.java ├── AndroidManifest.xml └── Makefile /.gitignore: -------------------------------------------------------------------------------- 1 | build 2 | -------------------------------------------------------------------------------- /res/drawable-xhdpi/icon.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/czak/handbuilt-android-project/HEAD/res/drawable-xhdpi/icon.png -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # handbuilt-android-project 2 | 3 | This is a companion project to my blog post [Jack, Jill & building Android apps by hand](http://czak.pl/2016/05/31/handbuilt-android-project.html). 4 | 5 | I'm exploring building an Android app "by hand" (i.e. without and IDE or Gradle even). 6 | 7 | For the tl;dr version, see the [Makefile](Makefile) 8 | -------------------------------------------------------------------------------- /res/layout/activity_main.xml: -------------------------------------------------------------------------------- 1 | 2 | 5 | 6 | 11 | 12 | 13 | -------------------------------------------------------------------------------- /src/pl/czak/handbuilt/MainActivity.java: -------------------------------------------------------------------------------- 1 | package pl.czak.handbuilt; 2 | 3 | import android.app.Activity; 4 | import android.os.Bundle; 5 | import android.widget.ImageView; 6 | 7 | import com.squareup.picasso.Picasso; 8 | 9 | public class MainActivity extends Activity 10 | { 11 | @Override 12 | public void onCreate(Bundle savedInstanceState) { 13 | super.onCreate(savedInstanceState); 14 | setContentView(R.layout.activity_main); 15 | 16 | ImageView imageView = (ImageView) findViewById(R.id.image); 17 | Picasso.with(this).load("http://i.imgur.com/DvpvklR.png").into(imageView); 18 | } 19 | } 20 | -------------------------------------------------------------------------------- /AndroidManifest.xml: -------------------------------------------------------------------------------- 1 | 2 | 4 | 5 | 7 | 8 | 9 | 10 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | -------------------------------------------------------------------------------- /Makefile: -------------------------------------------------------------------------------- 1 | # Environment variables 2 | ANDROID_HOME ?= 3 | 4 | # Build tools & SDK versions 5 | build_tools := 24.0.0-preview 6 | target := android-n 7 | 8 | # Variables 9 | project := handbuilt 10 | package := pl.czak.handbuilt 11 | 12 | src_dir := src 13 | res_dir := res 14 | 15 | lib_dir := build/libraries 16 | gen_dir := build/generated 17 | int_dir := build/intermediate 18 | out_dir := build/output 19 | 20 | sources := $(shell find $(src_dir) -name '*.java') 21 | resources := $(shell find $(res_dir) -type f) 22 | generated := $(gen_dir)/pl/czak/handbuilt/R.java 23 | libraries := $(lib_dir)/com/squareup/picasso/picasso/2.5.2/picasso-2.5.2.jar 24 | 25 | # Final zipaligned APK 26 | $(out_dir)/$(project).apk: $(out_dir)/$(project)-unaligned.apk 27 | @echo -n Zipaligning... 28 | @zipalign -f 4 $< $@ 29 | @echo Done. 30 | 31 | # Packaging the APK 32 | $(out_dir)/$(project)-unaligned.apk: $(out_dir) AndroidManifest.xml $(resources) $(int_dir)/classes.dex 33 | @echo -n Packaging... 34 | @aapt package -f \ 35 | -M AndroidManifest.xml \ 36 | -I $(ANDROID_HOME)/platforms/$(target)/android.jar \ 37 | -S $(res_dir) \ 38 | -F $@ 39 | @cd $(int_dir) && aapt add $(abspath $@) classes.dex > /dev/null 40 | @echo Done. 41 | @echo -n Signing the APK... 42 | @jarsigner -verbose \ 43 | -keystore ~/.android/debug.keystore \ 44 | -storepass android \ 45 | -keypass android \ 46 | $@ \ 47 | androiddebugkey \ 48 | > /dev/null 49 | @echo Done. 50 | 51 | # Compilation & dexing w/ Jack 52 | $(int_dir)/classes.dex: $(int_dir) $(sources) $(generated) $(libraries) 53 | @echo -n Compiling with Jack... 54 | @java -jar $(ANDROID_HOME)/build-tools/$(build_tools)/jack.jar \ 55 | --classpath $(ANDROID_HOME)/platforms/$(target)/android.jar \ 56 | $(foreach lib,$(libraries),--import $(lib)) \ 57 | --output-dex $(int_dir) \ 58 | $(sources) $(generated) 59 | @echo Done. 60 | 61 | # Generating R.java based on the manifest and resources 62 | $(generated): $(gen_dir) AndroidManifest.xml $(resources) 63 | @echo -n Generating R.java... 64 | @aapt package -f \ 65 | -M AndroidManifest.xml \ 66 | -I $(ANDROID_HOME)/platforms/$(target)/android.jar \ 67 | -S $(res_dir) \ 68 | -J $(gen_dir) \ 69 | -m 70 | @echo Done. 71 | 72 | # Fetching dependencies from Maven Central 73 | $(libraries): 74 | @echo -n Fetching dependency $(notdir $@)... 75 | @curl --silent \ 76 | --location \ 77 | --output $@ \ 78 | --create-dirs \ 79 | http://search.maven.org/remotecontent?filepath=$(subst $(lib_dir)/,,$@) 80 | @echo Done. 81 | 82 | # Subfolders in build/ 83 | $(gen_dir) $(out_dir) $(int_dir): 84 | @mkdir -p $@ 85 | 86 | .PHONY: clean 87 | clean: 88 | rm -rf build 89 | 90 | .PHONY: install 91 | install: $(out_dir)/$(project).apk 92 | adb install -r $< 93 | 94 | .PHONY: uninstall 95 | uninstall: 96 | adb uninstall $(package) 97 | 98 | .PHONY: run 99 | run: 100 | adb shell am start $(package)/.MainActivity 101 | --------------------------------------------------------------------------------