Программирование под Android

Ответить
Аватара пользователя
blackstrip
Админ
Сообщения: 1176
Зарегистрирован: Ср янв 02, 2008 1:42 pm
Откуда: Подольск
Контактная информация:

Программирование под Android

Сообщение blackstrip » Пт май 10, 2013 10:30 pm

to be continued...

Итак, охота что нибудь написать. Начать грызть этот гранит, чтобы не умереть в неведении. Хотя меня и тошнит от всего линуксоподобного, линуксорождённого, а еще от проектов с этими стопятьсоттысячами модулей, когда создаешь один пустой проект и на тебя высыпается 50 файлов в 20 папках аля "всем hello world посоны".

Допустим, у вас уже есть Android SDK, и даже вы скачали уже разные версии этих модулей, документации, инструментов, ридмифайлов и прочей чепухи, проставив галочки и дождавшись когда же Android SDK Manager закончит тупить со скачиванием.

Нужна еще одна вещь - IDE (окно с дыркой, куды текст вводить, вкладками там разными, кнопкой "запустить" и т.п.)

Беглый поиск по инету показывает, что каждый андроидофил пишет о своем, и непонятно толком как начать то, а еще он показывает, что есть несколько сред (IDE):
1) Бесплатный Eclipse - http://www.eclipse.org/downloads/
2) Бесплатная комьюнити-версия Intellij IDEA: http://www.jetbrains.com/idea/download/index.html (и там еще есть платная супер-пупер-версия)

Есть сборник от Гугла "Android SDK Bundle": уже с Elipse-ом и Android SDK внутри: http://developer.android.com/sdk/index.html . Когда вы его поставите, то (теоретически) там все будет настроено, эклипс будет знать где лежит андроид сдк и как с ним связаться. Но если, не дай бог, вы что нибудь переместите куда нибудь не туда, удалите, растащите по другим папкам - все придется настраивать вручную.

Поэтому я лучше буду пытать связку "отдельный чистый эклипс" и "отдельный чистый андроид-сдк". Только хардкор, только ручные настройки, нафиг этот бундл.

Аватара пользователя
blackstrip
Админ
Сообщения: 1176
Зарегистрирован: Ср янв 02, 2008 1:42 pm
Откуда: Подольск
Контактная информация:

Re: Программирование под Android

Сообщение blackstrip » Пт май 10, 2013 10:43 pm

Чтобы эклипс узнал что андроид есть - надо поставить туда плагин. Как это сделать - рассказывается тут http://developer.android.com/sdk/instal ... g-adt.html

1) Сначала надо скачать "Eclipse для разработчиков под мобильные устройства": http://www.eclipse.org/mobile/

2) Потом распаковать его и запустить Eclipse.exe.

3) Потом зайти в Help > Install New Software, нажать там Add (Добавить) и ввести путь "https://dl-ssl.google.com/android/eclipse/". Появятся галки - выбрать там Developers tools (NDK выбирать походу не надо, это для задротов, которые пишут под андроид в нативном коде на си) и скачать его. Потом он будет установлен.

Эклипс выдаст по окончании загрузки и установки запрос на рестарт среды - жмем Yes.

В итоге в окне нового проекта должен появиться раздел Android:
Изображение

Аватара пользователя
blackstrip
Админ
Сообщения: 1176
Зарегистрирован: Ср янв 02, 2008 1:42 pm
Откуда: Подольск
Контактная информация:

Re: Программирование под Android

Сообщение blackstrip » Сб май 11, 2013 2:07 am

Как сделать обычный проект с рисованием пикселями в полноэкранном режиме

Самый простой вариант - использовать SurfaceView как основу такого экрана.

В андроиде все очень похоже на яву (на j2me в том числе).

Гугл видимо побоялся судьбы j2me, когда все достаточно трудно и делается зачастую вручную. И поэтому гугл сделал очень много удобств для расстановки различных элементов (полей ввода, кнопок, флажков и т.п.) на экране. Каждая отображаемая форма представляет собой так называемый layout ("раскладка элементов на экране" по-русски).

И в отличии от jbuildera и j2me - андроидовский плагин ADT в эклипсе даже не мыслит себе, что я могу захотеть сделать приложение с пустым экраном и рисовать на экране пикселями.

Поэтому делаем все хирургическим путём:
1) File - New - Project, выбираем Android Application Project,
2) берем там все по минимуму типа Blank Workspace, андроид постарее типа 2.2 и т.д.
3) даже когда просили по минимум - получаем от ADT все равно туеву хучу каких то элементов, 25 видов иконок приложения для различных экранов, наш "любимый" layout в виде xml-файла и т.д.

