5 апреля 2011 г.

Сдаем лампу Аладина в утиль

Сделаем Санкт-Петербург чище будем сдавать отработавшие люминесцентные - галогенные - энергосберегающие лампы на утилизацию, а не в мусорный бак, как обычно.
ГУП "ЭКОСТРОЙ" в городе Санкт-Петербург по адресу  В.О. 13-я линия д. 22 принимает на утилизацию отработанные энергосберегающие лампы.
Так же туда можно сдать:

  1. градусники;
  2. таблетки - лекарства (кому уже не нужно).

Подробнее по ссылке на оф. сайт
Так же http://www.infoeco.ru/

16 марта 2011 г.

Размещаем номер телефона на странице

Продолжаю исследование возможностей браузеров на Webkit (предыдущая заметка про gps). На этот раз в поле зрения попала полезная вещь  - мобильный браузер (опыты ставились на Androidе) способен распознавать и преобразовывать в активную ссылку номера телефонов на странице.
Коммерческому сайту это может помочь в выколачивании денег повышении юзабилити сайта.
Как оформить номер телефона, так чтоб он светился, когда к нему подводили палец -
элементарно, просто грамотно его записать:
(904)620 2095 или 962-6182095 или 904-618-2094 и или (904) 618 2094

Чтобы отключить авто распознавание номера телефона на странице в браузере в хедере страницы нужно указать:
<meta name="format-detection" content="telephone=no">Syhi-подсветка кода
П. С. Подключить к делу можно и гипперссылки:
<a href="tel:1234567">XXX</a>
<a href="sms:1232334">XXX</a>Syhi-подсветка кода

11 марта 2011 г.

Пишем Web App c использованием html5 под Android

И так оглянемся и посмотрим что в наличие - Android аппарат: LG Optimus One (P500)  с Android 2.2 на борту.
И мы хотим нетолько быть потребителем чужих программок для имеющегося Android аппарата, но и творцом. Для этого у нас есть
Потенциальная возможность кодить на Java
Теоретическая (на данный момент теоретическая) возможность кодить на ruby (Ruboto) и др.
Возможность сверстать страничку для браузера с использованием html5.

В данном посте будет сверстана страница, которая будет представлять собой одностраничнное веб приложение позволяющее определять положение по сигналам gps. Данное приложение будет полностью построено на html5+css3+javascript и продемонстрирует возможность создания клиентских приложений для android на веб технологиях.
Почему я указал модель телефона — во первых только на этом телефоне проверялась работоспособность  и потому что возможности приложений будут дрейфовать от модели к модели телефона (хотя можно и найти компромисс между ними).

План мероприятий:
Особенность запуска страницы с SD карты
Принимаем сигнал gps на странице
Верстаем итоговую страницу


Особенность запуска страницы с SD карты
Стоить отметить, что этот пункт встанет ребром, когда понадобится запустить созданное приложение на аппарате. Страницу можно загрузить на хостинг, но можно разместить в папке  в корне SD-карты и потом  просто сделать закладку в браузере на эту страницу.
Допустим мы создаем в корне SD карты папку html5 а в нем файл index.html (html5/index.html)
Тогда, чтобы запустить эту страницу в адресной строке необходимо набрать: content://com.android.htmlfileprovider/sdcard/html5/index.html

Принимаем сигнал gps на странице
Одна из возможностей html5 — определять текущие координаты при помощи gps приемника.  Работоспособность проверялась только на LG Optimus One/ Android 2.2.
 Привожу пример реализующий функционал (gpsListener.js):

function gpsListener(){
       if(navigator.geolocation==undefined) return false;//
        else return true;//Браузер поддерживает работу с gps
}
with(gpsListener){
        //получаем сигнал
        prototype.turnOn= function(successCallback, errorCallback){
                if (this.watchId==undefined){
                        successCallback = successCallback || function(){};
                        errorCallback = errorCallback || function(){};
                        try {
                                function handleSuccess(position) {
                                successCallback(position);
                                }
                                this.watchId=navigator.geolocation.watchPosition(handleSuccess, errorCallback, {
                                        enableHighAccuracy: true,
                                        maximumAge: 10000, // 10 сек.
                                        timeout:1000
                                });
                       
                        }catch(err){
                                errorCallback(err);
                        }
                }
        }
        prototype.turnOff=function(endCallback){
                endCallback=endCallback||function(){};
                if (this.watchId > 0) {
                        navigator.geolocation.clearWatch(this.watchId);
                        endCallback();
                        this.watchId=undefined;
                }
               

        }
}

