[maemo-commits] [maemo-commits] r12593 - projects/tools/trunk/maemo_testing/maemo-examples

From: subversion at stage.maemo.org subversion at stage.maemo.org
Date: Mon Jul 2 14:58:46 EEST 2007
Author: jampekka
Date: 2007-07-02 14:58:34 +0300 (Mon, 02 Jul 2007)
New Revision: 12593

Added:
   projects/tools/trunk/maemo_testing/maemo-examples/example_wavlaunch.c
Log:
Added wavlaunch example


Added: projects/tools/trunk/maemo_testing/maemo-examples/example_wavlaunch.c
===================================================================
--- projects/tools/trunk/maemo_testing/maemo-examples/example_wavlaunch.c	2007-07-02 09:28:43 UTC (rev 12592)
+++ projects/tools/trunk/maemo_testing/maemo-examples/example_wavlaunch.c	2007-07-02 11:58:34 UTC (rev 12593)
@@ -0,0 +1,414 @@
+/**
+ * This file is part of maemo-examples package
+ * 
+ * Copyright (c) 2007 Nokia Corporation
+ * 
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to deal
+ * in the Software without restriction, including without limitation the rights
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ * 
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ * 
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+ * THE SOFTWARE. */
+
+
+#include <hildon-widgets/hildon-app.h>
+#include <hildon-widgets/hildon-appview.h>
+#include <hildon-widgets/hildon-file-chooser-dialog.h>
+#include <gtk/gtk.h>
+#include <gtk/gtkfilechooser.h>
+
+#include <stdlib.h>
+#include <gst/gst.h>
+#include <esd.h>
+
+
+/*---------------------------------------------------------------------------*/
+/* Application UI data struct */
+typedef struct _AppData AppData;
+
+struct _AppData {
+  HildonApp *app;
+  HildonAppView *appview;
+  GtkWidget *tb_statusbar;
+  gint context_id;
+  gchar *filename;
+  GstElement *pipeline;
+};
+
+
+/*---------------------------------------------------------------------------*/
+static int esdlaunch(short *buf, int bufsize)
+{
+  int sock = -1;
+
+  /* Play 16bit mono stream */
+  esd_format_t format = ESD_BITS16 | ESD_MONO | ESD_STREAM | ESD_PLAY;
+
+  sock = esd_play_stream_fallback(format, ESD_DEFAULT_RATE, NULL, "wavlaunch");
+  if (sock <= 0) {
+    fprintf (stderr, "Error at esd open: %d", sock);
+    return -1;
+  }
+
+  write(sock, buf, bufsize);
+
+  close(sock);
+
+  return 0;
+}
+
+
+/*---------------------------------------------------------------------------*/
+static int bling(void)
+{
+  int sts = -1;
+  short *buf;
+  int bufsize, i, samplestoplay;
+  float samplerate, frequency;
+  float played, playtime;
+  float amplitude, amplitudemax;
+  float phase, phasescale;
+
+  samplerate   = 44100.0;
+  amplitudemax = 32000.0;
+  frequency    =  1000.0;
+  playtime     =    0.25;
+
+  samplestoplay = (int)(playtime * samplerate);
+
+  /* allocate buffer for "Bling". 16 bit samples. */
+  bufsize = samplestoplay * 2;
+  buf = (short *)malloc(bufsize);
+  if (buf) {
+
+    /* generate sinewave with linearly decreasing amplitude */
+    phasescale = 6.28 * (float)frequency * playtime;
+    for (i = 0; i < samplestoplay; i++) {
+      played = (float)i / (float)samplestoplay;
+      phase = played * phasescale;
+      amplitude =  amplitudemax * (1.0 - played);
+      buf[i] = (short)(amplitude * sin(phase));
+    }
+
+    /* play the buffer */
+    sts = esdlaunch(buf, bufsize);
+
+    free(buf);
+  }
+
+  return sts;  
+}
+
+
+/*---------------------------------------------------------------------------*/
+static void eos_message_received (GstBus * bus, GstMessage * message,
+    AppData * appdata)
+{
+  /* stop playback and free pipeline */
+  gst_element_set_state (appdata->pipeline, GST_STATE_NULL);
+  gst_object_unref (GST_OBJECT(appdata->pipeline));
+  appdata->pipeline = NULL;
+}
+
+
+/*---------------------------------------------------------------------------*/
+static int play_file (AppData * appdata)
+{
+  GstElement *filesrc;
+  GstBus *bus;
+  GError *error = NULL;
+
+  /* we're already playing */
+  if (appdata->pipeline) return -1;
+  
+  /* setup pipeline and configure elements */
+  appdata->pipeline = gst_parse_launch (
+#ifdef __arm__
+        "filesrc name=my_filesrc ! wavparse ! dsppcmsink",
+#else
+        "filesrc name=my_filesrc ! wavparse ! osssink",
+#endif
+         &error);
+  if (!appdata->pipeline) {
+    fprintf (stderr, "Parse error: %s\n", error->message);
+    goto error;
+  }
+
+  filesrc = gst_bin_get_by_name (GST_BIN (appdata->pipeline), "my_filesrc");
+  if (!filesrc) {
+    fprintf (stderr, "Parse error: no filesrc\n");
+    goto error;
+  }
+
+  g_object_set (G_OBJECT (filesrc), "location", appdata->filename, NULL);
+
+  /* setup message handling */
+  bus = gst_pipeline_get_bus (GST_PIPELINE (appdata->pipeline));
+  gst_bus_add_signal_watch_full (bus, G_PRIORITY_HIGH);
+  g_signal_connect (bus, "message::eos", (GCallback) eos_message_received,
+      appdata);
+  gst_object_unref (GST_OBJECT(bus));
+  
+  /* start playback */
+  gst_element_set_state (appdata->pipeline, GST_STATE_PLAYING);
+  return 0;
+
+error:
+  gst_object_unref (GST_OBJECT(appdata->pipeline));
+  appdata->pipeline = NULL;
+  return -1;  
+}
+
+
+/*---------------------------------------------------------------------------*/
+static gchar *file_chooser(AppData * appdata)
+{
+  GtkWidget *dialog;
+  gchar *filename = NULL;
+
+#if __arm__
+  dialog = hildon_file_chooser_dialog_new(
+             GTK_WINDOW(appdata->app), 
+             GTK_FILE_CHOOSER_ACTION_OPEN);
+#else
+  dialog = gtk_file_chooser_dialog_new("Open File",
+             GTK_WINDOW(appdata->app), 
+             GTK_FILE_CHOOSER_ACTION_OPEN,
+             GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL,
+             GTK_STOCK_OPEN, GTK_RESPONSE_OK,
+             NULL);
+#endif
+  if (dialog) {
+    gint response;
+
+    gtk_file_chooser_set_current_folder(GTK_FILE_CHOOSER(dialog),
+                                        "/home/user");
+    gtk_widget_show_all(GTK_WIDGET(dialog));
+
+    response = gtk_dialog_run(GTK_DIALOG(dialog));
+    if (response  == GTK_RESPONSE_OK) {
+      filename = gtk_file_chooser_get_filename(GTK_FILE_CHOOSER(dialog));
+    }
+
+    gtk_widget_destroy(dialog);
+  }
+
+  return filename;
+}
+
+
+/*---------------------------------------------------------------------------*/
+static void tb_open_cb(GtkToolButton *button, AppData * appdata)
+{
+  gchar *filename = NULL;
+
+  filename = file_chooser(appdata);
+
+  if (filename) {
+    if (appdata->filename) g_free(appdata->filename);
+    appdata->filename = g_strdup(filename);
+
+    gtk_statusbar_push (GTK_STATUSBAR (appdata->tb_statusbar),
+                        GPOINTER_TO_INT (appdata->context_id),
+                        filename);
+  }
+
+  /* Play audible bling sound */
+#ifdef __arm__
+  bling();
+#endif
+
+  return;
+}
+
+
+/*---------------------------------------------------------------------------*/
+/* Callback for "Play" toolbar button */
+static void tb_play_cb(GtkToolButton * button, AppData * appdata)
+{
+  g_print("Playing file %s\n", appdata->filename );
+
+  play_file( appdata );
+}
+
+
+/*---------------------------------------------------------------------------*/
+/* Callback for "Close" menu entry */
+static void item_close_cb(void)
+{
+  g_print("Closing application...\n");
+
+  gtk_main_quit();
+}
+
+
+/*---------------------------------------------------------------------------*/
+/* Create the menu items needed for the main view */
+static void create_menu(HildonAppView * main_view)
+{
+  /* Create needed variables */
+  GtkMenu *main_menu;
+  GtkWidget *item_close;
+
+  GtkWidget *item_separator;
+
+
+  /* Get the menu from view */
+  main_menu = hildon_appview_get_menu(main_view);
+
+  if (main_menu) {
+    /* Create menu items */
+    item_close = gtk_menu_item_new_with_label("Close");
+    if (item_close) {
+      item_separator = gtk_separator_menu_item_new();
+
+      /* Add menu items */
+      gtk_menu_append(main_menu, item_close);
+
+      /* Attach the callback functions to the activate signal */
+      g_signal_connect(G_OBJECT(item_close), "activate",
+                       GTK_SIGNAL_FUNC(item_close_cb), NULL);
+
+      /* Make all menu widgets visible */
+      gtk_widget_show_all(GTK_WIDGET(main_menu));
+    }
+  }
+}
+
+
+
+/*---------------------------------------------------------------------------*/
+/* Create the toolbar needed for the main view */
+static void create_toolbar(HildonAppView * main_view, AppData *appdata)
+{
+  /* Create needed variables */
+  GtkWidget *main_toolbar;
+  GtkToolItem *tb_open;
+  GtkToolItem *tb_play;
+  GtkToolItem *tb_separator;
+  GtkToolItem *tb_comboitem;
+  GtkComboBox *tb_combo;
+
+  /* Create toolbar */
+  main_toolbar = gtk_toolbar_new();
+
+  if (main_toolbar) {
+  /* Create toolbar button items */
+    tb_open = gtk_tool_button_new_from_stock(GTK_STOCK_OPEN);
+    tb_play = gtk_tool_button_new_from_stock(GTK_STOCK_MEDIA_PLAY);
+
+    /* Create toolbar combobox item */
+    tb_comboitem = gtk_tool_item_new();
+
+    appdata->tb_statusbar = gtk_statusbar_new();
+
+    appdata->context_id = gtk_statusbar_get_context_id(
+                          GTK_STATUSBAR (appdata->tb_statusbar),
+                          "Playing file");
+
+    gtk_statusbar_push (GTK_STATUSBAR (appdata->tb_statusbar),
+                        GPOINTER_TO_INT (appdata->context_id),
+                        "  Please open pcm wav file to play");
+
+
+    /* Make combobox to use all available toolbar space */
+    gtk_tool_item_set_expand(tb_comboitem, TRUE);
+
+    /* Add combobox inside toolitem */
+    gtk_container_add(GTK_CONTAINER(tb_comboitem),
+                      GTK_WIDGET(appdata->tb_statusbar));
+
+
+    /* Create separator */
+    tb_separator = gtk_separator_tool_item_new();
+
+    /* Add all items to toolbar */
+    gtk_toolbar_insert(GTK_TOOLBAR(main_toolbar), tb_open, -1);
+    gtk_toolbar_insert(GTK_TOOLBAR(main_toolbar), tb_play, -1);
+    gtk_toolbar_insert(GTK_TOOLBAR(main_toolbar), tb_comboitem, -1);
+
+    /* Add signal lister to "Close" button */
+    g_signal_connect(G_OBJECT(tb_open), "clicked",
+                     G_CALLBACK(tb_open_cb), appdata);
+    g_signal_connect(G_OBJECT(tb_play), "clicked",
+                     G_CALLBACK(tb_play_cb), appdata);
+
+    /* Add toolbar to 'vbox' of HildonAppView */
+    gtk_box_pack_end(GTK_BOX(main_view->vbox), main_toolbar, TRUE, TRUE, 0);
+  }
+}
+
+
+
+/*---------------------------------------------------------------------------*/
+/* Main application */
+int main(int argc, char *argv[])
+{
+  /* Create needed variables */
+  AppData *appdata;
+
+  HildonApp *app;
+  HildonAppView *appview;
+
+  /* Initialize the GTK and GStreamer. */
+  gtk_init(&argc, &argv);
+  gst_init(&argc, &argv);
+
+  /* Create the hildon application and setup the title */
+  app = HILDON_APP(hildon_app_new());
+  hildon_app_set_title(app, "Wav Launch Demo");
+
+  /* Create HildonAppView and set it to HildonApp */
+  appview = HILDON_APPVIEW(hildon_appview_new(NULL));
+  hildon_app_set_appview(app, appview);
+
+  /* Create AppData */
+  appdata = g_new0(AppData, 1);
+  if (appdata) {
+    GtkWidget *label;
+
+    appdata->app = app;
+    appdata->appview = appview;
+
+    /* Add example label to appview */
+    label = gtk_label_new(NULL);
+    gtk_label_set_markup(GTK_LABEL(label),
+        "<b>GStreamer launch Demo</b>\n\n"
+        "Plays pcm wav files.\n\n"
+        "Uses gstreamer function gst_parse_launch, with plugins\n"
+        "filesrc, wavparse and dsppcmsink.\n\n"
+        "Also shows how to listen to messages from the GStreamer bus.\n\n"
+        "At file open, audible response is given using esd low level API.\n");
+
+    gtk_container_add(GTK_CONTAINER(appview), label);
+
+      /* Create menu for view */
+    create_menu(appview);
+
+    /* Create toolbar for view */
+    create_toolbar(appview, appdata);
+
+    /* Begin the main application */
+    gtk_widget_show_all(GTK_WIDGET(app));
+
+    gtk_main();
+
+    if (appdata->pipeline) gst_object_unref(GST_OBJECT(appdata->pipeline));
+    if (appdata->filename) g_free(appdata->filename);
+    g_free(appdata);
+  }    
+
+  /* Exit */
+  return 0;
+}


More information about the maemo-commits mailing list