4) Смотрим в структуру проекта. Лезем в src - имя вашего пакета - MainActivity.java. Открываем его. Там видим, подобно яве, по дефолту делается вызов super.onCreate(savedInstanceState);

а затем делается setContentView с указанием нашего layouta (на который вы можете полюбоваться в структуре проекта в папке res - layout). Вот это все я снес к чертям. Я хочу просто рисовать как в яве. Создать в runtime новый "экран" для отрисовки и рисовать на нем.

В общем, использовав кучу статей из инета я перелопатил этот код таким образом:

package com.example.tezd;

import android.os.Bundle;
import android.view.*;
import android.view.View.*;
import android.app.Activity;
import android.graphics.*;

//тут я сделал implements на несколько модулей, первый при создании активити выдаст мне ключи от рисовального движка, а второй будет передавать мне в одну из процедур нажатия на экран (клавы то у большинства андроидов нету, хотя конечно можно сделать еще и обработчик клавиатуры)

public class MainActivity extends Activity implements SurfaceHolder.Callback, OnTouchListener {

//вот наша штука, "удерживатель поверхности", который мы запомним в эту переменную
SurfaceHolder surh;
//заодно сделаем флажок - запоминали ли мы этот холдер или нет. чтоб не пытаться рисовать в null
boolean IsCreat = false;

@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
//эта забавная функция сотрет отображение заголовка окна, чтоб побольше места на экране осталось под графику
//правда строка со временем, зарядкой батареи и прочими делами все равно на экране останется
requestWindowFeature(Window.FEATURE_NO_TITLE);

//вот самая главная фича - создаем графический пиксельный родной экран типа SurfaceView
SurfaceView view = new SurfaceView(this);
//и говорим андроиду - давай показывай не layout, а наш SurfaceView
setContentView(view);
//заодно говорим чтоб события на создание, изменение и удаление SurfaceView передались нам в процедуры surfaceCreated, surfaceChanged, surfaceDestroyed
view.getHolder().addCallback(this);
//ну и заодно начинаем "слушать" что же там пользователь нажимает
view.setOnTouchListener(this);
}

@Override
public void surfaceCreated(SurfaceHolder holder) {
//ага, SurfaceView создается - запоминаем холдер и ставим флажок что у нас есть холдер
//холдер - ключ к канвасу, на котором можно рисовать
surh = holder;
IsCreat = true;
}

@Override
public void surfaceChanged(SurfaceHolder holder, int frmt, int w, int h) {

}

@Override
public void surfaceDestroyed(SurfaceHolder holder) {
//тут вырубаем флажок как только SurfaceView разрушится
IsCreat = false;
}

//это моя личная процедура, ностальгия по яве, в андроиде репаинтов никаких вроде бы не бывает, бывает invalidate зато
public void repaint() {
//если флажок стоит и мы запоминали холдер
if (IsCreat) {
//то блокируем канвас
Canvas canvas = surh.lockCanvas();
//вызываем процедуру paint, название которой - опять же всего лишь ностальгия по яве2ме, можно как хотите по другому ее назвать
paint(canvas);
//и после отрисовки на канвасе - разблокируем его и мгновенно выкидываем его содержимое на экран
surh.unlockCanvasAndPost(canvas);
}
}

//наша придуманная процедура paint - в нее приходит канвас, на котором можно рисовать
public void paint(Canvas canvas)
{
//первое что в голову пришло - рисовать на черном фоне красную линию из точки 0,0 в точку прикосновения пальца (xp, yp записываются ниже в процедуре отлова нажатий пальцем)
canvas.drawColor(Color.BLACK);
p.setColor(Color.RED);
canvas.drawLine(0, 0, xp, yp, p);
}

//это наша инфа о цвете, андроидовский плагин вежливо рекомендует объявить ее один раз, а не создавать каждый раз в процедуре paint, так и сделаем
public Paint p = new Paint();

//координаты последнего нажатия
public int xp = 0;
public int yp = 0;

