In GTK+, is it possible to access the GtkWidget -- text entry for file name in GtkFileChooser? I want to disable the editable attribute of the text entry using gtk_entry_set_editable.
As far as I know, no.
What do you ultimately want to achieve? Perhaps there is another approach.
If one had a legitimate reason to get a pointer to the GtkEntry, then derive from GtkFileChooserDialog, which will probably mutate into a GtkFileChooserDefault. GObject will complain about an illegal cast when checking type instance even though it works and the data of derived object can be accessed without errors, use GTK_FILE_CHOOSER instead of MY_FILE_CHOOSER to avoid the warning messages and a local static for the entry pointer. The entry widget is NOT accessible during construction. Here is the pertinent code:
static GtkEntry *chooser_entry;
static void my_file_chooser_finalize (GObject *object)
{
chooser_entry = NULL;
(G_OBJECT_CLASS (my_file_chooser_parent_class))->finalize (object);
}
static void my_file_chooser_init (MyFileChooser *self)
{
chooser_entry = NULL;
}
static void look_for_entry(GtkWidget *widget, void *self)
{
if (GTK_IS_ENTRY(widget)) {
chooser_entry = (GtkEntry*)widget;
}
else if (GTK_IS_CONTAINER(widget)) {
gtk_container_forall ( GTK_CONTAINER (widget), look_for_entry, self);
}
}
static void file_chooser_find_entry (GtkWidget *chooser)
{
GList *children, *iter;
/* Get all objects inside the dialog */
children = gtk_container_get_children (GTK_CONTAINER (chooser));
for (iter = children; iter; iter = iter->next) {
if (GTK_IS_CONTAINER(iter->data)) {
gtk_container_forall ( GTK_CONTAINER (iter->data), look_for_entry, chooser);
if (chooser_entry != NULL) {
break;
}
}
}
g_list_free (children);
}
GtkEntry *my_file_chooser_get_entry (GtkWidget *widget)
{
if (chooser_entry == NULL) {
file_chooser_find_entry (widget);
}
return chooser_entry;
}
char *my_file_chooser_get_entry_text(GtkWidget *widget)
{
char *text;
GtkEntry *entry;
text = NULL;
if (GTK_IS_FILE_CHOOSER(widget)) {
entry = my_file_chooser_get_entry(widget);
if (GTK_IS_ENTRY(entry)) {
if (gtk_entry_get_text_length (entry)) {
text = g_strdup (gtk_entry_get_text(entry));
}
}
}
return text;
}
Maybe not ideal, but works.
Related
I tried to re-use code (http://msdn.microsoft.com/en-us/library/windows/desktop/ff625913(v=vs.85).aspx#FindByName), but I want to wrap it in a simple class. When I'm run this code it falls on:
hr = g_pAutomation->CreatePropertyCondition(UIA_ClassNamePropertyId, varProp, &pCondition);
with 0xc0000005.
I know, it because of empty or broken pointer. But when I run this code without any classes (from main()), it works perfect.
What should I read and from where to understand why it happens?
#pragma once
#include <UIAutomation.h>
class Automator
{
protected:
IUIAutomation* g_pAutomation;
IUIAutomationElement* pRoot;
IUIAutomationElementArray* pArrFound;
IUIAutomationElement* pFound;
public:
Automator(void);
~Automator(void);
void ClearResources(void);
void FindAllWindows(void);
};
#include "Automator.h"
Automator::Automator(void)
{
pRoot = NULL;
pArrFound = NULL;
pFound = NULL;
g_pAutomation = NULL;
CoInitialize(NULL);
HRESULT hr;
hr = CoCreateInstance(__uuidof(CUIAutomation), NULL, CLSCTX_INPROC_SERVER,
__uuidof(IUIAutomation), (void**)&g_pAutomation);
if(FAILED(hr))
ClearResources();
else
{
hr = g_pAutomation->GetRootElement(&pRoot);
if (FAILED(hr) || pRoot == NULL)
ClearResources();
}
}
Automator::~Automator(void)
{
ClearResources();
}
//
//Doesn't work
//
void Automator::FindAllWindows(void)
{
VARIANT varProp;
varProp.vt = VT_BSTR;
varProp.bstrVal = L"";
IUIAutomationCondition* pCondition;
HRESULT hr = NULL;
if (g_pAutomation != NULL)
{
hr = g_pAutomation->CreatePropertyCondition(UIA_ClassNamePropertyId, varProp, &pCondition);
if(FAILED(hr))
{
if (pCondition != NULL)
pCondition->Release();
ClearResources();
}
else
{
pRoot->FindAll(TreeScope_Subtree, pCondition, &pArrFound);
}
}
if(pCondition != NULL)
pCondition->Release();
}
void Automator::ClearResources(void)
{
if (pRoot != NULL)
pRoot->Release();
if (pArrFound != NULL)
pArrFound->Release();
if (pFound != NULL)
pFound->Release();
if (g_pAutomation != NULL)
g_pAutomation->Release();
CoUninitialize();
}
I see a couple of issues:
Don't call CoInitialize/CoUninitialize from class constructors/destructors; do it inside your main (or thread entry point). A fair amount of code runs before main() gets called (static class initializers, for one) and having that run outside main() can result in problems.
You haven't shown your main() - where are you creating your Automator object? I suspect you haven't actually created an Automator, which is why it's crashing.
If I were going to write your main, it would look like this:
_wmain(int argc, wchar_t **argv)
{
CoInitialize();
{
Automator automator;
automator.FindAllWindows();
}
CoUninitialize();
}
The extra scope bracket is there to insure that the Automator destructor runs before CoUninitialize().
I have an element that decodes a media type, mytype for example. I want to register the type so that the decodebin element can use my element if needed. I added the code for what I thought would work, but my type_find() function is never called. Any ideas on what I'm doing wrong? Here's what the code looks like:
#define MY_CAPS (gst_static_caps_get(&my_caps))
static GstStaticCaps my_caps = GST_STATIC_CAPS("audio/x-mycaps");
static gchar *my_exts[] = { "mtype", NULL };
static void type_find(GstTypeFind *_type_find, gpointer callback)
{
printf("Type Find Function\r\n");
gst_type_find_suggest(_type_find, GST_TYPE_FIND_POSSIBLE, gst_static_caps_get(&my_caps));
}
gboolean plugin_init(GstPlugin *plugin)
{
if(!gst_type_find_register(plugin, "mytype", GST_RANK_PRIMARY, type_find, my_exts, MY_CAPS, NULL, NULL))
return FALSE;
if(!gst_element_register(plugin, "myelement", GST_RANK_PRIMARY, MY_ELEMENT_TYPE)
return FALSE;
return(TRUE);
}
I develop extension of PDT plugin. I need dialog with interfaces only (not classes). Basic code looks like it:
OpenTypeSelectionDialog2 dialog = new OpenTypeSelectionDialog2(
DLTKUIPlugin.getActiveWorkbenchShell(),
multi,
PlatformUI.getWorkbench().getProgressService(),
null,
type,
PHPUILanguageToolkit.getInstance());
It's works fine but I get classes and interfaces together (type variables). Is any method to filter it? I can't find this kind of mechanism in PDT but classes and interfaces are recognize correctly (icons next to names).
I don't know if its the best solution but it works.
int falseFlags = 0;
int trueFlags = 0;
IDLTKSearchScope scope = SearchEngine.createSearchScope(getScriptFolder().getScriptProject());
trueFlags = PHPFlags.AccInterface;
OpenTypeSelectionDialog2 dialog = new OpenTypeSelectionDialog2(
DLTKUIPlugin.getActiveWorkbenchShell(),
multi,
PlatformUI.getWorkbench().getProgressService(),
scope,
IDLTKSearchConstants.TYPE,
new PHPTypeSelectionExtension(trueFlags, falseFlags),
PHPUILanguageToolkit.getInstance());
And PHPTypeSelectionExtension looks like this:
public class PHPTypeSelectionExtension extends TypeSelectionExtension {
/**
* #see PHPFlags
*/
private int trueFlags = 0;
private int falseFlags = 0;
public PHPTypeSelectionExtension() {
}
public PHPTypeSelectionExtension(int trueFlags, int falseFlags) {
super();
this.trueFlags = trueFlags;
this.falseFlags = falseFlags;
}
#Override
public ITypeInfoFilterExtension getFilterExtension() {
return new ITypeInfoFilterExtension() {
#Override
public boolean select(ITypeInfoRequestor typeInfoRequestor) {
if (falseFlags != 0 && (falseFlags & typeInfoRequestor.getModifiers()) != 0) {
// Try to filter by black list.
return false;
} else if (trueFlags == 0 || (trueFlags & typeInfoRequestor.getModifiers()) != 0) {
// Try to filter by white list, if trueFlags == 0 this is fine 'couse we pass black list.
return true;
} else {
// Rest is filter out.
return false;
}
}
};
}
#SuppressWarnings("restriction")
#Override
public ISelectionStatusValidator getSelectionValidator() {
return new TypedElementSelectionValidator(new Class[] {IType.class, INamespace.class}, false);
}
}
has someone been able to correctly to update a cell browser at runtime, i.e. when u remove a node or add a node, the change is reflected immediately in the CEll Browser, because I am using a List and when i am making a change it is not being updated on the spot
You can use ListDataProvider setList(...) method for dynamic updates. Here is an example how I update cell browser via RPC:
private void loadAllData(final ListDataProvider<Data> dataProvider) {
dBservice.getAllData(new AsyncCallback<List<Data>>() {
public void onSuccess(List<Data> result) {
dataProvider.setList(result);
}
public void onFailure(Throwable caught) {
caught.printStackTrace();
}
});
}
to refresh a cellBrowser you have to close all the child on the root node.
anyway something like this
for (int i = 0; i < cellBrowser.getRootTreeNode().getChildCount(); i++) {
cellBrowser.getRootTreeNode().setChildOpen(i, false);
}
the AsyncDataProvider calls refreshes data
private final class Model implements TreeViewModel{
private List<ZonaProxy> zonaList = null;
private List<CategoriaProxy> categoriaList = null;
public void setCategoriaList(List<CategoriaProxy> categoriaList) {
this.categoriaList = categoriaList;
}
public void setListZona(List<ZonaProxy> zonaList) {
this.zonaList = zonaList;
}
#SuppressWarnings({ "unchecked", "rawtypes" })
public <T> NodeInfo<?> getNodeInfo(T value) {
CategoryDataProvider dataProvider1 = new CategoryDataProvider();
return new DefaultNodeInfo(dataProvider1, new CategoriaCell());
}
/**
* Check if the specified value represents a leaf node. Leaf nodes cannot be
* opened.
*/
public boolean isLeaf(Object value) {
if (value instanceof CategoriaProxy){
if (((CategoriaProxy) value).getLivello() == 3) {
return true;
}
}
return false;
}
}
private class CategoryDataProvider extends AsyncDataProvider<CategoriaProxy>
{
#Override
protected void onRangeChanged(HasData<CategoriaProxy> display)
{
requests.categoriaRequest().findAllCategorias(0, 8).with().fire(new Receiver<List<CategoriaProxy>>() {
#Override
public void onSuccess(List<CategoriaProxy> values) {
updateRowCount(values.size(), true);
updateRowData(0, values);
}
});
}
}
it Works.
Apparently it is not enough to change the data provider and refresh it.
You need also to force the affected cell to close and reopen it, as in this example
public void updateCellBrowser(String id) {
TreeNode node = getNode(cellBrowser.getRootTreeNode(),id);
if(node != null && ! node.isDestroyed()) {
TreeNode parent = node.getParent();
int index = node.getIndex();
parent.setChildOpen(index, false,true);
parent.setChildOpen(index, true, true);
}
}
In my particular example the cell ids are pathnames hence the following
implementation of getNode().
private TreeNode getNode(TreeNode node, String id) {
for(int i=0; i < node.getChildCount(); i++)
if(node.isChildOpen(i)) {
Object value = node.getChildValue(i);
if(value instanceof String) {
String nodeId = ((String) value);
if(id.equals(nodeId))
return node.setChildOpen(i, true);
if(id.startsWith(nodeId))
getNode(node.setChildOpen(i, true),id);
}
}
return null;
}
I am sending CurrentPage value 1, but it gives a null reference exception in set.
lblCurrentPage is a label control. CurrentPage is one variable.
public int CurrentPage
{
get { return int.Parse(lblCurrentPage.Text); }
set {
lblCurrentPage.Text = Convert.ToString(value);
}
}
You have a massive lack of info for us to go on, but i'll make a suggestion. Check that lblCurrentPage is actually set to a real control, i.e. make sure the label has been instantiated before you try to set its properties.
public int CurrentPage
{
get
{
int temp = 0;
if (lblCurrentPage != null)
{
int.TryParse(lblCurrentPage.Text, out temp);
}
return temp;
}
set
{
if (lblCurrentPage != null)
lblCurrentPage.Text = Convert.ToString(value);
}
}