Добро пожаловать в форум, Guest  >>   Войти | Регистрация | Поиск | Правила | В избранное | Подписаться
Все форумы / WinForms, .Net Framework Новый топик    Ответить
 Консольное приложение: нужен совет  [new]
256k
Member

Откуда: с.Торчилово, Псковская обл.
Сообщений: 437
Есть работающее WinForms приложение, простое, с одной главной формой и неколькоими батонами, как сделать, чтобы оно по флажку умело работать еще и в режиме консольного приложения: типа без формы, с выводом лога в консоль?
22 ноя 18, 11:42    [21741008]     Ответить | Цитировать Сообщить модератору
 Re: Консольное приложение: нужен совет  [new]
Shocker.Pro
Member

Откуда: ->|<- :адуктО
Сообщений: 20662
Нужно, чтобы оно прям натуральную консоль использовала?
Или просто текстбокс на всю форму с черным фоном и белыми буквами? Картинка с другого сайта.
22 ноя 18, 11:52    [21741032]     Ответить | Цитировать Сообщить модератору
 Re: Консольное приложение: нужен совет  [new]
256k
Member

Откуда: с.Торчилово, Псковская обл.
Сообщений: 437
Shocker.Pro,
Это приложение работает так: в форме юзер отмечает нужные параметры: чекбоксы, комбобоксы и т.д и жмет батон "Экзэк"
и оно выполняет набор команд на диске и в базе, рисует прогресс.
Юзер хочет запускать его в тимсити сервере, там надо приложение без гуи, с командной строкой, все параметры можно передать через аргументы и чтобы лог писался. А натянуть дурилку на форму не получится.
Ну, вот.
22 ноя 18, 12:06    [21741059]     Ответить | Цитировать Сообщить модератору
 Re: Консольное приложение: нужен совет  [new]
Petro123
Member

Откуда: Загрузочный сектор Москвы (AutoPOI.ru)
Сообщений: 38643
256k,
Тога перегрузить вроде..... По флажку.
22 ноя 18, 12:11    [21741078]     Ответить | Цитировать Сообщить модератору
 Re: Консольное приложение: нужен совет  [new]
Roman Mejtes
Member

Откуда: г. Пермь
Сообщений: 3463
Есть вариант такой:
Изначально приложение нужно делать консольным. В консольном приложении, если оно запущено без аргументов вызываете WinAPI функцию FreeConcole, что приведет к закрытию окна и освобождению консоли, затем создаете Application.
Недостатком такого применения будет то, что консольное окно будет отображаться при каждом запуска, до момент FreeConsole.

    class Program
    {
        [DllImport("kernel32.dll", SetLastError = true, ExactSpelling = true)]
        static extern bool FreeConsole();

        [STAThread]
        static void Main(string[] args)
        {
            if (args.Length  < 1)
            {
                StartWinFormsApp(args);
            }
            else
            {
                StartConsoleApp(args);
            }
        }

        static void StartWinFormsApp(string[] args)
        {
            FreeConsole();
            Application.EnableVisualStyles();
            Application.SetCompatibleTextRenderingDefault(false);
            Application.Run(new Form1());
        }

        static void StartConsoleApp(string[] args)
        {
            Console.WriteLine("Hello world");
        }
    }
22 ноя 18, 12:20    [21741096]     Ответить | Цитировать Сообщить модератору
 Re: Консольное приложение: нужен совет  [new]
256k
Member

Откуда: с.Торчилово, Псковская обл.
Сообщений: 437
Roman Mejtes
Есть вариант такой:
Изначально приложение нужно делать консольным. В консольном приложении, если оно запущено без аргументов вызываете WinAPI функцию FreeConcole, что приведет к закрытию окна и освобождению консоли, затем создаете Application.
Недостатком такого применения будет то, что консольное окно будет отображаться при каждом запуска, до момент FreeConsole.

    class Program
    {
        [DllImport("kernel32.dll", SetLastError = true, ExactSpelling = true)]
        static extern bool FreeConsole();

        [STAThread]
        static void Main(string[] args)
        {
            if (args.Length  < 1)
            {
                StartWinFormsApp(args);
            }
            else
            {
                StartConsoleApp(args);
            }
        }

        static void StartWinFormsApp(string[] args)
        {
            FreeConsole();
            Application.EnableVisualStyles();
            Application.SetCompatibleTextRenderingDefault(false);
            Application.Run(new Form1());
        }

        static void StartConsoleApp(string[] args)
        {
            Console.WriteLine("Hello world");
        }
    }



ясно, но, что значит "изначально"? оно уже есть финформс, хотелось бы прикрутить и такую возможность.
А что избавиться от постоянного появления консоли никак?
22 ноя 18, 12:24    [21741102]     Ответить | Цитировать Сообщить модератору
 Re: Консольное приложение: нужен совет  [new]
Roman Mejtes
Member