//Получаем размер доступной области экрана
function androidWindowSize(){
        if(screen){
                var landscapeOrPortrait
                //landscape=true; portrait=false;
                if (screen.width>screen.height) landscapeOrPortrait=true;
                else landscapeOrPortrait=false;
                return {width:screen.width, height:screen.height, orientation:landscapeOrPortrait };
        }
        else return undefined;// машинка видимо не андроид
}Syhi-подсветка кода

Верстаем итоговую страницу.
Ключевые моменты на которые следует обратить внимание будут отмечены в коде комментариями.
Код представлен на github в папке simple-gps

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

14 февраля 2011 г.

Silverlght: Бадания с Canvas

Простая задача. Необходимо на странице разместить в экземпляре ScrollViewer разместить  Canavas, а в нем уже изображение, TextBox или что-то еще. Делалось с той целью, чтобы получился такой объект в него можно было добавлять новые компоненты (помимо Image или TextBox), а он при этом растягивался и оставлял для доступа «ползунок” . Зараза Canvas, совсем не так работает как предполагалось. Скриншот тогда не сделал, поэтому не могу продемонстрировать — все содержимое обрезалось по фактическому размеру ScrollViewer (полоса прокрутки не потребовалась).
Озарение: Canvas не определяет свой размер по размеру дочернего элемента.
Второй целью этой задачи было создать компонент, который сможет не только справится с выше озвученной проблемой, но и сможет принимать новые параметры. Понятным языком — необходимо сделать доступным в xaml разметке компонента пользовательские свойства, через которые можно передавать параметры новому компоненту.
Озарение: Для создания пользовательских свойств компонента, доступных в xaml разметки необходимо использовать объект   свойств зависимостей public static readonly DependencyProperty.
 И так, постановка задачи:
1) Любой ценой разместить Canvas в ScrollViewer;
2) Реализовать эту задачу, как чисто в xaml так и чисто в C# (создав компонент)
3) Привести пример использование DependencyProperty

Замечание: Добавлять Canvas в ScrollViewer напрямую не удастся, вместо этого в ScrollViewer будет вложен Grid, в нем что угодно, в том числе Canvas. Все прочее что необходимо будет добавить добавляем в Grid:
Реализация на xaml:
<ScrollViewer HorizontalScrollBarVisibility="Auto"  Width="auto" Height="auto" Grid.Column="0" Grid.Row="1">
    <ScrollViewer.Content>
        <!-- Объект Canvas вложенный В объект ScrollViewer примет размер Scroll viewer и не будет учитывать
        рамер объектов размещенных в  Canvasе!! - поэтому используется Grid, а в нем Canvas -->

        <Grid Width="auto" Height="auto" >
            <!-- Смастерим просмотрщик: Размер Gridа будет под размер изображения-->
            <Image x:Name="loadedImage" Width="auto" Height="auto">
               <Image.RenderTransform>
               <CompositeTransform ScaleX="1" ScaleY="1"/><!-- Задел для масштабирования-->
               </Image.RenderTransform>
               </Image>
            <!-- Если не все дочерние эл-ты в Grid разместить в одной ячейки то они могут идти как два слоя  -->
               <Canvas Background="Transparent" >
               <!-- Поверх Image будет прозрачный Холст, а на нем кнопка (можно заменить на что, нибудь другое) -->
                <Button Content="It s Canvas" Canvas.Left="100" Canvas.Top="100"/>
              <!-- Вообщим Canvas будет такого-же размера как и  Image -->
            </Canvas>
        </Grid>
    </ScrollViewer.Content>
