void start_stop_visual (gboolean exiting)
{
    static char started = 0;

    if (config.player_visible && config.vis_type != VIS_OFF && ! exiting)
    {
        if (! started)
        {
            aud_vis_func_add (AUD_VIS_TYPE_CLEAR, (VisFunc) vis_clear_cb);
            aud_vis_func_add (AUD_VIS_TYPE_MONO_PCM, (VisFunc) render_mono_pcm);
            aud_vis_func_add (AUD_VIS_TYPE_MULTI_PCM, (VisFunc) render_multi_pcm);
            aud_vis_func_add (AUD_VIS_TYPE_FREQ, (VisFunc) render_freq);
            started = 1;
        }
    }
    else
    {
        if (started)
        {
            aud_vis_func_remove ((VisFunc) vis_clear_cb);
            aud_vis_func_remove ((VisFunc) render_mono_pcm);
            aud_vis_func_remove ((VisFunc) render_multi_pcm);
            aud_vis_func_remove ((VisFunc) render_freq);
            started = 0;
        }
    }
}
void ui_infoarea_show_vis (bool_t show)
{
    if (! area)
        return;

    if (show)
    {
        if (vis.widget)
            return;

        vis.widget = gtk_drawing_area_new ();

        /* note: "realize" signal must be connected before adding to box */
        g_signal_connect (vis.widget, "realize", (GCallback) realize_cb, NULL);

        gtk_widget_set_size_request (vis.widget, VIS_WIDTH + 2 * SPACING, HEIGHT);
        gtk_box_pack_start ((GtkBox *) area->box, vis.widget, FALSE, FALSE, 0);

        g_signal_connect (vis.widget, "draw", (GCallback) draw_vis_cb, NULL);
        gtk_widget_show (vis.widget);

        aud_vis_func_add (AUD_VIS_TYPE_CLEAR, (VisFunc) vis_clear_cb);
        aud_vis_func_add (AUD_VIS_TYPE_FREQ, (VisFunc) vis_render_cb);
    }
    else
    {
        if (! vis.widget)
            return;

        aud_vis_func_remove ((VisFunc) vis_clear_cb);
        aud_vis_func_remove ((VisFunc) vis_render_cb);

        gtk_widget_destroy (vis.widget);

        memset (& vis, 0, sizeof vis);
    }
}
static gboolean destroy_event (void)
{
    aud_vis_func_remove ((VisFunc) render_cb);
    spect_widget = NULL;
    return TRUE;
}