Откуда: г. Пермь
Сообщений: 3463
256k
ясно, но, что значит "изначально"? оно уже есть финформс, хотелось бы прикрутить и такую возможность.
А что избавиться от постоянного появления консоли никак?
Если оно уже WinForms, вам не составит большого труда переключить его на "Console Application" в свойствах проекта.
Гуглите методы AllocConsole(void) и AttachConsole и другие методы работы с консолью.
Проблема в том, что Console.WriteLine будет криво работать, если приатачиться к родительскому процессу :(
будут проблемы с перенаправлением ввода вывода, а консоль не будет ожидать завершение процесса, а сразу вернет управление в консоль, при этом вывод в консоль будет продолжаться параллельно с выводом другой программы.
с FreeConsole самый быстрый, простой и рабочий вариант
22 ноя 18, 13:26    [21741253]     Ответить | Цитировать Сообщить модератору
 Re: Консольное приложение: нужен совет  [new]
Roman Mejtes
Member

Откуда: г. Пермь
Сообщений: 3463
думаю есть еще 1 вариант, вы пишите Native приложение на С++, которое создаст домен, загрузит в него сборку вашего приложения и запустит. Перед этим оно аллоцирует консоль и выполнит все операции, которые требуются для работы pipe маршрутизации, тогда всё будет как вам хочется
22 ноя 18, 13:58    [21741312]     Ответить | Цитировать Сообщить модератору
 Re: Консольное приложение: нужен совет  [new]
256k
Member

Откуда: с.Торчилово, Псковская обл.
Сообщений: 437
Roman Mejtes
думаю есть еще 1 вариант, вы пишите Native приложение на С++, которое создаст домен, загрузит в него сборку вашего приложения и запустит. Перед этим оно аллоцирует консоль и выполнит все операции, которые требуются для работы pipe маршрутизации, тогда всё будет как вам хочется


Такое нашел, вроде не мигает консоль, когда не надо

static class Program
    {
        [STAThread]
        static void Main(string[] args)
        {
            if (args.Length > 0)
            {
                // Command line given, display console 
                AllocConsole();
                ConsoleMain(args);
            }
            else
            {
                Application.EnableVisualStyles();
                Application.SetCompatibleTextRenderingDefault(false);
                Application.Run(new Form1());
            }
        }
        private static void ConsoleMain(string[] args)
        {
            Console.WriteLine("Command line = {0}", Environment.CommandLine);
            for (int ix = 0; ix < args.Length; ++ix)
                Console.WriteLine("Argument{0} = {1}", ix + 1, args[ix]);
            Console.ReadLine();
        }

        [System.Runtime.InteropServices.DllImport("kernel32.dll")]
        private static extern bool AllocConsole();
    }
22 ноя 18, 14:17    [21741344]     Ответить | Цитировать Сообщить модератору
 Re: Консольное приложение: нужен совет  [new]
kealon(Ruslan)
Member

Откуда: Нижневартовск
Сообщений: 5213
256k,

есть ещё такая штука: AttachConsole(ATTACH_PARENT_PROCESS). Если из консоли запукают, то проканает
22 ноя 18, 14:40    [21741395]     Ответить | Цитировать Сообщить модератору
 Re: Консольное приложение: нужен совет  [new]
Roman Mejtes
Member

Откуда: г. Пермь
Сообщений: 3463
kealon(Ruslan)
256k,

есть ещё такая штука: AttachConsole(ATTACH_PARENT_PROCESS). Если из консоли запукают, то проканает

запускать можно от куда угодно, но pipe'ы работать не будут и проблему с тем, что WinForms приложение немедленно возвращает управление тоже ни как не решается.
22 ноя 18, 14:54    [21741428]     Ответить | Цитировать Сообщить модератору
 Re: Консольное приложение: нужен совет  [new]
kealon(Ruslan)
Member

Откуда: Нижневартовск
Сообщений: 5213
Roman Mejtes,

ну пайпы это не консоль - речь вроде о консоли шла, и если консоли у родителя нет, то и подцепляться не к чему

ну а в общем конечно принципиально, то что консольное\не консольное это флаг в заголовке исполнимого файла, и надо выбирать
22 ноя 18, 15:00    [21741443]     Ответить | Цитировать Сообщить модератору
 Re: Консольное приложение: нужен совет  [new]
Roman Mejtes
Member

Откуда: г. Пермь
Сообщений: 3463
kealon(Ruslan),

есть вариант проще, делайте 2 приложения на одной сборке или просто Console приложение, у которой в Reference стоит ваша неконсольная программа или наоборот и всех делов. Либо вариант с загрузчиком домена, но как по мне, овчинка выделки не стоит.
Тот вариант, что я кинул в начале, самый просто и главное рабочий. А появляющееся окно в начале, не самое страшное, что могло случиться.
22 ноя 18, 15:32    [21741507]     Ответить | Цитировать Сообщить модератору
 Re: Консольное приложение: нужен совет  [new]
256k
Member

Откуда: с.Торчилово, Псковская обл.
Сообщений: 437
Roman Mejtes
256k
ясно, но, что значит "изначально"? оно уже есть финформс, хотелось бы прикрутить и такую возможность.
А что избавиться от постоянного появления консоли никак?
Если оно уже WinForms, вам не составит большого труда переключить его на "Console Application" в свойствах проекта.
Гуглите методы AllocConsole(void) и AttachConsole и другие методы работы с консолью.
Проблема в том, что Console.WriteLine будет криво работать, если приатачиться к родительскому процессу :(
будут проблемы с перенаправлением ввода вывода, а консоль не будет ожидать завершение процесса, а сразу вернет управление в консоль, при этом вывод в консоль будет продолжаться параллельно с выводом другой программы.
с FreeConsole самый быстрый, простой и рабочий вариант



мне надо, чтобы по флажку юзер мог запустить как гуёвое приложение или как консоль.

Еще вопрос: как прилепить иконку и титул консоли, если использовать вариант типа тех, что выше приведены с использованием
kernel32
AllocConsole();

и т.д.
11 дек 18, 12:23    [21760097]     Ответить | Цитировать Сообщить модератору
 Re: Консольное приложение: нужен совет  [new]
Изопропил
Member

Откуда:
Сообщений: 31211
256k
Еще вопрос: как прилепить иконку и титул консоли, если использовать вариант типа тех, что выше приведены с использованием
kernel32
AllocConsole();

Console.Title установить
иконку - в свойствах проекта задать
11 дек 18, 14:59    [21760399]     Ответить | Цитировать Сообщить модератору
 Re: Консольное приложение: нужен совет  [new]
256k
Member

Откуда: с.Торчилово, Псковская обл.
Сообщений: 437
Изопропил
256k
Еще вопрос: как прилепить иконку и титул консоли, если использовать вариант типа тех, что выше приведены с использованием
kernel32
AllocConsole();

Console.Title установить
иконку - в свойствах проекта задать


ясно, сбило с толку то, что, если пускаю из-под студии с vshost, то иконки нет
11 дек 18, 15:06    [21760411]     Ответить | Цитировать Сообщить модератору
 Re: Консольное приложение: нужен совет  [new]
Сон Веры Павловны
Member

Откуда:
Сообщений: 5185
Roman Mejtes
kealon(Ruslan),

есть вариант проще, делайте 2 приложения на одной сборке или просто Console приложение, у которой в Reference стоит ваша неконсольная программа или наоборот и всех делов. Либо вариант с загрузчиком домена, но как по мне, овчинка выделки не стоит.
Тот вариант, что я кинул в начале, самый просто и главное рабочий. А появляющееся окно в начале, не самое страшное, что могло случиться.

Я бы просто завел conditional variable в проекте, отдельную платформу под консольную конфигурацию, и зависимости от её значения собирал бы проект либо в консольной конфигурации, либо в оконной - как-то так:
в .csproj:
<Choose>
  <When Condition=" '$(Platform)' == 'ConsoleApp' ">
    <PropertyGroup>
      <OutputType>Exe</OutputType>
    </PropertyGroup>
  </When>
  <Otherwise>
    <PropertyGroup>
      <OutputType>WinExe</OutputType>
    </PropertyGroup>
  </Otherwise>
</Choose>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|ConsoleApp' ">
  <PlatformTarget>x86</PlatformTarget>
  <DebugSymbols>true</DebugSymbols>
  <DebugType>full</DebugType>
  <Optimize>false</Optimize>
  <OutputPath>bin\Debug\</OutputPath>
  <DefineConstants>DEBUG;TRACE</DefineConstants>
  <ErrorReport>prompt</ErrorReport>
  <WarningLevel>4</WarningLevel>
  <DefineConstants>CONSOLE</DefineConstants>
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|ConsoleApp' ">
  <PlatformTarget>x86</PlatformTarget>
  <DebugType>pdbonly</DebugType>
  <Optimize>true</Optimize>
  <OutputPath>bin\Release\</OutputPath>
  <DefineConstants>TRACE</DefineConstants>
  <ErrorReport>prompt</ErrorReport>
  <WarningLevel>4</WarningLevel>
  <DefineConstants>CONSOLE</DefineConstants>
</PropertyGroup>

в Program.cs:
namespace wf_test
{
  static class Program
  {
#if !CONSOLE
    [STAThread]
    static void Main()
    {
      Application.EnableVisualStyles();
      Application.SetCompatibleTextRenderingDefault(false);
      Application.Run(new Form1());
    }
#endif

#if CONSOLE
    static void Main()
    {
      Console.WriteLine("This is console app");
    }
#endif
  }
}

Потом в конфигурации проекта просто нужно будет выбрать нужную платформу перед компиляцией.
11 дек 18, 17:47    [21760644]     Ответить | Цитировать Сообщить модератору
Все форумы / WinForms, .Net Framework Ответить