//прослушиватель нажатий
public boolean onTouch(View v, MotionEvent event)
{

//получаем координаты последнего действа в "сырых" пикселях, название такое потому что, видимо, это является кошмаром для тех, кто программирует на андроиде, плавая в layout-ах и делая всё в относительных единицах, долях длины-ширины экрана и т.п. А для нас это привычно.
int x = (int)Math.floor(event.getRawX());
int y = (int)Math.floor(event.getRawY());

//если эвент это ВНИЗ
if (event.getAction()==MotionEvent.ACTION_DOWN) {
//то запоминаем координаты нажатия и вызываем перерисовку экрана
xp = x;
yp = y;
repaint();
}
//возвращаем тру, это говорит андроиду о том что мы обработали нажатие на экран, а не пропустили его.
return true;
}
}

Вот так можно сделать андроид программу, рисующую нормальными пикселями на почти что полном экране и отслеживающую нажатия на экран всего лишь в одном файле и без всяких мусорных layoutов.

Вот так она работает на экране, и даже заработала на моем старом и пыльном galaxy ace.

Изображение

Аватара пользователя
blackstrip
Админ
Сообщения: 1176
Зарегистрирован: Ср янв 02, 2008 1:42 pm
Откуда: Подольск
Контактная информация:

Re: Программирование под Android

Сообщение blackstrip » Пн май 13, 2013 9:40 pm

Еще один вариант)

Попробовал раскрыть импорты, и делать их по одному - размер apk не изменился (и не должен был, это же просто ссылки на api). Значит можно все таки через * писать импорты.

Полностью полный экран удается сделать если добавить не одну строку, а сразу две вот такие строки:
requestWindowFeature(Window.FEATURE_NO_TITLE);
getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN, WindowManager.LayoutParams.FLAG_FULLSCREEN);

На эмуляторе все ок, весь экран используется под графику. На galaxy ace тоже ок.

Функция DrawStroke рисует текст с каймой. Хотя судя по списку функций переменной типа Paint, бывает еще и встроенный в андроид stroke.

В sw и sh сохраняется доступный для рисования размер экрана. Теперь можно заниматься тем же, чем и в яве - рисовать окошки полноэкранные, самому вручную их натягивать на нужный размер экрана и т.п. =)

В surfaceChanged запишем то же, что и в created. Оно вызывается при переворачивании экрана из вертикального в горизонтальное. Проверил на galaxy ace - действительно, после переворачивания перерисовывается вертикально и посередине альбомно-ориентированного экрана, и пишет что ширина 480, а высота 320.

А setAntiAlias(true) включает сглаживание при выводе примитивов и текста с помощью конкретного paint-а. Правда из-за сглаживания кайма текста плохо видна.

При клике на экран - синий кружок отрисовывается по месту клика.

package com.example.tezd;

import android.os.Bundle;
import android.view.MotionEvent;
import android.view.SurfaceHolder;
import android.view.SurfaceView;
import android.view.View;
import android.view.View.OnTouchListener;
import android.view.Window;
import android.view.WindowManager;
import android.app.Activity;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.Paint.Align;


public class MainActivity extends Activity implements SurfaceHolder.Callback, OnTouchListener {

SurfaceHolder surh;
boolean IsCreat = false;

public int sw = 0;
public int sh = 0;

public Paint serv = new Paint();
public Paint p = new Paint();
public Paint textp = new Paint();

public int xp = -100;
public int yp = -100;

public boolean Inter3D = true;


@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
requestWindowFeature(Window.FEATURE_NO_TITLE);
getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN, WindowManager.LayoutParams.FLAG_FULLSCREEN);
SurfaceView view = new SurfaceView(this);
setContentView(view);
view.getHolder().addCallback(this);
view.setOnTouchListener(this);

}

@Override
public void surfaceCreated(SurfaceHolder holder) {

surh = holder;
Canvas canvas = surh.lockCanvas();
sw = canvas.getClipBounds().width();
sh = canvas.getClipBounds().height();
paint(canvas);
surh.unlockCanvasAndPost(canvas);
IsCreat = true;
}

@Override
public void surfaceChanged(SurfaceHolder holder, int frmt, int w, int h) {
Canvas canvas = surh.lockCanvas();
sw = canvas.getClipBounds().width();
sh = canvas.getClipBounds().height();
paint(canvas);
surh.unlockCanvasAndPost(canvas);
IsCreat = true;
}

@Override
public void surfaceDestroyed(SurfaceHolder holder) {
IsCreat = false;
}

public void repaint() {
if (IsCreat) {
Canvas canvas = surh.lockCanvas();
paint(canvas);
surh.unlockCanvasAndPost(canvas);
}
}

