Часть 1. Пишем компоненту работы с графикой на Delphi.
Для работы с графикой решено использовать внешнюю компоненту, т.к возможности 1С в этом ограничены.
Открываем старый и добрый Дельфи 7, и создаем новый проект.
Переходим на вкладку ActiveX и выбираем ActiveX Form
Вводим имя ActiveX
Для хранения изображений колоды карт будем использовать компонент TImage. Кидаем его на форму.
и загружаем в TImage колоду карт найденную в интернете:
Отображать карты будем на канве формы, предварительно вырезав нужную из TImage. Поэтому, чтобы TImage не светилось - прячем его. Для этого свойство Visible у TImage ставим в False.
Теперь опишем методы работы с изображением. Их будет два:
1. Отображение на канве формы нужной игральной карты.
2. Очистка самой канвы.
Открываем Type Library
И добавляем 2 метода: AddCard и ClearCanvas
у метода AddCard вводим параметры: x,y - это координаты отображения карты. row, column - это номер игральной карты из загруженного нами изображения. Например 0 ряд 2 карта.
Опишем реализацию методов в модуле:
//вырезаем и отображаем на канве нужную нам игральную карту
procedure Tw0rm21.AddCard(x, y, row, colimn: Integer);
const
h=215; //высота карты
w=148; //длина карты
begin
Canvas.CopyRect(Rect(x, y, x+w, y+h), Image1.Canvas, Rect(colimn*w ,row*h, (colimn*w)+w, (row*h)+h));
end;
//Очищаем канву
procedure Tw0rm21.ClearCanvas;
begin
InvalidateRect(0, nil, true);
end;
На этом реализация компоненты закончена. Вы можете ее в дальнейшем доработать как вам нужно.
Осталось только зарегистировать компоненту.
2. Реализуем игровую логику на 1С
Создаем внешнюю обработку. На форму обработки размещаем наш компонент:
Располагаем контролы (кнопки, надписи) на форме:
И описываем реализацию логики игры:
Перем КолодаКарт, ОбщийСчетИгрок, ОбщийСчетПК;
Перем ИгрокX, ИгрокY, КомпX, КомпY, ШагКарты;
Перем карта1ПК, карта2ПК;
Перем СтоимостьКарт;
Процедура КнопкаВыполнитьНажатие(Кнопка)
Колонка = ПолучитьСлучайноеЧисло(0, 12);
Ряд = ПолучитьСлучайноеЧисло(0, 3);
ЭлементыФормы.ЭлементУправления1.AddCard(1,1, Ряд, Колонка);
КонецПроцедуры
Функция ПолучитьСлучайноеЧисло(Мин,Макс)
//вместо Randomize
Для н = 1 По 100 Цикл
Уник = Новый УникальныйИдентификатор;
КонецЦикла;
//генерируем GUID
Уник = СокрЛП(Новый УникальныйИдентификатор);
//оставляем только цифры
Уник = СтрЗаменить(Уник,"-","");
Уник = СтрЗаменить(Уник,"a","");
Уник = СтрЗаменить(Уник,"b","");
Уник = СтрЗаменить(Уник,"c","");
Уник = СтрЗаменить(Уник,"d","");
Уник = СтрЗаменить(Уник,"e","");
Уник = СтрЗаменить(Уник,"f","");
//знаменатель должен иметь такое же количество нулей + 1
Знаменатель = 10;
Для н = 2 По (СтрДлина(СтрЗаменить(Уник,Символы.НПП,""))) Цикл
Знаменатель = Знаменатель * 10;
КонецЦикла;
Случ = Число(Уник) / Знаменатель; //здесь получается дробное случайное число от 0 до 1
//преобразуем его в случайное число из заданного интервала, округляем до целого
ЧислоИзИнтервала = Мин(Макс(Окр(Мин + (Макс-Мин)*Случ),Мин),Макс);
Возврат ЧислоИзИнтервала;
КонецФункции
Процедура РаздатьКартыНажатие(Элемент)
СтоимостьКарт = "11;2;3;4;5;6;7;8;9;10;2;3;4";
СтоимостьКарт = СтрЗаменить(СтоимостьКарт, ";", Символы.ПС);
ЭлементыФормы.ЭлементУправления1.ClearCanvas();
ИнициализоватьКолоду();
СчетИгрок = 0;
СчетПК = 0;
ИгрокX = 2; ИгрокY = 3;
КомпX = 2; КомпY = 500;
Шагкарты = 180;
карта1ПК = Неопределено;
карта2ПК = Неопределено;
карта1Игрок =ПолучитьКарту();
карта2Игрок =ПолучитьКарту();
СчетИгрок = СчетИгрок + карта1Игрок.Стоимость;
СчетИгрок = СчетИгрок + карта2Игрок.Стоимость;
ЭлементыФормы.ЭлементУправления1.AddCard(ИгрокX, ИгрокY, карта1Игрок.Ряд, карта1Игрок.Колонка);
ИгрокX = ИгрокX + Шагкарты;
ЭлементыФормы.ЭлементУправления1.AddCard(ИгрокX, ИгрокY, карта2Игрок.Ряд, карта2Игрок.Колонка);
карта1ПК =ПолучитьКарту();
карта2ПК =ПолучитьКарту();
ЭлементыФормы.ЭлементУправления1.AddCard(КомпX, КомпY, 4, 2);
КомпX = КомпX + Шагкарты;
ЭлементыФормы.ЭлементУправления1.AddCard(КомпX, КомпY, 4, 2);
КомпX = 2;
ОбновитьФорму(Ложь, Истина, Истина);
Если СчетИгрок = 21 Тогда
Предупреждение("У ВАС ОЧКО! Вы победили!");
ОбщийИгрок = ОбщийИгрок + 1;
ОбновитьФорму(Истина, Ложь, Ложь);
Возврат;
КонецЕсли;
Если СчетИгрок = 22 Тогда
Предупреждение("У ВАС ЗОЛОТОЙ! Вы победили!");
ОбщийИгрок = ОбщийИгрок + 1;
ОбновитьФорму(Истина, Ложь, Ложь);
Возврат;
КонецЕсли;
КонецПроцедуры
Процедура ИнициализоватьКолоду()
Колонка = 13;
Строк = 4;
КолодаКарт = Новый Массив(Строк, Колонка);
Для а = 0 по Строк-1 Цикл
Для б = 0 по Колонка-1 Цикл
КолодаКарт[а][б] = 0;
КонецЦикла;
КонецЦикла;
КонецПроцедуры
Функция ПолучитьКарту()
Карта = Новый Структура;
КартаНайдена = Ложь;
Пока КартаНайдена = Ложь Цикл
Колонка = ПолучитьСлучайноеЧисло(0, 12);
Ряд = ПолучитьСлучайноеЧисло(0, 3);
Если КолодаКарт[Ряд][Колонка] = 0 Тогда
Карта.Вставить("Ряд", Ряд);
Карта.Вставить("Колонка", Колонка);
Стоимость = СтрПолучитьСтроку(СтоимостьКарт, Колонка+1);
Карта.Вставить("Стоимость", Число(Стоимость));
//Сообщить(Стоимость);
КолодаКарт[Ряд][Колонка] = 1;
КартаНайдена = Истина;
КонецЕсли;
КонецЦикла;
Возврат(Карта);
КонецФункции
Процедура ВзятьКартуНажатие(Элемент)
ИгрокX = ИгрокX + Шагкарты;
карта = ПолучитьКарту();
ЭлементыФормы.ЭлементУправления1.AddCard(ИгрокX, ИгрокY, карта.Ряд, карта.Колонка);
СчетИгрок = СчетИгрок + карта.Стоимость;
Если СчетИгрок > 21 Тогда
Предупреждение("У ВАС ПЕРЕБОР! Вы проиграли!");
ОбщийПК = ОбщийПК + 1;
ОбновитьФорму(Истина, Ложь, Ложь);
КонецЕсли;
КонецПроцедуры
Процедура ХватитНажатие(Элемент)
ОбновитьФорму(Ложь, Ложь, Ложь);
Пауза(2);
ЭлементыФормы.ЭлементУправления1.AddCard(КомпX, КомпY, карта1ПК.Ряд, карта1ПК.Колонка);
СчетПК = СчетПК + карта1ПК.Стоимость;
Пауза(2);
КомпX = КомпX + Шагкарты;
ЭлементыФормы.ЭлементУправления1.AddCard(КомпX, КомпY, карта2ПК.Ряд, карта2ПК.Колонка);
СчетПК = СчетПК + карта2ПК.Стоимость;
Если СчетПК = 22 Тогда
Предупреждение("У Меня ЗОЛОТОЙ! Я Победил!");
ОбщийИгрок = ОбщийИгрок + 1;
ОбновитьФорму(Истина, Ложь, Ложь);
Возврат;
КонецЕсли;
Пока СчетПК < 17 Цикл
Пауза(2);
КомпX = КомпX + Шагкарты;
картаПК =ПолучитьКарту();
ЭлементыФормы.ЭлементУправления1.AddCard(КомпX, КомпY, картаПК.Ряд, картаПК.Колонка);
СчетПК = СчетПК + картаПК.Стоимость;
КонецЦикла;
ОбновитьФорму(Истина, Ложь, Ложь);
Если СчетПК > 21 Тогда
Предупреждение("У меня перебор! ВЫ ВЫЙГРАЛИ!");
ОбщийИгрок = ОбщийИгрок + 1;
Возврат;
КонецЕсли;
Если СчетПК = 21 Тогда
Предупреждение("У меня ОЧКО! Я победил!");
ОбщийПК = ОбщийПК + 1;
Возврат;
КонецЕсли;
Если СчетПК = СчетИгрок Тогда
Предупреждение("Ничья!");
Возврат;
КонецЕсли;
Если СчетПК > СчетИгрок Тогда
Предупреждение("Я победил!");
ОбщийПК = ОбщийПК + 1;
Возврат;
КонецЕсли;
Если СчетПК < СчетИгрок Тогда
Предупреждение("Вы Победили!");
ОбщийИгрок = ОбщийИгрок + 1;
Возврат;
КонецЕсли;
КонецПроцедуры
Процедура Пауза(Секунд)
КонДата = ТекущаяДата() + Секунд;
Пока ТекущаяДата() < КонДата Цикл
// ждемссс....
КонецЦикла;
КонецПроцедуры
Процедура ПриОткрытии()
ОбщийИгрок = 0;
ОбщийПК = 0;
ОбновитьФорму(Истина, Ложь, Ложь);
КонецПроцедуры
Процедура ОбновитьФорму(РаздатьКарты, ВзятьКарту, Хватит)
ЭлементыФормы.РаздатьКарты.Доступность = РаздатьКарты;
ЭлементыФормы.ВзятьКарту.Доступность = ВзятьКарту;
ЭлементыФормы.Хватит.Доступность = Хватит;
КонецПроцедуры
Вызов наших методов из компоненты написанной на Delphi выглядит так: ЭлементыФормы.ЭлементУправления1.AddCard(1,1, Ряд, Колонка); и ЭлементыФормы.ЭлементУправления1.ClearCanvas();
запускаем и проверяем
На этом у меня все! Вы можете сами доработать правила игрового процесса, так как считаете нужным.
Архив с примером выкладываю ниже.
Перед тем как запустить обработку из архива необходимо зарегистрировать компоненту w0rm21Proj1.ocx.
Готов ответить на вопросы.
Спасибо за внимание!