</ScrollViewer>Syhi-подсветка кода
Реализация компонента на C#:
// Небольшой класс реализующий возможность простых манипуляций изображений
// В данном случае возможность просмотра изображения превышающего размер окна
public class ImageManipulate : ContentControl
{
    // Добавляем произвольное свойство к создаваемому компоненту - исходное изображение
    public static readonly DependencyProperty SourceProperty =
        DependencyProperty.Register("Source", typeof(Image),typeof(ImageManipulate), null);
    //Дополнительное свойство позволяющее принимать canvas как параметр в xaml разметке
    public static readonly DependencyProperty CanvasInsideProperty =
        DependencyProperty.Register("CanvasInside", typeof(Canvas), typeof(ImageManipulate), null);
    private double _imageWidth;     // Ширина оригинального изображения
    private double _imageHeight;    // Высота оригинального изображения
    private Image _image;           // Изображение для возможных манипуляций
    private ScrollViewer viewerBox;
    private Grid mainGridContainer;
        //Свойство которое и осуществляет прием  и передачу изображения
    public Image Source
    {
                get { return (Image)GetValue(SourceProperty); }
        set
            {
            SetValue(SourceProperty, value);
            _image = value;//Кэшируем изображение
            _imageWidth = _image.Width;
            _imageHeight = _image.Height;
            this.mainGridContainer.Children.Add(this._image);//Добавляем изображение в Grid
            }
    }
    public Canvas CanvasInside
    {
        get { return (Canvas)GetValue(CanvasInsideProperty); }
        set
        {
            SetValue(CanvasInsideProperty, value);
            this.mainGridContainer.Children.Add(value);
        }
    }
    public ImageManipulate()
    {
        this.mainGridContainer = new Grid();
        viewerBox = new ScrollViewer() { HorizontalScrollBarVisibility = ScrollBarVisibility.Auto };
        viewerBox.Content = this.mainGridContainer;// Создаем объект контейнера с "ползунками" и добаляем в него Грид
        this.Content = viewerBox;
    }
}Syhi-подсветка кода
Его ре инкарнация в xaml разметке:
<!-- xmlns:local="clr-namespace:FotoDocDemo1;assembly=FotoDocDemo1" - ссылаемся на пространство имен
в котором находится класс ImageManipulate-->

<local:ImageManipulate Grid.Row="1" Width="auto" Height="auto">
        <!-- Свойство Source: -->
    <local:ImageManipulate.Source>
        <Image Source="img/avstria.jpg" Width="auto" Height="auto"/>
    </local:ImageManipulate.Source>
        <!-- Свойство CanvasInside-->
    <local:ImageManipulate.CanvasInside>
        <Canvas Width="auto" Height="auto">
            <Button Content="Click" Canvas.Left="200" Canvas.Top="200"/>
        </Canvas>
</local:ImageManipulate.CanvasInside>
</local:ImageManipulate>Syhi-подсветка кода

10 февраля 2011 г.

Задача "Восемь Ферзей"

Matraska продолжает изучать алгоритмические задачи. На этот раз задача будет о Восьми ферзях (см. WikiPedia).
Эта задача, да и все подобные полезны тем, что позволяют отточить навыки кодинга, здорово поломать голову, и конечно научится новому.
Так на примере этой задачи небезызвестный автор этого труда познал приемы работы с двумерными массивами (до этого как то не доходили руки), почесал репу и не смог найти другого  алгоритма решения этой задачи, кроме как метода подбора... И в правду задача немного сложнее, а написанный на ruby код немного объемнее, чем реализации этой задачи  других авторов на C, Basic и прочих языках, которые удалось найти при не продолжительном поиске по Гуглю.
class Eight_ferz
  attr_reader :chease_board
  def initialize()
    #Создаем многомерный массив
    @chease_board = Array.new(8)
    @chease_board.map! { Array.new(8,0) }# Инициализируем массив 0-ми
  end
 #Метод демонстрирующий всю доску
  def show_board
    @chease_board.each do |row|
      p row
    end
  end
  # Метод устанавливающий фигуру на шахматной доске
  # n- номер строки, m - номер столбца
  def set_figure(n,m)
    # Устанавливаем 1 (замораживаем точки) по ортогональным линиям шахмотной доски
    (0..7).each{|index| @chease_board[n][index]=@chease_board[index][m]=1}
    # Рассматриваем 4 ю четверть СК(центр СК точка n,m)
    n4,m4=n,m
    #puts("n: #{n4}, m: #{m4}")
    while (n4<8&&m4<8)
      @chease_board[n4][m4]=1
      n4+=1;
      m4+=1
      #puts("n: #{n4}, m: #{m4}")
    end
    n1,m1=n,m
    while(n1>=0&&m1<8)
      @chease_board[n1][m1]=1
      n1-=1;
      m1+=1
    end
    n2,m2=n,m
    while(n2>=0&&m2>=0)
      @chease_board[n2][m2]=1
      n2-=1
      m2-=1
    end
    n3,m3=n,m
    while(n3<8&&m3>=0)
      @chease_board[n3][m3]=1
      n3+=1
      m3-=1
    end
    @chease_board[n][m]=2;
  end
  def free_positions()
    free_pos=Array.new()
    # Перебираем все позиции, если равен 0 в массив
    (0..7).each do|n|
      (0..7).each do |m|
        if @chease_board[n][m]==0
          #puts("N[#{n}], M[#{m}]")
          free_pos<<[n,m]
        end
      end
    end
    # В качестве ответа метода выводим координаты выбранной точки и кол-во свободных позиций
    if free_pos.size>0
      free_pos[rand(free_pos.size-1)]<<free_pos.size
    else
      nil
    end
   
  end
  # Решение методом перебора(может заполнить доску 5-8 ферзями!)
  def start
  count=0
  current_position=self.free_positions()# получаем координаты позицию на которую можно поставить ферзя
    while (!current_position.nil?)
      self.set_figure(current_position[0],current_position[1]) # устанавливаем ферзя
      current_position=self.free_positions() #
      count+=1
    end
  puts("Count #{count}")
  end