public void DrawStroke(Canvas c, String s, int x, int y, int siz, int col1, int col2, Align al) {
textp.setAntiAlias(true);
textp.setColor(col2);
textp.setTextSize(siz);
textp.setTextAlign(al);
c.drawText(s, x+1, y, textp);
c.drawText(s, x-1, y, textp);
c.drawText(s, x, y+1, textp);
c.drawText(s, x, y-1, textp);
textp.setColor(col1);
c.drawText(s, x, y, textp);
}

public void paint(Canvas canvas)
{
canvas.drawColor(Color.BLACK);
DrawStroke(canvas,"Android",sw/2,100,40,Color.rgb(240,180,0),Color.rgb(200,140,0),Align.CENTER);
DrawStroke(canvas,"Ширина экрана: "+String.valueOf(sw)+" пкс",sw/2,140,30,Color.rgb(240,180,0),Color.rgb(200,140,0),Align.CENTER);
DrawStroke(canvas,"Высота экрана: "+String.valueOf(sh)+" пкс",sw/2,180,30,Color.rgb(240,180,0),Color.rgb(200,140,0),Align.CENTER);
p.setAntiAlias(true);
p.setColor(Color.rgb(0,128,255));
canvas.drawCircle(xp, yp, 20, p);
}

public boolean onTouch(View v, MotionEvent event)
{

int x = (int)Math.floor(event.getRawX());
int y = (int)Math.floor(event.getRawY());

if (event.getAction()==MotionEvent.ACTION_DOWN) {
xp = x;
yp = y;
repaint();
}

return true;

}



}


Изображение

Phantom
Обсуждатель
Сообщения: 179
Зарегистрирован: Сб янв 05, 2008 12:01 pm
Контактная информация:

Re: Программирование под Android

Сообщение Phantom » Ср июн 26, 2013 4:12 am

Я пытался сделать на андроид программу-бот, которая могла бы через браузерный компонент лазить по сайтам и делать всякие интересные, полезные или вредные вещи. Логика боту писалась на JavaScript. Но столкнулся с проблемой того, что андроид может грохнуть любую активити в произвольный момент времени, а в сервисе WebViewы всякие не работают как надо. Короче говоря, бот через некоторое время как бы "засыпал" и переставал делать что-либо. А я даже научил прогу при установке делать ассоциацию файлов с составным расширением *.bot.html, чтобы они запускались при клике на них. В итоге забил и к программированию на андроид пока больше не притрагивался. Упоротых вещей в нём хватает с головой. В J2me по крайней мере можно исповедовать свою философию при подходе к созданию приложений, а андроид принуждает к своей.

rus084
Новичок
Сообщения: 11
Зарегистрирован: Ср июл 14, 2010 10:13 am

Re: Программирование под Android

Сообщение rus084 » Вс ноя 30, 2014 7:27 am

я совершенно не знаю java но умею c/c++

у меня появилась идея :
будет ли работать arm-linux программа , которая пишет напрямик в frame buffer и читает из /dev/input ?

rus084
Новичок
Сообщения: 11
Зарегистрирован: Ср июл 14, 2010 10:13 am

Re: Программирование под Android

Сообщение rus084 » Вс ноя 30, 2014 10:59 pm

начал учить яву , но образовалась проблема :
eclipse для разработки андроид программ потребляет слишком много памяти , не для моих 2gb ram . эмулятор грузится 5 минут и не догружается до конца

Аватара пользователя
blackstrip
Админ
Сообщения: 1176
Зарегистрирован: Ср янв 02, 2008 1:42 pm
Откуда: Подольск
Контактная информация:

Re: Программирование под Android

Сообщение blackstrip » Ср дек 10, 2014 1:23 pm

rus084 писал(а):начал учить яву , но образовалась проблема :
eclipse для разработки андроид программ потребляет слишком много памяти , не для моих 2gb ram . эмулятор грузится 5 минут и не догружается до конца
Если эмуль слишком жирен для компьютера, то есть геморный вариант - отлаживать на устройстве. Я под телефон так отлаживал когда перестал верить эмулям, каждый билд закидывал на телефон, устанавливал и вручную проверял то что только что написал. Но так можно делать когда программа разрослась уже. Я когда только учишься, то конечно по минуте тратить на каждую загрузку/установку/проверку и понимать что опять что-то не работает (и непонятно что, ибо мобила не покажет где слетело, только если много try catch ставить в разные места и выводить сообщения об ошибках и о состоянии разных переменных в момент краша на экран проги самому).

Ответить

Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и 5 гостей