endSyhi-подсветка кода
Пример вызова (может быть от 5-до 8 ферзей!):

obj1=Eight_ferz.new()
obj1.start
obj1.show_board

5 февраля 2011 г.

Задача «Треугольник Пифагора»

Ну или оригинальное название (http://habrahabr.ru/blogs/python/111898/) - «Double Squares»
Эта задача из Hacker Cup Qualification Round, очень нравится :
Matraska хочет участвовать в Facebook Hacker Cup 2011 (хоть и заочно) и заодно представить решение этой задачи на ruby ибо python-ом автор опуса не орудует, в отличие от авторов оригинальной статьи (ссылка была в начале абзаца).
Автор (Matraska пр. ред.) позволил себе назвать эту задачу, казалось бы таким уже «истертым» названием, потому что увидел в ней скрытый смысл, о котором будет написано далее. А все скрытое неприменно привлекает внимание и побуждает к действию.
И так текст задачи:
«Найти число представлений целого числа в виде суммы двух полных квадратов целых. Диапазон входящих чисел от нуля до 2147483647.»
Рассмотрим задачу на двух пальцах. Пусть  имеется коллекция целых  неотрицательных чисел m; 0, 2, 67 и т. д. и необходимо определить  для каждого числа количество возможных комбинаций вида
c^2=b^2+a^2,
где с, b и а целые положительные числа.
Почему Пифагора — потому что если обозначить c,  a и b как стороны прямоугольного треугольника, то  c будет гипотенузой, a и b — катетами.
Представляю код:
class Pifagor
  # Метод, который возращает корень входного числа если оно имеет целый корень и nil если иначе
  def simple?(input_number)
    # Dy=number -round(sqrt(number))^2
    dy=input_number- Math.sqrt(input_number).floor**2
    dy==0?Math.sqrt(input_number):nil
  end
  def work(number) #number - то число которое раскладываем
    a_limit=self.simple?(number)
    b_limit=0 # a_limit, b_limit определяют диапазон значений a и b для перебора
    i=0 #кол-во комбинаций
    if !a_limit.nil?
      (0..a_limit).each do|a|
        (0..b_limit).each do |b|
          if(a**2+b**2)==number
            puts("a: #{a}, b: #{b}")
            i+=1
          end
        end
        b_limit+=1# Делаем нижне треугольная матрицу [a_limit x b_limit]
      end
    end
    puts("Number: #{i}")
  end
endSyhi-подсветка кода
Здесь задачу решаем перебором, перебираем в двух циклах от 0 до round(sqrt(c^2) )
Пример вызова:
Pifagor.new.work(25)

25 января 2011 г.

Кирилица в проектах ruby NetBeans

Кратко, суть проблемы:
В проекте Ruby IDE Netbeans  под Windows не отображается кирилица. В то время, как с NetBeans под Убунтой такого небыло - кирилица выводилась без каких-либо проблем.
Решение - необходима настройка проекта ruby:
[окошко "Projects"]=>ПКМ на [названии вашего проекта]=>[Properties]=>[Sources] в открывшемся окне, слева=>[Encoding]выпадающее меню в самом низу=>выбрать интересующую кодировку. Я выбрал Windows-1251.
Перезапуск NetBeans. Все.